Lint
[deliverable/binutils-gdb.git] / gdb / convex-xdep.c
CommitLineData
dd3b648e
RP
1/* Convex stuff for GDB.
2 Copyright (C) 1990-1991 Free Software Foundation, Inc.
3
4This file is part of GDB.
5
99a7de40 6This program is free software; you can redistribute it and/or modify
dd3b648e 7it under the terms of the GNU General Public License as published by
99a7de40
JG
8the Free Software Foundation; either version 2 of the License, or
9(at your option) any later version.
dd3b648e 10
99a7de40 11This program is distributed in the hope that it will be useful,
dd3b648e
RP
12but WITHOUT ANY WARRANTY; without even the implied warranty of
13MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14GNU General Public License for more details.
15
16You should have received a copy of the GNU General Public License
99a7de40
JG
17along with this program; if not, write to the Free Software
18Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */
dd3b648e 19
dd3b648e 20#include "defs.h"
dd3b648e
RP
21#include "command.h"
22#include "symtab.h"
23#include "value.h"
24#include "frame.h"
25#include "inferior.h"
26#include "wait.h"
27
28#include <signal.h>
29#include <fcntl.h>
30#include "gdbcore.h"
31
32#include <sys/param.h>
33#include <sys/dir.h>
34#include <sys/user.h>
35#include <sys/ioctl.h>
36#include <sys/pcntl.h>
37#include <sys/thread.h>
38#include <sys/proc.h>
39#include <sys/file.h>
40#include <sys/stat.h>
41#include <sys/mman.h>
42
43#include <convex/vmparam.h>
44#include <convex/filehdr.h>
45#include <convex/opthdr.h>
46#include <convex/scnhdr.h>
47#include <convex/core.h>
48
49/* Per-thread data, read from the inferior at each stop and written
50 back at each resume. */
51
52/* Number of active threads.
53 Tables are valid for thread numbers less than this. */
54
55static int n_threads;
56
57#define MAXTHREADS 8
58
59/* Thread state. The remaining data is valid only if this is PI_TALIVE. */
60
61static int thread_state[MAXTHREADS];
62
63/* Stop pc, signal, signal subcode */
64
65static int thread_pc[MAXTHREADS];
66static int thread_signal[MAXTHREADS];
67static int thread_sigcode[MAXTHREADS];
68
69/* Thread registers.
70 If thread is selected, the regs are in registers[] instead. */
71
72static char thread_regs[MAXTHREADS][REGISTER_BYTES];
73
74/* 1 if the top frame on the thread's stack was a context frame,
75 meaning that the kernel is up to something and we should not
76 touch the thread at all except to resume it. */
77
78static char thread_is_in_kernel[MAXTHREADS];
79
80/* The currently selected thread's number. */
81
82static int inferior_thread;
83
84/* Inferior process's file handle and a process control block
85 to feed args to ioctl with. */
86
87static int inferior_fd;
88static struct pcntl ps;
89
90/* SOFF file headers for exec or core file. */
91
92static FILEHDR filehdr;
93static OPTHDR opthdr;
94static SCNHDR scnhdr;
95
96/* Address maps constructed from section headers of exec and core files.
97 Defines process address -> file address translation. */
98
99struct pmap
100{
101 long mem_addr; /* process start address */
102 long mem_end; /* process end+1 address */
103 long file_addr; /* file start address */
104 long thread; /* -1 shared; 0,1,... thread-local */
105 long type; /* S_TEXT S_DATA S_BSS S_TBSS etc */
106 long which; /* used to sort map for info files */
107};
108
109static int n_exec, n_core;
110static struct pmap exec_map[100];
111static struct pmap core_map[100];
112
113/* Offsets in the core file of core_context and core_tcontext blocks. */
114
115static int context_offset;
116static int tcontext_offset[MAXTHREADS];
117
118/* Core file control blocks. */
119
120static struct core_context_v70 c;
121static struct core_tcontext_v70 tc;
122static struct user u;
123static thread_t th;
124static proc_t pr;
125
126/* The registers of the currently selected thread. */
127
128extern char registers[REGISTER_BYTES];
129
130/* Vector and communication registers from core dump or from inferior.
131 These are read on demand, ie, not normally valid. */
132
133static struct vecst vector_registers;
134static struct creg_ctx comm_registers;
135
136/* Flag, set on a vanilla CONT command and cleared when the inferior
137 is continued. */
138
139static int all_continue;
140
141/* Flag, set when the inferior is continued by a vanilla CONT command,
142 cleared if it is continued for any other purpose. */
143
144static int thread_switch_ok;
145
146/* Stack of signals recieved from threads but not yet delivered to gdb. */
147
148struct threadpid
149{
150 int pid;
151 int thread;
152 int signo;
153 int subsig;
154 int pc;
155};
156
157static struct threadpid signal_stack_bot[100];
158static struct threadpid *signal_stack = signal_stack_bot;
159
160/* How to detect empty stack -- bottom frame is all zero. */
161
162#define signal_stack_is_empty() (signal_stack->pid == 0)
163
164/* Mode controlled by SET PIPE command, controls the psw SEQ bit
165 which forces each instruction to complete before the next one starts. */
166
167static int sequential = 0;
168
169/* Mode controlled by the SET PARALLEL command. Values are:
170 0 concurrency limit 1 thread, dynamic scheduling
171 1 no concurrency limit, dynamic scheduling
172 2 no concurrency limit, fixed scheduling */
173
174static int parallel = 1;
175
176/* Mode controlled by SET BASE command, output radix for unformatted
177 integer typeout, as in argument lists, aggregates, and so on.
178 Zero means guess whether it's an address (hex) or not (decimal). */
179
180static int output_radix = 0;
181
182/* Signal subcode at last thread stop. */
183
184static int stop_sigcode;
185
186/* Hack, see wait() below. */
187
188static int exec_trap_timer;
189
190#include "gdbcmd.h"
191
192/* Nonzero if we are debugging an attached outside process
193 rather than an inferior. */
194
195extern int attach_flag;
196
197
198
199static struct type *vector_type ();
200static long *read_vector_register ();
201static long *read_vector_register_1 ();
202static void write_vector_register ();
203static REGISTER_TYPE read_comm_register ();
204static void write_comm_register ();
205static void convex_cont_command ();
206static void thread_continue ();
207static void select_thread ();
208static void scan_stack ();
209static void set_fixed_scheduling ();
210static char *subsig_name ();
211static void psw_info ();
212static sig_noop ();
213static ptr_cmp ();
214
dd3b648e
RP
215\f
216/* Execute ptrace. Convex V7 replaced ptrace with pattach.
217 Allow ptrace (0) as a no-op. */
218
219int
220call_ptrace (request, pid, procaddr, buf)
221 int request, pid, procaddr, buf;
222{
223 if (request == 0)
224 return;
225 error ("no ptrace");
226}
227
228/* Replacement for system execle routine.
229 Convert it to an equivalent exect, which pattach insists on. */
230
231execle (name, argv)
232 char *name, *argv;
233{
234 char ***envp = (char ***) &argv;
235 while (*envp++) ;
236
237 signal (SIGTRAP, sig_noop);
238 exect (name, &argv, *envp);
239}
240
241/* Stupid handler for stupid trace trap that otherwise causes
242 startup to stupidly hang. */
243
244static sig_noop ()
245{}
246
247/* Read registers from inferior into registers[] array.
248 For convex, they are already there, read in when the inferior stops. */
249
250void
251fetch_inferior_registers (regno)
252 int regno;
253{
254}
255
256/* Store our register values back into the inferior.
257 For Convex, do this only once, right before resuming inferior. */
258
1ab3bf1b 259void
dd3b648e
RP
260store_inferior_registers (regno)
261 int regno;
262{
263}
264
265/* Copy LEN bytes from inferior's memory starting at MEMADDR
266 to debugger memory starting at MYADDR.
267 On failure (cannot read from inferior, usually because address is out
268 of bounds) returns the value of errno. */
269
270int
271read_inferior_memory (memaddr, myaddr, len)
272 CORE_ADDR memaddr;
273 char *myaddr;
274 int len;
275{
276 errno = 0;
277 while (len > 0)
278 {
279 /* little-known undocumented max request size */
280 int i = (len < 12288) ? len : 12288;
281
282 lseek (inferior_fd, memaddr, 0);
283 read (inferior_fd, myaddr, i);
284
285 memaddr += i;
286 myaddr += i;
287 len -= i;
288 }
289 if (errno)
290 bzero (myaddr, len);
291 return errno;
292}
293
294/* Copy LEN bytes of data from debugger memory at MYADDR
295 to inferior's memory at MEMADDR.
296 Returns errno on failure (cannot write the inferior) */
297
298int
299write_inferior_memory (memaddr, myaddr, len)
300 CORE_ADDR memaddr;
301 char *myaddr;
302 int len;
303{
304 errno = 0;
305 lseek (inferior_fd, memaddr, 0);
306 write (inferior_fd, myaddr, len);
307 return errno;
308}
309
310/* Here from create_inferior when the inferior process has been created
311 and started up. We must do a pattach to grab it for debugging.
312
313 Also, intercept the CONT command by altering its dispatch address. */
314
315create_inferior_hook (pid)
316 int pid;
317{
318 static char cont[] = "cont";
319 static char cont1[] = "c";
320 char *linep = cont;
321 char *linep1 = cont1;
322 char **line = &linep;
323 char **line1 = &linep1;
324 struct cmd_list_element *c;
325
326 c = lookup_cmd (line, cmdlist, "", 0);
327 c->function = convex_cont_command;
328 c = lookup_cmd (line1, cmdlist, "", 0);
329 c->function = convex_cont_command;
330
331 inferior_fd = pattach (pid, O_EXCL);
332 if (inferior_fd < 0)
333 perror_with_name ("pattach");
334 inferior_thread = 0;
335 set_fixed_scheduling (pid, parallel == 2);
336}
337
338/* Attach process PID for debugging. */
339
340attach (pid)
341 int pid;
342{
343 int fd = pattach (pid, O_EXCL);
344 if (fd < 0)
345 perror_with_name ("pattach");
346 attach_flag = 1;
347 /* wait for strange kernel reverberations to go away */
348 sleep (1);
349
350 setpgrp (pid, pid);
351
352 inferior_fd = fd;
353 inferior_thread = 0;
354 return pid;
355}
356
357/* Stop debugging the process whose number is PID
358 and continue it with signal number SIGNAL.
359 SIGNAL = 0 means just continue it. */
360
361void
362detach (signal)
363 int signal;
364{
365 signal_stack = signal_stack_bot;
366 thread_continue (-1, 0, signal);
367 ioctl (inferior_fd, PIXDETACH, &ps);
368 close (inferior_fd);
369 inferior_fd = 0;
370 attach_flag = 0;
371}
372
373/* Kill off the inferior process. */
374
375kill_inferior ()
376{
377 if (inferior_pid == 0)
378 return;
379 ioctl (inferior_fd, PIXTERMINATE, 0);
380 wait (0);
381 target_mourn_inferior ();
382}
383
384/* This is used when GDB is exiting. It gives less chance of error.*/
385
386kill_inferior_fast ()
387{
388 if (inferior_pid == 0)
389 return;
390 ioctl (inferior_fd, PIXTERMINATE, 0);
391 wait (0);
392}
393
394/* Read vector register REG, and return a pointer to the value. */
395
396static long *
397read_vector_register (reg)
398 int reg;
399{
400 if (have_inferior_p ())
401 {
402 errno = 0;
403 ps.pi_buffer = (char *) &vector_registers;
404 ps.pi_nbytes = sizeof vector_registers;
405 ps.pi_offset = 0;
406 ps.pi_thread = inferior_thread;
407 ioctl (inferior_fd, PIXRDVREGS, &ps);
408 if (errno)
409 bzero (&vector_registers, sizeof vector_registers);
410 }
411 else if (corechan >= 0)
412 {
413 lseek (corechan, tcontext_offset[inferior_thread], 0);
414 if (myread (corechan, &tc, sizeof tc) < 0)
415 perror_with_name (corefile);
416 lseek (corechan, tc.core_thread_p, 0);
417 if (myread (corechan, &th, sizeof th) < 0)
418 perror_with_name (corefile);
419 lseek (corechan, tc.core_vregs_p, 0);
420 if (myread (corechan, &vector_registers, 16*128) < 0)
421 perror_with_name (corefile);
422 vector_registers.vm[0] = th.t_vect_ctx.vc_vm[0];
423 vector_registers.vm[1] = th.t_vect_ctx.vc_vm[1];
424 vector_registers.vls = th.t_vect_ctx.vc_vls;
425 }
426
427 return read_vector_register_1 (reg);
428}
429
430/* Return a pointer to vector register REG, which must already have been
431 fetched from the inferior or core file. */
432
433static long *
434read_vector_register_1 (reg)
435 int reg;
436{
437 switch (reg)
438 {
439 case VM_REGNUM:
440 return (long *) vector_registers.vm;
441 case VS_REGNUM:
442 return (long *) &vector_registers.vls;
443 case VL_REGNUM:
444 return 1 + (long *) &vector_registers.vls;
445 default:
446 return (long *) &vector_registers.vr[reg];
447 }
448}
449
450/* Write vector register REG, element ELEMENT, new value VAL.
451 NB: must use read-modify-write on the entire vector state,
452 since pattach does not do offsetted writes correctly. */
453
454static void
455write_vector_register (reg, element, val)
456 int reg, element;
457 REGISTER_TYPE val;
458{
459 if (have_inferior_p ())
460 {
461 errno = 0;
462 ps.pi_thread = inferior_thread;
463 ps.pi_offset = 0;
464 ps.pi_buffer = (char *) &vector_registers;
465 ps.pi_nbytes = sizeof vector_registers;
466
467 ioctl (inferior_fd, PIXRDVREGS, &ps);
468
469 switch (reg)
470 {
471 case VL_REGNUM:
472 vector_registers.vls =
473 (vector_registers.vls & 0xffffffff00000000LL)
474 + (unsigned long) val;
475 break;
476
477 case VS_REGNUM:
478 vector_registers.vls =
479 (val << 32) + (unsigned long) vector_registers.vls;
480 break;
481
482 default:
483 vector_registers.vr[reg].el[element] = val;
484 break;
485 }
486
487 ioctl (inferior_fd, PIXWRVREGS, &ps);
488
489 if (errno)
490 perror_with_name ("writing vector register");
491 }
492}
493
494/* Return the contents of communication register NUM. */
495
496static REGISTER_TYPE
497read_comm_register (num)
498 int num;
499{
500 if (have_inferior_p ())
501 {
502 ps.pi_buffer = (char *) &comm_registers;
503 ps.pi_nbytes = sizeof comm_registers;
504 ps.pi_offset = 0;
505 ps.pi_thread = inferior_thread;
506 ioctl (inferior_fd, PIXRDCREGS, &ps);
507 }
508 return comm_registers.crreg.r4[num];
509}
510
511/* Store a new value VAL into communication register NUM.
512 NB: Must use read-modify-write on the whole comm register set
513 since pattach does not do offsetted writes correctly. */
514
515static void
516write_comm_register (num, val)
517 int num;
518 REGISTER_TYPE val;
519{
520 if (have_inferior_p ())
521 {
522 ps.pi_buffer = (char *) &comm_registers;
523 ps.pi_nbytes = sizeof comm_registers;
524 ps.pi_offset = 0;
525 ps.pi_thread = inferior_thread;
526 ioctl (inferior_fd, PIXRDCREGS, &ps);
527 comm_registers.crreg.r4[num] = val;
528 ioctl (inferior_fd, PIXWRCREGS, &ps);
529 }
530}
531
532/* Resume execution of the inferior process.
533 If STEP is nonzero, single-step it.
534 If SIGNAL is nonzero, give it that signal. */
535
536void
537resume (step, signal)
538 int step;
539 int signal;
540{
541 errno = 0;
542 if (step || signal)
543 thread_continue (inferior_thread, step, signal);
544 else
545 thread_continue (-1, 0, 0);
546}
547
548/* Maybe resume some threads.
549 THREAD is which thread to resume, or -1 to resume them all.
550 STEP and SIGNAL are as in resume.
551
552 Global variable ALL_CONTINUE is set when we are here to do a
553 `cont' command; otherwise we may be doing `finish' or a call or
554 something else that will not tolerate an automatic thread switch.
555
556 If there are stopped threads waiting to deliver signals, and
557 ALL_CONTINUE, do not actually resume anything. gdb will do a wait
558 and see one of the stopped threads in the queue. */
559
560static void
561thread_continue (thread, step, signal)
562 int thread, step, signal;
563{
564 int n;
565
566 /* If we are to continue all threads, but not for the CONTINUE command,
567 pay no attention and continue only the selected thread. */
568
569 if (thread < 0 && ! all_continue)
570 thread = inferior_thread;
571
572 /* If we are not stepping, we have now executed the continue part
573 of a CONTINUE command. */
574
575 if (! step)
576 all_continue = 0;
577
578 /* Allow wait() to switch threads if this is an all-out continue. */
579
580 thread_switch_ok = thread < 0;
581
582 /* If there are threads queued up, don't resume. */
583
584 if (thread_switch_ok && ! signal_stack_is_empty ())
585 return;
586
587 /* OK, do it. */
588
589 for (n = 0; n < n_threads; n++)
590 if (thread_state[n] == PI_TALIVE)
591 {
592 select_thread (n);
593
594 if ((thread < 0 || n == thread) && ! thread_is_in_kernel[n])
595 {
596 /* Blam the trace bits in the stack's saved psws to match
597 the desired step mode. This is required so that
598 single-stepping a return doesn't restore a psw with a
599 clear trace bit and fly away, and conversely,
600 proceeding through a return in a routine that was
601 stepped into doesn't cause a phantom break by restoring
602 a psw with the trace bit set. */
603 scan_stack (PSW_T_BIT, step);
604 scan_stack (PSW_S_BIT, sequential);
605 }
606
607 ps.pi_buffer = registers;
608 ps.pi_nbytes = REGISTER_BYTES;
609 ps.pi_offset = 0;
610 ps.pi_thread = n;
611 if (! thread_is_in_kernel[n])
612 if (ioctl (inferior_fd, PIXWRREGS, &ps))
613 perror_with_name ("PIXWRREGS");
614
615 if (thread < 0 || n == thread)
616 {
617 ps.pi_pc = 1;
618 ps.pi_signo = signal;
619 if (ioctl (inferior_fd, step ? PIXSTEP : PIXCONTINUE, &ps) < 0)
620 perror_with_name ("PIXCONTINUE");
621 }
622 }
623
624 if (ioctl (inferior_fd, PIXRUN, &ps) < 0)
625 perror_with_name ("PIXRUN");
626}
627
628/* Replacement for system wait routine.
629
630 The system wait returns with one or more threads stopped by
631 signals. Put stopped threads on a stack and return them one by
632 one, so that it appears that wait returns one thread at a time.
633
634 Global variable THREAD_SWITCH_OK is set when gdb can tolerate wait
635 returning a new thread. If it is false, then only one thread is
636 running; we will do a real wait, the thread will do something, and
637 we will return that. */
638
639pid_t
640wait (w)
641 union wait *w;
642{
643 int pid;
644
645 if (!w)
646 return wait3 (0, 0, 0);
647
648 /* Do a real wait if we were told to, or if there are no queued threads. */
649
650 if (! thread_switch_ok || signal_stack_is_empty ())
651 {
652 int thread;
653
654 pid = wait3 (w, 0, 0);
655
656 if (!WIFSTOPPED (*w) || pid != inferior_pid)
657 return pid;
658
659 /* The inferior has done something and stopped. Read in all the
660 threads' registers, and queue up any signals that happened. */
661
662 if (ioctl (inferior_fd, PIXGETTHCOUNT, &ps) < 0)
663 perror_with_name ("PIXGETTHCOUNT");
664
665 n_threads = ps.pi_othdcnt;
666 for (thread = 0; thread < n_threads; thread++)
667 {
668 ps.pi_thread = thread;
669 if (ioctl (inferior_fd, PIXGETSUBCODE, &ps) < 0)
670 perror_with_name ("PIXGETSUBCODE");
671 thread_state[thread] = ps.pi_otstate;
672
673 if (ps.pi_otstate == PI_TALIVE)
674 {
675 select_thread (thread);
676 ps.pi_buffer = registers;
677 ps.pi_nbytes = REGISTER_BYTES;
678 ps.pi_offset = 0;
679 ps.pi_thread = thread;
680 if (ioctl (inferior_fd, PIXRDREGS, &ps) < 0)
681 perror_with_name ("PIXRDREGS");
682
683 registers_fetched ();
684
685 thread_pc[thread] = read_pc ();
686 thread_signal[thread] = ps.pi_osigno;
687 thread_sigcode[thread] = ps.pi_osigcode;
688
689 /* If the thread's stack has a context frame
690 on top, something fucked is going on. I do not
691 know what, but do I know this: the only thing you
692 can do with such a thread is continue it. */
693
694 thread_is_in_kernel[thread] =
695 ((read_register (PS_REGNUM) >> 25) & 3) == 0;
696
697 /* Signals push an extended frame and then fault
698 with a ridiculous pc. Pop the frame. */
699
700 if (thread_pc[thread] > STACK_END_ADDR)
701 {
702 POP_FRAME;
703 if (is_break_pc (thread_pc[thread]))
704 thread_pc[thread] = read_pc () - 2;
705 else
706 thread_pc[thread] = read_pc ();
707 write_register (PC_REGNUM, thread_pc[thread]);
708 }
709
710 if (ps.pi_osigno || ps.pi_osigcode)
711 {
712 signal_stack++;
713 signal_stack->pid = pid;
714 signal_stack->thread = thread;
715 signal_stack->signo = thread_signal[thread];
716 signal_stack->subsig = thread_sigcode[thread];
717 signal_stack->pc = thread_pc[thread];
718 }
719
720 /* The following hackery is caused by a unix 7.1 feature:
721 the inferior's fixed scheduling mode is cleared when
722 it execs the shell (since the shell is not a parallel
723 program). So, note the 5.4 trap we get when
724 the shell does its exec, then catch the 5.0 trap
725 that occurs when the debuggee starts, and set fixed
726 scheduling mode properly. */
727
728 if (ps.pi_osigno == 5 && ps.pi_osigcode == 4)
729 exec_trap_timer = 1;
730 else
731 exec_trap_timer--;
732
733 if (ps.pi_osigno == 5 && exec_trap_timer == 0)
734 set_fixed_scheduling (pid, parallel == 2);
735 }
736 }
737
738 if (signal_stack_is_empty ())
739 error ("no active threads?!");
740 }
741
742 /* Select the thread that stopped, and return *w saying why. */
743
744 select_thread (signal_stack->thread);
745
746 stop_signal = signal_stack->signo;
747 stop_sigcode = signal_stack->subsig;
748
749 WSETSTOP (*w, signal_stack->signo);
750 w->w_thread = signal_stack->thread;
751 return (signal_stack--)->pid;
752}
753
754/* Select thread THREAD -- its registers, stack, per-thread memory.
755 This is the only routine that may assign to inferior_thread
756 or thread_regs[]. */
757
758static void
759select_thread (thread)
760 int thread;
761{
762 if (thread == inferior_thread)
763 return;
764
765 bcopy (registers, thread_regs[inferior_thread], REGISTER_BYTES);
766 ps.pi_thread = inferior_thread = thread;
767 if (have_inferior_p ())
768 ioctl (inferior_fd, PISETRWTID, &ps);
769 bcopy (thread_regs[thread], registers, REGISTER_BYTES);
770}
771
772/* Routine to set or clear a psw bit in the psw and also all psws
773 saved on the stack. Quits when we get to a frame in which the
774 saved psw is correct. */
775
776static void
777scan_stack (bit, val)
778 long bit, val;
779{
780 long ps = read_register (PS_REGNUM);
781 long fp;
782 if (val ? !(ps & bit) : (ps & bit))
783 {
784 ps ^= bit;
785 write_register (PS_REGNUM, ps);
786
787 fp = read_register (FP_REGNUM);
788 while (fp & 0x80000000)
789 {
790 ps = read_memory_integer (fp + 4, 4);
791 if (val ? (ps & bit) : !(ps & bit))
792 break;
793 ps ^= bit;
794 write_memory (fp + 4, &ps, 4);
795 fp = read_memory_integer (fp + 8, 4);
796 }
797 }
798}
799
800/* Set fixed scheduling (alliant mode) of process PID to ARG (0 or 1). */
801
802static void
803set_fixed_scheduling (pid, arg)
804 int arg;
805{
806 struct pattributes pattr;
807 getpattr (pid, &pattr);
808 pattr.pattr_pfixed = arg;
809 setpattr (pid, &pattr);
810}
811\f
812void
813core_file_command (filename, from_tty)
814 char *filename;
815 int from_tty;
816{
817 int n;
818
819 /* Discard all vestiges of any previous core file
820 and mark data and stack spaces as empty. */
821
822 if (corefile)
823 free (corefile);
824 corefile = 0;
825
826 if (corechan >= 0)
827 close (corechan);
828 corechan = -1;
829
830 data_start = 0;
831 data_end = 0;
832 stack_start = STACK_END_ADDR;
833 stack_end = STACK_END_ADDR;
834 n_core = 0;
835
836 /* Now, if a new core file was specified, open it and digest it. */
837
838 if (filename)
839 {
840 filename = tilde_expand (filename);
841 make_cleanup (free, filename);
842
843 if (have_inferior_p ())
844 error ("To look at a core file, you must kill the inferior with \"kill\".");
845 corechan = open (filename, O_RDONLY, 0);
846 if (corechan < 0)
847 perror_with_name (filename);
848
849 if (myread (corechan, &filehdr, sizeof filehdr) < 0)
850 perror_with_name (filename);
851
852 if (!IS_CORE_SOFF_MAGIC (filehdr.h_magic))
853 error ("%s: not a core file.\n", filename);
854
855 if (myread (corechan, &opthdr, filehdr.h_opthdr) < 0)
856 perror_with_name (filename);
857
858 /* Read through the section headers.
859 For text, data, etc, record an entry in the core file map.
860 For context and tcontext, record the file address of
861 the context blocks. */
862
863 lseek (corechan, (long) filehdr.h_scnptr, 0);
864
865 n_threads = 0;
866 for (n = 0; n < filehdr.h_nscns; n++)
867 {
868 if (myread (corechan, &scnhdr, sizeof scnhdr) < 0)
869 perror_with_name (filename);
870 if ((scnhdr.s_flags & S_TYPMASK) >= S_TEXT
871 && (scnhdr.s_flags & S_TYPMASK) <= S_COMON)
872 {
873 core_map[n_core].mem_addr = scnhdr.s_vaddr;
874 core_map[n_core].mem_end = scnhdr.s_vaddr + scnhdr.s_size;
875 core_map[n_core].file_addr = scnhdr.s_scnptr;
876 core_map[n_core].type = scnhdr.s_flags & S_TYPMASK;
877 if (core_map[n_core].type != S_TBSS
878 && core_map[n_core].type != S_TDATA
879 && core_map[n_core].type != S_TTEXT)
880 core_map[n_core].thread = -1;
881 else if (n_core == 0
882 || core_map[n_core-1].mem_addr != scnhdr.s_vaddr)
883 core_map[n_core].thread = 0;
884 else
885 core_map[n_core].thread = core_map[n_core-1].thread + 1;
886 n_core++;
887 }
888 else if ((scnhdr.s_flags & S_TYPMASK) == S_CONTEXT)
889 context_offset = scnhdr.s_scnptr;
890 else if ((scnhdr.s_flags & S_TYPMASK) == S_TCONTEXT)
891 tcontext_offset[n_threads++] = scnhdr.s_scnptr;
892 }
893
894 /* Read the context block, struct user, struct proc,
895 and the comm regs. */
896
897 lseek (corechan, context_offset, 0);
898 if (myread (corechan, &c, sizeof c) < 0)
899 perror_with_name (filename);
900 lseek (corechan, c.core_user_p, 0);
901 if (myread (corechan, &u, sizeof u) < 0)
902 perror_with_name (filename);
903 lseek (corechan, c.core_proc_p, 0);
904 if (myread (corechan, &pr, sizeof pr) < 0)
905 perror_with_name (filename);
906 comm_registers = pr.p_creg;
907
908 /* Core file apparently is really there. Make it really exist
909 for xfer_core_file so we can do read_memory on it. */
910
911 if (filename[0] == '/')
912 corefile = savestring (filename, strlen (filename));
913 else
58ae87f6 914 corefile = concat (current_directory, "/", filename, NULL);
dd3b648e
RP
915
916 printf_filtered ("Program %s ", u.u_comm);
917
918 /* Read the thread registers and fill in the thread_xxx[] data. */
919
920 for (n = 0; n < n_threads; n++)
921 {
922 select_thread (n);
923
924 lseek (corechan, tcontext_offset[n], 0);
925 if (myread (corechan, &tc, sizeof tc) < 0)
926 perror_with_name (corefile);
927 lseek (corechan, tc.core_thread_p, 0);
928 if (myread (corechan, &th, sizeof th) < 0)
929 perror_with_name (corefile);
930
931 lseek (corechan, tc.core_syscall_context_p, 0);
932 if (myread (corechan, registers, REGISTER_BYTES) < 0)
933 perror_with_name (corefile);
934
935 thread_signal[n] = th.t_cursig;
936 thread_sigcode[n] = th.t_code;
937 thread_state[n] = th.t_state;
938 thread_pc[n] = read_pc ();
939
940 if (thread_pc[n] > STACK_END_ADDR)
941 {
942 POP_FRAME;
943 if (is_break_pc (thread_pc[n]))
944 thread_pc[n] = read_pc () - 2;
945 else
946 thread_pc[n] = read_pc ();
947 write_register (PC_REGNUM, thread_pc[n]);
948 }
949
950 printf_filtered ("thread %d received signal %d, %s\n",
951 n, thread_signal[n],
4ace50a5 952 safe_strsignal (thread_signal[n]));
dd3b648e
RP
953 }
954
955 /* Select an interesting thread -- also-rans died with SIGKILL,
956 so find one that didn't. */
957
958 for (n = 0; n < n_threads; n++)
959 if (thread_signal[n] != 0 && thread_signal[n] != SIGKILL)
960 {
961 select_thread (n);
962 stop_signal = thread_signal[n];
963 stop_sigcode = thread_sigcode[n];
964 break;
965 }
966
967 core_aouthdr.a_magic = 0;
968
969 flush_cached_frames ();
970 set_current_frame (create_new_frame (read_register (FP_REGNUM),
971 read_pc ()));
972 select_frame (get_current_frame (), 0);
973 validate_files ();
974
cadbb07a 975 print_stack_frame (selected_frame, selected_frame_level, -1);
dd3b648e
RP
976 }
977 else if (from_tty)
978 printf_filtered ("No core file now.\n");
979}
This page took 0.088446 seconds and 4 git commands to generate.