* gdb.base/macscp.exp (objfile): Move it to ${objdir}/${subdir}/.
[deliverable/binutils-gdb.git] / gdb / sol-thread.c
1 /* Solaris threads debugging interface.
2
3 Copyright (C) 1996, 1997, 1998, 1999, 2000, 2001, 2002, 2003, 2004, 2005,
4 2007, 2008, 2009 Free Software Foundation, Inc.
5
6 This file is part of GDB.
7
8 This program is free software; you can redistribute it and/or modify
9 it under the terms of the GNU General Public License as published by
10 the Free Software Foundation; either version 3 of the License, or
11 (at your option) any later version.
12
13 This program is distributed in the hope that it will be useful,
14 but WITHOUT ANY WARRANTY; without even the implied warranty of
15 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
16 GNU General Public License for more details.
17
18 You should have received a copy of the GNU General Public License
19 along with this program. If not, see <http://www.gnu.org/licenses/>. */
20
21 /* This module implements a sort of half target that sits between the
22 machine-independent parts of GDB and the /proc interface (procfs.c)
23 to provide access to the Solaris user-mode thread implementation.
24
25 Solaris threads are true user-mode threads, which are invoked via
26 the thr_* and pthread_* (native and POSIX respectivly) interfaces.
27 These are mostly implemented in user-space, with all thread context
28 kept in various structures that live in the user's heap. These
29 should not be confused with lightweight processes (LWPs), which are
30 implemented by the kernel, and scheduled without explicit
31 intervention by the process.
32
33 Just to confuse things a little, Solaris threads (both native and
34 POSIX) are actually implemented using LWPs. In general, there are
35 going to be more threads than LWPs. There is no fixed
36 correspondence between a thread and an LWP. When a thread wants to
37 run, it gets scheduled onto the first available LWP and can
38 therefore migrate from one LWP to another as time goes on. A
39 sleeping thread may not be associated with an LWP at all!
40
41 To make it possible to mess with threads, Sun provides a library
42 called libthread_db.so.1 (not to be confused with
43 libthread_db.so.0, which doesn't have a published interface). This
44 interface has an upper part, which it provides, and a lower part
45 which we provide. The upper part consists of the td_* routines,
46 which allow us to find all the threads, query their state, etc...
47 The lower part consists of all of the ps_*, which are used by the
48 td_* routines to read/write memory, manipulate LWPs, lookup
49 symbols, etc... The ps_* routines actually do most of their work
50 by calling functions in procfs.c. */
51
52 #include "defs.h"
53 #include <thread.h>
54 #include <proc_service.h>
55 #include <thread_db.h>
56 #include "gdbthread.h"
57 #include "target.h"
58 #include "inferior.h"
59 #include <fcntl.h>
60 #include "gdb_stat.h"
61 #include <dlfcn.h>
62 #include "gdbcmd.h"
63 #include "gdbcore.h"
64 #include "regcache.h"
65 #include "solib.h"
66 #include "symfile.h"
67 #include "observer.h"
68
69 #include "gdb_string.h"
70
71 extern struct target_ops sol_thread_ops; /* Forward declaration */
72 extern struct target_ops sol_core_ops; /* Forward declaration */
73
74 /* place to store core_ops before we overwrite it */
75 static struct target_ops orig_core_ops;
76
77 struct target_ops sol_thread_ops;
78 struct target_ops sol_core_ops;
79
80 extern int procfs_suppress_run;
81 extern struct target_ops procfs_ops; /* target vector for procfs.c */
82 extern struct target_ops core_ops; /* target vector for corelow.c */
83 extern char *procfs_pid_to_str (struct target_ops *ops, ptid_t ptid);
84
85 /* Prototypes for supply_gregset etc. */
86 #include "gregset.h"
87
88 /* This struct is defined by us, but mainly used for the proc_service
89 interface. We don't have much use for it, except as a handy place
90 to get a real PID for memory accesses. */
91
92 struct ps_prochandle
93 {
94 ptid_t ptid;
95 };
96
97 struct string_map
98 {
99 int num;
100 char *str;
101 };
102
103 static struct ps_prochandle main_ph;
104 static td_thragent_t *main_ta;
105 static int sol_thread_active = 0;
106
107 static void sol_thread_resume (ptid_t ptid, int step, enum target_signal signo);
108 static int sol_thread_alive (ptid_t ptid);
109 static void sol_core_close (int quitting);
110
111 static void init_sol_thread_ops (void);
112 static void init_sol_core_ops (void);
113
114 /* Default definitions: These must be defined in tm.h if they are to
115 be shared with a process module such as procfs. */
116
117 #define GET_PID(ptid) ptid_get_pid (ptid)
118 #define GET_LWP(ptid) ptid_get_lwp (ptid)
119 #define GET_THREAD(ptid) ptid_get_tid (ptid)
120
121 #define is_lwp(ptid) (GET_LWP (ptid) != 0)
122 #define is_thread(ptid) (GET_THREAD (ptid) != 0)
123
124 #define BUILD_LWP(lwp, pid) ptid_build (pid, lwp, 0)
125 #define BUILD_THREAD(tid, pid) ptid_build (pid, 0, tid)
126
127 /* Pointers to routines from libthread_db resolved by dlopen(). */
128
129 static void (*p_td_log)(const int on_off);
130 static td_err_e (*p_td_ta_new)(const struct ps_prochandle *ph_p,
131 td_thragent_t **ta_pp);
132 static td_err_e (*p_td_ta_delete)(td_thragent_t *ta_p);
133 static td_err_e (*p_td_init)(void);
134 static td_err_e (*p_td_ta_get_ph)(const td_thragent_t *ta_p,
135 struct ps_prochandle **ph_pp);
136 static td_err_e (*p_td_ta_get_nthreads)(const td_thragent_t *ta_p,
137 int *nthread_p);
138 static td_err_e (*p_td_ta_tsd_iter)(const td_thragent_t *ta_p,
139 td_key_iter_f *cb, void *cbdata_p);
140 static td_err_e (*p_td_ta_thr_iter)(const td_thragent_t *ta_p,
141 td_thr_iter_f *cb, void *cbdata_p,
142 td_thr_state_e state, int ti_pri,
143 sigset_t *ti_sigmask_p,
144 unsigned ti_user_flags);
145 static td_err_e (*p_td_thr_validate)(const td_thrhandle_t *th_p);
146 static td_err_e (*p_td_thr_tsd)(const td_thrhandle_t * th_p,
147 const thread_key_t key, void **data_pp);
148 static td_err_e (*p_td_thr_get_info)(const td_thrhandle_t *th_p,
149 td_thrinfo_t *ti_p);
150 static td_err_e (*p_td_thr_getfpregs)(const td_thrhandle_t *th_p,
151 prfpregset_t *fpregset);
152 static td_err_e (*p_td_thr_getxregsize)(const td_thrhandle_t *th_p,
153 int *xregsize);
154 static td_err_e (*p_td_thr_getxregs)(const td_thrhandle_t *th_p,
155 const caddr_t xregset);
156 static td_err_e (*p_td_thr_sigsetmask)(const td_thrhandle_t *th_p,
157 const sigset_t ti_sigmask);
158 static td_err_e (*p_td_thr_setprio)(const td_thrhandle_t *th_p,
159 const int ti_pri);
160 static td_err_e (*p_td_thr_setsigpending)(const td_thrhandle_t *th_p,
161 const uchar_t ti_pending_flag,
162 const sigset_t ti_pending);
163 static td_err_e (*p_td_thr_setfpregs)(const td_thrhandle_t *th_p,
164 const prfpregset_t *fpregset);
165 static td_err_e (*p_td_thr_setxregs)(const td_thrhandle_t *th_p,
166 const caddr_t xregset);
167 static td_err_e (*p_td_ta_map_id2thr)(const td_thragent_t *ta_p,
168 thread_t tid,
169 td_thrhandle_t *th_p);
170 static td_err_e (*p_td_ta_map_lwp2thr)(const td_thragent_t *ta_p,
171 lwpid_t lwpid,
172 td_thrhandle_t *th_p);
173 static td_err_e (*p_td_thr_getgregs)(const td_thrhandle_t *th_p,
174 prgregset_t regset);
175 static td_err_e (*p_td_thr_setgregs)(const td_thrhandle_t *th_p,
176 const prgregset_t regset);
177 \f
178
179 /* Return the libthread_db error string associated with ERRCODE. If
180 ERRCODE is unknown, return an appropriate message. */
181
182 static char *
183 td_err_string (td_err_e errcode)
184 {
185 static struct string_map td_err_table[] =
186 {
187 { TD_OK, "generic \"call succeeded\"" },
188 { TD_ERR, "generic error." },
189 { TD_NOTHR, "no thread can be found to satisfy query" },
190 { TD_NOSV, "no synch. variable can be found to satisfy query" },
191 { TD_NOLWP, "no lwp can be found to satisfy query" },
192 { TD_BADPH, "invalid process handle" },
193 { TD_BADTH, "invalid thread handle" },
194 { TD_BADSH, "invalid synchronization handle" },
195 { TD_BADTA, "invalid thread agent" },
196 { TD_BADKEY, "invalid key" },
197 { TD_NOMSG, "td_thr_event_getmsg() called when there was no message" },
198 { TD_NOFPREGS, "FPU register set not available for given thread" },
199 { TD_NOLIBTHREAD, "application not linked with libthread" },
200 { TD_NOEVENT, "requested event is not supported" },
201 { TD_NOCAPAB, "capability not available" },
202 { TD_DBERR, "Debugger service failed" },
203 { TD_NOAPLIC, "Operation not applicable to" },
204 { TD_NOTSD, "No thread specific data for this thread" },
205 { TD_MALLOC, "Malloc failed" },
206 { TD_PARTIALREG, "Only part of register set was written/read" },
207 { TD_NOXREGS, "X register set not available for given thread" }
208 };
209 const int td_err_size = sizeof td_err_table / sizeof (struct string_map);
210 int i;
211 static char buf[50];
212
213 for (i = 0; i < td_err_size; i++)
214 if (td_err_table[i].num == errcode)
215 return td_err_table[i].str;
216
217 sprintf (buf, "Unknown libthread_db error code: %d", errcode);
218
219 return buf;
220 }
221
222 /* Return the the libthread_db state string assicoated with STATECODE.
223 If STATECODE is unknown, return an appropriate message. */
224
225 static char *
226 td_state_string (td_thr_state_e statecode)
227 {
228 static struct string_map td_thr_state_table[] =
229 {
230 { TD_THR_ANY_STATE, "any state" },
231 { TD_THR_UNKNOWN, "unknown" },
232 { TD_THR_STOPPED, "stopped" },
233 { TD_THR_RUN, "run" },
234 { TD_THR_ACTIVE, "active" },
235 { TD_THR_ZOMBIE, "zombie" },
236 { TD_THR_SLEEP, "sleep" },
237 { TD_THR_STOPPED_ASLEEP, "stopped asleep" }
238 };
239 const int td_thr_state_table_size =
240 sizeof td_thr_state_table / sizeof (struct string_map);
241 int i;
242 static char buf[50];
243
244 for (i = 0; i < td_thr_state_table_size; i++)
245 if (td_thr_state_table[i].num == statecode)
246 return td_thr_state_table[i].str;
247
248 sprintf (buf, "Unknown libthread_db state code: %d", statecode);
249
250 return buf;
251 }
252 \f
253
254 /* Convert a POSIX or Solaris thread ID into a LWP ID. If THREAD_ID
255 doesn't exist, that's an error. If it's an inactive thread, return
256 DEFAULT_LWP.
257
258 NOTE: This function probably shouldn't call error(). */
259
260 static ptid_t
261 thread_to_lwp (ptid_t thread_id, int default_lwp)
262 {
263 td_thrinfo_t ti;
264 td_thrhandle_t th;
265 td_err_e val;
266
267 if (is_lwp (thread_id))
268 return thread_id; /* It's already an LWP ID. */
269
270 /* It's a thread. Convert to LWP. */
271
272 val = p_td_ta_map_id2thr (main_ta, GET_THREAD (thread_id), &th);
273 if (val == TD_NOTHR)
274 return pid_to_ptid (-1); /* Thread must have terminated. */
275 else if (val != TD_OK)
276 error (_("thread_to_lwp: td_ta_map_id2thr %s"), td_err_string (val));
277
278 val = p_td_thr_get_info (&th, &ti);
279 if (val == TD_NOTHR)
280 return pid_to_ptid (-1); /* Thread must have terminated. */
281 else if (val != TD_OK)
282 error (_("thread_to_lwp: td_thr_get_info: %s"), td_err_string (val));
283
284 if (ti.ti_state != TD_THR_ACTIVE)
285 {
286 if (default_lwp != -1)
287 return pid_to_ptid (default_lwp);
288 error (_("thread_to_lwp: thread state not active: %s"),
289 td_state_string (ti.ti_state));
290 }
291
292 return BUILD_LWP (ti.ti_lid, PIDGET (thread_id));
293 }
294
295 /* Convert an LWP ID into a POSIX or Solaris thread ID. If LWP_ID
296 doesn't exists, that's an error.
297
298 NOTE: This function probably shouldn't call error(). */
299
300 static ptid_t
301 lwp_to_thread (ptid_t lwp)
302 {
303 td_thrinfo_t ti;
304 td_thrhandle_t th;
305 td_err_e val;
306
307 if (is_thread (lwp))
308 return lwp; /* It's already a thread ID. */
309
310 /* It's an LWP. Convert it to a thread ID. */
311
312 if (!sol_thread_alive (lwp))
313 return pid_to_ptid (-1); /* Must be a defunct LPW. */
314
315 val = p_td_ta_map_lwp2thr (main_ta, GET_LWP (lwp), &th);
316 if (val == TD_NOTHR)
317 return pid_to_ptid (-1); /* Thread must have terminated. */
318 else if (val != TD_OK)
319 error (_("lwp_to_thread: td_ta_map_lwp2thr: %s."), td_err_string (val));
320
321 val = p_td_thr_validate (&th);
322 if (val == TD_NOTHR)
323 return lwp; /* Unknown to libthread; just return LPW, */
324 else if (val != TD_OK)
325 error (_("lwp_to_thread: td_thr_validate: %s."), td_err_string (val));
326
327 val = p_td_thr_get_info (&th, &ti);
328 if (val == TD_NOTHR)
329 return pid_to_ptid (-1); /* Thread must have terminated. */
330 else if (val != TD_OK)
331 error (_("lwp_to_thread: td_thr_get_info: %s."), td_err_string (val));
332
333 return BUILD_THREAD (ti.ti_tid, PIDGET (lwp));
334 }
335 \f
336
337 /* Most target vector functions from here on actually just pass
338 through to procfs.c, as they don't need to do anything specific for
339 threads. */
340
341 static void
342 sol_thread_open (char *arg, int from_tty)
343 {
344 procfs_ops.to_open (arg, from_tty);
345 }
346
347 /* Attach to process PID, then initialize for debugging it and wait
348 for the trace-trap that results from attaching. */
349
350 static void
351 sol_thread_attach (struct target_ops *ops, char *args, int from_tty)
352 {
353 sol_thread_active = 0;
354 procfs_ops.to_attach (&procfs_ops, args, from_tty);
355
356 /* Must get symbols from shared libraries before libthread_db can run! */
357 solib_add (NULL, from_tty, (struct target_ops *) 0, auto_solib_add);
358
359 if (sol_thread_active)
360 {
361 ptid_t ptid;
362 printf_filtered ("sol-thread active.\n");
363 main_ph.ptid = inferior_ptid; /* Save for xfer_memory. */
364 push_target (&sol_thread_ops);
365 ptid = lwp_to_thread (inferior_ptid);
366 if (PIDGET (ptid) != -1)
367 thread_change_ptid (inferior_ptid, ptid);
368 }
369
370 /* FIXME: Might want to iterate over all the threads and register
371 them. */
372 }
373
374 /* Take a program previously attached to and detaches it. The program
375 resumes execution and will no longer stop on signals, etc. We'd
376 better not have left any breakpoints in the program or it'll die
377 when it hits one. For this to work, it may be necessary for the
378 process to have been previously attached. It *might* work if the
379 program was started via the normal ptrace (PTRACE_TRACEME). */
380
381 static void
382 sol_thread_detach (struct target_ops *ops, char *args, int from_tty)
383 {
384 sol_thread_active = 0;
385 inferior_ptid = pid_to_ptid (PIDGET (main_ph.ptid));
386 unpush_target (&sol_thread_ops);
387 procfs_ops.to_detach (&procfs_ops, args, from_tty);
388 }
389
390 /* Resume execution of process PTID. If STEP is nozero, then just
391 single step it. If SIGNAL is nonzero, restart it with that signal
392 activated. We may have to convert PTID from a thread ID to an LWP
393 ID for procfs. */
394
395 static void
396 sol_thread_resume (ptid_t ptid, int step, enum target_signal signo)
397 {
398 struct cleanup *old_chain;
399
400 old_chain = save_inferior_ptid ();
401
402 inferior_ptid = thread_to_lwp (inferior_ptid, PIDGET (main_ph.ptid));
403 if (PIDGET (inferior_ptid) == -1)
404 inferior_ptid = procfs_first_available ();
405
406 if (PIDGET (ptid) != -1)
407 {
408 ptid_t save_ptid = ptid;
409
410 ptid = thread_to_lwp (ptid, -2);
411 if (PIDGET (ptid) == -2) /* Inactive thread. */
412 error (_("This version of Solaris can't start inactive threads."));
413 if (info_verbose && PIDGET (ptid) == -1)
414 warning (_("Specified thread %ld seems to have terminated"),
415 GET_THREAD (save_ptid));
416 }
417
418 procfs_ops.to_resume (ptid, step, signo);
419
420 do_cleanups (old_chain);
421 }
422
423 /* Wait for any threads to stop. We may have to convert PTID from a
424 thread ID to an LWP ID, and vice versa on the way out. */
425
426 static ptid_t
427 sol_thread_wait (struct target_ops *ops,
428 ptid_t ptid, struct target_waitstatus *ourstatus)
429 {
430 ptid_t rtnval;
431 ptid_t save_ptid;
432 struct cleanup *old_chain;
433
434 save_ptid = inferior_ptid;
435 old_chain = save_inferior_ptid ();
436
437 inferior_ptid = thread_to_lwp (inferior_ptid, PIDGET (main_ph.ptid));
438 if (PIDGET (inferior_ptid) == -1)
439 inferior_ptid = procfs_first_available ();
440
441 if (PIDGET (ptid) != -1)
442 {
443 ptid_t save_ptid = ptid;
444
445 ptid = thread_to_lwp (ptid, -2);
446 if (PIDGET (ptid) == -2) /* Inactive thread. */
447 error (_("This version of Solaris can't start inactive threads."));
448 if (info_verbose && PIDGET (ptid) == -1)
449 warning (_("Specified thread %ld seems to have terminated"),
450 GET_THREAD (save_ptid));
451 }
452
453 rtnval = procfs_ops.to_wait (&procfs_ops, ptid, ourstatus);
454
455 if (ourstatus->kind != TARGET_WAITKIND_EXITED)
456 {
457 /* Map the LWP of interest back to the appropriate thread ID. */
458 rtnval = lwp_to_thread (rtnval);
459 if (PIDGET (rtnval) == -1)
460 rtnval = save_ptid;
461
462 /* See if we have a new thread. */
463 if (is_thread (rtnval)
464 && !ptid_equal (rtnval, save_ptid)
465 && (!in_thread_list (rtnval)
466 || is_exited (rtnval)))
467 add_thread (rtnval);
468 }
469
470 /* During process initialization, we may get here without the thread
471 package being initialized, since that can only happen after we've
472 found the shared libs. */
473
474 do_cleanups (old_chain);
475
476 return rtnval;
477 }
478
479 static void
480 sol_thread_fetch_registers (struct regcache *regcache, int regnum)
481 {
482 thread_t thread;
483 td_thrhandle_t thandle;
484 td_err_e val;
485 prgregset_t gregset;
486 prfpregset_t fpregset;
487 gdb_gregset_t *gregset_p = &gregset;
488 gdb_fpregset_t *fpregset_p = &fpregset;
489
490 #if 0
491 int xregsize;
492 caddr_t xregset;
493 #endif
494
495 if (!is_thread (inferior_ptid))
496 {
497 /* It's an LWP; pass the request on to procfs. */
498 if (target_has_execution)
499 procfs_ops.to_fetch_registers (regcache, regnum);
500 else
501 orig_core_ops.to_fetch_registers (regcache, regnum);
502 return;
503 }
504
505 /* Solaris thread: convert INFERIOR_PTID into a td_thrhandle_t. */
506 thread = GET_THREAD (inferior_ptid);
507 if (thread == 0)
508 error (_("sol_thread_fetch_registers: thread == 0"));
509
510 val = p_td_ta_map_id2thr (main_ta, thread, &thandle);
511 if (val != TD_OK)
512 error (_("sol_thread_fetch_registers: td_ta_map_id2thr: %s"),
513 td_err_string (val));
514
515 /* Get the general-purpose registers. */
516
517 val = p_td_thr_getgregs (&thandle, gregset);
518 if (val != TD_OK && val != TD_PARTIALREG)
519 error (_("sol_thread_fetch_registers: td_thr_getgregs %s"),
520 td_err_string (val));
521
522 /* For SPARC, TD_PARTIALREG means that only %i0...%i7, %l0..%l7, %pc
523 and %sp are saved (by a thread context switch). */
524
525 /* And, now the floating-point registers. */
526
527 val = p_td_thr_getfpregs (&thandle, &fpregset);
528 if (val != TD_OK && val != TD_NOFPREGS)
529 error (_("sol_thread_fetch_registers: td_thr_getfpregs %s"),
530 td_err_string (val));
531
532 /* Note that we must call supply_gregset and supply_fpregset *after*
533 calling the td routines because the td routines call ps_lget*
534 which affect the values stored in the registers array. */
535
536 supply_gregset (regcache, (const gdb_gregset_t *) gregset_p);
537 supply_fpregset (regcache, (const gdb_fpregset_t *) fpregset_p);
538
539 #if 0
540 /* FIXME: libthread_db doesn't seem to handle this right. */
541 val = td_thr_getxregsize (&thandle, &xregsize);
542 if (val != TD_OK && val != TD_NOXREGS)
543 error (_("sol_thread_fetch_registers: td_thr_getxregsize %s"),
544 td_err_string (val));
545
546 if (val == TD_OK)
547 {
548 xregset = alloca (xregsize);
549 val = td_thr_getxregs (&thandle, xregset);
550 if (val != TD_OK)
551 error (_("sol_thread_fetch_registers: td_thr_getxregs %s"),
552 td_err_string (val));
553 }
554 #endif
555 }
556
557 static void
558 sol_thread_store_registers (struct regcache *regcache, int regnum)
559 {
560 thread_t thread;
561 td_thrhandle_t thandle;
562 td_err_e val;
563 prgregset_t gregset;
564 prfpregset_t fpregset;
565 #if 0
566 int xregsize;
567 caddr_t xregset;
568 #endif
569
570 if (!is_thread (inferior_ptid))
571 {
572 /* It's an LWP; pass the request on to procfs.c. */
573 procfs_ops.to_store_registers (regcache, regnum);
574 return;
575 }
576
577 /* Solaris thread: convert INFERIOR_PTID into a td_thrhandle_t. */
578 thread = GET_THREAD (inferior_ptid);
579
580 val = p_td_ta_map_id2thr (main_ta, thread, &thandle);
581 if (val != TD_OK)
582 error (_("sol_thread_store_registers: td_ta_map_id2thr %s"),
583 td_err_string (val));
584
585 if (regnum != -1)
586 {
587 /* Not writing all the registers. */
588 char old_value[MAX_REGISTER_SIZE];
589
590 /* Save new register value. */
591 regcache_raw_collect (regcache, regnum, old_value);
592
593 val = p_td_thr_getgregs (&thandle, gregset);
594 if (val != TD_OK)
595 error (_("sol_thread_store_registers: td_thr_getgregs %s"),
596 td_err_string (val));
597 val = p_td_thr_getfpregs (&thandle, &fpregset);
598 if (val != TD_OK)
599 error (_("sol_thread_store_registers: td_thr_getfpregs %s"),
600 td_err_string (val));
601
602 /* Restore new register value. */
603 regcache_raw_supply (regcache, regnum, old_value);
604
605 #if 0
606 /* FIXME: libthread_db doesn't seem to handle this right. */
607 val = td_thr_getxregsize (&thandle, &xregsize);
608 if (val != TD_OK && val != TD_NOXREGS)
609 error (_("sol_thread_store_registers: td_thr_getxregsize %s"),
610 td_err_string (val));
611
612 if (val == TD_OK)
613 {
614 xregset = alloca (xregsize);
615 val = td_thr_getxregs (&thandle, xregset);
616 if (val != TD_OK)
617 error (_("sol_thread_store_registers: td_thr_getxregs %s"),
618 td_err_string (val));
619 }
620 #endif
621 }
622
623 fill_gregset (regcache, (gdb_gregset_t *) &gregset, regnum);
624 fill_fpregset (regcache, (gdb_fpregset_t *) &fpregset, regnum);
625
626 val = p_td_thr_setgregs (&thandle, gregset);
627 if (val != TD_OK)
628 error (_("sol_thread_store_registers: td_thr_setgregs %s"),
629 td_err_string (val));
630 val = p_td_thr_setfpregs (&thandle, &fpregset);
631 if (val != TD_OK)
632 error (_("sol_thread_store_registers: td_thr_setfpregs %s"),
633 td_err_string (val));
634
635 #if 0
636 /* FIXME: libthread_db doesn't seem to handle this right. */
637 val = td_thr_getxregsize (&thandle, &xregsize);
638 if (val != TD_OK && val != TD_NOXREGS)
639 error (_("sol_thread_store_registers: td_thr_getxregsize %s"),
640 td_err_string (val));
641
642 /* ??? Should probably do something about writing the xregs here,
643 but what are they? */
644 #endif
645 }
646
647 /* Get ready to modify the registers array. On machines which store
648 individual registers, this doesn't need to do anything. On
649 machines which store all the registers in one fell swoop, this
650 makes sure that registers contains all the registers from the
651 program being debugged. */
652
653 static void
654 sol_thread_prepare_to_store (struct regcache *regcache)
655 {
656 procfs_ops.to_prepare_to_store (regcache);
657 }
658
659 /* Transfer LEN bytes between GDB address MYADDR and target address
660 MEMADDR. If DOWRITE is non-zero, transfer them to the target,
661 otherwise transfer them from the target. TARGET is unused.
662
663 Returns the number of bytes transferred. */
664
665 static int
666 sol_thread_xfer_memory (CORE_ADDR memaddr, gdb_byte *myaddr, int len,
667 int dowrite, struct mem_attrib *attrib,
668 struct target_ops *target)
669 {
670 int retval;
671 struct cleanup *old_chain;
672
673 old_chain = save_inferior_ptid ();
674
675 if (is_thread (inferior_ptid) || !target_thread_alive (inferior_ptid))
676 {
677 /* It's either a thread or an LWP that isn't alive. Any live
678 LWP will do so use the first available.
679
680 NOTE: We don't need to call switch_to_thread; we're just
681 reading memory. */
682 inferior_ptid = procfs_first_available ();
683 }
684
685 if (target_has_execution)
686 retval = procfs_ops.deprecated_xfer_memory (memaddr, myaddr, len,
687 dowrite, attrib, target);
688 else
689 retval = orig_core_ops.deprecated_xfer_memory (memaddr, myaddr, len,
690 dowrite, attrib, target);
691
692 do_cleanups (old_chain);
693
694 return retval;
695 }
696
697 /* Perform partial transfers on OBJECT. See target_read_partial and
698 target_write_partial for details of each variant. One, and only
699 one, of readbuf or writebuf must be non-NULL. */
700
701 static LONGEST
702 sol_thread_xfer_partial (struct target_ops *ops, enum target_object object,
703 const char *annex, gdb_byte *readbuf,
704 const gdb_byte *writebuf,
705 ULONGEST offset, LONGEST len)
706 {
707 int retval;
708 struct cleanup *old_chain;
709
710 old_chain = save_inferior_ptid ();
711
712 if (is_thread (inferior_ptid) || !target_thread_alive (inferior_ptid))
713 {
714 /* It's either a thread or an LWP that isn't alive. Any live
715 LWP will do so use the first available.
716
717 NOTE: We don't need to call switch_to_thread; we're just
718 reading memory. */
719 inferior_ptid = procfs_first_available ();
720 }
721
722 if (target_has_execution)
723 retval = procfs_ops.to_xfer_partial (ops, object, annex,
724 readbuf, writebuf, offset, len);
725 else
726 retval = orig_core_ops.to_xfer_partial (ops, object, annex,
727 readbuf, writebuf, offset, len);
728
729 do_cleanups (old_chain);
730
731 return retval;
732 }
733
734 /* Print status information about what we're accessing. */
735
736 static void
737 sol_thread_files_info (struct target_ops *ignore)
738 {
739 procfs_ops.to_files_info (ignore);
740 }
741
742 static void
743 sol_thread_kill_inferior (void)
744 {
745 procfs_ops.to_kill ();
746 }
747
748 static void
749 sol_thread_notice_signals (ptid_t ptid)
750 {
751 procfs_ops.to_notice_signals (pid_to_ptid (PIDGET (ptid)));
752 }
753
754 /* Fork an inferior process, and start debugging it with /proc. */
755
756 static void
757 sol_thread_create_inferior (struct target_ops *ops, char *exec_file,
758 char *allargs, char **env, int from_tty)
759 {
760 sol_thread_active = 0;
761 procfs_ops.to_create_inferior (&procfs_ops, exec_file, allargs, env, from_tty);
762
763 if (sol_thread_active && !ptid_equal (inferior_ptid, null_ptid))
764 {
765 ptid_t ptid;
766
767 /* Save for xfer_memory. */
768 main_ph.ptid = inferior_ptid;
769
770 push_target (&sol_thread_ops);
771
772 ptid = lwp_to_thread (inferior_ptid);
773 if (PIDGET (ptid) != -1)
774 thread_change_ptid (inferior_ptid, ptid);
775 }
776 }
777
778 /* This routine is called whenever a new symbol table is read in, or
779 when all symbol tables are removed. libthread_db can only be
780 initialized when it finds the right variables in libthread.so.
781 Since it's a shared library, those variables don't show up until
782 the library gets mapped and the symbol table is read in. */
783
784 static void
785 sol_thread_new_objfile (struct objfile *objfile)
786 {
787 td_err_e val;
788
789 if (!objfile)
790 {
791 sol_thread_active = 0;
792 return;
793 }
794
795 /* Don't do anything if init failed to resolve the libthread_db
796 library. */
797 if (!procfs_suppress_run)
798 return;
799
800 /* Now, initialize libthread_db. This needs to be done after the
801 shared libraries are located because it needs information from
802 the user's thread library. */
803
804 val = p_td_init ();
805 if (val != TD_OK)
806 {
807 warning (_("sol_thread_new_objfile: td_init: %s"), td_err_string (val));
808 return;
809 }
810
811 val = p_td_ta_new (&main_ph, &main_ta);
812 if (val == TD_NOLIBTHREAD)
813 return;
814 else if (val != TD_OK)
815 {
816 warning (_("sol_thread_new_objfile: td_ta_new: %s"), td_err_string (val));
817 return;
818 }
819
820 sol_thread_active = 1;
821 }
822
823 /* Clean up after the inferior dies. */
824
825 static void
826 sol_thread_mourn_inferior (struct target_ops *ops)
827 {
828 sol_thread_active = 0;
829 unpush_target (&sol_thread_ops);
830 procfs_ops.to_mourn_inferior (&procfs_ops);
831 }
832
833 /* Mark our target-struct as eligible for stray "run" and "attach"
834 commands. */
835
836 static int
837 sol_thread_can_run (void)
838 {
839 return procfs_suppress_run;
840 }
841
842 /*
843
844 LOCAL FUNCTION
845
846 sol_thread_alive - test thread for "aliveness"
847
848 SYNOPSIS
849
850 static bool sol_thread_alive (ptid_t ptid);
851
852 DESCRIPTION
853
854 returns true if thread still active in inferior.
855
856 */
857
858 /* Return true if PTID is still active in the inferior. */
859
860 static int
861 sol_thread_alive (ptid_t ptid)
862 {
863 if (is_thread (ptid))
864 {
865 /* It's a (user-level) thread. */
866 td_err_e val;
867 td_thrhandle_t th;
868 int pid;
869
870 pid = GET_THREAD (ptid);
871 if ((val = p_td_ta_map_id2thr (main_ta, pid, &th)) != TD_OK)
872 return 0; /* Thread not found. */
873 if ((val = p_td_thr_validate (&th)) != TD_OK)
874 return 0; /* Thread not valid. */
875 return 1; /* Known thread. */
876 }
877 else
878 {
879 /* It's an LPW; pass the request on to procfs. */
880 if (target_has_execution)
881 return procfs_ops.to_thread_alive (ptid);
882 else
883 return orig_core_ops.to_thread_alive (ptid);
884 }
885 }
886
887 static void
888 sol_thread_stop (ptid_t ptid)
889 {
890 procfs_ops.to_stop (ptid);
891 }
892 \f
893 /* These routines implement the lower half of the thread_db interface,
894 i.e. the ps_* routines. */
895
896 /* Various versions of <proc_service.h> have slightly different
897 function prototypes. In particular, we have
898
899 NEWER OLDER
900 struct ps_prochandle * const struct ps_prochandle *
901 void* char*
902 const void* char*
903 int size_t
904
905 Which one you have depends on the Solaris version and what patches
906 you've applied. On the theory that there are only two major
907 variants, we have configure check the prototype of ps_pdwrite (),
908 and use that info to make appropriate typedefs here. */
909
910 #ifdef PROC_SERVICE_IS_OLD
911 typedef const struct ps_prochandle *gdb_ps_prochandle_t;
912 typedef char *gdb_ps_read_buf_t;
913 typedef char *gdb_ps_write_buf_t;
914 typedef int gdb_ps_size_t;
915 typedef psaddr_t gdb_ps_addr_t;
916 #else
917 typedef struct ps_prochandle *gdb_ps_prochandle_t;
918 typedef void *gdb_ps_read_buf_t;
919 typedef const void *gdb_ps_write_buf_t;
920 typedef size_t gdb_ps_size_t;
921 typedef psaddr_t gdb_ps_addr_t;
922 #endif
923
924 /* The next four routines are called by libthread_db to tell us to
925 stop and stop a particular process or lwp. Since GDB ensures that
926 these are all stopped by the time we call anything in thread_db,
927 these routines need to do nothing. */
928
929 /* Process stop. */
930
931 ps_err_e
932 ps_pstop (gdb_ps_prochandle_t ph)
933 {
934 return PS_OK;
935 }
936
937 /* Process continue. */
938
939 ps_err_e
940 ps_pcontinue (gdb_ps_prochandle_t ph)
941 {
942 return PS_OK;
943 }
944
945 /* LWP stop. */
946
947 ps_err_e
948 ps_lstop (gdb_ps_prochandle_t ph, lwpid_t lwpid)
949 {
950 return PS_OK;
951 }
952
953 /* LWP continue. */
954
955 ps_err_e
956 ps_lcontinue (gdb_ps_prochandle_t ph, lwpid_t lwpid)
957 {
958 return PS_OK;
959 }
960
961 /* Looks up the symbol LD_SYMBOL_NAME in the debugger's symbol table. */
962
963 ps_err_e
964 ps_pglobal_lookup (gdb_ps_prochandle_t ph, const char *ld_object_name,
965 const char *ld_symbol_name, gdb_ps_addr_t *ld_symbol_addr)
966 {
967 struct minimal_symbol *ms;
968
969 ms = lookup_minimal_symbol (ld_symbol_name, NULL, NULL);
970 if (!ms)
971 return PS_NOSYM;
972
973 *ld_symbol_addr = SYMBOL_VALUE_ADDRESS (ms);
974 return PS_OK;
975 }
976
977 /* Common routine for reading and writing memory. */
978
979 static ps_err_e
980 rw_common (int dowrite, const struct ps_prochandle *ph, gdb_ps_addr_t addr,
981 char *buf, int size)
982 {
983 struct cleanup *old_chain;
984
985 old_chain = save_inferior_ptid ();
986
987 if (is_thread (inferior_ptid) || !target_thread_alive (inferior_ptid))
988 {
989 /* It's either a thread or an LWP that isn't alive. Any live
990 LWP will do so use the first available.
991
992 NOTE: We don't need to call switch_to_thread; we're just
993 reading memory. */
994 inferior_ptid = procfs_first_available ();
995 }
996
997 #if defined (__sparcv9)
998 /* For Sparc64 cross Sparc32, make sure the address has not been
999 accidentally sign-extended (or whatever) to beyond 32 bits. */
1000 if (bfd_get_arch_size (exec_bfd) == 32)
1001 addr &= 0xffffffff;
1002 #endif
1003
1004 while (size > 0)
1005 {
1006 int cc;
1007
1008 /* FIXME: passing 0 as attrib argument. */
1009 if (target_has_execution)
1010 cc = procfs_ops.deprecated_xfer_memory (addr, buf, size,
1011 dowrite, 0, &procfs_ops);
1012 else
1013 cc = orig_core_ops.deprecated_xfer_memory (addr, buf, size,
1014 dowrite, 0, &core_ops);
1015
1016 if (cc < 0)
1017 {
1018 if (dowrite == 0)
1019 print_sys_errmsg ("rw_common (): read", errno);
1020 else
1021 print_sys_errmsg ("rw_common (): write", errno);
1022
1023 do_cleanups (old_chain);
1024
1025 return PS_ERR;
1026 }
1027 else if (cc == 0)
1028 {
1029 if (dowrite == 0)
1030 warning (_("rw_common (): unable to read at addr 0x%lx"),
1031 (long) addr);
1032 else
1033 warning (_("rw_common (): unable to write at addr 0x%lx"),
1034 (long) addr);
1035
1036 do_cleanups (old_chain);
1037
1038 return PS_ERR;
1039 }
1040
1041 size -= cc;
1042 buf += cc;
1043 }
1044
1045 do_cleanups (old_chain);
1046
1047 return PS_OK;
1048 }
1049
1050 /* Copies SIZE bytes from target process .data segment to debugger memory. */
1051
1052 ps_err_e
1053 ps_pdread (gdb_ps_prochandle_t ph, gdb_ps_addr_t addr,
1054 gdb_ps_read_buf_t buf, gdb_ps_size_t size)
1055 {
1056 return rw_common (0, ph, addr, buf, size);
1057 }
1058
1059 /* Copies SIZE bytes from debugger memory .data segment to target process. */
1060
1061 ps_err_e
1062 ps_pdwrite (gdb_ps_prochandle_t ph, gdb_ps_addr_t addr,
1063 gdb_ps_write_buf_t buf, gdb_ps_size_t size)
1064 {
1065 return rw_common (1, ph, addr, (char *) buf, size);
1066 }
1067
1068 /* Copies SIZE bytes from target process .text segment to debugger memory. */
1069
1070 ps_err_e
1071 ps_ptread (gdb_ps_prochandle_t ph, gdb_ps_addr_t addr,
1072 gdb_ps_read_buf_t buf, gdb_ps_size_t size)
1073 {
1074 return rw_common (0, ph, addr, buf, size);
1075 }
1076
1077 /* Copies SIZE bytes from debugger memory .text segment to target process. */
1078
1079 ps_err_e
1080 ps_ptwrite (gdb_ps_prochandle_t ph, gdb_ps_addr_t addr,
1081 gdb_ps_write_buf_t buf, gdb_ps_size_t size)
1082 {
1083 return rw_common (1, ph, addr, (char *) buf, size);
1084 }
1085
1086 /* Get general-purpose registers for LWP. */
1087
1088 ps_err_e
1089 ps_lgetregs (gdb_ps_prochandle_t ph, lwpid_t lwpid, prgregset_t gregset)
1090 {
1091 struct cleanup *old_chain;
1092 struct regcache *regcache;
1093
1094 old_chain = save_inferior_ptid ();
1095
1096 inferior_ptid = BUILD_LWP (lwpid, PIDGET (inferior_ptid));
1097 regcache = get_thread_regcache (inferior_ptid);
1098
1099 if (target_has_execution)
1100 procfs_ops.to_fetch_registers (regcache, -1);
1101 else
1102 orig_core_ops.to_fetch_registers (regcache, -1);
1103 fill_gregset (regcache, (gdb_gregset_t *) gregset, -1);
1104
1105 do_cleanups (old_chain);
1106
1107 return PS_OK;
1108 }
1109
1110 /* Set general-purpose registers for LWP. */
1111
1112 ps_err_e
1113 ps_lsetregs (gdb_ps_prochandle_t ph, lwpid_t lwpid,
1114 const prgregset_t gregset)
1115 {
1116 struct cleanup *old_chain;
1117 struct regcache *regcache;
1118
1119 old_chain = save_inferior_ptid ();
1120
1121 inferior_ptid = BUILD_LWP (lwpid, PIDGET (inferior_ptid));
1122 regcache = get_thread_regcache (inferior_ptid);
1123
1124 supply_gregset (regcache, (const gdb_gregset_t *) gregset);
1125 if (target_has_execution)
1126 procfs_ops.to_store_registers (regcache, -1);
1127 else
1128 orig_core_ops.to_store_registers (regcache, -1);
1129
1130 do_cleanups (old_chain);
1131
1132 return PS_OK;
1133 }
1134
1135 /* Log a message (sends to gdb_stderr). */
1136
1137 void
1138 ps_plog (const char *fmt, ...)
1139 {
1140 va_list args;
1141
1142 va_start (args, fmt);
1143
1144 vfprintf_filtered (gdb_stderr, fmt, args);
1145 }
1146
1147 /* Get size of extra register set. Currently a noop. */
1148
1149 ps_err_e
1150 ps_lgetxregsize (gdb_ps_prochandle_t ph, lwpid_t lwpid, int *xregsize)
1151 {
1152 #if 0
1153 int lwp_fd;
1154 int regsize;
1155 ps_err_e val;
1156
1157 val = get_lwp_fd (ph, lwpid, &lwp_fd);
1158 if (val != PS_OK)
1159 return val;
1160
1161 if (ioctl (lwp_fd, PIOCGXREGSIZE, &regsize))
1162 {
1163 if (errno == EINVAL)
1164 return PS_NOFREGS; /* XXX Wrong code, but this is the closest
1165 thing in proc_service.h */
1166
1167 print_sys_errmsg ("ps_lgetxregsize (): PIOCGXREGSIZE", errno);
1168 return PS_ERR;
1169 }
1170 #endif
1171
1172 return PS_OK;
1173 }
1174
1175 /* Get extra register set. Currently a noop. */
1176
1177 ps_err_e
1178 ps_lgetxregs (gdb_ps_prochandle_t ph, lwpid_t lwpid, caddr_t xregset)
1179 {
1180 #if 0
1181 int lwp_fd;
1182 ps_err_e val;
1183
1184 val = get_lwp_fd (ph, lwpid, &lwp_fd);
1185 if (val != PS_OK)
1186 return val;
1187
1188 if (ioctl (lwp_fd, PIOCGXREG, xregset))
1189 {
1190 print_sys_errmsg ("ps_lgetxregs (): PIOCGXREG", errno);
1191 return PS_ERR;
1192 }
1193 #endif
1194
1195 return PS_OK;
1196 }
1197
1198 /* Set extra register set. Currently a noop. */
1199
1200 ps_err_e
1201 ps_lsetxregs (gdb_ps_prochandle_t ph, lwpid_t lwpid, caddr_t xregset)
1202 {
1203 #if 0
1204 int lwp_fd;
1205 ps_err_e val;
1206
1207 val = get_lwp_fd (ph, lwpid, &lwp_fd);
1208 if (val != PS_OK)
1209 return val;
1210
1211 if (ioctl (lwp_fd, PIOCSXREG, xregset))
1212 {
1213 print_sys_errmsg ("ps_lsetxregs (): PIOCSXREG", errno);
1214 return PS_ERR;
1215 }
1216 #endif
1217
1218 return PS_OK;
1219 }
1220
1221 /* Get floating-point registers for LWP. */
1222
1223 ps_err_e
1224 ps_lgetfpregs (gdb_ps_prochandle_t ph, lwpid_t lwpid,
1225 prfpregset_t *fpregset)
1226 {
1227 struct cleanup *old_chain;
1228 struct regcache *regcache;
1229
1230 old_chain = save_inferior_ptid ();
1231
1232 inferior_ptid = BUILD_LWP (lwpid, PIDGET (inferior_ptid));
1233 regcache = get_thread_regcache (inferior_ptid);
1234
1235 if (target_has_execution)
1236 procfs_ops.to_fetch_registers (regcache, -1);
1237 else
1238 orig_core_ops.to_fetch_registers (regcache, -1);
1239 fill_fpregset (regcache, (gdb_fpregset_t *) fpregset, -1);
1240
1241 do_cleanups (old_chain);
1242
1243 return PS_OK;
1244 }
1245
1246 /* Set floating-point regs for LWP */
1247
1248 ps_err_e
1249 ps_lsetfpregs (gdb_ps_prochandle_t ph, lwpid_t lwpid,
1250 const prfpregset_t * fpregset)
1251 {
1252 struct cleanup *old_chain;
1253 struct regcache *regcache;
1254
1255 old_chain = save_inferior_ptid ();
1256
1257 inferior_ptid = BUILD_LWP (lwpid, PIDGET (inferior_ptid));
1258 regcache = get_thread_regcache (inferior_ptid);
1259
1260 supply_fpregset (regcache, (const gdb_fpregset_t *) fpregset);
1261 if (target_has_execution)
1262 procfs_ops.to_store_registers (regcache, -1);
1263 else
1264 orig_core_ops.to_store_registers (regcache, -1);
1265
1266 do_cleanups (old_chain);
1267
1268 return PS_OK;
1269 }
1270
1271 #ifdef PR_MODEL_LP64
1272 /* Identify process as 32-bit or 64-bit. At the moment we're using
1273 BFD to do this. There might be a more Solaris-specific
1274 (e.g. procfs) method, but this ought to work. */
1275
1276 ps_err_e
1277 ps_pdmodel (gdb_ps_prochandle_t ph, int *data_model)
1278 {
1279 if (exec_bfd == 0)
1280 *data_model = PR_MODEL_UNKNOWN;
1281 else if (bfd_get_arch_size (exec_bfd) == 32)
1282 *data_model = PR_MODEL_ILP32;
1283 else
1284 *data_model = PR_MODEL_LP64;
1285
1286 return PS_OK;
1287 }
1288 #endif /* PR_MODEL_LP64 */
1289
1290 #if (defined(__i386__) || defined(__x86_64__)) && defined (sun)
1291
1292 /* Reads the local descriptor table of a LWP.
1293
1294 This function is necessary on x86-solaris only. Without it, the loading
1295 of libthread_db would fail because of ps_lgetLDT being undefined. */
1296
1297 ps_err_e
1298 ps_lgetLDT (gdb_ps_prochandle_t ph, lwpid_t lwpid,
1299 struct ssd *pldt)
1300 {
1301 /* NOTE: only used on Solaris, therefore OK to refer to procfs.c. */
1302 extern struct ssd *procfs_find_LDT_entry (ptid_t);
1303 struct ssd *ret;
1304
1305 /* FIXME: can't I get the process ID from the prochandle or
1306 something? */
1307
1308 if (PIDGET (inferior_ptid) <= 0 || lwpid <= 0)
1309 return PS_BADLID;
1310
1311 ret = procfs_find_LDT_entry (BUILD_LWP (lwpid, PIDGET (inferior_ptid)));
1312 if (ret)
1313 {
1314 memcpy (pldt, ret, sizeof (struct ssd));
1315 return PS_OK;
1316 }
1317 else
1318 /* LDT not found. */
1319 return PS_ERR;
1320 }
1321 #endif
1322 \f
1323
1324 /* Convert PTID to printable form. */
1325
1326 char *
1327 solaris_pid_to_str (struct target_ops *ops, ptid_t ptid)
1328 {
1329 static char buf[100];
1330
1331 /* In case init failed to resolve the libthread_db library. */
1332 if (!procfs_suppress_run)
1333 return procfs_pid_to_str (&procfs_ops, ptid);
1334
1335 if (is_thread (ptid))
1336 {
1337 ptid_t lwp;
1338
1339 lwp = thread_to_lwp (ptid, -2);
1340
1341 if (PIDGET (lwp) == -1)
1342 sprintf (buf, "Thread %ld (defunct)", GET_THREAD (ptid));
1343 else if (PIDGET (lwp) != -2)
1344 sprintf (buf, "Thread %ld (LWP %ld)",
1345 GET_THREAD (ptid), GET_LWP (lwp));
1346 else
1347 sprintf (buf, "Thread %ld ", GET_THREAD (ptid));
1348 }
1349 else if (GET_LWP (ptid) != 0)
1350 sprintf (buf, "LWP %ld ", GET_LWP (ptid));
1351 else
1352 sprintf (buf, "process %d ", PIDGET (ptid));
1353
1354 return buf;
1355 }
1356 \f
1357
1358 /* Worker bee for find_new_threads. Callback function that gets
1359 called once per user-level thread (i.e. not for LWP's). */
1360
1361 static int
1362 sol_find_new_threads_callback (const td_thrhandle_t *th, void *ignored)
1363 {
1364 td_err_e retval;
1365 td_thrinfo_t ti;
1366 ptid_t ptid;
1367
1368 retval = p_td_thr_get_info (th, &ti);
1369 if (retval != TD_OK)
1370 return -1;
1371
1372 ptid = BUILD_THREAD (ti.ti_tid, PIDGET (inferior_ptid));
1373 if (!in_thread_list (ptid) || is_exited (ptid))
1374 add_thread (ptid);
1375
1376 return 0;
1377 }
1378
1379 static void
1380 sol_find_new_threads (void)
1381 {
1382 /* Don't do anything if init failed to resolve the libthread_db
1383 library. */
1384 if (!procfs_suppress_run)
1385 return;
1386
1387 if (PIDGET (inferior_ptid) == -1)
1388 {
1389 printf_filtered ("No process.\n");
1390 return;
1391 }
1392
1393 /* First Find any new LWP's. */
1394 procfs_ops.to_find_new_threads ();
1395
1396 /* Then find any new user-level threads. */
1397 p_td_ta_thr_iter (main_ta, sol_find_new_threads_callback, (void *) 0,
1398 TD_THR_ANY_STATE, TD_THR_LOWEST_PRIORITY,
1399 TD_SIGNO_MASK, TD_THR_ANY_USER_FLAGS);
1400 }
1401
1402 static void
1403 sol_core_open (char *filename, int from_tty)
1404 {
1405 orig_core_ops.to_open (filename, from_tty);
1406 }
1407
1408 static void
1409 sol_core_close (int quitting)
1410 {
1411 orig_core_ops.to_close (quitting);
1412 }
1413
1414 static void
1415 sol_core_detach (struct target_ops *ops, char *args, int from_tty)
1416 {
1417 unpush_target (&core_ops);
1418 orig_core_ops.to_detach (&orig_core_ops, args, from_tty);
1419 }
1420
1421 static void
1422 sol_core_files_info (struct target_ops *t)
1423 {
1424 orig_core_ops.to_files_info (t);
1425 }
1426
1427 /* Worker bee for the "info sol-thread" command. This is a callback
1428 function that gets called once for each Solaris user-level thread
1429 (i.e. not for LWPs) in the inferior. Print anything interesting
1430 that we can think of. */
1431
1432 static int
1433 info_cb (const td_thrhandle_t *th, void *s)
1434 {
1435 td_err_e ret;
1436 td_thrinfo_t ti;
1437
1438 ret = p_td_thr_get_info (th, &ti);
1439 if (ret == TD_OK)
1440 {
1441 printf_filtered ("%s thread #%d, lwp %d, ",
1442 ti.ti_type == TD_THR_SYSTEM ? "system" : "user ",
1443 ti.ti_tid, ti.ti_lid);
1444 switch (ti.ti_state)
1445 {
1446 default:
1447 case TD_THR_UNKNOWN:
1448 printf_filtered ("<unknown state>");
1449 break;
1450 case TD_THR_STOPPED:
1451 printf_filtered ("(stopped)");
1452 break;
1453 case TD_THR_RUN:
1454 printf_filtered ("(run) ");
1455 break;
1456 case TD_THR_ACTIVE:
1457 printf_filtered ("(active) ");
1458 break;
1459 case TD_THR_ZOMBIE:
1460 printf_filtered ("(zombie) ");
1461 break;
1462 case TD_THR_SLEEP:
1463 printf_filtered ("(asleep) ");
1464 break;
1465 case TD_THR_STOPPED_ASLEEP:
1466 printf_filtered ("(stopped asleep)");
1467 break;
1468 }
1469 /* Print thr_create start function. */
1470 if (ti.ti_startfunc != 0)
1471 {
1472 struct minimal_symbol *msym;
1473 msym = lookup_minimal_symbol_by_pc (ti.ti_startfunc);
1474 if (msym)
1475 printf_filtered (" startfunc: %s\n",
1476 SYMBOL_PRINT_NAME (msym));
1477 else
1478 printf_filtered (" startfunc: 0x%s\n", paddr (ti.ti_startfunc));
1479 }
1480
1481 /* If thread is asleep, print function that went to sleep. */
1482 if (ti.ti_state == TD_THR_SLEEP)
1483 {
1484 struct minimal_symbol *msym;
1485 msym = lookup_minimal_symbol_by_pc (ti.ti_pc);
1486 if (msym)
1487 printf_filtered (" - Sleep func: %s\n",
1488 SYMBOL_PRINT_NAME (msym));
1489 else
1490 printf_filtered (" - Sleep func: 0x%s\n", paddr (ti.ti_startfunc));
1491 }
1492
1493 /* Wrap up line, if necessary. */
1494 if (ti.ti_state != TD_THR_SLEEP && ti.ti_startfunc == 0)
1495 printf_filtered ("\n"); /* don't you hate counting newlines? */
1496 }
1497 else
1498 warning (_("info sol-thread: failed to get info for thread."));
1499
1500 return 0;
1501 }
1502
1503 /* List some state about each Solaris user-level thread in the
1504 inferior. */
1505
1506 static void
1507 info_solthreads (char *args, int from_tty)
1508 {
1509 p_td_ta_thr_iter (main_ta, info_cb, args,
1510 TD_THR_ANY_STATE, TD_THR_LOWEST_PRIORITY,
1511 TD_SIGNO_MASK, TD_THR_ANY_USER_FLAGS);
1512 }
1513
1514 static int
1515 sol_find_memory_regions (int (*func) (CORE_ADDR, unsigned long,
1516 int, int, int, void *),
1517 void *data)
1518 {
1519 return procfs_ops.to_find_memory_regions (func, data);
1520 }
1521
1522 static char *
1523 sol_make_note_section (bfd *obfd, int *note_size)
1524 {
1525 return procfs_ops.to_make_corefile_notes (obfd, note_size);
1526 }
1527
1528 static int
1529 ignore (struct bp_target_info *bp_tgt)
1530 {
1531 return 0;
1532 }
1533
1534 static void
1535 init_sol_thread_ops (void)
1536 {
1537 sol_thread_ops.to_shortname = "solaris-threads";
1538 sol_thread_ops.to_longname = "Solaris threads and pthread.";
1539 sol_thread_ops.to_doc = "Solaris threads and pthread support.";
1540 sol_thread_ops.to_open = sol_thread_open;
1541 sol_thread_ops.to_attach = sol_thread_attach;
1542 sol_thread_ops.to_detach = sol_thread_detach;
1543 sol_thread_ops.to_resume = sol_thread_resume;
1544 sol_thread_ops.to_wait = sol_thread_wait;
1545 sol_thread_ops.to_fetch_registers = sol_thread_fetch_registers;
1546 sol_thread_ops.to_store_registers = sol_thread_store_registers;
1547 sol_thread_ops.to_prepare_to_store = sol_thread_prepare_to_store;
1548 sol_thread_ops.deprecated_xfer_memory = sol_thread_xfer_memory;
1549 sol_thread_ops.to_xfer_partial = sol_thread_xfer_partial;
1550 sol_thread_ops.to_files_info = sol_thread_files_info;
1551 sol_thread_ops.to_insert_breakpoint = memory_insert_breakpoint;
1552 sol_thread_ops.to_remove_breakpoint = memory_remove_breakpoint;
1553 sol_thread_ops.to_terminal_init = terminal_init_inferior;
1554 sol_thread_ops.to_terminal_inferior = terminal_inferior;
1555 sol_thread_ops.to_terminal_ours_for_output = terminal_ours_for_output;
1556 sol_thread_ops.to_terminal_ours = terminal_ours;
1557 sol_thread_ops.to_terminal_save_ours = terminal_save_ours;
1558 sol_thread_ops.to_terminal_info = child_terminal_info;
1559 sol_thread_ops.to_kill = sol_thread_kill_inferior;
1560 sol_thread_ops.to_create_inferior = sol_thread_create_inferior;
1561 sol_thread_ops.to_mourn_inferior = sol_thread_mourn_inferior;
1562 sol_thread_ops.to_can_run = sol_thread_can_run;
1563 sol_thread_ops.to_notice_signals = sol_thread_notice_signals;
1564 sol_thread_ops.to_thread_alive = sol_thread_alive;
1565 sol_thread_ops.to_pid_to_str = solaris_pid_to_str;
1566 sol_thread_ops.to_find_new_threads = sol_find_new_threads;
1567 sol_thread_ops.to_stop = sol_thread_stop;
1568 sol_thread_ops.to_stratum = process_stratum;
1569 sol_thread_ops.to_has_all_memory = 1;
1570 sol_thread_ops.to_has_memory = 1;
1571 sol_thread_ops.to_has_stack = 1;
1572 sol_thread_ops.to_has_registers = 1;
1573 sol_thread_ops.to_has_execution = 1;
1574 sol_thread_ops.to_has_thread_control = tc_none;
1575 sol_thread_ops.to_find_memory_regions = sol_find_memory_regions;
1576 sol_thread_ops.to_make_corefile_notes = sol_make_note_section;
1577 sol_thread_ops.to_magic = OPS_MAGIC;
1578 }
1579
1580 static void
1581 init_sol_core_ops (void)
1582 {
1583 sol_core_ops.to_shortname = "solaris-core";
1584 sol_core_ops.to_longname = "Solaris core threads and pthread.";
1585 sol_core_ops.to_doc = "Solaris threads and pthread support for core files.";
1586 sol_core_ops.to_open = sol_core_open;
1587 sol_core_ops.to_close = sol_core_close;
1588 sol_core_ops.to_attach = sol_thread_attach;
1589 sol_core_ops.to_detach = sol_core_detach;
1590 sol_core_ops.to_fetch_registers = sol_thread_fetch_registers;
1591 sol_core_ops.deprecated_xfer_memory = sol_thread_xfer_memory;
1592 sol_core_ops.to_xfer_partial = sol_thread_xfer_partial;
1593 sol_core_ops.to_files_info = sol_core_files_info;
1594 sol_core_ops.to_insert_breakpoint = ignore;
1595 sol_core_ops.to_remove_breakpoint = ignore;
1596 sol_core_ops.to_create_inferior = sol_thread_create_inferior;
1597 sol_core_ops.to_stratum = core_stratum;
1598 sol_core_ops.to_has_memory = 1;
1599 sol_core_ops.to_has_stack = 1;
1600 sol_core_ops.to_has_registers = 1;
1601 sol_core_ops.to_has_thread_control = tc_none;
1602 sol_core_ops.to_thread_alive = sol_thread_alive;
1603 sol_core_ops.to_pid_to_str = solaris_pid_to_str;
1604 /* On Solaris/x86, when debugging a threaded core file from process
1605 <n>, the following causes "info threads" to produce "procfs:
1606 couldn't find pid <n> in procinfo list" where <n> is the pid of
1607 the process that produced the core file. Disable it for now. */
1608 #if 0
1609 sol_core_ops.to_find_new_threads = sol_find_new_threads;
1610 #endif
1611 sol_core_ops.to_magic = OPS_MAGIC;
1612 }
1613
1614 /* We suppress the call to add_target of core_ops in corelow because
1615 if there are two targets in the stratum core_stratum,
1616 find_core_target won't know which one to return. See corelow.c for
1617 an additonal comment on coreops_suppress_target. */
1618 int coreops_suppress_target = 1;
1619
1620 void
1621 _initialize_sol_thread (void)
1622 {
1623 void *dlhandle;
1624
1625 init_sol_thread_ops ();
1626 init_sol_core_ops ();
1627
1628 dlhandle = dlopen ("libthread_db.so.1", RTLD_NOW);
1629 if (!dlhandle)
1630 goto die;
1631
1632 #define resolve(X) \
1633 if (!(p_##X = dlsym (dlhandle, #X))) \
1634 goto die;
1635
1636 resolve (td_log);
1637 resolve (td_ta_new);
1638 resolve (td_ta_delete);
1639 resolve (td_init);
1640 resolve (td_ta_get_ph);
1641 resolve (td_ta_get_nthreads);
1642 resolve (td_ta_tsd_iter);
1643 resolve (td_ta_thr_iter);
1644 resolve (td_thr_validate);
1645 resolve (td_thr_tsd);
1646 resolve (td_thr_get_info);
1647 resolve (td_thr_getfpregs);
1648 resolve (td_thr_getxregsize);
1649 resolve (td_thr_getxregs);
1650 resolve (td_thr_sigsetmask);
1651 resolve (td_thr_setprio);
1652 resolve (td_thr_setsigpending);
1653 resolve (td_thr_setfpregs);
1654 resolve (td_thr_setxregs);
1655 resolve (td_ta_map_id2thr);
1656 resolve (td_ta_map_lwp2thr);
1657 resolve (td_thr_getgregs);
1658 resolve (td_thr_setgregs);
1659
1660 add_target (&sol_thread_ops);
1661
1662 procfs_suppress_run = 1;
1663
1664 add_cmd ("sol-threads", class_maintenance, info_solthreads,
1665 _("Show info on Solaris user threads."), &maintenanceinfolist);
1666
1667 /* FIXME: This code takes errant advantage of the order in which
1668 initialization routines are run. _initialize_corelow must run before
1669 this one otherwise orig_core_ops will still contain zeros and the work
1670 of init_sol_core_ops will be undone. */
1671 memcpy (&orig_core_ops, &core_ops, sizeof (struct target_ops));
1672 memcpy (&core_ops, &sol_core_ops, sizeof (struct target_ops));
1673 add_target (&core_ops);
1674
1675 /* Hook into new_objfile notification. */
1676 observer_attach_new_objfile (sol_thread_new_objfile);
1677 return;
1678
1679 die:
1680 fprintf_unfiltered (gdb_stderr, "\
1681 [GDB will not be able to debug user-mode threads: %s]\n", dlerror ());
1682
1683 if (dlhandle)
1684 dlclose (dlhandle);
1685
1686 /* Allow the user to debug non-threaded core files. */
1687 add_target (&core_ops);
1688
1689 return;
1690 }
This page took 0.065259 seconds and 4 git commands to generate.