1 |
1026 |
ivang |
@c
|
2 |
|
|
@c RTEMS Remote Debugger Server Specifications
|
3 |
|
|
@c
|
4 |
|
|
@c Written by: Eric Valette
|
5 |
|
|
@c Emmanuel Raguet
|
6 |
|
|
@c
|
7 |
|
|
@c
|
8 |
|
|
@c daemon.t,v 1.4 2002/01/17 21:47:46 joel Exp
|
9 |
|
|
@c
|
10 |
|
|
|
11 |
|
|
@chapter RTEMS Debugger Server Daemon
|
12 |
|
|
|
13 |
|
|
We will describe in this section how this debugger server will be
|
14 |
|
|
implemented on RTEMS environment. Our initial target is based on Intel Pentium
|
15 |
|
|
and we will use an Ethernet link to communicate between the host and the target.
|
16 |
|
|
|
17 |
|
|
The RTEMS remote debugger will be composed by several tasks and exception
|
18 |
|
|
handlers :
|
19 |
|
|
|
20 |
|
|
@itemize @bullet
|
21 |
|
|
@item an initialization task which opens the sockets and runs the SUN RPC
|
22 |
|
|
server. This task will also connect the interrupt handlers and launch the communication
|
23 |
|
|
task
|
24 |
|
|
@item a communication task which receives the SUN RPC commands, executes
|
25 |
|
|
them and sends the result to the GDB client,
|
26 |
|
|
@item A debuggee event management task which waits for events. We need a different
|
27 |
|
|
task than the command management task in order to be able to still accept commands
|
28 |
|
|
while no event has yet occurred for the debuggee. An example could be a continue
|
29 |
|
|
command from GDB and then hitting to DEL key to see what is currently going
|
30 |
|
|
on on the target side because an expected breakpoint is not caught...
|
31 |
|
|
@item a debug exception handler which manages the hardware breakpoint and
|
32 |
|
|
single step exceptions (INT 1 on Intel x86),
|
33 |
|
|
@item a breakpoint exception handler which manages the software breakpoints
|
34 |
|
|
exceptions (INT 3 on Intel x86),
|
35 |
|
|
@item a default exception handler used to catch every possible errors make on the
|
36 |
|
|
target system,
|
37 |
|
|
@end itemize
|
38 |
|
|
|
39 |
|
|
@c XXX figure reference
|
40 |
|
|
@c XXX references to other sections
|
41 |
|
|
Figure @b{remote debugger tasks and handlers} represents these
|
42 |
|
|
different tasks and handlers. The synchronization between the different task
|
43 |
|
|
and exception handlers will be described below in the section
|
44 |
|
|
@b{Synchronization Among Tasks and Exception Handlers}.
|
45 |
|
|
Some open issues we have faced for a prototype implementation are described
|
46 |
|
|
in the section @b{Open Issues}. The temporary workaround we chose are described
|
47 |
|
|
in chapter @b{Workarounds for Open Issues in Prototype}.
|
48 |
|
|
|
49 |
|
|
|
50 |
|
|
@section The INITIALIZATION task
|
51 |
|
|
|
52 |
|
|
This is the task that must be executed at the boot phase of RTEMS.
|
53 |
|
|
It initializes the debug context. It must :
|
54 |
|
|
|
55 |
|
|
@itemize @bullet
|
56 |
|
|
@item open the UDP sockets,
|
57 |
|
|
@item run the SUN RPC server main loop,
|
58 |
|
|
@item create the COMMAND MANAGEMENT task,
|
59 |
|
|
@item connect the DEBUG EXCEPTION handler,
|
60 |
|
|
@item connect the SOFTWARE BREAKPOINT handler,
|
61 |
|
|
@item delete itself.
|
62 |
|
|
@end itemize
|
63 |
|
|
If an error occurs at any step of the execution, the connections established
|
64 |
|
|
before the error will be closed, before the initialization task deletes itself.
|
65 |
|
|
|
66 |
|
|
|
67 |
|
|
@section The COMMAND_MNGT task
|
68 |
|
|
|
69 |
|
|
This task is in charge of receiving the SUN RPC messages and executing
|
70 |
|
|
the associated commands. This task must have an important priority because it
|
71 |
|
|
must be executed each time a command message comes from the debugger. It must
|
72 |
|
|
be executed even if one or both exception handlers are executed. But the COMMAND
|
73 |
|
|
MANAGEMENT task must not block the TCP/IP module without which no message can
|
74 |
|
|
be received.
|
75 |
|
|
|
76 |
|
|
When not executing a command, this task is waiting for a SUN RPC message
|
77 |
|
|
on the primary port. This idle state blocks the task, so the other active tasks
|
78 |
|
|
can run. Once a message comes from Ethernet via the primary port, the COMMAND
|
79 |
|
|
MANAGEMENT task wakes up and receives the message which is a request from GDB.
|
80 |
|
|
This request is sent to the SUN RPC server code which extracts the command and
|
81 |
|
|
its arguments, executes it and, if needed, sends a result to GDB. After having
|
82 |
|
|
performed these actions, the task sleeps, waiting for another message.
|
83 |
|
|
|
84 |
|
|
A particular case is the reception of the ATTACH command : in this
|
85 |
|
|
case the COMMAND_MNGT task creates the EVENT_MNGT task described below before
|
86 |
|
|
going to wait on UDP socket again.
|
87 |
|
|
|
88 |
|
|
|
89 |
|
|
@section The EVENT_MNGT task
|
90 |
|
|
|
91 |
|
|
This task is in charge of managing events happening on the debuggee such as
|
92 |
|
|
breakpoint, exceptions. This task does a basic simple loop waiting for event
|
93 |
|
|
on a synchronization variable. It is waken up by exception handlers code. It
|
94 |
|
|
then signals GDB that an event occurred and then go sleeping again as further
|
95 |
|
|
requests will be processed by the COMMAND_MNGT task.
|
96 |
|
|
|
97 |
|
|
|
98 |
|
|
@section The DEBUG EXCEPTION handler
|
99 |
|
|
|
100 |
|
|
This handler is connected to the DEBUG exception (INT 1 on Intel ix86).
|
101 |
|
|
This exception is entered when :
|
102 |
|
|
|
103 |
|
|
@itemize @bullet
|
104 |
|
|
@item executing a single-step instruction,
|
105 |
|
|
@item hardware breakpoint condition is true,
|
106 |
|
|
@end itemize
|
107 |
|
|
These events will be treated by the debugger because they are the
|
108 |
|
|
primary event used when debugging a software for instruction stepping. In both
|
109 |
|
|
cases, the DEBUG EXCEPTION handler code is executed. Please note that the execution
|
110 |
|
|
context of the exception handler is the supervisor stack of the task that generated
|
111 |
|
|
the exception. This implies:
|
112 |
|
|
|
113 |
|
|
@itemize @bullet
|
114 |
|
|
@item We may sleep in this context,
|
115 |
|
|
@item We have as many possible execution context for the DEBUG EXCEPTION handler as
|
116 |
|
|
we need to,
|
117 |
|
|
@item When we enter the high level exception handler code, a normalized exception
|
118 |
|
|
context has been pushed on the system stack and a pointer to this context is
|
119 |
|
|
available as the first argument (cf c/src/exec/score/cpu/i386/cpu.c for more
|
120 |
|
|
details),
|
121 |
|
|
@end itemize
|
122 |
|
|
First the exception handler wakeup the EVENT_MNGT task. Then it will
|
123 |
|
|
cause the faulting thread to sleep on a synchronization object. As soon as GDB
|
124 |
|
|
receives the event notifying that the debuggee status has changed, it will start
|
125 |
|
|
sending requests to get the debuggee status (registers set, faulty task id,
|
126 |
|
|
...). These requests are handled by the COMMAND MANAGEMENT task. When this task
|
127 |
|
|
receive a PTRACE_CONT command it will resume the execution of the task that
|
128 |
|
|
caused the exception by doing a V on the synchronization object.
|
129 |
|
|
|
130 |
|
|
|
131 |
|
|
@section The BREAKPOINT EXCEPTION handler
|
132 |
|
|
|
133 |
|
|
This handler is connected to the BREAKPOINT exception (INT3 on Intel
|
134 |
|
|
Ix86). Each time the debugger wants to place a software breakpoint in the debuggee,
|
135 |
|
|
a debuggee opcode is temporarily replaced by an instruction causing BREAKPOINT
|
136 |
|
|
exception (the ``INT 3'' instruction on Intel ix86). When ``INT 3'' is executed,
|
137 |
|
|
the BREAKPOINT handler is executed. Otherwise, the exception processing is the
|
138 |
|
|
same than the one described in previous section.
|
139 |
|
|
|
140 |
|
|
|
141 |
|
|
@section Synchronization Among Tasks and Exception Handlers
|
142 |
|
|
|
143 |
|
|
The previous chapters have presented a simplified and static view of the various
|
144 |
|
|
tasks and exceptions handlers. This chapter is more focussed on synchronization
|
145 |
|
|
requirements about the various pieces of code executed when RGDBSD is operating.
|
146 |
|
|
|
147 |
|
|
|
148 |
|
|
@subsection Implicit Synchronization Using Task Priorities
|
149 |
|
|
|
150 |
|
|
This chapter is relevant on Uniprocessor System (UP) only. However, it will
|
151 |
|
|
also list the requirements for explicit synchronization on Multi-processor Systems
|
152 |
|
|
(MP). Below are the task priorities sorted by high priority. They are not supposed
|
153 |
|
|
to be equal :
|
154 |
|
|
|
155 |
|
|
@enumerate
|
156 |
|
|
@item Network Input Task. This is the highest priority task. This can be regarded
|
157 |
|
|
as a software interrupt task for FreeBSD code,
|
158 |
|
|
@item RGDBSD command task. As this task waits on UDP sockets, it shall not prevent
|
159 |
|
|
the previous task from running. As the main debug entry point, it should preempt
|
160 |
|
|
any other task in the system,
|
161 |
|
|
@item RGDBSD event task. This task should preempt any task but the two mentionned
|
162 |
|
|
before to signal a debug event to GDB. The command task shall be able to preempt
|
163 |
|
|
this task for emergency command such as DEL, or REBOOT,
|
164 |
|
|
@item Applications tasks (task we are able to debug),
|
165 |
|
|
@end enumerate
|
166 |
|
|
|
167 |
|
|
Using theses priorities eliminates the need for adding more synchronization
|
168 |
|
|
objects in the next section. My belief is that symmetric MP support will require
|
169 |
|
|
more important change in the RTEMS than RGDBSD itself like multiple scheduler
|
170 |
|
|
queues, task to processor binding for non symmetric IO, use a different implementation
|
171 |
|
|
for @emph{task_disable_preemption}, ...
|
172 |
|
|
|
173 |
|
|
|
174 |
|
|
@subsection Explicit Synchronization
|
175 |
|
|
|
176 |
|
|
This chapter will describe the synchronization variables that need to be implemented
|
177 |
|
|
in order to sequence debug events in a way that is compatible with what GDB
|
178 |
|
|
code expects. The root of the problem is that GDB code mainly expects that once
|
179 |
|
|
a debug event has occurred on the debuggee, the entire debuggee is frozen and
|
180 |
|
|
no other event will occur before the CONTINUE command is issued. This behavior
|
181 |
|
|
is hard to achieve in our case as once we hit a breakpoint, only the task that
|
182 |
|
|
hits the breakpoint will be asleep on a synchronization object. Other tasks
|
183 |
|
|
may hit other breakpoints while we are waiting commands from GDB generating
|
184 |
|
|
potential unexpected events. There is a solutions if RGDBSD itself use RTEMS
|
185 |
|
|
threads to fix this problem by creating a task that loops forever at a priority
|
186 |
|
|
superior to any debugged task but below RGDBSD task priorities. Unfortunately
|
187 |
|
|
this will not work for the case we use the nano-kernel implementation and we
|
188 |
|
|
think it is better to study synchronization problems now. We also expects that
|
189 |
|
|
multi-thread debug support hardening in GDB will remove some event serializations
|
190 |
|
|
requirements. Here is the list of synchronization variables we plan to use and
|
191 |
|
|
their usage. They are all regular semaphores. They are not binary semaphores
|
192 |
|
|
because the task that does V is not the task that has done the P.
|
193 |
|
|
|
194 |
|
|
@itemize @bullet
|
195 |
|
|
@item @emph{WakeUpEventTask} : used by exception handler code to wake up the EVENT_MNGT
|
196 |
|
|
task by doing a V operation on this object. When target code is running normally
|
197 |
|
|
the EVENT_MNGT task sleeps due to a P operation on this semaphore,
|
198 |
|
|
@item @emph{SerializeDebugEvent} : used to serialize events in a way compatible to
|
199 |
|
|
what GDB expects. Before doing a V operation on @emph{WakeUpEventTask}, the
|
200 |
|
|
exception handler does a P on this semaphore to be sure processing of another
|
201 |
|
|
exception is not in progress. Upon reception of a CONTINUE command, the COMMAND_MNGT
|
202 |
|
|
task will issue a V operation so that the exception code can wake up EVENT_MNGT
|
203 |
|
|
task using the mechanism described above,
|
204 |
|
|
@item @emph{RestartFromException} : (in fact one semaphore per task) used by exception
|
205 |
|
|
handling code to put a faulty task to sleep once it has generated an exception
|
206 |
|
|
by doing a P operation on this semaphore. In the case the exception was generated
|
207 |
|
|
due to a breakpoint, GDB command will modify back the BREAKPOINT opcode to the
|
208 |
|
|
original value before doing the CONTINUE command. This command will perform
|
209 |
|
|
a V on this semaphore. In the case it is a real non restartable exception (faulty
|
210 |
|
|
memory reference via invalid pointer for example), GDB will not allow to restart
|
211 |
|
|
the program avoiding any loop. So not special analysis of cause of exception
|
212 |
|
|
is foreseen as far as RGDBSD code is concerned,
|
213 |
|
|
@end itemize
|
214 |
|
|
|
215 |
|
|
@section Open Issues
|
216 |
|
|
|
217 |
|
|
Here are some problems we have faced while implementing our prototype :
|
218 |
|
|
|
219 |
|
|
@table @b
|
220 |
|
|
@item [Protected ReadMem/WriteMem (I1)]:
|
221 |
|
|
A GDB user can request to see the content
|
222 |
|
|
of a corrupted pointer. The request PEEK_DATA will be performed by the COMMAND_MNGT
|
223 |
|
|
task. It shall not enter the default exception handler set by RGDBSD or it will
|
224 |
|
|
cause a dead lock in the RGDBSD code. Replacing the default exception vector
|
225 |
|
|
before calling @b{readMem/writeMem} can be temporarily sufficient but :
|
226 |
|
|
|
227 |
|
|
@itemize @bullet
|
228 |
|
|
@item It will never work on MP system as it will rely on task priorities to insure
|
229 |
|
|
that other task will not cause exceptions while we have removed the default
|
230 |
|
|
exception handler,
|
231 |
|
|
|
232 |
|
|
@item This feature should not be usable in RGDBSD only but also by an embedded debugger
|
233 |
|
|
that may run without any task. It is also unavoidable in case of protected memory
|
234 |
|
|
and in this case no priority mechanism can be used,
|
235 |
|
|
|
236 |
|
|
@item In the case of using RGDBSD code on a dedicated nano kernel, this code will
|
237 |
|
|
be called from interrupt level and we need a way to be sure we can debug other
|
238 |
|
|
interrupts that may also cause exceptions,
|
239 |
|
|
@end itemize
|
240 |
|
|
|
241 |
|
|
@item [ATTACH Command Implementation (I2)]:
|
242 |
|
|
After the @emph{target rtems symbolic_ip_target_name}
|
243 |
|
|
command, the normal operation is to issue an @emph{attach lid} command where
|
244 |
|
|
@emph{lid} represents a valid execution context. For Unix this is a process
|
245 |
|
|
id, for other multi-tasking system this is the id of a thread. After the attach
|
246 |
|
|
command, GDB expects to be waken up in the same manner as it is for normal events.
|
247 |
|
|
Once waken up it expects to have a complete register context available and also
|
248 |
|
|
that the target task is in a stopped state and that it can restart it using
|
249 |
|
|
the regular CONTINUE command. In RTEMS there is a way to get force a thread
|
250 |
|
|
to become inactive via @emph{rtems_task_suspend} but no way to get the full
|
251 |
|
|
registers set for the thread. A partial context can be retrieved from the task
|
252 |
|
|
@emph{Registers} data structure. On the other hand, relying on @emph{rtems_task_suspend}
|
253 |
|
|
will be a problem for the nano-kernel implementation.
|
254 |
|
|
|
255 |
|
|
@item [Stopping Target System (I3)]:
|
256 |
|
|
Allthough it might not be obvious, most of the
|
257 |
|
|
actions made by a GDB user assume the target is not running. If you modify a
|
258 |
|
|
variable via the @emph{set variable = value} command you expect that the value
|
259 |
|
|
is the one you have put when restarting. If a still running task modifies the
|
260 |
|
|
same value in the mean time, this may be false. On the other hand, stopping
|
261 |
|
|
all the tasks on the target system impose to have a very deep knowledge of the
|
262 |
|
|
system. Using an interrupt driven RGDBSD, may facilitate the implementation
|
263 |
|
|
on the nano-kernel.
|
264 |
|
|
|
265 |
|
|
@item [Getting Tasks Contexts (I4)]:
|
266 |
|
|
As previously mentionned there is no way to get
|
267 |
|
|
tasks execution contexts via the RTEMS API. This is needed when debugging for
|
268 |
|
|
example via this classical sequence :
|
269 |
|
|
|
270 |
|
|
@enumerate
|
271 |
|
|
|
272 |
|
|
@item @emph{(gdb) target rtems symbolic_ip_target_name}
|
273 |
|
|
|
274 |
|
|
@item @emph{(gdb) info threads <=} get a thread list on screen
|
275 |
|
|
|
276 |
|
|
@item @emph{(gdb)} @emph{attach thread_id} <= thread_id is one of the thread in
|
277 |
|
|
the list
|
278 |
|
|
|
279 |
|
|
@item @emph{(gdb) b a_function_of_interest }
|
280 |
|
|
|
281 |
|
|
@item @emph{(gdb) continue}
|
282 |
|
|
|
283 |
|
|
@item @emph{(gdb)} @emph{backtrace} <= print the call stack on the screen once we
|
284 |
|
|
have hit the breakpoint
|
285 |
|
|
|
286 |
|
|
@item @emph{(gdb) thread target another_thread_li <=} change implicit current thread
|
287 |
|
|
value for gdb commands
|
288 |
|
|
|
289 |
|
|
@item @emph{(gdb)} @emph{backtrace <=} should print the backtrace for the chosen thread
|
290 |
|
|
@end enumerate
|
291 |
|
|
In our execution model, we have a valid context only for the threads that hits
|
292 |
|
|
the breakpoint as it has been pushed by the exception handler code. The other
|
293 |
|
|
thread is still running and during the various RPC requesting memory access,
|
294 |
|
|
it even changes as the COMMAND_MNGT thread is going to sleep. So the backtrace
|
295 |
|
|
command will fail. We must find a way to make this work as it is very usefull
|
296 |
|
|
when debugging multi-threaded programs,
|
297 |
|
|
|
298 |
|
|
|
299 |
|
|
@item [Backtrace Stop convention (I5)]:
|
300 |
|
|
The backtrace command on RTEMS task does not
|
301 |
|
|
gracefully terminate as GDB does not find some backtrace termination condition
|
302 |
|
|
it expects.
|
303 |
|
|
@end table
|
304 |
|
|
|
305 |
|
|
@section Workarounds for Open Issues in Prototype
|
306 |
|
|
|
307 |
|
|
@table @b
|
308 |
|
|
|
309 |
|
|
@item [(I1)]:
|
310 |
|
|
Not implemented.We would rather like to work on the formalization of
|
311 |
|
|
per thread flags and global flags that are much more general than any kludge
|
312 |
|
|
we could implement,
|
313 |
|
|
|
314 |
|
|
@item [(I2)]:
|
315 |
|
|
We have tried two solutions in our prototype. The first one was to use
|
316 |
|
|
the @emph{idle} thread context contained in the @emph{Registers} task control
|
317 |
|
|
block field. The drawback of this solution was that we had to implement specific
|
318 |
|
|
code for the continue operation immediately following the attach command. We
|
319 |
|
|
then decided to create a dedicated task that will only exist during the attach
|
320 |
|
|
phase. This task will call the ``ENTER_RGDB'' exception. This call will execute
|
321 |
|
|
the Exception Handler that saves a valid context and that notifies a change
|
322 |
|
|
to GDB. After the first CONTINUE command from GDB, this task will continue its
|
323 |
|
|
execution and delete itself,
|
324 |
|
|
|
325 |
|
|
@item [(I3)]:
|
326 |
|
|
As explained above in the synchronization chapter, we choose to serialize
|
327 |
|
|
events in a way that makes GDB think the system is frozen,
|
328 |
|
|
|
329 |
|
|
@item [(I4)]:
|
330 |
|
|
As a temporary fix, we have called @emph{rtems_task_suspend} and used
|
331 |
|
|
the context switch contex for tasks that are unknown to RGDBSD,
|
332 |
|
|
|
333 |
|
|
@item [(I5)]:
|
334 |
|
|
Not Implemented yet. If I remember correctly, setting the frame pointer
|
335 |
|
|
to 0 at task initialization for CISC processor solves this problem (ebp = 0x0
|
336 |
|
|
on Intel or a6 = 0x0 on 680x0). This should be done in rtems_task_create function
|
337 |
|
|
in the path to really starts the task for the first time. The processor/system
|
338 |
|
|
specific stop condition can be found as macros in the GDB source tree.
|
339 |
|
|
@end table
|
340 |
|
|
|
341 |
|
|
@section Output of a Debug Session with the Prototype
|
342 |
|
|
|
343 |
|
|
This is a sample session with the remote debugging prototype. Note that
|
344 |
|
|
some lines have been broken so they would print properly when printed.
|
345 |
|
|
|
346 |
|
|
@example
|
347 |
|
|
GNU gdb 4.17
|
348 |
|
|
Copyright 1998 Free Software Foundation, Inc.
|
349 |
|
|
GDB is free software, covered by the GNU General Public License,
|
350 |
|
|
and you are welcome to change it and/or distribute copies of it
|
351 |
|
|
under certain conditions. Type "show copying" to see the conditions.
|
352 |
|
|
There is absolutely no warranty for GDB.
|
353 |
|
|
Type "show warranty" for details.
|
354 |
|
|
This GDB was configured as --host=i686-pc-linux-gnu --target=i386-rtems.
|
355 |
|
|
Attaching remote machine across net...
|
356 |
|
|
Connected to net-test.
|
357 |
|
|
Now the "run" command will start a remote process.
|
358 |
|
|
Setting up the environment for debugging gdb.
|
359 |
|
|
(gdb) attach 1
|
360 |
|
|
Attaching program: /build-rtems/pc386/tests/debug.exe pid 1
|
361 |
|
|
0x230715 in enterRdbg ()
|
362 |
|
|
(gdb) info threads
|
363 |
|
|
There are 8 threads:
|
364 |
|
|
Id. Name Detached Suspended
|
365 |
|
|
134283273 Rini No No <= current target thread
|
366 |
|
|
0x230715 in enterRdbg ()
|
367 |
|
|
134283272 Evnt No No
|
368 |
|
|
_Thread_Dispatch () at /rtems/c/src/exec/score/src/thread.c:315
|
369 |
|
|
134283271 SPE2 No No
|
370 |
|
|
_Thread_Dispatch () at /rtems/c/src/exec/score/src/thread.c:315
|
371 |
|
|
134283270 SPE1 No No
|
372 |
|
|
_Thread_Handler () at /rtems/c/src/exec/score/src/thread.c:1107
|
373 |
|
|
134283269 RDBG No No
|
374 |
|
|
0x230715 in enterRdbg ()
|
375 |
|
|
134283268 SCrx No No
|
376 |
|
|
_Thread_Dispatch () at /rtems/c/src/exec/score/src/thread.c:315
|
377 |
|
|
134283267 SCtx No No
|
378 |
|
|
_Thread_Dispatch () at /rtems/c/src/exec/score/src/thread.c:315
|
379 |
|
|
134283266 ntwk No No
|
380 |
|
|
_Thread_Dispatch () at /rtems/c/src/exec/score/src/thread.c:315
|
381 |
|
|
(gdb) b init.c:89
|
382 |
|
|
Breakpoint 1 at 0x200180: file \
|
383 |
|
|
/rtems/c/src/tests/samples/debug/init.c, line 89.
|
384 |
|
|
(gdb) c
|
385 |
|
|
Continuing.
|
386 |
|
|
Thread 134283273 (Rini) has been deleted.
|
387 |
|
|
[Switching to Rtems thread 134283271 (Not suspended) \
|
388 |
|
|
( <= current target thread )]
|
389 |
|
|
Breakpoint 1, example2 (argument=4) at \
|
390 |
|
|
/rtems/c/src/tests/samples/debug/init.c:89
|
391 |
|
|
89 tuto += tuti;
|
392 |
|
|
(gdb) s
|
393 |
|
|
90 if (print_enable2)
|
394 |
|
|
(gdb) c
|
395 |
|
|
Continuing.
|
396 |
|
|
Breakpoint 1, example2 (argument=4) at \
|
397 |
|
|
/rtems/c/src/tests/samples/debug/init.c:89
|
398 |
|
|
89 tuto += tuti;
|
399 |
|
|
(gdb) b init.c:66
|
400 |
|
|
Breakpoint 2 at 0x200128: file \
|
401 |
|
|
/rtems/c/src/tests/samples/debug/init.c, line 66.
|
402 |
|
|
(gdb) c
|
403 |
|
|
Continuing.
|
404 |
|
|
Switching to Rtems thread 134283270 (Not suspended) \
|
405 |
|
|
( <= current target thread )]
|
406 |
|
|
Breakpoint 2, example1 (argument=4) at \
|
407 |
|
|
/rtems/c/src/tests/samples/debug/init.c:66
|
408 |
|
|
66 toto += titi;
|
409 |
|
|
(gdb) c
|
410 |
|
|
Continuing.
|
411 |
|
|
[Switching to Rtems thread 134283271 (Not suspended) \
|
412 |
|
|
( <= current target thread )]
|
413 |
|
|
Breakpoint 1, example2 (argument=4) at \
|
414 |
|
|
/rtems/c/src/tests/samples/debug/init.c:89
|
415 |
|
|
89 tuto += tuti;
|
416 |
|
|
(gdb) bt
|
417 |
|
|
#0 example2 (argument=4)
|
418 |
|
|
at /rtems/c/src/tests/samples/debug/init.c:89
|
419 |
|
|
#1 0xf0009bd0 in ?? ()
|
420 |
|
|
(gdb) thread target 134283270
|
421 |
|
|
thread 134283270 [SPE1], _Thread_Dispatch () at \
|
422 |
|
|
/rtems/c/src/exec/score/src/thread.c:315
|
423 |
|
|
315 executing = _Thread_Executing;
|
424 |
|
|
(gdb) c
|
425 |
|
|
Continuing.
|
426 |
|
|
Breakpoint 2, example1 (argument=4) at \
|
427 |
|
|
/rtems/c/src/tests/samples/debug/init.c:66
|
428 |
|
|
66 toto += titi;
|
429 |
|
|
(gdb) detach
|
430 |
|
|
Detaching program: /build-rtems/pc386/tests/debug.exe pid 1
|
431 |
|
|
Warning: the next command will be done localy! \
|
432 |
|
|
If you want to restart another remote
|
433 |
|
|
program, reuse the target command
|
434 |
|
|
(gdb)
|
435 |
|
|
@end example
|
436 |
|
|
|
437 |
|
|
|