* mn10300.igen (OP_F0F4): Need to load contents of register AN0
[platform/upstream/binutils.git] / gdb / hpux-thread.c
1 /* Low level interface for debugging HPUX/DCE threads for GDB, the GNU debugger.
2    Copyright 1996 Free Software Foundation, Inc.
3
4 This file is part of GDB.
5
6 This program is free software; you can redistribute it and/or modify
7 it under the terms of the GNU General Public License as published by
8 the Free Software Foundation; either version 2 of the License, or
9 (at your option) any later version.
10
11 This program is distributed in the hope that it will be useful,
12 but WITHOUT ANY WARRANTY; without even the implied warranty of
13 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
14 GNU General Public License for more details.
15
16 You should have received a copy of the GNU General Public License
17 along with this program; if not, write to the Free Software
18 Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.  */
19
20 /* This module implements a sort of half target that sits between the
21    machine-independent parts of GDB and the ptrace interface (infptrace.c) to
22    provide access to the HPUX user-mode thread implementation.
23
24    HPUX threads are true user-mode threads, which are invoked via the cma_*
25    and pthread_* (DCE and Posix respectivly) interfaces.  These are mostly
26    implemented in user-space, with all thread context kept in various
27    structures that live in the user's heap.  For the most part, the kernel has
28    no knowlege of these threads.
29
30    */
31
32 #include "defs.h"
33
34 #define _CMA_NOWRAPPERS_
35
36 #include <cma_tcb_defs.h>
37 #include <cma_deb_core.h>
38 #include "gdbthread.h"
39 #include "target.h"
40 #include "inferior.h"
41 #include <fcntl.h>
42 #include <unistd.h>
43 #include <sys/stat.h>
44 #include "gdbcore.h"
45
46 extern struct target_ops hpux_thread_ops; /* Forward declaration */
47
48 extern int child_suppress_run;
49 extern struct target_ops child_ops; /* target vector for inftarg.c */
50
51 struct string_map
52 {
53   int num;
54   char *str;
55 };
56
57 static int hpux_thread_active = 0;
58
59 static int main_pid;            /* Real process ID */
60
61 static CORE_ADDR P_cma__g_known_threads;
62 static CORE_ADDR P_cma__g_current_thread;
63
64 static struct cleanup * save_inferior_pid PARAMS ((void));
65 static void restore_inferior_pid PARAMS ((int pid));
66 static void hpux_thread_resume PARAMS ((int pid, int step,
67                                         enum target_signal signo));
68 \f
69 /*
70
71 LOCAL FUNCTION
72
73         save_inferior_pid - Save inferior_pid on the cleanup list
74         restore_inferior_pid - Restore inferior_pid from the cleanup list
75
76 SYNOPSIS
77
78         struct cleanup *save_inferior_pid ()
79         void restore_inferior_pid (int pid)
80
81 DESCRIPTION
82
83         These two functions act in unison to restore inferior_pid in
84         case of an error.
85
86 NOTES
87
88         inferior_pid is a global variable that needs to be changed by many of
89         these routines before calling functions in procfs.c.  In order to
90         guarantee that inferior_pid gets restored (in case of errors), you
91         need to call save_inferior_pid before changing it.  At the end of the
92         function, you should invoke do_cleanups to restore it.
93
94  */
95
96
97 static struct cleanup *
98 save_inferior_pid ()
99 {
100   return make_cleanup (restore_inferior_pid, inferior_pid);
101 }
102
103 static void
104 restore_inferior_pid (pid)
105      int pid;
106 {
107   inferior_pid = pid;
108 }
109 \f
110 static int find_active_thread PARAMS ((void));
111
112 static int cached_thread;
113 static int cached_active_thread;
114 static cma__t_int_tcb cached_tcb;
115
116 static int
117 find_active_thread ()
118 {
119   static cma__t_int_tcb tcb;
120   CORE_ADDR tcb_ptr;
121
122   if (cached_active_thread != 0)
123     return cached_active_thread;
124
125   read_memory ((CORE_ADDR)P_cma__g_current_thread,
126                (char *)&tcb_ptr,
127                sizeof tcb_ptr);
128
129   read_memory (tcb_ptr, (char *)&tcb, sizeof tcb);
130
131   return (cma_thread_get_unique (&tcb.prolog.client_thread) << 16) | main_pid;
132 }
133
134 static cma__t_int_tcb * find_tcb PARAMS ((int thread));
135
136 static cma__t_int_tcb *
137 find_tcb (thread)
138      int thread;
139 {
140   cma__t_known_object queue_header;
141   cma__t_queue *queue_ptr;
142
143   if (thread == cached_thread)
144     return &cached_tcb;
145
146   read_memory ((CORE_ADDR)P_cma__g_known_threads,
147                (char *)&queue_header,
148                sizeof queue_header);
149
150   for (queue_ptr = queue_header.queue.flink;
151        queue_ptr != (cma__t_queue *)P_cma__g_known_threads;
152        queue_ptr = cached_tcb.threads.flink)
153     {
154       cma__t_int_tcb *tcb_ptr;
155
156       tcb_ptr = cma__base (queue_ptr, threads, cma__t_int_tcb);
157
158       read_memory ((CORE_ADDR)tcb_ptr, (char *)&cached_tcb, sizeof cached_tcb);
159
160       if (cached_tcb.header.type == cma__c_obj_tcb)
161         if (cma_thread_get_unique (&cached_tcb.prolog.client_thread) == thread >> 16)
162           {
163             cached_thread = thread;
164             return &cached_tcb;
165           }
166     }
167
168   error ("Can't find TCB %d,%d", thread >> 16, thread & 0xffff);
169   return NULL;
170 }
171 \f
172 /* Most target vector functions from here on actually just pass through to
173    inftarg.c, as they don't need to do anything specific for threads.  */
174
175 /* ARGSUSED */
176 static void
177 hpux_thread_open (arg, from_tty)
178      char *arg;
179      int from_tty;
180 {
181   child_ops.to_open (arg, from_tty);
182 }
183
184 /* Attach to process PID, then initialize for debugging it
185    and wait for the trace-trap that results from attaching.  */
186
187 static void
188 hpux_thread_attach (args, from_tty)
189      char *args;
190      int from_tty;
191 {
192   child_ops.to_attach (args, from_tty);
193
194   /* XXX - might want to iterate over all the threads and register them. */
195 }
196
197 /* Take a program previously attached to and detaches it.
198    The program resumes execution and will no longer stop
199    on signals, etc.  We'd better not have left any breakpoints
200    in the program or it'll die when it hits one.  For this
201    to work, it may be necessary for the process to have been
202    previously attached.  It *might* work if the program was
203    started via the normal ptrace (PTRACE_TRACEME).  */
204
205 static void
206 hpux_thread_detach (args, from_tty)
207      char *args;
208      int from_tty;
209 {
210   child_ops.to_detach (args, from_tty);
211 }
212
213 /* Resume execution of process PID.  If STEP is nozero, then
214    just single step it.  If SIGNAL is nonzero, restart it with that
215    signal activated.  We may have to convert pid from a thread-id to an LWP id
216    for procfs.  */
217
218 static void
219 hpux_thread_resume (pid, step, signo)
220      int pid;
221      int step;
222      enum target_signal signo;
223 {
224   struct cleanup *old_chain;
225
226   old_chain = save_inferior_pid ();
227
228   pid = inferior_pid = main_pid;
229
230 #if 0
231   if (pid != -1)
232     {
233       pid = thread_to_lwp (pid, -2);
234       if (pid == -2)            /* Inactive thread */
235         error ("This version of Solaris can't start inactive threads.");
236     }
237 #endif
238
239   child_ops.to_resume (pid, step, signo);
240
241   cached_thread = 0;
242   cached_active_thread = 0;
243
244   do_cleanups (old_chain);
245 }
246
247 /* Wait for any threads to stop.  We may have to convert PID from a thread id
248    to a LWP id, and vice versa on the way out.  */
249
250 static int
251 hpux_thread_wait (pid, ourstatus)
252      int pid;
253      struct target_waitstatus *ourstatus;
254 {
255   int rtnval;
256   struct cleanup *old_chain;
257
258   old_chain = save_inferior_pid ();
259
260   inferior_pid = main_pid;
261
262   if (pid != -1)
263     pid = main_pid;
264
265   rtnval = child_ops.to_wait (pid, ourstatus);
266
267   rtnval = find_active_thread ();
268
269   do_cleanups (old_chain);
270
271   return rtnval;
272 }
273
274 static char regmap[NUM_REGS] =
275 {
276   -2, -1, -1, 0, 4, 8, 12, 16, 20, 24, /* flags, r1 -> r9 */
277   28, 32, 36, 40, 44, 48, 52, 56, 60, -1, /* r10 -> r19 */
278   -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, /* r20 -> r29 */
279
280   /* r30, r31, sar, pcoqh, pcsqh, pcoqt, pcsqt, eiem, iir, isr */
281   -2, -1, -1, -2, -1, -1, -1, -1, -1, -1,
282
283   /* ior, ipsw, goto, sr4, sr0, sr1, sr2, sr3, sr5, sr6 */
284   -1, -1, -1, -1, -1, -1, -1, -1, -1, -1,
285
286   /* sr7, cr0, cr8, cr9, ccr, cr12, cr13, cr24, cr25, cr26 */
287   -1, -1, -1, -1, -1, -1, -1, -1, -1, -1,
288
289   -1, -1, -1, -1,               /* mpsfu_high, mpsfu_low, mpsfu_ovflo, pad */
290   144, -1, -1, -1, -1, -1, -1, -1, /* fpsr, fpe1 -> fpe7 */
291   -1, -1, -1, -1, -1, -1, -1, -1, /* fr4 -> fr7 */
292   -1, -1, -1, -1, -1, -1, -1, -1, /* fr8 -> fr11 */
293   136, -1, 128, -1, 120, -1, 112, -1, /* fr12 -> fr15 */
294   104, -1, 96, -1, 88, -1, 80, -1, /* fr16 -> fr19 */
295   72, -1, 64, -1, -1, -1, -1, -1, /* fr20 -> fr23 */
296   -1, -1, -1, -1, -1, -1, -1, -1, /* fr24 -> fr27 */
297   -1, -1, -1, -1, -1, -1, -1, -1, /* fr28 -> fr31 */
298 };
299
300 static void
301 hpux_thread_fetch_registers (regno)
302      int regno;
303 {
304   cma__t_int_tcb tcb, *tcb_ptr;
305   struct cleanup *old_chain;
306   int i;
307   int first_regno, last_regno;
308
309   tcb_ptr = find_tcb (inferior_pid);
310
311   old_chain = save_inferior_pid ();
312
313   inferior_pid = main_pid;
314
315   if (tcb_ptr->state == cma__c_state_running)
316     {
317       child_ops.to_fetch_registers (regno);
318
319       do_cleanups (old_chain);
320
321       return;
322     }
323
324   if (regno == -1)
325     {
326       first_regno = 0;
327       last_regno = NUM_REGS - 1;
328     }
329   else
330     {
331       first_regno = regno;
332       last_regno = regno;
333     }
334
335   for (regno = first_regno; regno <= last_regno; regno++)
336     {
337       if (regmap[regno] == -1)
338         child_ops.to_fetch_registers (regno);
339       else
340         {
341           unsigned char buf[MAX_REGISTER_RAW_SIZE];
342           CORE_ADDR sp;
343
344           sp = (CORE_ADDR)tcb_ptr->static_ctx.sp - 160;
345
346           if (regno == FLAGS_REGNUM)
347             /* Flags must be 0 to avoid bogus value for SS_INSYSCALL */
348             memset (buf, '\000', REGISTER_RAW_SIZE (regno));
349           else if (regno == SP_REGNUM)
350             store_address (buf, sizeof sp, sp);
351           else if (regno == PC_REGNUM)
352             read_memory (sp - 20, buf, REGISTER_RAW_SIZE (regno));
353           else
354             read_memory (sp + regmap[regno], buf, REGISTER_RAW_SIZE (regno));
355
356           supply_register (regno, buf);
357         }
358     }
359
360   do_cleanups (old_chain);
361 }
362
363 static void
364 hpux_thread_store_registers (regno)
365      int regno;
366 {
367   cma__t_int_tcb tcb, *tcb_ptr;
368   struct cleanup *old_chain;
369   int i;
370   int first_regno, last_regno;
371
372   tcb_ptr = find_tcb (inferior_pid);
373
374   old_chain = save_inferior_pid ();
375
376   inferior_pid = main_pid;
377
378   if (tcb_ptr->state == cma__c_state_running)
379     {
380       child_ops.to_store_registers (regno);
381
382       do_cleanups (old_chain);
383
384       return;
385     }
386
387   if (regno == -1)
388     {
389       first_regno = 0;
390       last_regno = NUM_REGS - 1;
391     }
392   else
393     {
394       first_regno = regno;
395       last_regno = regno;
396     }
397
398   for (regno = first_regno; regno <= last_regno; regno++)
399     {
400       if (regmap[regno] == -1)
401         child_ops.to_store_registers (regno);
402       else
403         {
404           unsigned char buf[MAX_REGISTER_RAW_SIZE];
405           CORE_ADDR sp;
406
407           sp = (CORE_ADDR)tcb_ptr->static_ctx.sp - 160;
408
409           if (regno == FLAGS_REGNUM)
410             child_ops.to_store_registers (regno); /* Let lower layer handle this... */
411           else if (regno == SP_REGNUM)
412             {
413               write_memory ((CORE_ADDR)&tcb_ptr->static_ctx.sp,
414                             registers + REGISTER_BYTE (regno),
415                             REGISTER_RAW_SIZE (regno));
416               tcb_ptr->static_ctx.sp = (cma__t_hppa_regs *)
417                 (extract_address (registers + REGISTER_BYTE (regno), REGISTER_RAW_SIZE (regno)) + 160);
418             }
419           else if (regno == PC_REGNUM)
420             write_memory (sp - 20,
421                           registers + REGISTER_BYTE (regno),
422                           REGISTER_RAW_SIZE (regno));
423           else
424             write_memory (sp + regmap[regno],
425                           registers + REGISTER_BYTE (regno),
426                           REGISTER_RAW_SIZE (regno));
427         }
428     }
429
430   do_cleanups (old_chain);
431 }
432
433 /* Get ready to modify the registers array.  On machines which store
434    individual registers, this doesn't need to do anything.  On machines
435    which store all the registers in one fell swoop, this makes sure
436    that registers contains all the registers from the program being
437    debugged.  */
438
439 static void
440 hpux_thread_prepare_to_store ()
441 {
442   child_ops.to_prepare_to_store ();
443 }
444
445 static int
446 hpux_thread_xfer_memory (memaddr, myaddr, len, dowrite, target)
447      CORE_ADDR memaddr;
448      char *myaddr;
449      int len;
450      int dowrite;
451      struct target_ops *target; /* ignored */
452 {
453   int retval;
454   struct cleanup *old_chain;
455
456   old_chain = save_inferior_pid ();
457
458   inferior_pid = main_pid;
459
460   retval = child_ops.to_xfer_memory (memaddr, myaddr, len, dowrite, target);
461
462   do_cleanups (old_chain);
463
464   return retval;
465 }
466
467 /* Print status information about what we're accessing.  */
468
469 static void
470 hpux_thread_files_info (ignore)
471      struct target_ops *ignore;
472 {
473   child_ops.to_files_info (ignore);
474 }
475
476 static void
477 hpux_thread_kill_inferior ()
478 {
479   child_ops.to_kill ();
480 }
481
482 static void
483 hpux_thread_notice_signals (pid)
484      int pid;
485 {
486   child_ops.to_notice_signals (pid);
487 }
488
489 /* Fork an inferior process, and start debugging it with /proc.  */
490
491 static void
492 hpux_thread_create_inferior (exec_file, allargs, env)
493      char *exec_file;
494      char *allargs;
495      char **env;
496 {
497   child_ops.to_create_inferior (exec_file, allargs, env);
498
499   if (hpux_thread_active)
500     {
501       main_pid = inferior_pid;
502
503       push_target (&hpux_thread_ops);
504
505       inferior_pid = find_active_thread ();
506
507       add_thread (inferior_pid);
508     }
509 }
510
511 /* This routine is called whenever a new symbol table is read in, or when all
512    symbol tables are removed.  libthread_db can only be initialized when it
513    finds the right variables in libthread.so.  Since it's a shared library,
514    those variables don't show up until the library gets mapped and the symbol
515    table is read in.  */
516
517 void
518 hpux_thread_new_objfile (objfile)
519      struct objfile *objfile;
520 {
521   struct minimal_symbol *ms;
522
523   if (!objfile)
524     {
525       hpux_thread_active = 0;
526
527       return;
528     }
529
530   ms = lookup_minimal_symbol ("cma__g_known_threads", NULL, objfile);
531
532   if (!ms)
533     return;
534
535   P_cma__g_known_threads = SYMBOL_VALUE_ADDRESS (ms);
536
537   ms = lookup_minimal_symbol ("cma__g_current_thread", NULL, objfile);
538
539   if (!ms)
540     return;
541
542   P_cma__g_current_thread = SYMBOL_VALUE_ADDRESS (ms);
543
544   hpux_thread_active = 1;
545 }
546
547 /* Clean up after the inferior dies.  */
548
549 static void
550 hpux_thread_mourn_inferior ()
551 {
552   child_ops.to_mourn_inferior ();
553 }
554
555 /* Mark our target-struct as eligible for stray "run" and "attach" commands.  */
556
557 static int
558 hpux_thread_can_run ()
559 {
560   return child_suppress_run;
561 }
562
563 static int
564 hpux_thread_alive (pid)
565      int pid;
566 {
567   return 1;
568 }
569
570 static void
571 hpux_thread_stop ()
572 {
573   child_ops.to_stop ();
574 }
575 \f
576 /* Convert a pid to printable form. */
577
578 char *
579 hpux_pid_to_str (pid)
580      int pid;
581 {
582   static char buf[100];
583
584   sprintf (buf, "Thread %d", pid >> 16);
585
586   return buf;
587 }
588 \f
589 struct target_ops hpux_thread_ops = {
590   "hpux-threads",               /* to_shortname */
591   "HPUX threads and pthread.", /* to_longname */
592   "HPUX threads and pthread support.", /* to_doc */
593   hpux_thread_open,             /* to_open */
594   0,                            /* to_close */
595   hpux_thread_attach,           /* to_attach */
596   hpux_thread_detach,           /* to_detach */
597   hpux_thread_resume,           /* to_resume */
598   hpux_thread_wait,             /* to_wait */
599   hpux_thread_fetch_registers,  /* to_fetch_registers */
600   hpux_thread_store_registers,  /* to_store_registers */
601   hpux_thread_prepare_to_store, /* to_prepare_to_store */
602   hpux_thread_xfer_memory,      /* to_xfer_memory */
603   hpux_thread_files_info,       /* to_files_info */
604   memory_insert_breakpoint,     /* to_insert_breakpoint */
605   memory_remove_breakpoint,     /* to_remove_breakpoint */
606   terminal_init_inferior,       /* to_terminal_init */
607   terminal_inferior,            /* to_terminal_inferior */
608   terminal_ours_for_output,     /* to_terminal_ours_for_output */
609   terminal_ours,                /* to_terminal_ours */
610   child_terminal_info,          /* to_terminal_info */
611   hpux_thread_kill_inferior,    /* to_kill */
612   0,                            /* to_load */
613   0,                            /* to_lookup_symbol */
614   hpux_thread_create_inferior,  /* to_create_inferior */
615   hpux_thread_mourn_inferior,   /* to_mourn_inferior */
616   hpux_thread_can_run,          /* to_can_run */
617   hpux_thread_notice_signals,   /* to_notice_signals */
618   hpux_thread_alive,            /* to_thread_alive */
619   hpux_thread_stop,             /* to_stop */
620   process_stratum,              /* to_stratum */
621   0,                            /* to_next */
622   1,                            /* to_has_all_memory */
623   1,                            /* to_has_memory */
624   1,                            /* to_has_stack */
625   1,                            /* to_has_registers */
626   1,                            /* to_has_execution */
627   0,                            /* sections */
628   0,                            /* sections_end */
629   OPS_MAGIC                     /* to_magic */
630 };
631
632 void
633 _initialize_hpux_thread ()
634 {
635   add_target (&hpux_thread_ops);
636
637   child_suppress_run = 1;
638 }