1//===-- DNBThreadResumeActions.cpp ------------------------------*- C++ -*-===//
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//  Created by Greg Clayton on 03/13/2010
10//
11//===----------------------------------------------------------------------===//
12
13#include "DNBThreadResumeActions.h"
14
15DNBThreadResumeActions::DNBThreadResumeActions()
16    : m_actions(), m_signal_handled() {}
17
18DNBThreadResumeActions::DNBThreadResumeActions(
19    const DNBThreadResumeAction *actions, size_t num_actions)
20    : m_actions(), m_signal_handled() {
21  if (actions && num_actions) {
22    m_actions.assign(actions, actions + num_actions);
23    m_signal_handled.assign(num_actions, false);
24  }
25}
26
27DNBThreadResumeActions::DNBThreadResumeActions(nub_state_t default_action,
28                                               int signal)
29    : m_actions(), m_signal_handled() {
30  SetDefaultThreadActionIfNeeded(default_action, signal);
31}
32
33void DNBThreadResumeActions::Append(const DNBThreadResumeAction &action) {
34  m_actions.push_back(action);
35  m_signal_handled.push_back(false);
36}
37
38void DNBThreadResumeActions::AppendAction(nub_thread_t tid, nub_state_t state,
39                                          int signal, nub_addr_t addr) {
40  DNBThreadResumeAction action = {tid, state, signal, addr};
41  Append(action);
42}
43
44const DNBThreadResumeAction *
45DNBThreadResumeActions::GetActionForThread(nub_thread_t tid,
46                                           bool default_ok) const {
47  const size_t num_actions = m_actions.size();
48  for (size_t i = 0; i < num_actions; ++i) {
49    if (m_actions[i].tid == tid)
50      return &m_actions[i];
51  }
52  if (default_ok && tid != INVALID_NUB_THREAD)
53    return GetActionForThread(INVALID_NUB_THREAD, false);
54  return NULL;
55}
56
57size_t DNBThreadResumeActions::NumActionsWithState(nub_state_t state) const {
58  size_t count = 0;
59  const size_t num_actions = m_actions.size();
60  for (size_t i = 0; i < num_actions; ++i) {
61    if (m_actions[i].state == state)
62      ++count;
63  }
64  return count;
65}
66
67bool DNBThreadResumeActions::SetDefaultThreadActionIfNeeded(nub_state_t action,
68                                                            int signal) {
69  if (GetActionForThread(INVALID_NUB_THREAD, true) == NULL) {
70    // There isn't a default action so we do need to set it.
71    DNBThreadResumeAction default_action = {INVALID_NUB_THREAD, action, signal,
72                                            INVALID_NUB_ADDRESS};
73    m_actions.push_back(default_action);
74    m_signal_handled.push_back(false);
75    return true; // Return true as we did add the default action
76  }
77  return false;
78}
79
80void DNBThreadResumeActions::SetSignalHandledForThread(nub_thread_t tid) const {
81  if (tid != INVALID_NUB_THREAD) {
82    const size_t num_actions = m_actions.size();
83    for (size_t i = 0; i < num_actions; ++i) {
84      if (m_actions[i].tid == tid)
85        m_signal_handled[i] = true;
86    }
87  }
88}
89