UnixSignals.cpp revision 254721
1254721Semaste//===-- UnixSignals.cpp -----------------------------------------*- C++ -*-===//
2254721Semaste//
3254721Semaste//                     The LLVM Compiler Infrastructure
4254721Semaste//
5254721Semaste// This file is distributed under the University of Illinois Open Source
6254721Semaste// License. See LICENSE.TXT for details.
7254721Semaste//
8254721Semaste//===----------------------------------------------------------------------===//
9254721Semaste
10254721Semaste#include "lldb/Target/UnixSignals.h"
11254721Semaste
12254721Semaste// C Includes
13254721Semaste// C++ Includes
14254721Semaste// Other libraries and framework includes
15254721Semaste// Project includes
16254721Semaste#include "lldb/Interpreter/Args.h"
17254721Semaste
18254721Semasteusing namespace lldb_private;
19254721Semaste
20254721SemasteUnixSignals::Signal::Signal
21254721Semaste(
22254721Semaste    const char *name,
23254721Semaste    const char *short_name,
24254721Semaste    bool default_suppress,
25254721Semaste    bool default_stop,
26254721Semaste    bool default_notify,
27254721Semaste    const char *description
28254721Semaste) :
29254721Semaste    m_name (name),
30254721Semaste    m_short_name (short_name),
31254721Semaste    m_description (),
32254721Semaste    m_suppress (default_suppress),
33254721Semaste    m_stop (default_stop),
34254721Semaste    m_notify (default_notify)
35254721Semaste{
36254721Semaste    if (description)
37254721Semaste        m_description.assign (description);
38254721Semaste}
39254721Semaste
40254721Semaste//----------------------------------------------------------------------
41254721Semaste// UnixSignals constructor
42254721Semaste//----------------------------------------------------------------------
43254721SemasteUnixSignals::UnixSignals ()
44254721Semaste{
45254721Semaste    Reset ();
46254721Semaste}
47254721Semaste
48254721Semaste//----------------------------------------------------------------------
49254721Semaste// Destructor
50254721Semaste//----------------------------------------------------------------------
51254721SemasteUnixSignals::~UnixSignals ()
52254721Semaste{
53254721Semaste}
54254721Semaste
55254721Semastevoid
56254721SemasteUnixSignals::Reset ()
57254721Semaste{
58254721Semaste    // This builds one standard set of Unix Signals.  If yours aren't quite in this
59254721Semaste    // order, you can either subclass this class, and use Add & Remove to change them
60254721Semaste    // or you can subclass and build them afresh in your constructor;
61254721Semaste    m_signals.clear();
62254721Semaste    //        SIGNO  NAME         SHORT NAME SUPPRESS STOP   NOTIFY DESCRIPTION
63254721Semaste    //        ====== ============ ========== ======== ====== ====== ===================================================
64254721Semaste    AddSignal (1,    "SIGHUP",    "HUP",     false,   true , true , "hangup");
65254721Semaste    AddSignal (2,    "SIGINT",    "INT",     true ,   true , true , "interrupt");
66254721Semaste    AddSignal (3,    "SIGQUIT",   "QUIT",    false,   true , true , "quit");
67254721Semaste    AddSignal (4,    "SIGILL",    "ILL",     false,   true , true , "illegal instruction");
68254721Semaste    AddSignal (5,    "SIGTRAP",   "TRAP",    true ,   true , true , "trace trap (not reset when caught)");
69254721Semaste    AddSignal (6,    "SIGABRT",   "ABRT",    false,   true , true , "abort()");
70254721Semaste    AddSignal (7,    "SIGEMT",    "EMT",     false,   true , true , "pollable event");
71254721Semaste    AddSignal (8,    "SIGFPE",    "FPE",     false,   true , true , "floating point exception");
72254721Semaste    AddSignal (9,    "SIGKILL",   "KILL",    false,   true , true , "kill");
73254721Semaste    AddSignal (10,   "SIGBUS",    "BUS",     false,   true , true , "bus error");
74254721Semaste    AddSignal (11,   "SIGSEGV",   "SEGV",    false,   true , true , "segmentation violation");
75254721Semaste    AddSignal (12,   "SIGSYS",    "SYS",     false,   true , true , "bad argument to system call");
76254721Semaste    AddSignal (13,   "SIGPIPE",   "PIPE",    false,   true , true , "write on a pipe with no one to read it");
77254721Semaste    AddSignal (14,   "SIGALRM",   "ALRM",    false,   false, true , "alarm clock");
78254721Semaste    AddSignal (15,   "SIGTERM",   "TERM",    false,   true , true , "software termination signal from kill");
79254721Semaste    AddSignal (16,   "SIGURG",    "URG",     false,   false, false, "urgent condition on IO channel");
80254721Semaste    AddSignal (17,   "SIGSTOP",   "STOP",    true ,   true , true , "sendable stop signal not from tty");
81254721Semaste    AddSignal (18,   "SIGTSTP",   "TSTP",    false,   true , true , "stop signal from tty");
82254721Semaste    AddSignal (19,   "SIGCONT",   "CONT",    false,   true , true , "continue a stopped process");
83254721Semaste    AddSignal (20,   "SIGCHLD",   "CHLD",    false,   false, true , "to parent on child stop or exit");
84254721Semaste    AddSignal (21,   "SIGTTIN",   "TTIN",    false,   true , true , "to readers process group upon background tty read");
85254721Semaste    AddSignal (22,   "SIGTTOU",   "TTOU",    false,   true , true , "to readers process group upon background tty write");
86254721Semaste    AddSignal (23,   "SIGIO",     "IO",      false,   false, false, "input/output possible signal");
87254721Semaste    AddSignal (24,   "SIGXCPU",   "XCPU",    false,   true , true , "exceeded CPU time limit");
88254721Semaste    AddSignal (25,   "SIGXFSZ",   "XFSZ",    false,   true , true , "exceeded file size limit");
89254721Semaste    AddSignal (26,   "SIGVTALRM", "VTALRM",  false,   false, false, "virtual time alarm");
90254721Semaste    AddSignal (27,   "SIGPROF",   "PROF",    false,   false, false, "profiling time alarm");
91254721Semaste    AddSignal (28,   "SIGWINCH",  "WINCH",   false,   false, false, "window size changes");
92254721Semaste    AddSignal (29,   "SIGINFO",   "INFO",    false,   true , true , "information request");
93254721Semaste    AddSignal (30,   "SIGUSR1",   "USR1",    false,   true , true , "user defined signal 1");
94254721Semaste    AddSignal (31,   "SIGUSR2",   "USR2",    false,   true , true , "user defined signal 2");
95254721Semaste}
96254721Semaste
97254721Semastevoid
98254721SemasteUnixSignals::AddSignal
99254721Semaste(
100254721Semaste    int signo,
101254721Semaste    const char *name,
102254721Semaste    const char *short_name,
103254721Semaste    bool default_suppress,
104254721Semaste    bool default_stop,
105254721Semaste    bool default_notify,
106254721Semaste    const char *description
107254721Semaste)
108254721Semaste{
109254721Semaste    Signal new_signal (name, short_name, default_suppress, default_stop, default_notify, description);
110254721Semaste    m_signals.insert (std::make_pair(signo, new_signal));
111254721Semaste}
112254721Semaste
113254721Semastevoid
114254721SemasteUnixSignals::RemoveSignal (int signo)
115254721Semaste{
116254721Semaste    collection::iterator pos = m_signals.find (signo);
117254721Semaste    if (pos != m_signals.end())
118254721Semaste        m_signals.erase (pos);
119254721Semaste}
120254721Semaste
121254721Semasteconst char *
122254721SemasteUnixSignals::GetSignalAsCString (int signo) const
123254721Semaste{
124254721Semaste    collection::const_iterator pos = m_signals.find (signo);
125254721Semaste    if (pos == m_signals.end())
126254721Semaste        return NULL;
127254721Semaste    else
128254721Semaste        return pos->second.m_name.GetCString ();
129254721Semaste}
130254721Semaste
131254721Semaste
132254721Semastebool
133254721SemasteUnixSignals::SignalIsValid (int32_t signo) const
134254721Semaste{
135254721Semaste    return m_signals.find (signo) != m_signals.end();
136254721Semaste}
137254721Semaste
138254721Semaste
139254721Semasteint32_t
140254721SemasteUnixSignals::GetSignalNumberFromName (const char *name) const
141254721Semaste{
142254721Semaste    ConstString const_name (name);
143254721Semaste
144254721Semaste    collection::const_iterator pos, end = m_signals.end ();
145254721Semaste    for (pos = m_signals.begin (); pos != end; pos++)
146254721Semaste    {
147254721Semaste        if ((const_name == pos->second.m_name) || (const_name == pos->second.m_short_name))
148254721Semaste            return pos->first;
149254721Semaste    }
150254721Semaste
151254721Semaste    const int32_t signo = Args::StringToSInt32(name, LLDB_INVALID_SIGNAL_NUMBER, 0);
152254721Semaste    if (signo != LLDB_INVALID_SIGNAL_NUMBER)
153254721Semaste        return signo;
154254721Semaste    return LLDB_INVALID_SIGNAL_NUMBER;
155254721Semaste}
156254721Semaste
157254721Semasteint32_t
158254721SemasteUnixSignals::GetFirstSignalNumber () const
159254721Semaste{
160254721Semaste    if (m_signals.empty())
161254721Semaste        return LLDB_INVALID_SIGNAL_NUMBER;
162254721Semaste
163254721Semaste    return (*m_signals.begin ()).first;
164254721Semaste}
165254721Semaste
166254721Semasteint32_t
167254721SemasteUnixSignals::GetNextSignalNumber (int32_t current_signal) const
168254721Semaste{
169254721Semaste    collection::const_iterator pos = m_signals.find (current_signal);
170254721Semaste    collection::const_iterator end = m_signals.end();
171254721Semaste    if (pos == end)
172254721Semaste        return LLDB_INVALID_SIGNAL_NUMBER;
173254721Semaste    else
174254721Semaste    {
175254721Semaste        pos++;
176254721Semaste        if (pos == end)
177254721Semaste            return LLDB_INVALID_SIGNAL_NUMBER;
178254721Semaste        else
179254721Semaste            return pos->first;
180254721Semaste    }
181254721Semaste}
182254721Semaste
183254721Semasteconst char *
184254721SemasteUnixSignals::GetSignalInfo
185254721Semaste(
186254721Semaste    int32_t signo,
187254721Semaste    bool &should_suppress,
188254721Semaste    bool &should_stop,
189254721Semaste    bool &should_notify
190254721Semaste) const
191254721Semaste{
192254721Semaste    collection::const_iterator pos = m_signals.find (signo);
193254721Semaste    if (pos == m_signals.end())
194254721Semaste        return NULL;
195254721Semaste    else
196254721Semaste    {
197254721Semaste        const Signal &signal = pos->second;
198254721Semaste        should_suppress = signal.m_suppress;
199254721Semaste        should_stop     = signal.m_stop;
200254721Semaste        should_notify   = signal.m_notify;
201254721Semaste        return signal.m_name.AsCString("");
202254721Semaste    }
203254721Semaste}
204254721Semaste
205254721Semastebool
206254721SemasteUnixSignals::GetShouldSuppress (int signo) const
207254721Semaste{
208254721Semaste    collection::const_iterator pos = m_signals.find (signo);
209254721Semaste    if (pos != m_signals.end())
210254721Semaste        return pos->second.m_suppress;
211254721Semaste    return false;
212254721Semaste}
213254721Semaste
214254721Semastebool
215254721SemasteUnixSignals::SetShouldSuppress (int signo, bool value)
216254721Semaste{
217254721Semaste    collection::iterator pos = m_signals.find (signo);
218254721Semaste    if (pos != m_signals.end())
219254721Semaste    {
220254721Semaste        pos->second.m_suppress = value;
221254721Semaste        return true;
222254721Semaste    }
223254721Semaste    return false;
224254721Semaste}
225254721Semaste
226254721Semastebool
227254721SemasteUnixSignals::SetShouldSuppress (const char *signal_name, bool value)
228254721Semaste{
229254721Semaste    const int32_t signo = GetSignalNumberFromName (signal_name);
230254721Semaste    if (signo != LLDB_INVALID_SIGNAL_NUMBER)
231254721Semaste        return SetShouldSuppress (signo, value);
232254721Semaste    return false;
233254721Semaste}
234254721Semaste
235254721Semastebool
236254721SemasteUnixSignals::GetShouldStop (int signo) const
237254721Semaste{
238254721Semaste    collection::const_iterator pos = m_signals.find (signo);
239254721Semaste    if (pos != m_signals.end())
240254721Semaste        return pos->second.m_stop;
241254721Semaste    return false;
242254721Semaste}
243254721Semaste
244254721Semastebool
245254721SemasteUnixSignals::SetShouldStop (int signo, bool value)
246254721Semaste{
247254721Semaste    collection::iterator pos = m_signals.find (signo);
248254721Semaste    if (pos != m_signals.end())
249254721Semaste    {
250254721Semaste        pos->second.m_stop = value;
251254721Semaste        return true;
252254721Semaste    }
253254721Semaste    return false;
254254721Semaste}
255254721Semaste
256254721Semastebool
257254721SemasteUnixSignals::SetShouldStop (const char *signal_name, bool value)
258254721Semaste{
259254721Semaste    const int32_t signo = GetSignalNumberFromName (signal_name);
260254721Semaste    if (signo != LLDB_INVALID_SIGNAL_NUMBER)
261254721Semaste        return SetShouldStop (signo, value);
262254721Semaste    return false;
263254721Semaste}
264254721Semaste
265254721Semastebool
266254721SemasteUnixSignals::GetShouldNotify (int signo) const
267254721Semaste{
268254721Semaste    collection::const_iterator pos = m_signals.find (signo);
269254721Semaste    if (pos != m_signals.end())
270254721Semaste        return pos->second.m_notify;
271254721Semaste    return false;
272254721Semaste}
273254721Semaste
274254721Semastebool
275254721SemasteUnixSignals::SetShouldNotify (int signo, bool value)
276254721Semaste{
277254721Semaste    collection::iterator pos = m_signals.find (signo);
278254721Semaste    if (pos != m_signals.end())
279254721Semaste    {
280254721Semaste        pos->second.m_notify = value;
281254721Semaste        return true;
282254721Semaste    }
283254721Semaste    return false;
284254721Semaste}
285254721Semaste
286254721Semastebool
287254721SemasteUnixSignals::SetShouldNotify (const char *signal_name, bool value)
288254721Semaste{
289254721Semaste    const int32_t signo = GetSignalNumberFromName (signal_name);
290254721Semaste    if (signo != LLDB_INVALID_SIGNAL_NUMBER)
291254721Semaste        return SetShouldNotify (signo, value);
292254721Semaste    return false;
293254721Semaste}
294