* linux-nat.c (linux_nat_wait): Adjust.
[external/binutils.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 }