uint32_t NativeRegisterContextLinux_s390x::SetHardwareWatchpoint(
    lldb::addr_t addr, size_t size, uint32_t watch_flags) {
  per_struct per_info;

  if (watch_flags != 0x1)
    return LLDB_INVALID_INDEX32;

  if (m_watchpoint_addr != LLDB_INVALID_ADDRESS)
    return LLDB_INVALID_INDEX32;

  Status error = PeekUserArea(offsetof(user_regs_struct, per_info), &per_info,
                              sizeof(per_info));
  if (error.Fail())
    return LLDB_INVALID_INDEX32;

  per_info.control_regs.bits.em_storage_alteration = 1;
  per_info.control_regs.bits.storage_alt_space_ctl = 1;
  per_info.starting_addr = addr;
  per_info.ending_addr = addr + size - 1;

  error = PokeUserArea(offsetof(user_regs_struct, per_info), &per_info,
                       sizeof(per_info));
  if (error.Fail())
    return LLDB_INVALID_INDEX32;

  m_watchpoint_addr = addr;
  return 0;
}
bool NativeRegisterContextLinux_s390x::ClearHardwareWatchpoint(
    uint32_t wp_index) {
  per_struct per_info;

  if (wp_index >= NumSupportedHardwareWatchpoints())
    return false;

  Status error = PeekUserArea(offsetof(user_regs_struct, per_info), &per_info,
                              sizeof(per_info));
  if (error.Fail())
    return false;

  per_info.control_regs.bits.em_storage_alteration = 0;
  per_info.control_regs.bits.storage_alt_space_ctl = 0;
  per_info.starting_addr = 0;
  per_info.ending_addr = 0;

  error = PokeUserArea(offsetof(user_regs_struct, per_info), &per_info,
                       sizeof(per_info));
  if (error.Fail())
    return false;

  m_watchpoint_addr = LLDB_INVALID_ADDRESS;
  return true;
}
Ejemplo n.º 3
0
static void ServerCallbackv4(const void *baton, in_port_t port) {
  auto child_pid = fork();
  if (child_pid == 0) {
    Socket *client_socket;
    char addr_buffer[256];
    sprintf(addr_buffer, "%s:%d", baton, port);
    Status err = Socket::TcpConnect(addr_buffer, false, client_socket);
    if (err.Fail())
      abort();
    char buffer[32];
    size_t read_size = 32;
    err = client_socket->Read((void *)&buffer[0], read_size);
    if (err.Fail())
      abort();
    std::string Recv(&buffer[0], read_size);
    if (Recv != hello)
      abort();
    size_t write_size = goodbye.length();
    err = client_socket->Write(goodbye.c_str(), write_size);
    if (err.Fail())
      abort();
    if (write_size != goodbye.length())
      abort();
    delete client_socket;
    exit(0);
  }
}
Ejemplo n.º 4
0
bool lldb_private::formatters::NSError_SummaryProvider(
    ValueObject &valobj, Stream &stream, const TypeSummaryOptions &options) {
  ProcessSP process_sp(valobj.GetProcessSP());
  if (!process_sp)
    return false;

  lldb::addr_t ptr_value = DerefToNSErrorPointer(valobj);
  if (ptr_value == LLDB_INVALID_ADDRESS)
    return false;

  size_t ptr_size = process_sp->GetAddressByteSize();
  lldb::addr_t code_location = ptr_value + 2 * ptr_size;
  lldb::addr_t domain_location = ptr_value + 3 * ptr_size;

  Status error;
  uint64_t code = process_sp->ReadUnsignedIntegerFromMemory(code_location,
                                                            ptr_size, 0, error);
  if (error.Fail())
    return false;

  lldb::addr_t domain_str_value =
      process_sp->ReadPointerFromMemory(domain_location, error);
  if (error.Fail() || domain_str_value == LLDB_INVALID_ADDRESS)
    return false;

  if (!domain_str_value) {
    stream.Printf("domain: nil - code: %" PRIu64, code);
    return true;
  }

  InferiorSizedWord isw(domain_str_value, *process_sp);

  ValueObjectSP domain_str_sp = ValueObject::CreateValueObjectFromData(
      "domain_str", isw.GetAsData(process_sp->GetByteOrder()),
      valobj.GetExecutionContextRef(), process_sp->GetTarget()
                                           .GetScratchClangASTContext()
                                           ->GetBasicType(lldb::eBasicTypeVoid)
                                           .GetPointerType());

  if (!domain_str_sp)
    return false;

  StreamString domain_str_summary;
  if (NSStringSummaryProvider(*domain_str_sp, domain_str_summary, options) &&
      !domain_str_summary.Empty()) {
    stream.Printf("domain: %s - code: %" PRIu64, domain_str_summary.GetData(),
                  code);
    return true;
  } else {
    stream.Printf("domain: nil - code: %" PRIu64, code);
    return true;
  }
}
Ejemplo n.º 5
0
Status Socket::UnixDomainAccept(llvm::StringRef name,
                                bool child_processes_inherit, Socket *&socket) {
  Status error;
  std::unique_ptr<Socket> listen_socket(
      Create(ProtocolUnixDomain, child_processes_inherit, error));
  if (error.Fail())
    return error;

  error = listen_socket->Listen(name, 5);
  if (error.Fail())
    return error;

  error = listen_socket->Accept(socket);
  return error;
}
Status NativeRegisterContextLinux_s390x::IsWatchpointHit(uint32_t wp_index,
                                                         bool &is_hit) {
  per_lowcore_bits per_lowcore;

  if (wp_index >= NumSupportedHardwareWatchpoints())
    return Status("Watchpoint index out of range");

  if (m_watchpoint_addr == LLDB_INVALID_ADDRESS) {
    is_hit = false;
    return Status();
  }

  Status error = PeekUserArea(offsetof(user_regs_struct, per_info.lowcore),
                              &per_lowcore, sizeof(per_lowcore));
  if (error.Fail()) {
    is_hit = false;
    return error;
  }

  is_hit = (per_lowcore.perc_storage_alteration == 1 &&
            per_lowcore.perc_store_real_address == 0);

  if (is_hit) {
    // Do not report this watchpoint again.
    memset(&per_lowcore, 0, sizeof(per_lowcore));
    PokeUserArea(offsetof(user_regs_struct, per_info.lowcore), &per_lowcore,
                 sizeof(per_lowcore));
  }

  return Status();
}
bool NativeRegisterContextLinux_mips64::ClearHardwareWatchpoint(
    uint32_t wp_index) {
  if (wp_index >= NumSupportedHardwareWatchpoints())
    return false;

  struct pt_watch_regs regs;
  // First reading the current state of watch regs
  DoReadWatchPointRegisterValue(m_thread.GetID(), static_cast<void *>(&regs));

  if (regs.style == pt_watch_style_mips32) {
    regs.mips32.watchlo[wp_index] = default_watch_regs.mips32.watchlo[wp_index];
    regs.mips32.watchhi[wp_index] = default_watch_regs.mips32.watchhi[wp_index];
    regs.mips32.watch_masks[wp_index] =
        default_watch_regs.mips32.watch_masks[wp_index];
  } else // pt_watch_style_mips64
  {
    regs.mips64.watchlo[wp_index] = default_watch_regs.mips64.watchlo[wp_index];
    regs.mips64.watchhi[wp_index] = default_watch_regs.mips64.watchhi[wp_index];
    regs.mips64.watch_masks[wp_index] =
        default_watch_regs.mips64.watch_masks[wp_index];
  }

  Status error = DoWriteWatchPointRegisterValue(m_thread.GetID(),
                                                static_cast<void *>(&regs));
  if (!error.Fail()) {
    hw_addr_map[wp_index] = LLDB_INVALID_ADDRESS;
    return true;
  }
  return false;
}
Status PlatformAndroidRemoteGDBServer::MakeConnectURL(
    const lldb::pid_t pid, const uint16_t remote_port,
    llvm::StringRef remote_socket_name, std::string &connect_url) {
  static const int kAttempsNum = 5;

  Status error;
  // There is a race possibility that somebody will occupy a port while we're
  // in between FindUnusedPort and ForwardPortWithAdb - adding the loop to
  // mitigate such problem.
  for (auto i = 0; i < kAttempsNum; ++i) {
    uint16_t local_port = 0;
    error = FindUnusedPort(local_port);
    if (error.Fail())
      return error;

    error = ForwardPortWithAdb(local_port, remote_port, remote_socket_name,
                               m_socket_namespace, m_device_id);
    if (error.Success()) {
      m_port_forwards[pid] = local_port;
      std::ostringstream url_str;
      url_str << "connect://localhost:" << local_port;
      connect_url = url_str.str();
      break;
    }
  }

  return error;
}
Ejemplo n.º 9
0
bool DYLDRendezvous::FindMetadata(const char *name, PThreadField field,
                                  uint32_t &value) {
  Target &target = m_process->GetTarget();

  SymbolContextList list;
  if (!target.GetImages().FindSymbolsWithNameAndType(ConstString(name),
                                                     eSymbolTypeAny, list))
    return false;

  Address address = list[0].symbol->GetAddress();
  addr_t addr = address.GetLoadAddress(&target);
  if (addr == LLDB_INVALID_ADDRESS)
    return false;

  Status error;
  value = (uint32_t)m_process->ReadUnsignedIntegerFromMemory(
      addr + field * sizeof(uint32_t), sizeof(uint32_t), 0, error);
  if (error.Fail())
    return false;

  if (field == eSize)
    value /= 8; // convert bits to bytes

  return true;
}
Ejemplo n.º 10
0
// Minidump string
llvm::Optional<std::string>
lldb_private::minidump::parseMinidumpString(llvm::ArrayRef<uint8_t> &data) {
  std::string result;

  const uint32_t *source_length;
  Status error = consumeObject(data, source_length);
  if (error.Fail() || *source_length > data.size() || *source_length % 2 != 0)
    return llvm::None;

  auto source_start = reinterpret_cast<const llvm::UTF16 *>(data.data());
  // source_length is the length of the string in bytes
  // we need the length of the string in UTF-16 characters/code points (16 bits
  // per char)
  // that's why it's divided by 2
  const auto source_end = source_start + (*source_length) / 2;
  // resize to worst case length
  result.resize(UNI_MAX_UTF8_BYTES_PER_CODE_POINT * (*source_length) / 2);
  auto result_start = reinterpret_cast<llvm::UTF8 *>(&result[0]);
  const auto result_end = result_start + result.size();
  llvm::ConvertUTF16toUTF8(&source_start, source_end, &result_start, result_end,
                           llvm::strictConversion);
  const auto result_size =
      std::distance(reinterpret_cast<llvm::UTF8 *>(&result[0]), result_start);
  result.resize(result_size); // shrink to actual length

  return result;
}
Ejemplo n.º 11
0
  bool Update() override {
    m_child_ptr = nullptr;
    m_child_sp.reset();

    ProcessSP process_sp(m_backend.GetProcessSP());
    if (!process_sp)
      return false;

    lldb::addr_t userinfo_location = DerefToNSErrorPointer(m_backend);
    if (userinfo_location == LLDB_INVALID_ADDRESS)
      return false;

    size_t ptr_size = process_sp->GetAddressByteSize();

    userinfo_location += 4 * ptr_size;
    Status error;
    lldb::addr_t userinfo =
        process_sp->ReadPointerFromMemory(userinfo_location, error);
    if (userinfo == LLDB_INVALID_ADDRESS || error.Fail())
      return false;
    InferiorSizedWord isw(userinfo, *process_sp);
    m_child_sp = CreateValueObjectFromData(
        "_userInfo", isw.GetAsData(process_sp->GetByteOrder()),
        m_backend.GetExecutionContextRef(),
        process_sp->GetTarget().GetScratchClangASTContext()->GetBasicType(
            lldb::eBasicTypeObjCID));
    return false;
  }
