* Makefile.in (VERSION): Roll to 4.6.8.
[deliverable/binutils-gdb.git] / gdb / hppabsd-core.c
CommitLineData
7da1e27d
SG
1/* Machine-dependent code which would otherwise be in core.c
2 for GDB, the GNU debugger. This code is for the HP PA-RISC cpu.
5140562f 3 Copyright 1986, 1987, 1989, 1990, 1991, 1992 Free Software Foundation, Inc.
7da1e27d
SG
4
5 Contributed by the Center for Software Science at the
6 University of Utah (pa-gdb-bugs@cs.utah.edu).
7
8This file is part of GDB.
9
5140562f 10This program is free software; you can redistribute it and/or modify
7da1e27d 11it under the terms of the GNU General Public License as published by
5140562f
JG
12the Free Software Foundation; either version 2 of the License, or
13(at your option) any later version.
7da1e27d 14
5140562f 15This program is distributed in the hope that it will be useful,
7da1e27d
SG
16but WITHOUT ANY WARRANTY; without even the implied warranty of
17MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
18GNU General Public License for more details.
19
20You should have received a copy of the GNU General Public License
5140562f
JG
21along with this program; if not, write to the Free Software
22Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */
7da1e27d 23
7da1e27d 24#include "defs.h"
7da1e27d
SG
25#include "frame.h"
26#include "inferior.h"
27
28#ifdef USG
29#include <sys/types.h>
30#endif
31
32#include <sys/param.h>
33#include <sys/dir.h>
34#include <signal.h>
35#include <sys/ioctl.h>
36/* #include <fcntl.h> Can we live without this? */
37
38#ifndef hpux
39#include <a.out.h>
40#include <machine/pcb.h>
41#include <sys/time.h>
42#include "/usr/src/sys/hpux/hpux.h"
43#define USRSTACK 0x68FF3000
44#else
45#include <sys/user.h> /* After a.out.h */
46#endif
47
48#include <sys/file.h>
49#include <sys/stat.h>
50#include <sys/ptrace.h>
51
52#ifndef hpux
53#undef USIZE
54#undef UPAGES
55
56#define USIZE 3
57#define UPAGES 7
58#endif
59
60extern int errno;
61
62/* File names of core file and executable file. */
63
64extern char *corefile;
65extern char *execfile;
66
67/* Descriptors on which core file and executable file are open.
68 Note that the execchan is closed when an inferior is created
69 and reopened if the inferior dies or is killed. */
70
71extern int corechan;
72extern int execchan;
73
74/* Last modification time of executable file.
75 Also used in source.c to compare against mtime of a source file. */
76
77extern int exec_mtime;
78
79/* Virtual addresses of bounds of the two areas of memory in the core file. */
80
81extern CORE_ADDR data_start;
82extern CORE_ADDR data_end;
83extern CORE_ADDR stack_start;
84extern CORE_ADDR stack_end;
85
86/* Virtual addresses of bounds of two areas of memory in the exec file.
87 Note that the data area in the exec file is used only when there is no core file. */
88
89extern CORE_ADDR text_start;
90extern CORE_ADDR text_end;
91
92extern CORE_ADDR exec_data_start;
93extern CORE_ADDR exec_data_end;
94
95/* Address in executable file of start of text area data. */
96
97extern int text_offset;
98
99/* Address in executable file of start of data area data. */
100
101extern int exec_data_offset;
102
103/* Address in core file of start of data area data. */
104
105extern int data_offset;
106
107/* Address in core file of start of stack area data. */
108
109extern int stack_offset;
110
111extern struct header file_hdr;
112extern struct som_exec_auxhdr exec_hdr;
113
114extern int (*core_file_hook)();
115
116#ifdef KERNELDEBUG
117
118extern int kernel_debugging;
119extern int kernel_core_file_hook();
120
121#endif
122
123core_file_command (filename, from_tty)
124 char *filename;
125 int from_tty;
126{
127 int val;
128 extern char registers[];
129#ifdef KERNELDEBUG
130 struct stat stb;
131#endif
132
133 /* Discard all vestiges of any previous core file
134 and mark data and stack spaces as empty. */
135
136 if (corefile)
137 free (corefile);
138 corefile = 0;
139 core_file_hook = 0;
140
141 if (corechan >= 0)
142 close (corechan);
143 corechan = -1;
144
145 data_start = 0;
146 data_end = 0;
147 stack_start = STACK_END_ADDR;
148 stack_end = STACK_END_ADDR;
149
150 /* Now, if a new core file was specified, open it and digest it. */
151
152 if (filename)
153 {
154 filename = tilde_expand (filename);
155 make_cleanup (free, filename);
156
157 if (have_inferior_p ())
158 error ("To look at a core file, you must kill the inferior with \"kill\".");
159 corechan = open (filename, O_RDONLY, 0);
160 if (corechan < 0)
161 perror_with_name (filename);
162
163#ifdef KERNELDEBUG
164 fstat(corechan, &stb);
165
166 if (kernel_debugging) {
167 setup_kernel_debugging();
168 core_file_hook = kernel_core_file_hook;
169 set_kernel_boundaries();
170 } else if ((stb.st_mode & S_IFMT) == S_IFCHR &&
171 stb.st_rdev == makedev(2, 1)) {
172 /* looking at /dev/kmem */
173 data_offset = data_start = KERNBASE;
174 data_end = ~0; /* XXX */
175 stack_end = stack_start = data_end;
176 set_kernel_boundaries();
177 } else
178#endif
179 {
180 /* HP PA-RISC style corefile. */
181#ifndef hpux
182 struct hpuxuser u;
183#else
184 struct user u;
185#endif
186
187 unsigned int reg_offset;
188
189 val = myread (corechan, &u, sizeof u);
190 if (val < 0)
191 perror_with_name ("Not a core file: reading upage");
192 if (val != sizeof u)
193 error ("Not a core file: could only read %d bytes", val);
194
195 /* We are depending on exec_file_command having been called
196 previously to set exec_data_start. Since the executable
197 and the core file share the same text segment, the address
198 of the data segment will be the same in both. */
199 data_start = exec_data_start;
200
201 data_end = data_start + NBPG * u.u_dsize;
202 stack_start = USRSTACK; /* from sys/param.h */
203 stack_end = stack_start + NBPG * u.u_ssize;
204 data_offset = NBPG * UPAGES;
205 stack_offset = NBPG * (UPAGES + u.u_dsize);
206
207 /* Some machines put an absolute address in here and some put
208 the offset in the upage of the regs. */
209 reg_offset = NBPG * USIZE;
210 /* Read the register values out of the core file and store
211 them where `read_register' will find them. */
212
213 {
214 register int regno;
215
216 for (regno = 0; regno < NUM_REGS; regno++)
217 {
218 unsigned char buf[MAX_REGISTER_RAW_SIZE];
219
220 val = lseek (corechan, register_addr (regno, reg_offset), 0);
221 if (val < 0
222 || (val = myread (corechan, buf, sizeof buf)) < 0)
223 {
224 char * buffer = (char *) alloca (strlen (reg_names[regno])
225 + 30);
226 strcpy (buffer, "Reading register ");
227 strcat (buffer, reg_names[regno]);
228
229 perror_with_name (buffer);
230 }
231 if (regno == PCOQ_HEAD_REGNUM || regno == PCOQ_TAIL_REGNUM)
232 buf[3] &= ~0x3;
233 supply_register (regno, buf);
234 }
235 }
236 }
237 if (filename[0] == '/')
238 corefile = savestring (filename, strlen (filename));
239 else
240 {
241 corefile = concat (current_directory, "/", filename);
242 }
243
244 set_current_frame ( create_new_frame (read_register (FP_REGNUM),
245 read_pc ()));
246 select_frame (get_current_frame (), 0);
247 validate_files ();
248 }
249 else if (from_tty)
250 printf ("No core file now.\n");
251}
This page took 0.041854 seconds and 4 git commands to generate.