36#include "lldb/Host/Config.h"
39#include "llvm/ADT/STLExtras.h"
40#include "llvm/ADT/StringSwitch.h"
41#include "llvm/Config/llvm-config.h"
42#include "llvm/Support/JSON.h"
44#if HAVE_LIBCOMPRESSION
45#include <compression.h>
51using namespace std::chrono;
55 return os << llvm::formatv(
56 "QOffsets({0}, [{1:@[x]}])", offsets.
segments,
91 std::chrono::steady_clock::time_point start_of_handshake =
92 std::chrono::steady_clock::now();
101 std::chrono::steady_clock::time_point end_of_handshake =
102 std::chrono::steady_clock::now();
103 auto handshake_timeout =
104 std::chrono::duration<double>(end_of_handshake - start_of_handshake)
110 "while waiting for reply to initial "
114 "failed to get reply to handshake packet within timeout of "
373 std::vector<std::string> features = {
"xmlRegisters=i386,arm,mips,arc",
381 for (uint32_t i = 0; i < features.size(); ++i) {
393 for (llvm::StringRef x : llvm::split(response.
GetStringRef(),
';')) {
394 if (x ==
"qXfer:auxv:read+")
396 else if (x ==
"qXfer:libraries-svr4:read+")
398 else if (x ==
"augmented-libraries-svr4-read") {
401 }
else if (x ==
"qXfer:libraries:read+")
403 else if (x ==
"qXfer:features:read+")
405 else if (x ==
"qXfer:memory-map:read+")
407 else if (x ==
"qXfer:siginfo:read+")
409 else if (x ==
"qEcho+")
411 else if (x ==
"QPassSignals+")
413 else if (x ==
"multiprocess+")
415 else if (x ==
"memory-tagging+")
417 else if (x ==
"qSaveCore+")
419 else if (x ==
"native-signals+")
421 else if (x ==
"binary-upload+")
423 else if (x ==
"ReverseContinue+")
425 else if (x ==
"ReverseStep+")
430 else if (x.consume_front(
"SupportedCompressions=")) {
431 llvm::SmallVector<llvm::StringRef, 4> compressions;
432 x.split(compressions,
',');
433 if (!compressions.empty())
435 }
else if (x.consume_front(
"SupportedWatchpointTypes=")) {
436 llvm::SmallVector<llvm::StringRef, 4> watchpoint_types;
437 x.split(watchpoint_types,
',');
439 for (
auto wp_type : watchpoint_types) {
440 if (wp_type ==
"x86_64")
442 if (wp_type ==
"aarch64-mask")
444 if (wp_type ==
"aarch64-bas")
447 }
else if (x.consume_front(
"PacketSize=")) {
454 LLDB_LOGF(log,
"Garbled PacketSize spec in qSupported response");
484 const char *response_cstr = response.
GetStringRef().data();
485 if (::strstr(response_cstr,
";c"))
488 if (::strstr(response_cstr,
";C"))
491 if (::strstr(response_cstr,
";s"))
494 if (::strstr(response_cstr,
";S"))
540 "GDBRemoteCommunicationClient::%s: Didn't get sequence mutex "
542 __FUNCTION__, payload.GetData());
547 payload.Printf(
";thread:%4.4" PRIx64
";", tid);
594 }
else if (!response.
Empty()) {
683 packet.
Printf(
"qMemTags:%" PRIx64
",%zx:%" PRIx32, addr, len, type);
691 LLDB_LOGF(log,
"GDBRemoteCommunicationClient::%s: qMemTags packet failed",
699 if (response.
GetChar() !=
'm') {
701 "GDBRemoteCommunicationClient::%s: qMemTags response did not "
712 if (response.
GetBytesLeft() || (expected_bytes != got_bytes)) {
715 "GDBRemoteCommunicationClient::%s: Invalid data in qMemTags response",
725 const std::vector<uint8_t> &tags) {
728 packet.
Printf(
"QMemTags:%" PRIx64
",%zx:%" PRIx32
":", addr, len, type);
774 if (response.
GetChar() ==
'Q') {
775 if (response.
GetChar() ==
'C') {
789 bool sequence_mutex_unavailable;
791 if (!ids.empty() && !sequence_mutex_unavailable) {
808 return llvm::createStringError(llvm::inconvertibleErrorCode(),
809 "Nothing to launch");
822 return llvm::createStringError(llvm::inconvertibleErrorCode(),
823 "Sending vRun packet failed");
832 return llvm::Error::success();
840 llvm::ListSeparator LS(
",");
841 for (
const auto &arg : llvm::enumerate(args)) {
843 packet.
Format(
"{0},{1},", arg.value().ref().size() * 2, arg.index());
850 return llvm::createStringError(llvm::inconvertibleErrorCode(),
851 "Sending A packet failed");
858 return llvm::createStringError(llvm::inconvertibleErrorCode(),
859 "Sending qLaunchSuccess packet failed");
862 return llvm::Error::success();
863 if (response.
GetChar() ==
'E') {
864 return llvm::createStringError(llvm::inconvertibleErrorCode(),
867 return llvm::createStringError(llvm::inconvertibleErrorCode(),
868 "unknown error occurred launching process");
872 llvm::SmallVector<std::pair<llvm::StringRef, llvm::StringRef>, 0> vec;
873 for (
const auto &kv : env)
874 vec.emplace_back(kv.first(), kv.second);
875 llvm::sort(vec, llvm::less_first());
876 for (
const auto &[k, v] : vec) {
885 char const *name_equal_value) {
886 if (name_equal_value && name_equal_value[0]) {
887 bool send_hex_encoding =
false;
888 for (
const char *p = name_equal_value; *p !=
'\0' && !send_hex_encoding;
890 if (llvm::isPrint(*p)) {
896 send_hex_encoding =
true;
903 send_hex_encoding =
true;
911 packet.
Printf(
"QEnvironment:%s", name_equal_value);
952 if (arch && arch[0]) {
954 packet.
Printf(
"QLaunchArch:%s", arch);
969 char const *data,
bool *was_supported) {
970 if (data && *data !=
'\0') {
972 packet.
Printf(
"QSetProcessEvent:%s", data);
978 *was_supported =
true;
982 *was_supported =
false;
987 *was_supported =
true;
1011 return std::nullopt;
1014std::optional<std::string>
1020 return std::nullopt;
1048 UUID &uuid,
addr_t &value,
bool &value_is_offset) {
1081 llvm::StringRef name, value;
1082 bool success =
false;
1084 if (name ==
"name") {
1087 }
else if (name ==
"version") {
1088 llvm::StringRef major, minor;
1089 std::tie(major, minor) = value.split(
'.');
1103 llvm::ArrayRef<llvm::StringRef> supported_compressions) {
1105 llvm::StringRef avail_name;
1107#if HAVE_LIBCOMPRESSION
1109 for (
auto compression : supported_compressions) {
1110 if (compression ==
"lzfse") {
1112 avail_name = compression;
1118 for (
auto compression : supported_compressions) {
1119 if (compression ==
"zlib-deflate") {
1121 avail_name = compression;
1130 for (
auto compression : supported_compressions) {
1131 if (compression ==
"zlib-deflate") {
1133 avail_name = compression;
1140#if HAVE_LIBCOMPRESSION
1142 for (
auto compression : supported_compressions) {
1143 if (compression ==
"lz4") {
1145 avail_name = compression;
1151 for (
auto compression : supported_compressions) {
1152 if (compression ==
"lzma") {
1154 avail_name = compression;
1163 std::string packet =
"QEnableCompression:type:" + avail_name.str() +
";";
1210 tid = pid_tid->second;
1217 std::string &environment) {
1218 if (value ==
"iossimulator" || value ==
"tvossimulator" ||
1219 value ==
"watchossimulator" || value ==
"xrossimulator" ||
1220 value ==
"visionossimulator") {
1221 environment =
"simulator";
1222 os_name = value.drop_back(environment.size()).str();
1223 }
else if (value ==
"maccatalyst") {
1225 environment =
"macabi";
1227 os_name = value.str();
1243 llvm::StringRef name;
1244 llvm::StringRef value;
1247 std::string arch_name;
1248 std::string os_name;
1249 std::string environment;
1250 std::string vendor_name;
1252 uint32_t pointer_byte_size = 0;
1254 uint32_t num_keys_decoded = 0;
1256 if (name ==
"cputype") {
1258 if (!value.getAsInteger(0, cpu))
1260 }
else if (name ==
"cpusubtype") {
1262 if (!value.getAsInteger(0, sub))
1264 }
else if (name ==
"arch") {
1265 arch_name = std::string(value);
1267 }
else if (name ==
"triple") {
1271 }
else if (name ==
"distribution_id") {
1275 }
else if (name ==
"os_build") {
1279 }
else if (name ==
"hostname") {
1283 }
else if (name ==
"os_kernel") {
1287 }
else if (name ==
"ostype") {
1290 }
else if (name ==
"vendor") {
1291 vendor_name = std::string(value);
1293 }
else if (name ==
"endian") {
1294 byte_order = llvm::StringSwitch<lldb::ByteOrder>(value)
1301 }
else if (name ==
"ptrsize") {
1302 if (!value.getAsInteger(0, pointer_byte_size))
1304 }
else if (name ==
"addressing_bits") {
1308 }
else if (name ==
"high_mem_addressing_bits") {
1311 }
else if (name ==
"low_mem_addressing_bits") {
1314 }
else if (name ==
"os_version" ||
1321 }
else if (name ==
"maccatalyst_version") {
1324 }
else if (name ==
"watchpoint_exceptions_received") {
1326 llvm::StringSwitch<LazyBool>(value)
1332 }
else if (name ==
"default_packet_timeout") {
1333 uint32_t timeout_seconds;
1334 if (!value.getAsInteger(0, timeout_seconds)) {
1339 }
else if (name ==
"vm-page-size") {
1341 if (!value.getAsInteger(0, page_size)) {
1348 if (num_keys_decoded > 0)
1351 if (triple.empty()) {
1352 if (arch_name.empty()) {
1355 if (pointer_byte_size) {
1356 assert(pointer_byte_size ==
m_host_arch.GetAddressByteSize());
1362 if (!vendor_name.empty())
1364 llvm::StringRef(vendor_name));
1365 if (!os_name.empty())
1366 m_host_arch.GetTriple().setOSName(llvm::StringRef(os_name));
1367 if (!environment.empty())
1368 m_host_arch.GetTriple().setEnvironmentName(environment);
1372 triple += arch_name;
1373 if (!vendor_name.empty() || !os_name.empty()) {
1375 if (vendor_name.empty())
1376 triple +=
"unknown";
1378 triple += vendor_name;
1380 if (os_name.empty())
1381 triple +=
"unknown";
1387 llvm::Triple &host_triple =
m_host_arch.GetTriple();
1388 if (host_triple.getVendor() == llvm::Triple::Apple &&
1389 host_triple.getOS() == llvm::Triple::Darwin) {
1391 case llvm::Triple::aarch64:
1392 case llvm::Triple::aarch64_32:
1393 case llvm::Triple::arm:
1394 case llvm::Triple::thumb:
1395 host_triple.setOS(llvm::Triple::IOS);
1398 host_triple.setOS(llvm::Triple::MacOSX);
1402 if (pointer_byte_size) {
1403 assert(pointer_byte_size ==
m_host_arch.GetAddressByteSize());
1411 if (pointer_byte_size) {
1412 assert(pointer_byte_size ==
m_host_arch.GetAddressByteSize());
1419 "GDBRemoteCommunicationClient::%s parsed host "
1420 "architecture as %s, triple as %s from triple text %s",
1424 :
"<null-arch-name>",
1464 return addressable_bits;
1474 uint32_t permissions) {
1478 const int packet_len = ::snprintf(
1479 packet,
sizeof(packet),
"_M%" PRIx64
",%s%s%s", (uint64_t)size,
1480 permissions & lldb::ePermissionsReadable ?
"r" :
"",
1481 permissions & lldb::ePermissionsWritable ?
"w" :
"",
1482 permissions & lldb::ePermissionsExecutable ?
"x" :
"");
1483 assert(packet_len < (
int)
sizeof(packet));
1503 const int packet_len =
1504 ::snprintf(packet,
sizeof(packet),
"_m%" PRIx64, (uint64_t)addr);
1505 assert(packet_len < (
int)
sizeof(packet));
1530 const int packet_len =
1531 ::snprintf(packet,
sizeof(packet),
"qSupportsDetachAndStayStopped:");
1532 assert(packet_len < (
int)
sizeof(packet));
1546 "Stays stopped not supported by this target.");
1562 "Multiprocess extension not supported by the server.");
1577 region_info.
Clear();
1582 const int packet_len = ::snprintf(
1583 packet,
sizeof(packet),
"qMemoryRegionInfo:%" PRIx64, (uint64_t)addr);
1584 assert(packet_len < (
int)
sizeof(packet));
1590 llvm::StringRef name;
1591 llvm::StringRef value;
1593 bool success =
true;
1594 bool saw_permissions =
false;
1596 if (name ==
"start") {
1597 if (!value.getAsInteger(16, addr_value))
1599 }
else if (name ==
"size") {
1600 if (!value.getAsInteger(16, addr_value)) {
1608 }
else if (name ==
"permissions" && region_info.
GetRange().
IsValid()) {
1609 saw_permissions =
true;
1611 if (value.contains(
'r'))
1616 if (value.contains(
'w'))
1621 if (value.contains(
'x'))
1635 }
else if (name ==
"name") {
1639 region_info.
SetName(name.c_str());
1640 }
else if (name ==
"flags") {
1644 llvm::StringRef flags = value;
1645 llvm::StringRef flag;
1646 while (flags.size()) {
1647 flags = flags.ltrim();
1648 std::tie(flag, flags) = flags.split(
' ');
1653 else if (flag ==
"ss")
1657 }
else if (name ==
"type") {
1658 for (llvm::StringRef entry : llvm::split(value,
',')) {
1659 if (entry ==
"stack")
1661 else if (entry ==
"heap")
1664 }
else if (name ==
"error") {
1666 std::string error_string;
1670 }
else if (name ==
"dirty-pages") {
1671 std::vector<addr_t> dirty_page_list;
1672 for (llvm::StringRef x : llvm::split(value,
',')) {
1674 x.consume_front(
"0x");
1675 if (llvm::to_integer(x, page, 16))
1676 dirty_page_list.push_back(page);
1688 if (!saw_permissions) {
1716 region_info = qXfer_region_info;
1719 region_info.
Clear();
1721 }
else if (qXfer_error.
Success()) {
1736 if (!
error.Success())
1739 if (map_region.GetRange().Contains(addr)) {
1740 region = map_region;
1766 llvm::Expected<std::string> xml =
ReadExtFeature(
"memory-map",
"");
1772 if (!xml_document.
ParseMemory(xml->c_str(), xml->size())) {
1788 if (memory_node.
GetName() !=
"memory")
1800 if (type ==
"rom") {
1803 }
else if (type ==
"ram") {
1807 }
else if (type ==
"flash") {
1810 [®ion](
const XMLNode &prop_node) ->
bool {
1813 if (prop_node.
GetName() !=
"property")
1816 if (propname ==
"blocksize") {
1838 std::optional<uint32_t> num;
1844 llvm::StringRef name;
1845 llvm::StringRef value;
1847 if (name ==
"num") {
1863WatchpointHardwareFeature
1882 return std::nullopt;
1887 std::string path{file_spec.
GetPath(
false)};
1907 std::string path{file_spec.
GetPath(
false)};
1927 std::string path{file_spec.
GetPath(
false)};
1956 return !cwd.empty();
1963 std::string path{working_dir.
GetPath(
false)};
1983 const int packet_len =
1984 ::snprintf(packet,
sizeof(packet),
"QSetDisableASLR:%i", enable ? 1 : 0);
1985 assert(packet_len < (
int)
sizeof(packet));
2000 const int packet_len = ::snprintf(packet,
sizeof(packet),
2001 "QSetDetachOnError:%i", enable ? 1 : 0);
2002 assert(packet_len < (
int)
sizeof(packet));
2018 llvm::StringRef name;
2019 llvm::StringRef value;
2025 std::string os_type;
2028 if (name ==
"pid") {
2030 value.getAsInteger(0, pid);
2032 }
else if (name ==
"ppid") {
2034 value.getAsInteger(0, pid);
2036 }
else if (name ==
"uid") {
2038 value.getAsInteger(0, uid);
2040 }
else if (name ==
"euid") {
2042 value.getAsInteger(0, uid);
2044 }
else if (name ==
"gid") {
2046 value.getAsInteger(0, gid);
2048 }
else if (name ==
"egid") {
2050 value.getAsInteger(0, gid);
2052 }
else if (name ==
"triple") {
2057 }
else if (name ==
"name") {
2064 }
else if (name ==
"args") {
2065 llvm::StringRef encoded_args(value), hex_arg;
2067 bool is_arg0 =
true;
2068 while (!encoded_args.empty()) {
2069 std::tie(hex_arg, encoded_args) = encoded_args.split(
'-');
2084 }
else if (name ==
"cputype") {
2085 value.getAsInteger(0, cpu);
2086 }
else if (name ==
"cpusubtype") {
2087 value.getAsInteger(0, sub);
2088 }
else if (name ==
"vendor") {
2089 vendor = std::string(value);
2090 }
else if (name ==
"ostype") {
2091 os_type = std::string(value);
2096 if (vendor ==
"apple") {
2100 llvm::StringRef(vendor));
2102 llvm::StringRef(os_type));
2114 process_info.
Clear();
2118 const int packet_len =
2119 ::snprintf(packet,
sizeof(packet),
"qProcessInfoPID:%" PRIu64, pid);
2120 assert(packet_len < (
int)
sizeof(packet));
2150 llvm::StringRef name;
2151 llvm::StringRef value;
2154 std::string os_name;
2155 std::string environment;
2156 std::string vendor_name;
2158 std::string elf_abi;
2159 uint32_t pointer_byte_size = 0;
2162 uint32_t num_keys_decoded = 0;
2165 if (name ==
"cputype") {
2166 if (!value.getAsInteger(16, cpu))
2168 }
else if (name ==
"cpusubtype") {
2169 if (!value.getAsInteger(16, sub)) {
2175 if (cpu == llvm::MachO::CPU_TYPE_ARM64 &&
2176 sub == llvm::MachO::CPU_SUBTYPE_ARM64E) {
2183 }
else if (name ==
"triple") {
2187 }
else if (name ==
"ostype") {
2190 }
else if (name ==
"vendor") {
2191 vendor_name = std::string(value);
2193 }
else if (name ==
"endian") {
2194 byte_order = llvm::StringSwitch<lldb::ByteOrder>(value)
2201 }
else if (name ==
"ptrsize") {
2202 if (!value.getAsInteger(16, pointer_byte_size))
2204 }
else if (name ==
"pid") {
2205 if (!value.getAsInteger(16, pid))
2207 }
else if (name ==
"elf_abi") {
2208 elf_abi = std::string(value);
2210 }
else if (name ==
"main-binary-uuid") {
2213 }
else if (name ==
"main-binary-slide") {
2221 }
else if (name ==
"main-binary-address") {
2229 }
else if (name ==
"binary-addresses") {
2232 for (llvm::StringRef x : llvm::split(value,
',')) {
2234 x.consume_front(
"0x");
2235 if (llvm::to_integer(x, vmaddr, 16))
2240 if (num_keys_decoded > 0)
2248 if (!triple.empty()) {
2251 if (pointer_byte_size) {
2252 assert(pointer_byte_size ==
m_process_arch.GetAddressByteSize());
2255 !vendor_name.empty()) {
2256 llvm::Triple triple(llvm::Twine(
"-") + vendor_name +
"-" + os_name);
2257 if (!environment.empty())
2258 triple.setEnvironmentName(environment);
2260 assert(triple.getObjectFormat() != llvm::Triple::UnknownObjectFormat);
2261 assert(triple.getObjectFormat() != llvm::Triple::Wasm);
2262 assert(triple.getObjectFormat() != llvm::Triple::XCOFF);
2263 switch (triple.getObjectFormat()) {
2264 case llvm::Triple::MachO:
2267 case llvm::Triple::ELF:
2270 case llvm::Triple::COFF:
2273 case llvm::Triple::GOFF:
2274 case llvm::Triple::SPIRV:
2275 case llvm::Triple::Wasm:
2276 case llvm::Triple::XCOFF:
2277 case llvm::Triple::DXContainer:
2278 LLDB_LOGF(log,
"error: not supported target architecture");
2280 case llvm::Triple::UnknownObjectFormat:
2281 LLDB_LOGF(log,
"error: failed to determine target architecture");
2285 if (pointer_byte_size) {
2286 assert(pointer_byte_size ==
m_process_arch.GetAddressByteSize());
2291 m_process_arch.GetTriple().setVendorName(llvm::StringRef(vendor_name));
2293 m_process_arch.GetTriple().setEnvironmentName(llvm::StringRef(environment));
2307 process_infos.clear();
2315 bool has_name_match =
false;
2316 if (name && name[0]) {
2317 has_name_match =
true;
2319 switch (name_match_type) {
2321 has_name_match =
false;
2333 packet.
PutCString(
"name_match:starts_with;");
2344 if (has_name_match) {
2352 packet.
Printf(
"pid:%" PRIu64
";",
2355 packet.
Printf(
"parent_pid:%" PRIu64
";",
2362 packet.
Printf(
"euid:%u;",
2365 packet.
Printf(
"egid:%u;",
2371 const llvm::Triple &triple = match_arch.
GetTriple();
2387 process_infos.push_back(process_info);
2396 return process_infos.size();
2400 std::string &name) {
2403 const int packet_len =
2404 ::snprintf(packet,
sizeof(packet),
"qUserName:%i", uid);
2405 assert(packet_len < (
int)
sizeof(packet));
2427 std::string &name) {
2430 const int packet_len =
2431 ::snprintf(packet,
sizeof(packet),
"qGroupName:%i", gid);
2432 assert(packet_len < (
int)
sizeof(packet));
2454 uint32_t recv_size) {
2456 packet.
Printf(
"qSpeedTest:response_size:%i;data:", recv_size);
2457 uint32_t bytes_left = send_size;
2458 while (bytes_left > 0) {
2459 if (bytes_left >= 26) {
2460 packet.
PutCString(
"abcdefghijklmnopqrstuvwxyz");
2463 packet.
Printf(
"%*.*s;", bytes_left, bytes_left,
2464 "abcdefghijklmnopqrstuvwxyz");
2473 return duration<float>::zero();
2474 using Dur = duration<float>;
2475 Dur sum = std::accumulate(std::begin(v), std::end(v), Dur());
2476 Dur mean = sum / v.size();
2479 float delta = (d - mean).count();
2480 accum += delta * delta;
2483 return Dur(sqrtf(accum / (v.size() - 1)));
2489 uint64_t recv_amount,
2490 bool json,
Stream &strm) {
2495 strm.
Printf(
"{ \"packet_speeds\" : {\n \"num_packets\" : %u,\n "
2499 strm.
Printf(
"Testing sending %u packets of various sizes:\n",
2503 uint32_t result_idx = 0;
2505 std::vector<duration<float>> packet_times;
2507 for (send_size = 0; send_size <= max_send;
2508 send_size ? send_size *= 2 : send_size = 4) {
2509 for (uint32_t recv_size = 0; recv_size <= max_recv;
2510 recv_size ? recv_size *= 2 : recv_size = 4) {
2513 packet_times.clear();
2515 const auto start_time = steady_clock::now();
2516 for (uint32_t i = 0; i < num_packets; ++i) {
2517 const auto packet_start_time = steady_clock::now();
2520 const auto packet_end_time = steady_clock::now();
2521 packet_times.push_back(packet_end_time - packet_start_time);
2523 const auto end_time = steady_clock::now();
2524 const auto total_time = end_time - start_time;
2526 float packets_per_second =
2527 ((float)num_packets) / duration<float>(total_time).count();
2528 auto average_per_packet = num_packets > 0 ? total_time / num_packets
2529 : duration<float>::zero();
2530 const duration<float> standard_deviation =
2533 strm.
Format(
"{0}\n {{\"send_size\" : {1,6}, \"recv_size\" : "
2534 "{2,6}, \"total_time_nsec\" : {3,12:ns-}, "
2535 "\"standard_deviation_nsec\" : {4,9:ns-f0}}",
2536 result_idx > 0 ?
"," :
"", send_size, recv_size,
2537 total_time, standard_deviation);
2540 strm.
Format(
"qSpeedTest(send={0,7}, recv={1,7}) in {2:s+f9} for "
2541 "{3,9:f2} packets/s ({4,10:ms+f6} per packet) with "
2542 "standard deviation of {5,10:ms+f6}\n",
2543 send_size, recv_size, duration<float>(total_time),
2544 packets_per_second, duration<float>(average_per_packet),
2545 standard_deviation);
2551 const float k_recv_amount_mb = (float)recv_amount / (1024.0f * 1024.0f);
2553 strm.
Printf(
"\n ]\n },\n \"download_speed\" : {\n \"byte_size\" "
2554 ": %" PRIu64
",\n \"results\" : [",
2557 strm.
Printf(
"Testing receiving %2.1fMB of data using varying receive "
2563 for (uint32_t recv_size = 32; recv_size <= max_recv; recv_size *= 2) {
2568 if (recv_size > 0) {
2569 const auto start_time = steady_clock::now();
2570 uint32_t bytes_read = 0;
2571 uint32_t packet_count = 0;
2572 while (bytes_read < recv_amount) {
2575 bytes_read += recv_size;
2578 const auto end_time = steady_clock::now();
2579 const auto total_time = end_time - start_time;
2580 float mb_second = ((float)recv_amount) /
2581 duration<float>(total_time).count() /
2583 float packets_per_second =
2584 ((float)packet_count) / duration<float>(total_time).count();
2585 const auto average_per_packet = packet_count > 0
2586 ? total_time / packet_count
2587 : duration<float>::zero();
2590 strm.
Format(
"{0}\n {{\"send_size\" : {1,6}, \"recv_size\" : "
2591 "{2,6}, \"total_time_nsec\" : {3,12:ns-}}",
2592 result_idx > 0 ?
"," :
"", send_size, recv_size,
2596 strm.
Format(
"qSpeedTest(send={0,7}, recv={1,7}) {2,6} packets needed "
2597 "to receive {3:f1}MB in {4:s+f9} for {5} MB/sec for "
2598 "{6,9:f2} packets/sec ({7,10:ms+f6} per packet)\n",
2599 send_size, recv_size, packet_count, k_recv_amount_mb,
2600 duration<float>(total_time), mb_second,
2601 packets_per_second, duration<float>(average_per_packet));
2607 strm.
Printf(
"\n ]\n }\n}\n");
2614 uint32_t recv_size) {
2616 packet.
Printf(
"qSpeedTest:response_size:%i;data:", recv_size);
2617 uint32_t bytes_left = send_size;
2618 while (bytes_left > 0) {
2619 if (bytes_left >= 26) {
2620 packet.
PutCString(
"abcdefghijklmnopqrstuvwxyz");
2623 packet.
Printf(
"%*.*s;", bytes_left, bytes_left,
2624 "abcdefghijklmnopqrstuvwxyz");
2635 const char *remote_accept_hostname,
lldb::pid_t &pid, uint16_t &port,
2636 std::string &socket_name) {
2639 socket_name.clear();
2644 std::string hostname;
2645 if (remote_accept_hostname && remote_accept_hostname[0])
2646 hostname = remote_accept_hostname;
2648 if (HostInfo::GetHostname(hostname)) {
2650 stream.
Printf(
"host:%s;", hostname.c_str());
2654 stream.
Printf(
"host:*;");
2665 llvm::StringRef name;
2666 llvm::StringRef value;
2669 value.getAsInteger(0, port);
2670 else if (name ==
"pid")
2671 value.getAsInteger(0, pid);
2672 else if (name.compare(
"socket_name") == 0) {
2683 std::vector<std::pair<uint16_t, std::string>> &connection_urls) {
2684 connection_urls.clear();
2700 for (
size_t i = 0, count = array->
GetSize(); i < count; ++i) {
2701 std::optional<StructuredData::Dictionary *> maybe_element =
2710 port = port_osp->GetUnsignedIntegerValue(0);
2712 std::string socket_name;
2715 socket_name = std::string(socket_name_osp->GetStringValue());
2717 if (port != 0 || !socket_name.empty())
2718 connection_urls.emplace_back(port, socket_name);
2720 return connection_urls.size();
2725 stream.
Printf(
"qKillSpawnedProcess:%" PRId64, pid);
2737 uint64_t tid, uint64_t pid,
char op) {
2743 packet.
Printf(
"p%" PRIx64
".", pid);
2748 packet.
Printf(
"%" PRIx64, tid);
2754 return {{pid, tid}};
2766 return std::nullopt;
2781 return ret.has_value();
2796 return ret.has_value();
2811 ::snprintf(packet,
sizeof(packet),
"qThreadStopInfo%" PRIx64, tid);
2812 assert(packet_len < (
int)
sizeof(packet));
2831 std::chrono::seconds timeout) {
2833 LLDB_LOGF(log,
"GDBRemoteCommunicationClient::%s() %s at addr = 0x%" PRIx64,
2834 __FUNCTION__, insert ?
"add" :
"remove", addr);
2841 const int packet_len =
2842 ::snprintf(packet,
sizeof(packet),
"%c%i,%" PRIx64
",%x",
2843 insert ?
'Z' :
'z', type, addr, length);
2845 assert(packet_len + 1 < (
int)
sizeof(packet));
2890std::vector<std::pair<lldb::pid_t, lldb::tid_t>>
2892 bool &sequence_mutex_unavailable) {
2893 std::vector<std::pair<lldb::pid_t, lldb::tid_t>> ids;
2897 sequence_mutex_unavailable =
false;
2901 for (packet_result =
2919 ids.push_back(*pid_tid);
2921 }
while (ch ==
',');
2935 ids.emplace_back(1, 1);
2939 LLDB_LOG(log,
"error: failed to get packet sequence mutex, not sending "
2940 "packet 'qfThreadInfo'");
2941 sequence_mutex_unavailable =
true;
2948 std::vector<lldb::tid_t> &thread_ids,
bool &sequence_mutex_unavailable) {
2953 if (ids.empty() || sequence_mutex_unavailable)
2956 for (
auto id : ids) {
2962 thread_ids.push_back(
id.second);
2965 return thread_ids.size();
2978 llvm::StringRef command,
2994 timeout_sec = std::ceil(std::chrono::duration<double>(*timeout).count());
2998 std::string path{working_dir.
GetPath(
false)};
3005 if (response.
GetChar() !=
'F')
3007 if (response.
GetChar() !=
',')
3012 else if (status_ptr)
3013 *status_ptr = exitcode;
3014 if (response.
GetChar() !=
',')
3019 if (response.
GetChar() !=
',')
3024 command_output->assign(output);
3031 uint32_t file_permissions) {
3032 std::string path{file_spec.
GetPath(
false)};
3038 llvm::StringRef packet = stream.
GetString();
3043 packet.str().c_str());
3045 if (response.
GetChar() !=
'F')
3047 packet.str().c_str());
3054 uint32_t file_permissions) {
3055 std::string path{file_spec.
GetPath(
false)};
3061 llvm::StringRef packet = stream.
GetString();
3068 if (response.
GetChar() !=
'F')
3077#define HANDLE_ERRNO(name, value) \
3080#include "Plugins/Process/gdb-remote/GDBRemoteErrno.def"
3089 if (response.
GetChar() !=
'F')
3091 int32_t result = response.
GetS32(-2, 16);
3094 if (response.
GetChar() ==
',') {
3096 if (result_errno != -1)
3108 std::string path(file_spec.
GetPath(
false));
3129 stream.
Printf(
"vFile:close:%x", (
int)fd);
3138std::optional<GDBRemoteFStatData>
3141 stream.
Printf(
"vFile:fstat:%" PRIx64, fd);
3145 if (response.
GetChar() !=
'F')
3146 return std::nullopt;
3147 int64_t size = response.
GetS64(-1, 16);
3148 if (size > 0 && response.
GetChar() ==
';') {
3152 if (buffer.size() !=
sizeof(out))
3153 return std::nullopt;
3154 memcpy(&out, buffer.data(),
sizeof(out));
3159 return std::nullopt;
3162std::optional<GDBRemoteFStatData>
3167 return std::nullopt;
3168 std::optional<GDBRemoteFStatData> st =
FStat(fd);
3177 std::string path(file_spec.
GetPath(
false));
3187 if (response.
GetChar() !=
'F')
3196 std::optional<GDBRemoteFStatData> st =
Stat(file_spec);
3214 while (response.
Peek()) {
3216 while ((ch = response.
GetHexU8(0,
false)) !=
'\0')
3219 if (response.
GetChar() !=
',')
3227 uint32_t &file_permissions) {
3229 std::string path{file_spec.
GetPath(
false)};
3242 if (response.
GetChar() !=
'F') {
3244 "invalid response to '%s' packet", stream.
GetData());
3246 const uint32_t mode = response.
GetS32(-1, 16);
3247 if (
static_cast<int32_t
>(mode) == -1) {
3248 if (response.
GetChar() ==
',') {
3250 if (response_errno > 0)
3267 if (std::optional<GDBRemoteFStatData> st =
Stat(file_spec)) {
3275 uint64_t offset,
void *dst,
3279 stream.
Printf(
"vFile:pread:%x,%" PRIx64
",%" PRIx64, (
int)fd, dst_len,
3284 if (response.
GetChar() !=
'F')
3286 int64_t retcode = response.
GetS64(-1, 16);
3287 if (retcode == -1) {
3289 if (response.
GetChar() ==
',') {
3291 if (response_errno > 0)
3296 const char next = (response.
Peek() ? *response.
Peek() : 0);
3303 const uint64_t data_to_write =
3304 std::min<uint64_t>(dst_len, buffer.size());
3305 if (data_to_write > 0)
3306 memcpy(dst, &buffer[0], data_to_write);
3307 return data_to_write;
3320 stream.
Printf(
"vFile:pwrite:%x,%" PRIx64
",", (
int)fd, offset);
3325 if (response.
GetChar() !=
'F') {
3329 int64_t bytes_written = response.
GetS64(-1, 16);
3330 if (bytes_written == -1) {
3332 if (response.
GetChar() ==
',') {
3334 if (response_errno > 0)
3339 return bytes_written;
3348 std::string src_path{src.
GetPath(
false)}, dst_path{dst.
GetPath(
false)};
3360 if (response.
GetChar() ==
'F') {
3364 if (response.
GetChar() ==
',') {
3366 if (response_errno > 0)
3381 std::string path{file_spec.
GetPath(
false)};
3391 if (response.
GetChar() ==
'F') {
3395 if (response.
GetChar() ==
',') {
3397 if (response_errno > 0)
3415 std::string path(file_spec.
GetPath(
false));
3424 if (response.
GetChar() !=
'F')
3426 if (response.
GetChar() !=
',')
3428 bool retcode = (response.
GetChar() !=
'0');
3445 std::string path(file_spec.
GetPath(
false));
3452 if (response.
GetChar() !=
'F')
3453 return std::make_error_code(std::errc::illegal_byte_sequence);
3454 if (response.
GetChar() !=
',')
3455 return std::make_error_code(std::errc::illegal_byte_sequence);
3456 if (response.
Peek() && *response.
Peek() ==
'x')
3457 return std::make_error_code(std::errc::no_such_file_or_directory);
3474 const size_t MD5_HALF_LENGTH =
sizeof(uint64_t) * 2;
3479 if (part.size() != MD5_HALF_LENGTH)
3480 return std::make_error_code(std::errc::illegal_byte_sequence);
3484 if (part.getAsInteger(16, low))
3485 return std::make_error_code(std::errc::illegal_byte_sequence);
3490 if (part.size() != MD5_HALF_LENGTH)
3491 return std::make_error_code(std::errc::illegal_byte_sequence);
3495 if (part.getAsInteger(16, high))
3496 return std::make_error_code(std::errc::illegal_byte_sequence);
3498 llvm::MD5::MD5Result result;
3499 llvm::support::endian::write<uint64_t, llvm::endianness::little>(
3500 result.data(), low);
3501 llvm::support::endian::write<uint64_t, llvm::endianness::little>(
3502 result.data() + 8, high);
3506 return std::make_error_code(std::errc::operation_canceled);
3516 arch.
GetTriple().getVendor() == llvm::Triple::Apple &&
3517 arch.
GetTriple().getOS() == llvm::Triple::IOS &&
3518 (arch.
GetTriple().getArch() == llvm::Triple::aarch64 ||
3519 arch.
GetTriple().getArch() == llvm::Triple::aarch64_32)) {
3522 if (gdb_server_version != 0) {
3524 if (gdb_server_name && strcmp(gdb_server_name,
"debugserver") == 0) {
3525 if (gdb_server_version >= 310)
3538 payload.
Printf(
"p%x", reg);
3547 response.
GetHexBytes(buffer_sp->GetData(),
'\xcc');
3562 response.
GetHexBytes(buffer_sp->GetData(),
'\xcc');
3568 llvm::ArrayRef<uint8_t> data) {
3570 payload.
Printf(
"P%x=", reg_num);
3594 uint32_t &save_id) {
3610 const uint32_t response_save_id = response.
GetU32(0);
3611 if (response_save_id == 0)
3614 save_id = response_save_id;
3627 payload.
Printf(
"QRestoreRegisterState:%u", save_id);
3647 packet.
Printf(
"QSyncThreadState:%4.4" PRIx64
";", tid);
3653llvm::Expected<TraceSupportedResponse>
3658 escaped_packet.
PutCString(
"jLLDBTraceSupported");
3667 return llvm::createStringError(llvm::inconvertibleErrorCode(),
3668 "jLLDBTraceSupported is unsupported");
3670 return llvm::json::parse<TraceSupportedResponse>(response.
Peek(),
3671 "TraceSupportedResponse");
3673 LLDB_LOG(log,
"failed to send packet: jLLDBTraceSupported");
3674 return llvm::createStringError(llvm::inconvertibleErrorCode(),
3675 "failed to send packet: jLLDBTraceSupported");
3680 std::chrono::seconds timeout) {
3684 escaped_packet.
PutCString(
"jLLDBTraceStop:");
3686 std::string json_string;
3687 llvm::raw_string_ostream os(json_string);
3690 escaped_packet.
PutEscapedBytes(json_string.c_str(), json_string.size());
3699 return llvm::createStringError(llvm::inconvertibleErrorCode(),
3700 "jLLDBTraceStop is unsupported");
3702 return llvm::Error::success();
3703 return llvm::createStringError(llvm::inconvertibleErrorCode(),
3704 "Invalid jLLDBTraceStart response");
3706 LLDB_LOG(log,
"failed to send packet: jLLDBTraceStop");
3707 return llvm::createStringError(llvm::inconvertibleErrorCode(),
3708 "failed to send packet: jLLDBTraceStop '%s'",
3714 std::chrono::seconds timeout) {
3718 escaped_packet.
PutCString(
"jLLDBTraceStart:");
3720 std::string json_string;
3721 llvm::raw_string_ostream os(json_string);
3724 escaped_packet.
PutEscapedBytes(json_string.c_str(), json_string.size());
3733 return llvm::createStringError(llvm::inconvertibleErrorCode(),
3734 "jLLDBTraceStart is unsupported");
3736 return llvm::Error::success();
3737 return llvm::createStringError(llvm::inconvertibleErrorCode(),
3738 "Invalid jLLDBTraceStart response");
3740 LLDB_LOG(log,
"failed to send packet: jLLDBTraceStart");
3741 return llvm::createStringError(llvm::inconvertibleErrorCode(),
3742 "failed to send packet: jLLDBTraceStart '%s'",
3746llvm::Expected<std::string>
3748 std::chrono::seconds timeout) {
3752 escaped_packet.
PutCString(
"jLLDBTraceGetState:");
3754 std::string json_string;
3755 llvm::raw_string_ostream os(json_string);
3758 escaped_packet.
PutEscapedBytes(json_string.c_str(), json_string.size());
3767 return llvm::createStringError(llvm::inconvertibleErrorCode(),
3768 "jLLDBTraceGetState is unsupported");
3769 return std::string(response.
Peek());
3772 LLDB_LOG(log,
"failed to send packet: jLLDBTraceGetState");
3773 return llvm::createStringError(
3774 llvm::inconvertibleErrorCode(),
3775 "failed to send packet: jLLDBTraceGetState '%s'",
3779llvm::Expected<std::vector<uint8_t>>
3785 escaped_packet.
PutCString(
"jLLDBTraceGetBinaryData:");
3787 std::string json_string;
3788 llvm::raw_string_ostream os(json_string);
3791 escaped_packet.
PutEscapedBytes(json_string.c_str(), json_string.size());
3801 return std::vector<uint8_t>(data.begin(), data.end());
3803 LLDB_LOG(log,
"failed to send packet: jLLDBTraceGetBinaryData");
3804 return llvm::createStringError(
3805 llvm::inconvertibleErrorCode(),
3806 "failed to send packet: jLLDBTraceGetBinaryData '%s'",
3814 return std::nullopt;
3816 return std::nullopt;
3820 const auto &GetOffset = [&] {
3822 if (ref.consumeInteger(16, offset))
3824 result.
offsets.push_back(offset);
3828 if (ref.consume_front(
"Text=")) {
3831 return std::nullopt;
3832 if (!ref.consume_front(
";Data=") || !GetOffset())
3833 return std::nullopt;
3836 if (ref.consume_front(
";Bss=") && GetOffset() && ref.empty())
3838 }
else if (ref.consume_front(
"TextSeg=")) {
3841 return std::nullopt;
3844 if (ref.consume_front(
";DataSeg=") && GetOffset() && ref.empty())
3847 return std::nullopt;
3856 std::string module_path = module_file_spec.
GetPath(
false);
3857 if (module_path.empty())
3864 const auto &triple = arch_spec.
GetTriple().getTriple();
3880 llvm::StringRef name;
3881 llvm::StringRef value;
3883 module_spec.
Clear();
3887 if (name ==
"uuid" || name ==
"md5") {
3892 }
else if (name ==
"triple") {
3897 }
else if (name ==
"file_offset") {
3899 if (!value.getAsInteger(16, ival))
3901 }
else if (name ==
"file_size") {
3903 if (!value.getAsInteger(16, ival))
3905 }
else if (name ==
"file_path") {
3916static std::optional<ModuleSpec>
3920 return std::nullopt;
3922 llvm::StringRef string;
3926 return std::nullopt;
3928 return std::nullopt;
3931 return std::nullopt;
3935 return std::nullopt;
3939 return std::nullopt;
3943 return std::nullopt;
3949std::optional<std::vector<ModuleSpec>>
3951 llvm::ArrayRef<FileSpec> module_file_specs,
const llvm::Triple &triple) {
3955 return std::nullopt;
3957 json::Array module_array;
3958 for (
const FileSpec &module_file_spec : module_file_specs) {
3959 module_array.push_back(
3960 json::Object{{
"file", module_file_spec.GetPath(
false)},
3961 {
"triple", triple.getTriple()}});
3964 unescaped_payload.
PutCString(
"jModulesInfo:");
3965 unescaped_payload.
AsRawOstream() << std::move(module_array);
3978 return std::nullopt;
3982 return std::nullopt;
3987 if (!response_object_sp)
3988 return std::nullopt;
3991 if (!response_array)
3992 return std::nullopt;
3994 std::vector<ModuleSpec> result;
3995 for (
size_t i = 0; i < response_array->
GetSize(); ++i) {
3998 result.push_back(*module_spec);
4008llvm::Expected<std::string>
4010 llvm::StringRef annex) {
4013 llvm::raw_string_ostream output_stream(output);
4027 std::string packet =
4028 (
"qXfer:" +
object +
":read:" + annex +
":" +
4029 llvm::Twine::utohexstr(offset) +
"," + llvm::Twine::utohexstr(size))
4037 return llvm::createStringError(llvm::inconvertibleErrorCode(),
4038 "Error sending $qXfer packet");
4056 return llvm::createStringError(
4057 llvm::inconvertibleErrorCode(),
4058 "Invalid continuation code from $qXfer packet");
4108 bool symbol_response_provided =
false;
4111 bool first_qsymbol_query =
true;
4122 if (symbol_response_provided || first_qsymbol_query) {
4129 first_qsymbol_query =
false;
4138 if (response_str.starts_with(
"qSymbol:")) {
4140 std::string symbol_name;
4142 if (symbol_name.empty())
4153 switch (sc.symbol->GetType()) {
4186 sc.symbol->GetLoadAddress(&process->
GetTarget());
4199 packet.
Printf(
"%" PRIx64, symbol_load_addr);
4200 symbol_response_provided =
true;
4202 symbol_response_provided =
false;
4218 "GDBRemoteCommunicationClient::%s: Didn't get sequence mutex.",
4243 "GDBRemoteCommunicationClient::%s(): "
4244 "QSupportedAsyncJSONPackets returned invalid "
4251 "GDBRemoteCommunicationClient::%s(): "
4252 "QSupportedAsyncJSONPackets unsupported",
4260 "GDBRemoteCommunicationClient::%s(): supported async "
4262 __FUNCTION__, stream.
GetData());
4272 llvm::ArrayRef<int32_t> signals) {
4275 auto range = llvm::make_range(signals.begin(), signals.end());
4276 std::string packet = formatv(
"QPassSignals:{0:$[;]@(x-2)}", range).str();
4288 "Unknown error happened during sending QPassSignals packet.");
4296 if (type_name.empty()) {
4309 config_sp->Dump(unescaped_stream);
4310 unescaped_stream.
Flush();
4328 "configuring StructuredData feature {0} failed with error {1}",
4334 "configuring StructuredData feature {0} failed when sending packet: "
4336 type_name, (
int)result);
4365 return llvm::createStringError(llvm::inconvertibleErrorCode(),
4366 "failed to send k packet");
4368 char packet_cmd = response.
GetChar(0);
4369 if (packet_cmd ==
'W' || packet_cmd ==
'X')
4372 return llvm::createStringError(llvm::inconvertibleErrorCode(),
4373 "unexpected response to k packet: %s",
static llvm::raw_ostream & error(Stream &strm)
duration< float > calculate_standard_deviation(const std::vector< duration< float > > &v)
static std::optional< ModuleSpec > ParseModuleSpec(StructuredData::Dictionary *dict)
static int gdb_errno_to_system(int err)
static void ParseOSType(llvm::StringRef value, std::string &os_name, std::string &environment)
static void MakeSpeedTestPacket(StreamString &packet, uint32_t send_size, uint32_t recv_size)
static uint64_t ParseHostIOPacketResponse(StringExtractorGDBRemote &response, uint64_t fail_result, Status &error)
#define LLDB_LOG(log,...)
The LLDB_LOG* macros defined below are the way to emit log messages.
#define LLDB_LOGF(log,...)
A class which holds the metadata from a remote stub/corefile note about how many bits are used for ad...
void SetAddressableBits(uint32_t addressing_bits)
When a single value is available for the number of bits.
An architecture specification class.
bool IsValid() const
Tests if this ArchSpec is valid.
llvm::Triple & GetTriple()
Architecture triple accessor.
bool SetTriple(const llvm::Triple &triple)
Architecture triple setter.
bool SetArchitecture(ArchitectureType arch_type, uint32_t cpu, uint32_t sub, uint32_t os=0)
Change the architecture object type, CPU type and OS type.
A command line argument class.
void AppendArgument(llvm::StringRef arg_str, char quote_char='\0')
Appends a new argument to the end of the list argument list.
const char * GetArgumentAtIndex(size_t idx) const
Gets the NULL terminated C string argument pointer for the argument at index idx.
void Clear()
Clear the arguments.
bool IsConnected() const
Check if the connection is valid.
virtual lldb::ConnectionStatus Disconnect(Status *error_ptr=nullptr)
Disconnect the communications connection if one is currently connected.
"lldb/Utility/ArgCompletionRequest.h"
void AddCompletion(llvm::StringRef completion, llvm::StringRef description="", CompletionMode mode=CompletionMode::Normal)
Adds a possible completion string.
llvm::StringRef GetCursorArgumentPrefix() const
A uniqued constant string class.
A subclass of DataBuffer that stores a data buffer on the heap.
void SetFile(llvm::StringRef path, Style style)
Change the file specified with a new path.
size_t GetPath(char *path, size_t max_path_length, bool denormalize=true) const
Extract the full path to the file.
void SetFlash(OptionalBool val)
void SetMapped(OptionalBool val)
void SetBlocksize(lldb::offset_t blocksize)
void SetMemoryTagged(OptionalBool val)
void SetReadable(OptionalBool val)
void SetExecutable(OptionalBool val)
void SetIsStackMemory(OptionalBool val)
void SetPageSize(int pagesize)
void SetName(const char *name)
void SetWritable(OptionalBool val)
lldb::offset_t GetBlocksize() const
void SetDirtyPageList(std::vector< lldb::addr_t > pagelist)
OptionalBool GetFlash() const
void SetIsShadowStack(OptionalBool val)
void FindSymbolsWithNameAndType(ConstString name, lldb::SymbolType symbol_type, SymbolContextList &sc_list) const
void SetObjectSize(uint64_t object_size)
ArchSpec & GetArchitecture()
void SetObjectOffset(uint64_t object_offset)
void SetGroupID(uint32_t gid)
bool ProcessIDIsValid() const
void SetArg0(llvm::StringRef arg)
const char * GetName() const
lldb::pid_t GetProcessID() const
void SetProcessID(lldb::pid_t pid)
FileSpec & GetExecutableFile()
bool UserIDIsValid() const
uint32_t GetUserID() const
uint32_t GetGroupID() const
void SetUserID(uint32_t uid)
bool GroupIDIsValid() const
ArchSpec & GetArchitecture()
bool MatchAllProcesses() const
NameMatch GetNameMatchType() const
bool GetMatchAllUsers() const
ProcessInstanceInfo & GetProcessInfo()
uint32_t GetEffectiveUserID() const
void SetEffectiveGroupID(uint32_t gid)
lldb::pid_t GetParentProcessID() const
bool ParentProcessIDIsValid() const
uint32_t GetEffectiveGroupID() const
bool EffectiveUserIDIsValid() const
bool EffectiveGroupIDIsValid() const
void SetParentProcessID(lldb::pid_t pid)
void SetEffectiveUserID(uint32_t uid)
A plug-in interface definition class for debugging a process.
Target & GetTarget()
Get the target object pointer for this module.
llvm::Error ToError() const
FIXME: Replace all uses with takeError() instead.
static Status FromErrorStringWithFormat(const char *format,...) __attribute__((format(printf
static Status FromErrorString(const char *str)
static Status static Status FromErrorStringWithFormatv(const char *format, Args &&...args)
static Status FromError(llvm::Error error)
Avoid using this in new code. Migrate APIs to llvm::Expected instead.
bool Success() const
Test for success condition.
int PutEscapedBytes(const void *s, size_t src_len)
Output a block of data to the stream performing GDB-remote escaping.
const char * GetData() const
void Flush() override
Flush the stream.
llvm::StringRef GetString() const
A stream class that can stream formatted output to a file.
void Format(const char *format, Args &&... args)
llvm::raw_ostream & AsRawOstream()
Returns a raw_ostream that forwards the data to this Stream object.
size_t PutStringAsRawHex8(llvm::StringRef s)
size_t PutHex64(uint64_t uvalue, lldb::ByteOrder byte_order=lldb::eByteOrderInvalid)
size_t Printf(const char *format,...) __attribute__((format(printf
Output printf formatted output to the stream.
size_t PutCString(llvm::StringRef cstr)
Output a C string to the stream.
size_t PutHex32(uint32_t uvalue, lldb::ByteOrder byte_order=lldb::eByteOrderInvalid)
virtual void Flush()=0
Flush the stream.
size_t EOL()
Output and End of Line character to the stream.
size_t PutBytesAsRawHex8(const void *src, size_t src_len, lldb::ByteOrder src_byte_order=lldb::eByteOrderInvalid, lldb::ByteOrder dst_byte_order=lldb::eByteOrderInvalid)
ObjectSP GetItemAtIndex(size_t idx) const
std::optional< Dictionary * > GetItemAtIndexAsDictionary(size_t idx) const
Retrieves the element at index idx from a StructuredData::Array if it is a Dictionary.
bool GetValueForKeyAsInteger(llvm::StringRef key, IntType &result) const
bool GetValueForKeyAsString(llvm::StringRef key, llvm::StringRef &result) const
ObjectSP GetValueForKey(llvm::StringRef key) const
std::shared_ptr< Object > ObjectSP
static ObjectSP ParseJSON(llvm::StringRef json_text)
Defines a list of symbol context objects.
Defines a symbol context baton that can be handed other debug core functions.
const ModuleList & GetImages() const
Get accessor for the images for this process.
const ArchSpec & GetArchitecture() const
Represents UUID's of various sizes.
bool SetFromStringRef(llvm::StringRef str)
XMLNode GetRootElement(const char *required_name=nullptr)
bool ParseMemory(const char *xml, size_t xml_length, const char *url="untitled.xml")
void ForEachChildElement(NodeCallback const &callback) const
llvm::StringRef GetName() const
std::string GetAttributeValue(const char *name, const char *fail_value=nullptr) const
bool GetElementTextAsUnsigned(uint64_t &value, uint64_t fail_value=0, int base=0) const
bool GetAttributeValueAsUnsigned(const char *name, uint64_t &value, uint64_t fail_value=0, int base=0) const
GDBRemoteClientBase(const char *comm_name)
PacketResult SendPacketAndWaitForResponse(llvm::StringRef payload, StringExtractorGDBRemote &response, std::chrono::seconds interrupt_timeout=std::chrono::seconds(0), bool sync_on_timeout=true)
PacketResult SendPacketAndWaitForResponseNoLock(llvm::StringRef payload, StringExtractorGDBRemote &response, bool sync_on_timeout=true)
virtual void OnRunPacketSent(bool first)
lldb::DataBufferSP ReadRegister(lldb::tid_t tid, uint32_t reg_num)
std::chrono::seconds m_default_packet_timeout
LazyBool m_supports_vCont_S
LazyBool m_supports_detach_stay_stopped
LazyBool m_supports_alloc_dealloc_memory
bool SupportsGDBStoppointPacket(GDBStoppointType type)
ArchSpec GetSystemArchitecture()
bool RestoreRegisterState(lldb::tid_t tid, uint32_t save_id)
const ArchSpec & GetHostArchitecture()
int SendLaunchArchPacket(const char *arch)
lldb::pid_t GetCurrentProcessID(bool allow_lazy=true)
bool AvoidGPackets(ProcessGDBRemote *process)
llvm::VersionTuple GetMacCatalystVersion()
Status CreateSymlink(const FileSpec &src, const FileSpec &dst)
PacketResult SendThreadSpecificPacketAndWaitForResponse(lldb::tid_t tid, StreamString &&payload, StringExtractorGDBRemote &response)
LazyBool m_qGDBServerVersion_is_valid
bool GetLoadedDynamicLibrariesInfosSupported()
bool GetHostInfo(bool force=false)
LazyBool m_supports_memory_region_info
LazyBool m_qHostInfo_is_valid
bool KillSpawnedProcess(lldb::pid_t pid)
bool m_supports_jModulesInfo
lldb_private::AddressableBits GetAddressableBits()
LazyBool m_supports_jGetSharedCacheInfo
bool GetReverseContinueSupported()
bool GetVContSupported(char flavor)
bool GetGroupName(uint32_t gid, std::string &name)
bool DecodeProcessInfoResponse(StringExtractorGDBRemote &response, ProcessInstanceInfo &process_info)
std::optional< std::string > GetOSKernelDescription()
int SendEnvironment(const Environment &env)
LazyBool m_supports_augmented_libraries_svr4_read
uint32_t m_high_mem_addressing_bits
llvm::VersionTuple GetOSVersion()
std::optional< uint32_t > GetWatchpointSlotCount()
bool HandshakeWithServer(Status *error_ptr)
bool GetAugmentedLibrariesSVR4ReadSupported()
lldb_private::StructuredData::Array * GetSupportedStructuredDataPlugins()
Return the array of async JSON packet types supported by the remote.
bool m_supports_vFileSize
uint64_t GetRemoteMaxPacketSize()
bool QueryNoAckModeSupported()
lldb::tid_t m_curr_tid_run
Current gdb remote protocol thread identifier for continue, step, etc.
int SendLaunchEventDataPacket(const char *data, bool *was_supported=nullptr)
bool m_qSymbol_requests_done
bool GetCurrentProcessInfo(bool allow_lazy_pid=true)
Status Unlink(const FileSpec &file_spec)
bool GetVAttachOrWaitSupported()
std::optional< std::vector< ModuleSpec > > GetModulesInfo(llvm::ArrayRef< FileSpec > module_file_specs, const llvm::Triple &triple)
llvm::Expected< std::string > ReadExtFeature(llvm::StringRef object, llvm::StringRef annex)
LazyBool m_supports_qXfer_features_read
bool m_supports_vFileMode
bool GetMultiprocessSupported()
LazyBool m_qProcessInfo_is_valid
LazyBool m_supports_vCont_c
std::optional< GDBRemoteFStatData > Stat(const FileSpec &file_spec)
std::optional< QOffsets > GetQOffsets()
Use qOffsets to query the offset used when relocating the target executable.
size_t QueryGDBServer(std::vector< std::pair< uint16_t, std::string > > &connection_urls)
int m_target_vm_page_size
llvm::Error SendTraceStop(const TraceStopRequest &request, std::chrono::seconds interrupt_timeout)
uint32_t m_num_supported_hardware_watchpoints
std::optional< xPacketState > m_x_packet_state
void TestPacketSpeed(const uint32_t num_packets, uint32_t max_send, uint32_t max_recv, uint64_t recv_amount, bool json, Stream &strm)
lldb::addr_t AllocateMemory(size_t size, uint32_t permissions)
std::string m_host_distribution_id
GDBRemoteCommunicationClient()
std::optional< std::string > GetOSBuildString()
bool LaunchGDBServer(const char *remote_accept_hostname, lldb::pid_t &pid, uint16_t &port, std::string &socket_name)
int SetSTDOUT(const FileSpec &file_spec)
LazyBool m_prepare_for_reg_writing_reply
bool m_supports_qThreadStopInfo
bool SetCurrentThreadForRun(uint64_t tid, lldb::pid_t pid=LLDB_INVALID_PROCESS_ID)
uint8_t SendGDBStoppointTypePacket(GDBStoppointType type, bool insert, lldb::addr_t addr, uint32_t length, std::chrono::seconds interrupt_timeout)
bool GetpPacketSupported(lldb::tid_t tid)
Status MakeDirectory(const FileSpec &file_spec, uint32_t mode)
Status RunShellCommand(llvm::StringRef command, const FileSpec &working_dir, int *status_ptr, int *signo_ptr, std::string *command_output, const Timeout< std::micro > &timeout)
uint64_t ReadFile(lldb::user_id_t fd, uint64_t offset, void *dst, uint64_t dst_len, Status &error)
LazyBool m_supports_vCont_any
bool GetWorkingDir(FileSpec &working_dir)
Gets the current working directory of a remote platform GDB server.
lldb::user_id_t OpenFile(const FileSpec &file_spec, File::OpenOptions flags, mode_t mode, Status &error)
LazyBool m_supports_error_string_reply
LazyBool m_supports_qXfer_siginfo_read
WatchpointHardwareFeature GetSupportedWatchpointTypes()
std::optional< GDBRemoteFStatData > FStat(lldb::user_id_t fd)
int SetSTDERR(const FileSpec &file_spec)
bool GetThreadSuffixSupported()
lldb::addr_t m_process_standalone_value
LazyBool m_supports_memory_tagging
llvm::Expected< std::string > SendTraceGetState(llvm::StringRef type, std::chrono::seconds interrupt_timeout)
void ResetDiscoverableSettings(bool did_exec)
llvm::Error LaunchProcess(const Args &args)
Launch the process using the provided arguments.
LazyBool m_supports_qXfer_libraries_svr4_read
bool m_process_standalone_value_is_offset
lldb_private::StructuredData::ObjectSP m_supported_async_json_packets_sp
LazyBool m_attach_or_wait_reply
bool m_supports_jThreadsInfo
bool GetGDBServerVersion()
lldb::user_id_t GetFileSize(const FileSpec &file_spec)
bool GetQXferFeaturesReadSupported()
LazyBool m_watchpoints_trigger_after_instruction
LazyBool m_supports_threads_in_stop_reply
std::vector< lldb::addr_t > m_binary_addresses
void GetRemoteQSupported()
bool GetQPassSignalsSupported()
Status ConfigureRemoteStructuredData(llvm::StringRef type_name, const StructuredData::ObjectSP &config_sp)
Configure a StructuredData feature on the remote end.
bool CloseFile(lldb::user_id_t fd, Status &error)
~GDBRemoteCommunicationClient() override
bool GetReverseStepSupported()
uint64_t WriteFile(lldb::user_id_t fd, uint64_t offset, const void *src, uint64_t src_len, Status &error)
LazyBool m_supports_vCont_s
bool m_supports_qGroupName
bool SetCurrentThread(uint64_t tid, lldb::pid_t pid=LLDB_INVALID_PROCESS_ID)
bool m_supports_vFileExists
bool GetDefaultThreadId(lldb::tid_t &tid)
void ServeSymbolLookups(lldb_private::Process *process)
LazyBool m_uses_native_signals
uint32_t m_low_mem_addressing_bits
lldb::tid_t m_curr_tid
Current gdb remote protocol thread identifier for all other operations.
LazyBool m_supports_qXfer_memory_map_read
bool GetHostname(std::string &s)
llvm::Expected< int > KillProcess(lldb::pid_t pid)
bool m_supported_async_json_packets_is_valid
bool GetSyncThreadStateSupported()
bool WriteAllRegisters(lldb::tid_t tid, llvm::ArrayRef< uint8_t > data)
bool m_supports_QEnvironmentHexEncoded
bool GetProcessInfo(lldb::pid_t pid, ProcessInstanceInfo &process_info)
Status SetFilePermissions(const FileSpec &file_spec, uint32_t file_permissions)
LazyBool m_curr_pid_is_valid
Status GetQXferMemoryMapRegionInfo(lldb::addr_t addr, MemoryRegionInfo ®ion)
int SetDetachOnError(bool enable)
Sets the DetachOnError flag to enable for the process controlled by the stub.
void OnRunPacketSent(bool first) override
bool m_supports_QEnvironment
lldb::addr_t GetShlibInfoAddr()
Status SendSignalsToIgnore(llvm::ArrayRef< int32_t > signals)
LazyBool m_supports_jThreadExtendedInfo
LazyBool GetThreadPacketSupported(lldb::tid_t tid, llvm::StringRef packetStr)
UUID m_process_standalone_uuid
LazyBool m_supports_not_sending_acks
LazyBool m_supports_watchpoint_support_info
bool WriteRegister(lldb::tid_t tid, uint32_t reg_num, llvm::ArrayRef< uint8_t > data)
uint64_t m_max_packet_size
void EnableErrorStringInPacket()
llvm::Expected< std::vector< uint8_t > > SendTraceGetBinaryData(const TraceGetBinaryDataRequest &request, std::chrono::seconds interrupt_timeout)
LazyBool m_supports_qXfer_libraries_read
bool GetSaveCoreSupported() const
LazyBool m_supports_jLoadedDynamicLibrariesInfos
Status LoadQXferMemoryMap()
LazyBool m_supports_thread_suffix
int SetSTDIN(const FileSpec &file_spec)
Sets the path to use for stdin/out/err for a process that will be launched with the 'A' packet.
LazyBool m_supports_vCont_C
lldb::pid_t m_curr_pid
Current gdb remote protocol process identifier for all other operations.
Status WriteMemoryTags(lldb::addr_t addr, size_t len, int32_t type, const std::vector< uint8_t > &tags)
LazyBool m_supports_qSaveCore
LazyBool m_supports_reverse_step
bool GetQXferLibrariesSVR4ReadSupported()
size_t GetCurrentThreadIDs(std::vector< lldb::tid_t > &thread_ids, bool &sequence_mutex_unavailable)
Status Detach(bool keep_stopped, lldb::pid_t pid=LLDB_INVALID_PROCESS_ID)
std::optional< bool > GetWatchpointReportedAfter()
std::string m_gdb_server_name
std::vector< lldb::addr_t > GetProcessStandaloneBinaries()
bool m_supports_qProcessInfoPID
llvm::VersionTuple m_os_version
bool GetQXferLibrariesReadSupported()
llvm::VersionTuple m_maccatalyst_version
int SetDisableASLR(bool enable)
Sets the disable ASLR flag to enable for a process that will be launched with the 'A' packet.
bool GetUserName(uint32_t uid, std::string &name)
Status GetMemoryRegionInfo(lldb::addr_t addr, MemoryRegionInfo &range_info)
std::vector< MemoryRegionInfo > m_qXfer_memory_map
bool SyncThreadState(lldb::tid_t tid)
bool m_supports_qfProcessInfo
std::chrono::seconds GetHostDefaultPacketTimeout()
int SendStdinNotification(const char *data, size_t data_len)
Sends a GDB remote protocol 'I' packet that delivers stdin data to the remote process.
bool GetThreadExtendedInfoSupported()
lldb::DataBufferSP ReadAllRegisters(lldb::tid_t tid)
bool GetMemoryTaggingSupported()
void AutoCompleteDiskFileOrDirectory(CompletionRequest &request, bool only_dir)
lldb::pid_t m_curr_pid_run
Current gdb remote protocol process identifier for continue, step, etc.
LazyBool m_supports_multiprocess
void MaybeEnableCompression(llvm::ArrayRef< llvm::StringRef > supported_compressions)
bool GetDynamicLoaderProcessStateSupported()
const ArchSpec & GetProcessArchitecture()
bool DeallocateMemory(lldb::addr_t addr)
llvm::Expected< TraceSupportedResponse > SendTraceSupported(std::chrono::seconds interrupt_timeout)
bool GetQXferAuxvReadSupported()
xPacketState GetxPacketState()
llvm::ErrorOr< llvm::MD5::MD5Result > CalculateMD5(const FileSpec &file_spec)
uint32_t GetGDBServerProgramVersion()
LazyBool m_supports_reverse_continue
llvm::Error SendTraceStart(const llvm::json::Value &request, std::chrono::seconds interrupt_timeout)
bool GetStopReply(StringExtractorGDBRemote &response)
bool m_supports_qUserName
bool GetQXferMemoryMapReadSupported()
bool m_qXfer_memory_map_loaded
bool GetModuleInfo(const FileSpec &module_file_spec, const ArchSpec &arch_spec, ModuleSpec &module_spec)
LazyBool m_supports_vCont_all
std::optional< PidTid > SendSetCurrentThreadPacket(uint64_t tid, uint64_t pid, char op)
bool SendSpeedTestPacket(uint32_t send_size, uint32_t recv_size)
LazyBool m_supports_QPassSignals
bool GetFileExists(const FileSpec &file_spec)
Status GetFilePermissions(const FileSpec &file_spec, uint32_t &file_permissions)
uint32_t FindProcesses(const ProcessInstanceInfoMatch &process_match_info, ProcessInstanceInfoList &process_infos)
lldb::DataBufferSP ReadMemoryTags(lldb::addr_t addr, size_t len, int32_t type)
bool GetQXferSigInfoReadSupported()
uint32_t m_gdb_server_version
int SetWorkingDir(const FileSpec &working_dir)
Sets the working directory to path for a process that will be launched with the 'A' packet for non pl...
LazyBool m_avoid_g_packets
std::vector< std::pair< lldb::pid_t, lldb::tid_t > > GetCurrentProcessAndThreadIDs(bool &sequence_mutex_unavailable)
bool GetThreadStopInfo(lldb::tid_t tid, StringExtractorGDBRemote &response)
bool SaveRegisterState(lldb::tid_t tid, uint32_t &save_id)
bool GetProcessStandaloneBinary(UUID &uuid, lldb::addr_t &value, bool &value_is_offset)
LazyBool m_supports_QSaveRegisterState
WatchpointHardwareFeature m_watchpoint_types
void GetListThreadsInStopReplySupported()
StructuredData::ObjectSP GetThreadsInfo()
std::string m_qSupported_response
bool GetSharedCacheInfoSupported()
LazyBool m_supports_qXfer_auxv_read
bool m_supports_qModuleInfo
const char * GetGDBServerProgramName()
LazyBool m_supports_jGetDyldProcessState
int SendEnvironmentPacket(char const *name_equal_value)
Sends a "QEnvironment:NAME=VALUE" packet that will build up the environment that will get used when l...
std::chrono::seconds SetPacketTimeout(std::chrono::seconds packet_timeout)
LazyBool m_supports_qEcho
CompressionType m_compression_type
std::chrono::seconds GetPacketTimeout() const
#define LLDB_INVALID_THREAD_ID
#define LLDB_INVALID_CPUTYPE
#define UNUSED_IF_ASSERT_DISABLED(x)
#define LLDB_INVALID_ADDRESS
#define LLDB_INVALID_PROCESS_ID
lldb::ByteOrder InlHostByteOrder()
llvm::raw_ostream & operator<<(llvm::raw_ostream &os, const QOffsets &offsets)
A class that represents a running process on the host machine.
Log * GetLog(Cat mask)
Retrieve the Log object for the channel associated with the given log enum.
std::vector< ProcessInstanceInfo > ProcessInstanceInfoList
llvm::json::Value toJSON(const TraceSupportedResponse &packet)
@ eErrorTypeGeneric
Generic errors that can be any value.
@ eErrorTypePOSIX
POSIX error codes.
@ eSymbolTypeVariableType
@ eSymbolTypeObjCMetaClass
@ eSymbolTypeAdditional
When symbols take more than one entry, the extra entries get this type.
@ eSymbolTypeInstrumentation
ByteOrder
Byte ordering definitions.
std::shared_ptr< lldb_private::DataBuffer > DataBufferSP
std::shared_ptr< lldb_private::WritableDataBuffer > WritableDataBufferSP
bool Contains(BaseType r) const
BaseType GetRangeBase() const
void SetRangeEnd(BaseType end)
void SetRangeBase(BaseType b)
Set the start value for the range, and keep the same size.
BaseType GetRangeEnd() const
void SetByteSize(SizeType s)
jLLDBTraceGetBinaryData gdb-remote packet
jLLDBTraceStop gdb-remote packet
The offsets used by the target when relocating the executable.
bool segments
If true, the offsets field describes segments.
std::vector< uint64_t > offsets
The individual offsets.