1 /*
2     SPDX-FileCopyrightText: 2009 Niko Sams <niko.sams@gmail.com>
3 
4     SPDX-License-Identifier: LGPL-2.0-or-later
5 */
6 
7 #ifndef KDEVPLATFORM_IDEBUGSESSION_H
8 #define KDEVPLATFORM_IDEBUGSESSION_H
9 
10 #include <debugger/debuggerexport.h>
11 
12 #include <QObject>
13 #include <QUrl>
14 
15 namespace KDevelop {
16 
17 class IVariableController;
18 class IBreakpointController;
19 class IFrameStackModel;
20 class Breakpoint;
21 class StackModel;
22 class IDebugSessionPrivate;
23 
24 class KDEVPLATFORMDEBUGGER_EXPORT IDebugSession : public QObject
25 {
26     Q_OBJECT
27 public:
28     IDebugSession();
29     ~IDebugSession() override;
30 
31     enum DebuggerState {
32         NotStartedState,
33         StartingState,
34         ActiveState,
35         PausedState,
36         StoppingState,
37         StoppedState,
38         EndedState
39     };
40     Q_ENUM(DebuggerState)
41 
42     enum event_t {
43         program_state_changed = 1,
44         program_exited,
45         debugger_exited,
46         // Emitted when the thread or frame that is selected in UI
47         // changes.
48         thread_or_frame_changed,
49         debugger_busy,
50         debugger_ready,
51         // Raised when debugger believe that program start running.
52         // Can be used to hide current line indicator.
53         // Don't count on this being raise in all cases where
54         // program is running.
55         program_running,
56         // Raise when the debugger is in touch with the program,
57         // and should have access to its debug symbols. The program
58         // is not necessary running yet, or might already exited,
59         // or be otherwise dead.
60         connected_to_program
61     };
62 
63 public:
64     /**
65      * Current state of the debug session
66      */
67     virtual DebuggerState state() const = 0;
68 
69     /**
70      * Should return if restart is currently available
71      */
72     virtual bool restartAvaliable() const = 0;
73 
74     /**
75      * Returns if the debugee is currently running. This includes paused.
76      */
77     bool isRunning() const;
78 
79     /**
80      * Returns the local Url for a source file used in the current debug session.
81      *
82      * The default implementation just returns the url and is sufficient for
83      * local debuggers. Remote debuggers can implement a path mapping mechanism.
84      */
85     virtual QPair<QUrl, int> convertToLocalUrl(const QPair<QUrl, int> &remoteUrl) const;
86 
87     /**
88      * Returns the remote Url for a source file used in the current debug session.
89      *
90      * The default implementation just returns the url and is sufficient for
91      * local debuggers. Remote debuggers can implement a path mapping mechanism.
92      */
93     virtual QPair<QUrl, int> convertToRemoteUrl(const QPair<QUrl, int> &localUrl) const;
94 
95     /**
96      * @return the breakpoint controller of this session
97      *
98      * @note Implementations must ensure that a breakpoint controller always exists (even if it
99      * is a dummy stub implementation that does nothing), and that it does not change during
100      * the lifetime of a session.
101      */
102     virtual IBreakpointController* breakpointController() const = 0;
103 
104     /**
105      * @return the variable controller of this session
106      *
107      * @note Implementations must ensure that a variable controller always exists (even if it
108      * is a dummy stub implementation that does nothing), and that it does not change during
109      * the lifetime of a session.
110      */
111     virtual IVariableController* variableController() const = 0;
112 
113     /**
114      * @return the frame stack model of this session
115      *
116      * @note Implementations must ensure that a frame stack model always exists (even if it
117      * is a dummy stub implementation that does nothing), and that it does not change during
118      * the lifetime of a session.
119      */
120     virtual IFrameStackModel* frameStackModel() const = 0;
121 
122 public Q_SLOTS:
123     virtual void restartDebugger() = 0;
124     virtual void stopDebugger() = 0;
125     /// @brief Kills the debugger process synchronously if it is still running.
126     virtual void killDebuggerNow() = 0;
127     virtual void interruptDebugger() = 0;
128     virtual void run() = 0;
129     virtual void runToCursor() = 0;
130     virtual void jumpToCursor() = 0;
131     virtual void stepOver() = 0;
132     virtual void stepIntoInstruction() = 0;
133     virtual void stepInto() = 0;
134     virtual void stepOverInstruction() = 0;
135     virtual void stepOut() = 0;
136 
137 Q_SIGNALS:
138     void stateChanged(KDevelop::IDebugSession::DebuggerState state);
139     void showStepInSource(const QUrl& file, int line, const QString &addr);
140     void showStepInDisassemble(const QString &addr);
141     void clearExecutionPoint();
142     void finished();
143 
144     void raiseFramestackViews();
145 
146     /** This signal is emitted whenever the given event in a program
147         happens. See DESIGN.txt for expected handled of each event.
148 
149         NOTE: this signal should never be emitted directly. Instead,
150         use raiseEvent.
151     */
152     void event(IDebugSession::event_t e);
153 
154 public:
155     using QObject::event; // prevent hiding of base method.
156 
157     QUrl currentUrl() const;
158     int currentLine() const;
159     QString currentAddr() const;
160 
161 protected:
162 
163     // Clear the position before running code
164     void clearCurrentPosition();
165     /// Sets new position and emits showStepInSource or showStepInDisassemble (if source file is unavailable) signal
166     void setCurrentPosition(const QUrl& url, int line, const QString& addr);
167 
168     /** Raises the specified event. Should be used instead of
169         emitting 'event' directly, since this method can perform
170         additional book-keeping for events.
171         FIXME: it might make sense to automatically route
172         events to all debugger components, as opposed to requiring
173         that they connect to any signal.
174     */
175     virtual void raiseEvent(event_t e);
176     friend class FrameStackModel;
177 
178 private:
179     friend class IDebugSessionPrivate;
180     const QScopedPointer<class IDebugSessionPrivate> d_ptr;
181     Q_DECLARE_PRIVATE(IDebugSession)
182 };
183 
184 }
185 
186 #endif
187