Ejemplo n.º 12
0
  bool DoExecute(Args &command, CommandReturnObject &result) override {
    StringList commands;
    commands.AppendString("thread backtrace");

    Thread *thread = m_exe_ctx.GetThreadPtr();
    if (thread) {
      char command_buffer[256];

      uint32_t frame_count = thread->GetStackFrameCount();
      for (uint32_t i = 0; i < frame_count; ++i) {
        StackFrameSP frame = thread->GetStackFrameAtIndex(i);
        lldb::addr_t pc = frame->GetStackID().GetPC();

        snprintf(command_buffer, sizeof(command_buffer),
                 "disassemble --bytes --address 0x%" PRIx64, pc);
        commands.AppendString(command_buffer);

        snprintf(command_buffer, sizeof(command_buffer),
                 "image show-unwind --address 0x%" PRIx64, pc);
        commands.AppendString(command_buffer);
      }
    }

    const FileSpec &outfile_spec =
        m_outfile_options.GetFile().GetCurrentValue();
    if (outfile_spec) {
      char path[PATH_MAX];
      outfile_spec.GetPath(path, sizeof(path));

      uint32_t open_options =
          File::eOpenOptionWrite | File::eOpenOptionCanCreate |
          File::eOpenOptionAppend | File::eOpenOptionCloseOnExec;

      const bool append = m_outfile_options.GetAppend().GetCurrentValue();
      if (!append)
        open_options |= File::eOpenOptionTruncate;

      StreamFileSP outfile_stream = std::make_shared<StreamFile>();
      Status error = outfile_stream->GetFile().Open(path, open_options);
      if (error.Fail()) {
        result.AppendErrorWithFormat("Failed to open file '%s' for %s: %s\n",
                                     path, append ? "append" : "write",
                                     error.AsCString());
        result.SetStatus(eReturnStatusFailed);
        return false;
      }

      result.SetImmediateOutputStream(outfile_stream);
    }

    CommandInterpreterRunOptions options;
    options.SetStopOnError(false);
    options.SetEchoCommands(true);
    options.SetPrintResults(true);
    options.SetAddToHistory(false);
    m_interpreter.HandleCommands(commands, &m_exe_ctx, options, result);

    return result.Succeeded();
  }
Ejemplo n.º 13
0
// Module stuff
const MinidumpModule *MinidumpModule::Parse(llvm::ArrayRef<uint8_t> &data) {
  const MinidumpModule *module = nullptr;
  Status error = consumeObject(data, module);
  if (error.Fail())
    return nullptr;

  return module;
}
Ejemplo n.º 14
0
// MinidumpThread
const MinidumpThread *MinidumpThread::Parse(llvm::ArrayRef<uint8_t> &data) {
  const MinidumpThread *thread = nullptr;
  Status error = consumeObject(data, thread);
  if (error.Fail())
    return nullptr;

  return thread;
}
Ejemplo n.º 15
0
lldb::OptionValueSP OptionValueUInt64::Create(llvm::StringRef value_str,
                                              Status &error) {
  lldb::OptionValueSP value_sp(new OptionValueUInt64());
  error = value_sp->SetValueFromString(value_str);
  if (error.Fail())
    value_sp.reset();
  return value_sp;
}
Ejemplo n.º 16
0
addr_t DynamicLoader::ReadPointer(addr_t addr) {
  Status error;
  addr_t value = m_process->ReadPointerFromMemory(addr, error);
  if (error.Fail())
    return LLDB_INVALID_ADDRESS;
  else
    return value;
}
Ejemplo n.º 17
0
// MinidumpMiscInfo
const MinidumpMiscInfo *MinidumpMiscInfo::Parse(llvm::ArrayRef<uint8_t> &data) {
  const MinidumpMiscInfo *misc_info;
  Status error = consumeObject(data, misc_info);
  if (error.Fail())
    return nullptr;

  return misc_info;
}
Ejemplo n.º 18
0
bool TestClient::StartDebugger() {
  const ArchSpec &arch_spec = HostInfo::GetArchitecture();
  Args args;
  args.AppendArgument(LLDB_SERVER);
  args.AppendArgument("gdbserver");
  args.AppendArgument("--log-channels=gdb-remote packets");
  args.AppendArgument("--reverse-connect");
  std::string log_file_name = GenerateLogFileName(arch_spec);
  if (log_file_name.size()) {
    args.AppendArgument("--log-file=" + log_file_name);
  }

  Status error;
  TCPSocket listen_socket(true, false);
  error = listen_socket.Listen("127.0.0.1:0", 5);
  if (error.Fail()) {
    GTEST_LOG_(ERROR) << "Unable to open listen socket.";
    return false;
  }

  char connect_remote_address[64];
  snprintf(connect_remote_address, sizeof(connect_remote_address),
           "localhost:%u", listen_socket.GetLocalPortNumber());

  args.AppendArgument(connect_remote_address);

  m_server_process_info.SetArchitecture(arch_spec);
  m_server_process_info.SetArguments(args, true);
  Status status = Host::LaunchProcess(m_server_process_info);
  if (status.Fail()) {
    GTEST_LOG_(ERROR)
        << formatv("Failure to launch lldb server: {0}.", status).str();
    return false;
  }

  char connect_remote_uri[64];
  snprintf(connect_remote_uri, sizeof(connect_remote_uri), "connect://%s",
           connect_remote_address);
  Socket *accept_socket;
  listen_socket.Accept(accept_socket);
  SetConnection(new ConnectionFileDescriptor(accept_socket));

  SendAck(); // Send this as a handshake.
  return true;
}
Ejemplo n.º 19
0
// Exception stuff
const MinidumpExceptionStream *
MinidumpExceptionStream::Parse(llvm::ArrayRef<uint8_t> &data) {
  const MinidumpExceptionStream *exception_stream = nullptr;
  Status error = consumeObject(data, exception_stream);
  if (error.Fail())
    return nullptr;

  return exception_stream;
}
Ejemplo n.º 20
0
addr_t DYLDRendezvous::ReadPointer(addr_t addr, addr_t *dst) {
  Status error;

  *dst = m_process->ReadPointerFromMemory(addr, error);
  if (error.Fail())
    return 0;

  return addr + m_process->GetAddressByteSize();
}
Ejemplo n.º 21
0
addr_t DYLDRendezvous::ReadWord(addr_t addr, uint64_t *dst, size_t size) {
  Status error;

  *dst = m_process->ReadUnsignedIntegerFromMemory(addr, size, 0, error);
  if (error.Fail())
    return 0;

  return addr + size;
}
Ejemplo n.º 22
0
// MinidumpSystemInfo
const MinidumpSystemInfo *
MinidumpSystemInfo::Parse(llvm::ArrayRef<uint8_t> &data) {
  const MinidumpSystemInfo *system_info;
  Status error = consumeObject(data, system_info);
  if (error.Fail())
    return nullptr;

  return system_info;
}
Status NativeRegisterContextLinux_s390x::WriteAllRegisterValues(
    const lldb::DataBufferSP &data_sp) {
  Status error;

  if (!data_sp) {
    error.SetErrorStringWithFormat(
        "NativeRegisterContextLinux_s390x::%s invalid data_sp provided",
        __FUNCTION__);
    return error;
  }

  if (data_sp->GetByteSize() != REG_CONTEXT_SIZE) {
    error.SetErrorStringWithFormat(
        "NativeRegisterContextLinux_s390x::%s data_sp contained mismatched "
        "data size, expected %" PRIu64 ", actual %" PRIu64,
        __FUNCTION__, REG_CONTEXT_SIZE, data_sp->GetByteSize());
    return error;
  }

  uint8_t *src = data_sp->GetBytes();
  if (src == nullptr) {
    error.SetErrorStringWithFormat("NativeRegisterContextLinux_s390x::%s "
                                   "DataBuffer::GetBytes() returned a null "
                                   "pointer",
                                   __FUNCTION__);
    return error;
  }

  error = DoWriteGPR(src, sizeof(s390_regs));
  src += sizeof(s390_regs);
  if (error.Fail())
    return error;

  error = DoWriteFPR(src, sizeof(s390_fp_regs));
  src += sizeof(s390_fp_regs);
  if (error.Fail())
    return error;

  // Ignore errors if the regset is unsupported (happens on older kernels).
  DoWriteRegisterSet(NT_S390_SYSTEM_CALL, src, 4);
  src += 4;

  return error;
}
Ejemplo n.º 24
0
int64_t DynamicLoader::ReadUnsignedIntWithSizeInBytes(addr_t addr,
                                                      int size_in_bytes) {
  Status error;
  uint64_t value =
      m_process->ReadUnsignedIntegerFromMemory(addr, size_in_bytes, 0, error);
  if (error.Fail())
    return -1;
  else
    return (int64_t)value;
}
Status NativeRegisterContextLinux_s390x::ReadAllRegisterValues(
    lldb::DataBufferSP &data_sp) {
  Status error;

  data_sp.reset(new DataBufferHeap(REG_CONTEXT_SIZE, 0));
  if (!data_sp) {
    error.SetErrorStringWithFormat(
        "failed to allocate DataBufferHeap instance of size %" PRIu64,
        REG_CONTEXT_SIZE);
    return error;
  }

  uint8_t *dst = data_sp->GetBytes();
  if (dst == nullptr) {
    error.SetErrorStringWithFormat("DataBufferHeap instance of size %" PRIu64
                                   " returned a null pointer",
                                   REG_CONTEXT_SIZE);
    return error;
  }

  error = DoReadGPR(dst, sizeof(s390_regs));
  dst += sizeof(s390_regs);
  if (error.Fail())
    return error;

  error = DoReadFPR(dst, sizeof(s390_fp_regs));
  dst += sizeof(s390_fp_regs);
  if (error.Fail())
    return error;

  // Ignore errors if the regset is unsupported (happens on older kernels).
  DoReadRegisterSet(NT_S390_SYSTEM_CALL, dst, 4);
  dst += 4;

  // To enable inferior function calls while the process is stopped in
  // an interrupted system call, we need to clear the system call flag.
  // It will be restored to its original value by WriteAllRegisterValues.
  // Again we ignore error if the regset is unsupported.
  uint32_t system_call = 0;
  DoWriteRegisterSet(NT_S390_SYSTEM_CALL, &system_call, 4);

  return error;
}
Ejemplo n.º 26
0
llvm::ArrayRef<MinidumpThread>
MinidumpThread::ParseThreadList(llvm::ArrayRef<uint8_t> &data) {
  const llvm::support::ulittle32_t *thread_count;
  Status error = consumeObject(data, thread_count);
  if (error.Fail() || *thread_count * sizeof(MinidumpThread) > data.size())
    return {};

  return llvm::ArrayRef<MinidumpThread>(
      reinterpret_cast<const MinidumpThread *>(data.data()), *thread_count);
}
Ejemplo n.º 27
0
std::pair<llvm::ArrayRef<MinidumpMemoryDescriptor64>, uint64_t>
MinidumpMemoryDescriptor64::ParseMemory64List(llvm::ArrayRef<uint8_t> &data) {
  const llvm::support::ulittle64_t *mem_ranges_count;
  Status error = consumeObject(data, mem_ranges_count);
  if (error.Fail() ||
      *mem_ranges_count * sizeof(MinidumpMemoryDescriptor64) > data.size())
    return {};

  const llvm::support::ulittle64_t *base_rva;
  error = consumeObject(data, base_rva);
  if (error.Fail())
    return {};

  return std::make_pair(
      llvm::makeArrayRef(
          reinterpret_cast<const MinidumpMemoryDescriptor64 *>(data.data()),
          *mem_ranges_count),
      *base_rva);
}
Ejemplo n.º 28
0
llvm::ArrayRef<MinidumpModule>
MinidumpModule::ParseModuleList(llvm::ArrayRef<uint8_t> &data) {

  const llvm::support::ulittle32_t *modules_count;
  Status error = consumeObject(data, modules_count);
  if (error.Fail() || *modules_count * sizeof(MinidumpModule) > data.size())
    return {};

  return llvm::ArrayRef<MinidumpModule>(
      reinterpret_cast<const MinidumpModule *>(data.data()), *modules_count);
}
static Status FindUnusedPort(uint16_t &port) {
  Status error;
  std::unique_ptr<TCPSocket> tcp_socket(new TCPSocket(true, false));
  if (error.Fail())
    return error;

  error = tcp_socket->Listen("127.0.0.1:0", 1);
  if (error.Success())
    port = tcp_socket->GetLocalPortNumber();

  return error;
}
Ejemplo n.º 30
0
llvm::ArrayRef<MinidumpMemoryDescriptor>
MinidumpMemoryDescriptor::ParseMemoryList(llvm::ArrayRef<uint8_t> &data) {
  const llvm::support::ulittle32_t *mem_ranges_count;
  Status error = consumeObject(data, mem_ranges_count);
  if (error.Fail() ||
      *mem_ranges_count * sizeof(MinidumpMemoryDescriptor) > data.size())
    return {};

  return llvm::makeArrayRef(
      reinterpret_cast<const MinidumpMemoryDescriptor *>(data.data()),
      *mem_ranges_count);
}