annotate agent/src/os/bsd/ps_core.c @ 17716:cdb71841f4bc

6498581: ThreadInterruptTest3 produces wrong output on Windows Summary: There is race condition between os::interrupt and os::is_interrupted on Windows. In JVM_Sleep(Thread.sleep), check if thread gets interrupted, it may see interrupted but not really interrupted so cause spurious waking up (early return from sleep). Fix by checking if interrupt event really gets set thus prevent false return. For intrinsic of _isInterrupted, on Windows, go fastpath only on bit not set. Reviewed-by: acorn, kvn Contributed-by: david.holmes@oracle.com, yumin.qi@oracle.com
author minqi
date Wed, 26 Feb 2014 15:20:41 -0800
parents 5705c7ee6dd7
children
Ignore whitespace changes - Everywhere: Within whitespace: At end of lines:
rev   line source
3960
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1 /*
8750
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
2 * Copyright (c) 2003, 2013, Oracle and/or its affiliates. All rights reserved.
3960
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
3 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
4 *
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
5 * This code is free software; you can redistribute it and/or modify it
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
6 * under the terms of the GNU General Public License version 2 only, as
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
7 * published by the Free Software Foundation.
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
8 *
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
9 * This code is distributed in the hope that it will be useful, but WITHOUT
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
10 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
11 * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
12 * version 2 for more details (a copy is included in the LICENSE file that
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
13 * accompanied this code).
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
14 *
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
15 * You should have received a copy of the GNU General Public License version
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
16 * 2 along with this work; if not, write to the Free Software Foundation,
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
17 * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
18 *
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
19 * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
20 * or visit www.oracle.com if you need additional information or have any
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
21 * questions.
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
22 *
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
23 */
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
24
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
25 #include <jni.h>
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
26 #include <unistd.h>
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
27 #include <fcntl.h>
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
28 #include <string.h>
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
29 #include <stdlib.h>
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
30 #include <stddef.h>
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
31 #include "libproc_impl.h"
8750
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
32
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
33 #ifdef __APPLE__
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
34 #include "sun_jvm_hotspot_debugger_amd64_AMD64ThreadContext.h"
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
35 #endif
3960
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
36
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
37 // This file has the libproc implementation to read core files.
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
38 // For live processes, refer to ps_proc.c. Portions of this is adapted
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
39 // /modelled after Solaris libproc.so (in particular Pcore.c)
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
40
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
41 //----------------------------------------------------------------------
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
42 // ps_prochandle cleanup helper functions
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
43
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
44 // close all file descriptors
8750
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
45 static void close_files(struct ps_prochandle* ph) {
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
46 lib_info* lib = NULL;
12807
5705c7ee6dd7 8025250: SA: Sync linux and bsd versions of ps_core file
dsamersoff
parents: 10229
diff changeset
47
8750
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
48 // close core file descriptor
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
49 if (ph->core->core_fd >= 0)
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
50 close(ph->core->core_fd);
3960
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
51
8750
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
52 // close exec file descriptor
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
53 if (ph->core->exec_fd >= 0)
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
54 close(ph->core->exec_fd);
3960
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
55
8750
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
56 // close interp file descriptor
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
57 if (ph->core->interp_fd >= 0)
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
58 close(ph->core->interp_fd);
3960
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
59
8750
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
60 // close class share archive file
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
61 if (ph->core->classes_jsa_fd >= 0)
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
62 close(ph->core->classes_jsa_fd);
3960
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
63
8750
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
64 // close all library file descriptors
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
65 lib = ph->libs;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
66 while (lib) {
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
67 int fd = lib->fd;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
68 if (fd >= 0 && fd != ph->core->exec_fd) {
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
69 close(fd);
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
70 }
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
71 lib = lib->next;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
72 }
3960
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
73 }
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
74
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
75 // clean all map_info stuff
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
76 static void destroy_map_info(struct ps_prochandle* ph) {
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
77 map_info* map = ph->core->maps;
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
78 while (map) {
8750
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
79 map_info* next = map->next;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
80 free(map);
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
81 map = next;
3960
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
82 }
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
83
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
84 if (ph->core->map_array) {
8750
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
85 free(ph->core->map_array);
3960
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
86 }
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
87
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
88 // Part of the class sharing workaround
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
89 map = ph->core->class_share_maps;
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
90 while (map) {
8750
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
91 map_info* next = map->next;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
92 free(map);
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
93 map = next;
3960
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
94 }
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
95 }
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
96
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
97 // ps_prochandle operations
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
98 static void core_release(struct ps_prochandle* ph) {
8750
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
99 if (ph->core) {
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
100 close_files(ph);
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
101 destroy_map_info(ph);
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
102 free(ph->core);
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
103 }
3960
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
104 }
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
105
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
106 static map_info* allocate_init_map(int fd, off_t offset, uintptr_t vaddr, size_t memsz) {
8750
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
107 map_info* map;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
108 if ( (map = (map_info*) calloc(1, sizeof(map_info))) == NULL) {
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
109 print_debug("can't allocate memory for map_info\n");
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
110 return NULL;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
111 }
3960
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
112
8750
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
113 // initialize map
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
114 map->fd = fd;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
115 map->offset = offset;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
116 map->vaddr = vaddr;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
117 map->memsz = memsz;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
118 return map;
3960
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
119 }
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
120
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
121 // add map info with given fd, offset, vaddr and memsz
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
122 static map_info* add_map_info(struct ps_prochandle* ph, int fd, off_t offset,
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
123 uintptr_t vaddr, size_t memsz) {
8750
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
124 map_info* map;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
125 if ((map = allocate_init_map(fd, offset, vaddr, memsz)) == NULL) {
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
126 return NULL;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
127 }
3960
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
128
8750
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
129 // add this to map list
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
130 map->next = ph->core->maps;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
131 ph->core->maps = map;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
132 ph->core->num_maps++;
3960
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
133
8750
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
134 return map;
3960
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
135 }
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
136
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
137 // Part of the class sharing workaround
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
138 static map_info* add_class_share_map_info(struct ps_prochandle* ph, off_t offset,
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
139 uintptr_t vaddr, size_t memsz) {
8750
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
140 map_info* map;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
141 if ((map = allocate_init_map(ph->core->classes_jsa_fd,
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
142 offset, vaddr, memsz)) == NULL) {
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
143 return NULL;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
144 }
3960
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
145
8750
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
146 map->next = ph->core->class_share_maps;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
147 ph->core->class_share_maps = map;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
148 return map;
3960
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
149 }
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
150
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
151 // Return the map_info for the given virtual address. We keep a sorted
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
152 // array of pointers in ph->map_array, so we can binary search.
12807
5705c7ee6dd7 8025250: SA: Sync linux and bsd versions of ps_core file
dsamersoff
parents: 10229
diff changeset
153 static map_info* core_lookup(struct ps_prochandle *ph, uintptr_t addr) {
8750
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
154 int mid, lo = 0, hi = ph->core->num_maps - 1;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
155 map_info *mp;
3960
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
156
8750
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
157 while (hi - lo > 1) {
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
158 mid = (lo + hi) / 2;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
159 if (addr >= ph->core->map_array[mid]->vaddr) {
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
160 lo = mid;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
161 } else {
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
162 hi = mid;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
163 }
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
164 }
3960
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
165
8750
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
166 if (addr < ph->core->map_array[hi]->vaddr) {
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
167 mp = ph->core->map_array[lo];
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
168 } else {
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
169 mp = ph->core->map_array[hi];
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
170 }
3960
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
171
8750
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
172 if (addr >= mp->vaddr && addr < mp->vaddr + mp->memsz) {
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
173 return (mp);
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
174 }
3960
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
175
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
176
8750
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
177 // Part of the class sharing workaround
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
178 // Unfortunately, we have no way of detecting -Xshare state.
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
179 // Check out the share maps atlast, if we don't find anywhere.
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
180 // This is done this way so to avoid reading share pages
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
181 // ahead of other normal maps. For eg. with -Xshare:off we don't
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
182 // want to prefer class sharing data to data from core.
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
183 mp = ph->core->class_share_maps;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
184 if (mp) {
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
185 print_debug("can't locate map_info at 0x%lx, trying class share maps\n", addr);
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
186 }
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
187 while (mp) {
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
188 if (addr >= mp->vaddr && addr < mp->vaddr + mp->memsz) {
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
189 print_debug("located map_info at 0x%lx from class share maps\n", addr);
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
190 return (mp);
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
191 }
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
192 mp = mp->next;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
193 }
3960
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
194
8750
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
195 print_debug("can't locate map_info at 0x%lx\n", addr);
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
196 return (NULL);
3960
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
197 }
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
198
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
199 //---------------------------------------------------------------
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
200 // Part of the class sharing workaround:
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
201 //
10229
f6a055fcf47d 8005038: remove crufty '_g' support from SA
sla
parents: 8750
diff changeset
202 // With class sharing, pages are mapped from classes.jsa file.
3960
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
203 // The read-only class sharing pages are mapped as MAP_SHARED,
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
204 // PROT_READ pages. These pages are not dumped into core dump.
10229
f6a055fcf47d 8005038: remove crufty '_g' support from SA
sla
parents: 8750
diff changeset
205 // With this workaround, these pages are read from classes.jsa.
3960
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
206
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
207 // FIXME: !HACK ALERT!
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
208 // The format of sharing achive file header is needed to read shared heap
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
209 // file mappings. For now, I am hard coding portion of FileMapHeader here.
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
210 // Refer to filemap.hpp.
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
211
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
212 // FileMapHeader describes the shared space data in the file to be
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
213 // mapped. This structure gets written to a file. It is not a class,
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
214 // so that the compilers don't add any compiler-private data to it.
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
215
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
216 #define NUM_SHARED_MAPS 4
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
217
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
218 // Refer to FileMapInfo::_current_version in filemap.hpp
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
219 #define CURRENT_ARCHIVE_VERSION 1
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
220
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
221 struct FileMapHeader {
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
222 int _magic; // identify file type.
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
223 int _version; // (from enum, above.)
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
224 size_t _alignment; // how shared archive should be aligned
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
225
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
226 struct space_info {
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
227 int _file_offset; // sizeof(this) rounded to vm page size
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
228 char* _base; // copy-on-write base address
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
229 size_t _capacity; // for validity checking
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
230 size_t _used; // for setting space top on read
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
231
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
232 // 4991491 NOTICE These are C++ bool's in filemap.hpp and must match up with
12807
5705c7ee6dd7 8025250: SA: Sync linux and bsd versions of ps_core file
dsamersoff
parents: 10229
diff changeset
233 // the C type matching the C++ bool type on any given platform.
5705c7ee6dd7 8025250: SA: Sync linux and bsd versions of ps_core file
dsamersoff
parents: 10229
diff changeset
234 // We assume the corresponding C type is char but licensees
5705c7ee6dd7 8025250: SA: Sync linux and bsd versions of ps_core file
dsamersoff
parents: 10229
diff changeset
235 // may need to adjust the type of these fields.
3960
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
236 char _read_only; // read only space?
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
237 char _allow_exec; // executable code in space?
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
238
6725
da91efe96a93 6964458: Reimplement class meta-data storage to use native memory
coleenp
parents: 3960
diff changeset
239 } _space[NUM_SHARED_MAPS];
3960
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
240
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
241 // Ignore the rest of the FileMapHeader. We don't need those fields here.
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
242 };
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
243
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
244 static bool read_jboolean(struct ps_prochandle* ph, uintptr_t addr, jboolean* pvalue) {
8750
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
245 jboolean i;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
246 if (ps_pread(ph, (psaddr_t) addr, &i, sizeof(i)) == PS_OK) {
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
247 *pvalue = i;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
248 return true;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
249 } else {
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
250 return false;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
251 }
3960
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
252 }
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
253
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
254 static bool read_pointer(struct ps_prochandle* ph, uintptr_t addr, uintptr_t* pvalue) {
8750
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
255 uintptr_t uip;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
256 if (ps_pread(ph, (psaddr_t) addr, (char *)&uip, sizeof(uip)) == PS_OK) {
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
257 *pvalue = uip;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
258 return true;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
259 } else {
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
260 return false;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
261 }
3960
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
262 }
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
263
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
264 // used to read strings from debuggee
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
265 static bool read_string(struct ps_prochandle* ph, uintptr_t addr, char* buf, size_t size) {
8750
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
266 size_t i = 0;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
267 char c = ' ';
3960
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
268
8750
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
269 while (c != '\0') {
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
270 if (ps_pread(ph, (psaddr_t) addr, &c, sizeof(char)) != PS_OK) {
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
271 return false;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
272 }
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
273 if (i < size - 1) {
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
274 buf[i] = c;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
275 } else {
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
276 // smaller buffer
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
277 return false;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
278 }
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
279 i++; addr++;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
280 }
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
281 buf[i] = '\0';
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
282 return true;
3960
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
283 }
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
284
8750
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
285 #ifdef __APPLE__
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
286 #define USE_SHARED_SPACES_SYM "_UseSharedSpaces"
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
287 // mangled name of Arguments::SharedArchivePath
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
288 #define SHARED_ARCHIVE_PATH_SYM "_ZN9Arguments17SharedArchivePathE"
12807
5705c7ee6dd7 8025250: SA: Sync linux and bsd versions of ps_core file
dsamersoff
parents: 10229
diff changeset
289 #define LIBJVM_NAME "/libjvm.dylib"
8750
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
290 #else
3960
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
291 #define USE_SHARED_SPACES_SYM "UseSharedSpaces"
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
292 // mangled name of Arguments::SharedArchivePath
8750
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
293 #define SHARED_ARCHIVE_PATH_SYM "__ZN9Arguments17SharedArchivePathE"
12807
5705c7ee6dd7 8025250: SA: Sync linux and bsd versions of ps_core file
dsamersoff
parents: 10229
diff changeset
294 #define LIBJVM_NAME "/libjvm.so"
8750
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
295 #endif // __APPLE_
3960
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
296
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
297 static bool init_classsharing_workaround(struct ps_prochandle* ph) {
8750
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
298 int m;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
299 size_t n;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
300 lib_info* lib = ph->libs;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
301 while (lib != NULL) {
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
302 // we are iterating over shared objects from the core dump. look for
10229
f6a055fcf47d 8005038: remove crufty '_g' support from SA
sla
parents: 8750
diff changeset
303 // libjvm.so.
8750
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
304 const char *jvm_name = 0;
12807
5705c7ee6dd7 8025250: SA: Sync linux and bsd versions of ps_core file
dsamersoff
parents: 10229
diff changeset
305 if ((jvm_name = strstr(lib->name, LIBJVM_NAME)) != 0) {
8750
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
306 char classes_jsa[PATH_MAX];
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
307 struct FileMapHeader header;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
308 int fd = -1;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
309 uintptr_t base = 0, useSharedSpacesAddr = 0;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
310 uintptr_t sharedArchivePathAddrAddr = 0, sharedArchivePathAddr = 0;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
311 jboolean useSharedSpaces = 0;
3960
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
312
8750
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
313 memset(classes_jsa, 0, sizeof(classes_jsa));
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
314 jvm_name = lib->name;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
315 useSharedSpacesAddr = lookup_symbol(ph, jvm_name, USE_SHARED_SPACES_SYM);
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
316 if (useSharedSpacesAddr == 0) {
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
317 print_debug("can't lookup 'UseSharedSpaces' flag\n");
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
318 return false;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
319 }
3960
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
320
8750
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
321 // Hotspot vm types are not exported to build this library. So
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
322 // using equivalent type jboolean to read the value of
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
323 // UseSharedSpaces which is same as hotspot type "bool".
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
324 if (read_jboolean(ph, useSharedSpacesAddr, &useSharedSpaces) != true) {
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
325 print_debug("can't read the value of 'UseSharedSpaces' flag\n");
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
326 return false;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
327 }
3960
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
328
8750
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
329 if ((int)useSharedSpaces == 0) {
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
330 print_debug("UseSharedSpaces is false, assuming -Xshare:off!\n");
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
331 return true;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
332 }
3960
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
333
8750
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
334 sharedArchivePathAddrAddr = lookup_symbol(ph, jvm_name, SHARED_ARCHIVE_PATH_SYM);
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
335 if (sharedArchivePathAddrAddr == 0) {
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
336 print_debug("can't lookup shared archive path symbol\n");
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
337 return false;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
338 }
3960
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
339
8750
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
340 if (read_pointer(ph, sharedArchivePathAddrAddr, &sharedArchivePathAddr) != true) {
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
341 print_debug("can't read shared archive path pointer\n");
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
342 return false;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
343 }
3960
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
344
8750
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
345 if (read_string(ph, sharedArchivePathAddr, classes_jsa, sizeof(classes_jsa)) != true) {
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
346 print_debug("can't read shared archive path value\n");
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
347 return false;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
348 }
3960
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
349
8750
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
350 print_debug("looking for %s\n", classes_jsa);
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
351 // open the class sharing archive file
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
352 fd = pathmap_open(classes_jsa);
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
353 if (fd < 0) {
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
354 print_debug("can't open %s!\n", classes_jsa);
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
355 ph->core->classes_jsa_fd = -1;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
356 return false;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
357 } else {
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
358 print_debug("opened %s\n", classes_jsa);
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
359 }
3960
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
360
8750
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
361 // read FileMapHeader from the file
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
362 memset(&header, 0, sizeof(struct FileMapHeader));
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
363 if ((n = read(fd, &header, sizeof(struct FileMapHeader)))
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
364 != sizeof(struct FileMapHeader)) {
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
365 print_debug("can't read shared archive file map header from %s\n", classes_jsa);
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
366 close(fd);
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
367 return false;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
368 }
3960
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
369
8750
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
370 // check file magic
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
371 if (header._magic != 0xf00baba2) {
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
372 print_debug("%s has bad shared archive file magic number 0x%x, expecing 0xf00baba2\n",
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
373 classes_jsa, header._magic);
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
374 close(fd);
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
375 return false;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
376 }
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
377
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
378 // check version
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
379 if (header._version != CURRENT_ARCHIVE_VERSION) {
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
380 print_debug("%s has wrong shared archive file version %d, expecting %d\n",
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
381 classes_jsa, header._version, CURRENT_ARCHIVE_VERSION);
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
382 close(fd);
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
383 return false;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
384 }
3960
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
385
8750
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
386 ph->core->classes_jsa_fd = fd;
10229
f6a055fcf47d 8005038: remove crufty '_g' support from SA
sla
parents: 8750
diff changeset
387 // add read-only maps from classes.jsa to the list of maps
8750
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
388 for (m = 0; m < NUM_SHARED_MAPS; m++) {
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
389 if (header._space[m]._read_only) {
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
390 base = (uintptr_t) header._space[m]._base;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
391 // no need to worry about the fractional pages at-the-end.
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
392 // possible fractional pages are handled by core_read_data.
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
393 add_class_share_map_info(ph, (off_t) header._space[m]._file_offset,
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
394 base, (size_t) header._space[m]._used);
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
395 print_debug("added a share archive map at 0x%lx\n", base);
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
396 }
3960
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
397 }
8750
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
398 return true;
12807
5705c7ee6dd7 8025250: SA: Sync linux and bsd versions of ps_core file
dsamersoff
parents: 10229
diff changeset
399 }
5705c7ee6dd7 8025250: SA: Sync linux and bsd versions of ps_core file
dsamersoff
parents: 10229
diff changeset
400 lib = lib->next;
8750
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
401 }
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
402 return true;
3960
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
403 }
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
404
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
405 //---------------------------------------------------------------------------
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
406 // functions to handle map_info
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
407
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
408 // Order mappings based on virtual address. We use this function as the
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
409 // callback for sorting the array of map_info pointers.
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
410 static int core_cmp_mapping(const void *lhsp, const void *rhsp)
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
411 {
8750
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
412 const map_info *lhs = *((const map_info **)lhsp);
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
413 const map_info *rhs = *((const map_info **)rhsp);
3960
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
414
8750
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
415 if (lhs->vaddr == rhs->vaddr) {
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
416 return (0);
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
417 }
3960
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
418
8750
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
419 return (lhs->vaddr < rhs->vaddr ? -1 : 1);
3960
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
420 }
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
421
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
422 // we sort map_info by starting virtual address so that we can do
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
423 // binary search to read from an address.
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
424 static bool sort_map_array(struct ps_prochandle* ph) {
8750
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
425 size_t num_maps = ph->core->num_maps;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
426 map_info* map = ph->core->maps;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
427 int i = 0;
3960
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
428
8750
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
429 // allocate map_array
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
430 map_info** array;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
431 if ( (array = (map_info**) malloc(sizeof(map_info*) * num_maps)) == NULL) {
12807
5705c7ee6dd7 8025250: SA: Sync linux and bsd versions of ps_core file
dsamersoff
parents: 10229
diff changeset
432 print_debug("can't allocate memory for map array\n");
5705c7ee6dd7 8025250: SA: Sync linux and bsd versions of ps_core file
dsamersoff
parents: 10229
diff changeset
433 return false;
8750
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
434 }
3960
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
435
8750
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
436 // add maps to array
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
437 while (map) {
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
438 array[i] = map;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
439 i++;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
440 map = map->next;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
441 }
3960
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
442
8750
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
443 // sort is called twice. If this is second time, clear map array
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
444 if (ph->core->map_array) {
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
445 free(ph->core->map_array);
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
446 }
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
447 ph->core->map_array = array;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
448 // sort the map_info array by base virtual address.
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
449 qsort(ph->core->map_array, ph->core->num_maps, sizeof (map_info*),
12807
5705c7ee6dd7 8025250: SA: Sync linux and bsd versions of ps_core file
dsamersoff
parents: 10229
diff changeset
450 core_cmp_mapping);
3960
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
451
8750
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
452 // print map
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
453 if (is_debug()) {
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
454 int j = 0;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
455 print_debug("---- sorted virtual address map ----\n");
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
456 for (j = 0; j < ph->core->num_maps; j++) {
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
457 print_debug("base = 0x%lx\tsize = %d\n", ph->core->map_array[j]->vaddr,
12807
5705c7ee6dd7 8025250: SA: Sync linux and bsd versions of ps_core file
dsamersoff
parents: 10229
diff changeset
458 ph->core->map_array[j]->memsz);
8750
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
459 }
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
460 }
3960
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
461
8750
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
462 return true;
3960
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
463 }
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
464
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
465 #ifndef MIN
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
466 #define MIN(x, y) (((x) < (y))? (x): (y))
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
467 #endif
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
468
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
469 static bool core_read_data(struct ps_prochandle* ph, uintptr_t addr, char *buf, size_t size) {
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
470 ssize_t resid = size;
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
471 int page_size=sysconf(_SC_PAGE_SIZE);
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
472 while (resid != 0) {
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
473 map_info *mp = core_lookup(ph, addr);
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
474 uintptr_t mapoff;
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
475 ssize_t len, rem;
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
476 off_t off;
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
477 int fd;
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
478
8750
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
479 if (mp == NULL) {
3960
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
480 break; /* No mapping for this address */
8750
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
481 }
3960
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
482
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
483 fd = mp->fd;
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
484 mapoff = addr - mp->vaddr;
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
485 len = MIN(resid, mp->memsz - mapoff);
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
486 off = mp->offset + mapoff;
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
487
8750
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
488 if ((len = pread(fd, buf, len, off)) <= 0) {
3960
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
489 break;
8750
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
490 }
3960
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
491
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
492 resid -= len;
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
493 addr += len;
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
494 buf = (char *)buf + len;
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
495
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
496 // mappings always start at page boundary. But, may end in fractional
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
497 // page. fill zeros for possible fractional page at the end of a mapping.
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
498 rem = mp->memsz % page_size;
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
499 if (rem > 0) {
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
500 rem = page_size - rem;
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
501 len = MIN(resid, rem);
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
502 resid -= len;
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
503 addr += len;
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
504 // we are not assuming 'buf' to be zero initialized.
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
505 memset(buf, 0, len);
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
506 buf += len;
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
507 }
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
508 }
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
509
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
510 if (resid) {
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
511 print_debug("core read failed for %d byte(s) @ 0x%lx (%d more bytes)\n",
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
512 size, addr, resid);
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
513 return false;
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
514 } else {
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
515 return true;
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
516 }
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
517 }
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
518
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
519 // null implementation for write
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
520 static bool core_write_data(struct ps_prochandle* ph,
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
521 uintptr_t addr, const char *buf , size_t size) {
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
522 return false;
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
523 }
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
524
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
525 static bool core_get_lwp_regs(struct ps_prochandle* ph, lwpid_t lwp_id,
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
526 struct reg* regs) {
8750
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
527 // for core we have cached the lwp regs after segment parsed
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
528 sa_thread_info* thr = ph->threads;
3960
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
529 while (thr) {
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
530 if (thr->lwp_id == lwp_id) {
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
531 memcpy(regs, &thr->regs, sizeof(struct reg));
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
532 return true;
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
533 }
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
534 thr = thr->next;
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
535 }
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
536 return false;
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
537 }
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
538
8750
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
539 static bool core_get_lwp_info(struct ps_prochandle *ph, lwpid_t id, void *info) {
3960
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
540 print_debug("core_get_lwp_info not implemented\n");
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
541 return false;
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
542 }
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
543
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
544 static ps_prochandle_ops core_ops = {
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
545 .release= core_release,
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
546 .p_pread= core_read_data,
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
547 .p_pwrite= core_write_data,
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
548 .get_lwp_regs= core_get_lwp_regs,
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
549 .get_lwp_info= core_get_lwp_info
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
550 };
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
551
8750
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
552 // from this point, mainly two blocks divided by def __APPLE__
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
553 // one for Macosx, the other for regular Bsd
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
554
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
555 #ifdef __APPLE__
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
556
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
557 void print_thread(sa_thread_info *threadinfo) {
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
558 print_debug("thread added: %d\n", threadinfo->lwp_id);
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
559 print_debug("registers:\n");
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
560 print_debug(" r_r15: 0x%" PRIx64 "\n", threadinfo->regs.r_r15);
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
561 print_debug(" r_r14: 0x%" PRIx64 "\n", threadinfo->regs.r_r14);
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
562 print_debug(" r_r13: 0x%" PRIx64 "\n", threadinfo->regs.r_r13);
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
563 print_debug(" r_r12: 0x%" PRIx64 "\n", threadinfo->regs.r_r12);
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
564 print_debug(" r_r11: 0x%" PRIx64 "\n", threadinfo->regs.r_r11);
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
565 print_debug(" r_r10: 0x%" PRIx64 "\n", threadinfo->regs.r_r10);
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
566 print_debug(" r_r9: 0x%" PRIx64 "\n", threadinfo->regs.r_r9);
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
567 print_debug(" r_r8: 0x%" PRIx64 "\n", threadinfo->regs.r_r8);
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
568 print_debug(" r_rdi: 0x%" PRIx64 "\n", threadinfo->regs.r_rdi);
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
569 print_debug(" r_rsi: 0x%" PRIx64 "\n", threadinfo->regs.r_rsi);
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
570 print_debug(" r_rbp: 0x%" PRIx64 "\n", threadinfo->regs.r_rbp);
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
571 print_debug(" r_rbx: 0x%" PRIx64 "\n", threadinfo->regs.r_rbx);
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
572 print_debug(" r_rdx: 0x%" PRIx64 "\n", threadinfo->regs.r_rdx);
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
573 print_debug(" r_rcx: 0x%" PRIx64 "\n", threadinfo->regs.r_rcx);
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
574 print_debug(" r_rax: 0x%" PRIx64 "\n", threadinfo->regs.r_rax);
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
575 print_debug(" r_fs: 0x%" PRIx32 "\n", threadinfo->regs.r_fs);
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
576 print_debug(" r_gs: 0x%" PRIx32 "\n", threadinfo->regs.r_gs);
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
577 print_debug(" r_rip 0x%" PRIx64 "\n", threadinfo->regs.r_rip);
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
578 print_debug(" r_cs: 0x%" PRIx64 "\n", threadinfo->regs.r_cs);
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
579 print_debug(" r_rsp: 0x%" PRIx64 "\n", threadinfo->regs.r_rsp);
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
580 print_debug(" r_rflags: 0x%" PRIx64 "\n", threadinfo->regs.r_rflags);
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
581 }
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
582
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
583 // read all segments64 commands from core file
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
584 // read all thread commands from core file
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
585 static bool read_core_segments(struct ps_prochandle* ph) {
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
586 int i = 0;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
587 int num_threads = 0;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
588 int fd = ph->core->core_fd;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
589 off_t offset = 0;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
590 mach_header_64 fhead;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
591 load_command lcmd;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
592 segment_command_64 segcmd;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
593 // thread_command thrcmd;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
594
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
595 lseek(fd, offset, SEEK_SET);
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
596 if(read(fd, (void *)&fhead, sizeof(mach_header_64)) != sizeof(mach_header_64)) {
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
597 goto err;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
598 }
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
599 print_debug("total commands: %d\n", fhead.ncmds);
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
600 offset += sizeof(mach_header_64);
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
601 for (i = 0; i < fhead.ncmds; i++) {
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
602 lseek(fd, offset, SEEK_SET);
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
603 if (read(fd, (void *)&lcmd, sizeof(load_command)) != sizeof(load_command)) {
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
604 goto err;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
605 }
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
606 offset += lcmd.cmdsize; // next command position
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
607 if (lcmd.cmd == LC_SEGMENT_64) {
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
608 lseek(fd, -sizeof(load_command), SEEK_CUR);
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
609 if (read(fd, (void *)&segcmd, sizeof(segment_command_64)) != sizeof(segment_command_64)) {
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
610 print_debug("failed to read LC_SEGMENT_64 i = %d!\n", i);
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
611 goto err;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
612 }
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
613 if (add_map_info(ph, fd, segcmd.fileoff, segcmd.vmaddr, segcmd.vmsize) == NULL) {
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
614 print_debug("Failed to add map_info at i = %d\n", i);
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
615 goto err;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
616 }
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
617 print_debug("segment added: %" PRIu64 " 0x%" PRIx64 " %d\n",
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
618 segcmd.fileoff, segcmd.vmaddr, segcmd.vmsize);
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
619 } else if (lcmd.cmd == LC_THREAD || lcmd.cmd == LC_UNIXTHREAD) {
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
620 typedef struct thread_fc {
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
621 uint32_t flavor;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
622 uint32_t count;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
623 } thread_fc;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
624 thread_fc fc;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
625 uint32_t size = sizeof(load_command);
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
626 while (size < lcmd.cmdsize) {
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
627 if (read(fd, (void *)&fc, sizeof(thread_fc)) != sizeof(thread_fc)) {
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
628 printf("Reading flavor, count failed.\n");
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
629 goto err;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
630 }
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
631 size += sizeof(thread_fc);
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
632 if (fc.flavor == x86_THREAD_STATE) {
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
633 x86_thread_state_t thrstate;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
634 if (read(fd, (void *)&thrstate, sizeof(x86_thread_state_t)) != sizeof(x86_thread_state_t)) {
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
635 printf("Reading flavor, count failed.\n");
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
636 goto err;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
637 }
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
638 size += sizeof(x86_thread_state_t);
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
639 // create thread info list, update lwp_id later
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
640 sa_thread_info* newthr = add_thread_info(ph, (pthread_t) -1, (lwpid_t) num_threads++);
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
641 if (newthr == NULL) {
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
642 printf("create thread_info failed\n");
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
643 goto err;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
644 }
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
645
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
646 // note __DARWIN_UNIX03 depengs on other definitions
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
647 #if __DARWIN_UNIX03
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
648 #define get_register_v(regst, regname) \
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
649 regst.uts.ts64.__##regname
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
650 #else
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
651 #define get_register_v(regst, regname) \
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
652 regst.uts.ts64.##regname
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
653 #endif // __DARWIN_UNIX03
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
654 newthr->regs.r_rax = get_register_v(thrstate, rax);
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
655 newthr->regs.r_rbx = get_register_v(thrstate, rbx);
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
656 newthr->regs.r_rcx = get_register_v(thrstate, rcx);
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
657 newthr->regs.r_rdx = get_register_v(thrstate, rdx);
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
658 newthr->regs.r_rdi = get_register_v(thrstate, rdi);
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
659 newthr->regs.r_rsi = get_register_v(thrstate, rsi);
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
660 newthr->regs.r_rbp = get_register_v(thrstate, rbp);
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
661 newthr->regs.r_rsp = get_register_v(thrstate, rsp);
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
662 newthr->regs.r_r8 = get_register_v(thrstate, r8);
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
663 newthr->regs.r_r9 = get_register_v(thrstate, r9);
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
664 newthr->regs.r_r10 = get_register_v(thrstate, r10);
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
665 newthr->regs.r_r11 = get_register_v(thrstate, r11);
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
666 newthr->regs.r_r12 = get_register_v(thrstate, r12);
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
667 newthr->regs.r_r13 = get_register_v(thrstate, r13);
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
668 newthr->regs.r_r14 = get_register_v(thrstate, r14);
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
669 newthr->regs.r_r15 = get_register_v(thrstate, r15);
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
670 newthr->regs.r_rip = get_register_v(thrstate, rip);
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
671 newthr->regs.r_rflags = get_register_v(thrstate, rflags);
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
672 newthr->regs.r_cs = get_register_v(thrstate, cs);
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
673 newthr->regs.r_fs = get_register_v(thrstate, fs);
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
674 newthr->regs.r_gs = get_register_v(thrstate, gs);
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
675 print_thread(newthr);
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
676 } else if (fc.flavor == x86_FLOAT_STATE) {
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
677 x86_float_state_t flstate;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
678 if (read(fd, (void *)&flstate, sizeof(x86_float_state_t)) != sizeof(x86_float_state_t)) {
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
679 print_debug("Reading flavor, count failed.\n");
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
680 goto err;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
681 }
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
682 size += sizeof(x86_float_state_t);
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
683 } else if (fc.flavor == x86_EXCEPTION_STATE) {
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
684 x86_exception_state_t excpstate;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
685 if (read(fd, (void *)&excpstate, sizeof(x86_exception_state_t)) != sizeof(x86_exception_state_t)) {
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
686 printf("Reading flavor, count failed.\n");
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
687 goto err;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
688 }
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
689 size += sizeof(x86_exception_state_t);
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
690 }
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
691 }
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
692 }
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
693 }
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
694 return true;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
695 err:
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
696 return false;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
697 }
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
698
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
699 /**local function **/
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
700 bool exists(const char *fname)
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
701 {
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
702 int fd;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
703 if ((fd = open(fname, O_RDONLY)) > 0) {
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
704 close(fd);
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
705 return true;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
706 }
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
707 return false;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
708 }
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
709
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
710 // we check: 1. lib
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
711 // 2. lib/server
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
712 // 3. jre/lib
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
713 // 4. jre/lib/server
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
714 // from: 1. exe path
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
715 // 2. JAVA_HOME
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
716 // 3. DYLD_LIBRARY_PATH
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
717 static bool get_real_path(struct ps_prochandle* ph, char *rpath) {
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
718 /** check if they exist in JAVA ***/
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
719 char* execname = ph->core->exec_path;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
720 char filepath[4096];
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
721 char* filename = strrchr(rpath, '/'); // like /libjvm.dylib
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
722 if (filename == NULL) {
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
723 return false;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
724 }
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
725
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
726 char* posbin = strstr(execname, "/bin/java");
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
727 if (posbin != NULL) {
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
728 memcpy(filepath, execname, posbin - execname); // not include trailing '/'
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
729 filepath[posbin - execname] = '\0';
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
730 } else {
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
731 char* java_home = getenv("JAVA_HOME");
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
732 if (java_home != NULL) {
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
733 strcpy(filepath, java_home);
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
734 } else {
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
735 char* dyldpath = getenv("DYLD_LIBRARY_PATH");
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
736 char* dypath = strtok(dyldpath, ":");
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
737 while (dypath != NULL) {
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
738 strcpy(filepath, dypath);
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
739 strcat(filepath, filename);
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
740 if (exists(filepath)) {
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
741 strcpy(rpath, filepath);
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
742 return true;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
743 }
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
744 dypath = strtok(dyldpath, ":");
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
745 }
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
746 // not found
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
747 return false;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
748 }
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
749 }
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
750 // for exec and java_home, jdkpath now is filepath
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
751 size_t filepath_base_size = strlen(filepath);
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
752
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
753 // first try /lib/ and /lib/server
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
754 strcat(filepath, "/lib");
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
755 strcat(filepath, filename);
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
756 if (exists(filepath)) {
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
757 strcpy(rpath, filepath);
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
758 return true;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
759 }
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
760 char* pos = strstr(filepath, filename); // like /libjvm.dylib
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
761 *pos = '\0';
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
762 strcat(filepath, "/server");
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
763 strcat(filepath, filename);
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
764 if (exists(filepath)) {
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
765 strcpy(rpath, filepath);
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
766 return true;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
767 }
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
768
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
769 // then try /jre/lib/ and /jre/lib/server
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
770 filepath[filepath_base_size] = '\0';
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
771 strcat(filepath, "/jre/lib");
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
772 strcat(filepath, filename);
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
773 if (exists(filepath)) {
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
774 strcpy(rpath, filepath);
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
775 return true;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
776 }
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
777 pos = strstr(filepath, filename);
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
778 *pos = '\0';
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
779 strcat(filepath, "/server");
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
780 strcat(filepath, filename);
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
781 if (exists(filepath)) {
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
782 strcpy(rpath, filepath);
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
783 return true;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
784 }
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
785
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
786 return false;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
787 }
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
788
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
789 static bool read_shared_lib_info(struct ps_prochandle* ph) {
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
790 static int pagesize = 0;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
791 int fd = ph->core->core_fd;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
792 int i = 0, j;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
793 uint32_t v;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
794 mach_header_64 header; // used to check if a file header in segment
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
795 load_command lcmd;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
796 dylib_command dylibcmd;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
797
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
798 char name[BUF_SIZE]; // use to store name
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
799
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
800 if (pagesize == 0) {
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
801 pagesize = getpagesize();
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
802 print_debug("page size is %d\n", pagesize);
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
803 }
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
804 for (j = 0; j < ph->core->num_maps; j++) {
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
805 map_info *iter = ph->core->map_array[j]; // head
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
806 off_t fpos = iter->offset;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
807 if (iter->fd != fd) {
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
808 // only search core file!
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
809 continue;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
810 }
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
811 print_debug("map_info %d: vmaddr = 0x%016" PRIx64 " fileoff = %" PRIu64 " vmsize = %" PRIu64 "\n",
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
812 j, iter->vaddr, iter->offset, iter->memsz);
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
813 lseek(fd, fpos, SEEK_SET);
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
814 // we assume .dylib loaded at segment address --- which is true for JVM libraries
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
815 // multiple files may be loaded in one segment.
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
816 // if first word is not a magic word, means this segment does not contain lib file.
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
817 if (read(fd, (void *)&v, sizeof(uint32_t)) == sizeof(uint32_t)) {
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
818 if (v != MH_MAGIC_64) {
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
819 continue;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
820 }
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
821 } else {
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
822 // may be encountered last map, which is not readable
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
823 continue;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
824 }
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
825 while (ltell(fd) - iter->offset < iter->memsz) {
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
826 lseek(fd, fpos, SEEK_SET);
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
827 if (read(fd, (void *)&v, sizeof(uint32_t)) != sizeof(uint32_t)) {
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
828 break;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
829 }
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
830 if (v != MH_MAGIC_64) {
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
831 fpos = (ltell(fd) + pagesize -1)/pagesize * pagesize;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
832 continue;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
833 }
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
834 lseek(fd, -sizeof(uint32_t), SEEK_CUR);
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
835 // this is the file begining to core file.
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
836 if (read(fd, (void *)&header, sizeof(mach_header_64)) != sizeof(mach_header_64)) {
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
837 goto err;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
838 }
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
839 fpos = ltell(fd);
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
840
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
841 // found a mach-o file in this segment
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
842 for (i = 0; i < header.ncmds; i++) {
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
843 // read commands in this "file"
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
844 // LC_ID_DYLIB is the file itself for a .dylib
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
845 lseek(fd, fpos, SEEK_SET);
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
846 if (read(fd, (void *)&lcmd, sizeof(load_command)) != sizeof(load_command)) {
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
847 return false; // error
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
848 }
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
849 fpos += lcmd.cmdsize; // next command position
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
850 // make sure still within seg size.
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
851 if (fpos - lcmd.cmdsize - iter->offset > iter->memsz) {
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
852 print_debug("Warning: out of segement limit: %ld \n", fpos - lcmd.cmdsize - iter->offset);
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
853 break; // no need to iterate all commands
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
854 }
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
855 if (lcmd.cmd == LC_ID_DYLIB) {
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
856 lseek(fd, -sizeof(load_command), SEEK_CUR);
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
857 if (read(fd, (void *)&dylibcmd, sizeof(dylib_command)) != sizeof(dylib_command)) {
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
858 return false;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
859 }
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
860 /**** name stored at dylib_command.dylib.name.offset, is a C string */
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
861 lseek(fd, dylibcmd.dylib.name.offset - sizeof(dylib_command), SEEK_CUR);
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
862 int j = 0;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
863 while (j < BUF_SIZE) {
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
864 read(fd, (void *)(name + j), sizeof(char));
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
865 if (name[j] == '\0') break;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
866 j++;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
867 }
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
868 print_debug("%s\n", name);
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
869 // changed name from @rpath/xxxx.dylib to real path
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
870 if (strrchr(name, '@')) {
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
871 get_real_path(ph, name);
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
872 print_debug("get_real_path returned: %s\n", name);
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
873 }
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
874 add_lib_info(ph, name, iter->vaddr);
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
875 break;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
876 }
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
877 }
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
878 // done with the file, advanced to next page to search more files
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
879 fpos = (ltell(fd) + pagesize - 1) / pagesize * pagesize;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
880 }
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
881 }
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
882 return true;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
883 err:
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
884 return false;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
885 }
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
886
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
887 bool read_macho64_header(int fd, mach_header_64* core_header) {
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
888 bool is_macho = false;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
889 if (fd < 0) return false;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
890 off_t pos = ltell(fd);
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
891 lseek(fd, 0, SEEK_SET);
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
892 if (read(fd, (void *)core_header, sizeof(mach_header_64)) != sizeof(mach_header_64)) {
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
893 is_macho = false;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
894 } else {
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
895 is_macho = (core_header->magic == MH_MAGIC_64 || core_header->magic == MH_CIGAM_64);
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
896 }
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
897 lseek(fd, pos, SEEK_SET);
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
898 return is_macho;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
899 }
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
900
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
901 // the one and only one exposed stuff from this file
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
902 struct ps_prochandle* Pgrab_core(const char* exec_file, const char* core_file) {
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
903 mach_header_64 core_header;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
904 mach_header_64 exec_header;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
905
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
906 struct ps_prochandle* ph = (struct ps_prochandle*) calloc(1, sizeof(struct ps_prochandle));
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
907 if (ph == NULL) {
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
908 print_debug("cant allocate ps_prochandle\n");
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
909 return NULL;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
910 }
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
911
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
912 if ((ph->core = (struct core_data*) calloc(1, sizeof(struct core_data))) == NULL) {
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
913 free(ph);
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
914 print_debug("can't allocate ps_prochandle\n");
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
915 return NULL;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
916 }
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
917
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
918 // initialize ph
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
919 ph->ops = &core_ops;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
920 ph->core->core_fd = -1;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
921 ph->core->exec_fd = -1;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
922 ph->core->interp_fd = -1;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
923
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
924 print_debug("exec: %s core: %s", exec_file, core_file);
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
925
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
926 strncpy(ph->core->exec_path, exec_file, sizeof(ph->core->exec_path));
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
927
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
928 // open the core file
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
929 if ((ph->core->core_fd = open(core_file, O_RDONLY)) < 0) {
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
930 print_error("can't open core file\n");
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
931 goto err;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
932 }
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
933
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
934 // read core file header
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
935 if (read_macho64_header(ph->core->core_fd, &core_header) != true || core_header.filetype != MH_CORE) {
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
936 print_debug("core file is not a valid Mach-O file\n");
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
937 goto err;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
938 }
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
939
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
940 if ((ph->core->exec_fd = open(exec_file, O_RDONLY)) < 0) {
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
941 print_error("can't open executable file\n");
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
942 goto err;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
943 }
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
944
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
945 if (read_macho64_header(ph->core->exec_fd, &exec_header) != true ||
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
946 exec_header.filetype != MH_EXECUTE) {
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
947 print_error("executable file is not a valid Mach-O file\n");
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
948 goto err;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
949 }
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
950
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
951 // process core file segments
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
952 if (read_core_segments(ph) != true) {
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
953 print_error("failed to read core segments\n");
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
954 goto err;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
955 }
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
956
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
957 // allocate and sort maps into map_array, we need to do this
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
958 // here because read_shared_lib_info needs to read from debuggee
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
959 // address space
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
960 if (sort_map_array(ph) != true) {
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
961 print_error("failed to sort segment map array\n");
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
962 goto err;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
963 }
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
964
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
965 if (read_shared_lib_info(ph) != true) {
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
966 print_error("failed to read libraries\n");
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
967 goto err;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
968 }
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
969
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
970 // sort again because we have added more mappings from shared objects
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
971 if (sort_map_array(ph) != true) {
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
972 print_error("failed to sort segment map array\n");
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
973 goto err;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
974 }
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
975
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
976 if (init_classsharing_workaround(ph) != true) {
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
977 print_error("failed to workaround classshareing\n");
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
978 goto err;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
979 }
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
980
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
981 print_debug("Leave Pgrab_core\n");
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
982 return ph;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
983
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
984 err:
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
985 Prelease(ph);
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
986 return NULL;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
987 }
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
988
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
989 #else // __APPLE__ (none macosx)
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
990
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
991 // read regs and create thread from core file
3960
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
992 static bool core_handle_prstatus(struct ps_prochandle* ph, const char* buf, size_t nbytes) {
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
993 // we have to read prstatus_t from buf
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
994 // assert(nbytes == sizeof(prstaus_t), "size mismatch on prstatus_t");
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
995 prstatus_t* prstat = (prstatus_t*) buf;
8750
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
996 sa_thread_info* newthr;
3960
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
997 print_debug("got integer regset for lwp %d\n", prstat->pr_pid);
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
998 // we set pthread_t to -1 for core dump
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
999 if((newthr = add_thread_info(ph, (pthread_t) -1, prstat->pr_pid)) == NULL)
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1000 return false;
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1001
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1002 // copy regs
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1003 memcpy(&newthr->regs, &prstat->pr_reg, sizeof(struct reg));
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1004
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1005 if (is_debug()) {
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1006 print_debug("integer regset\n");
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1007 #ifdef i386
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1008 // print the regset
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1009 print_debug("\teax = 0x%x\n", newthr->regs.r_eax);
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1010 print_debug("\tebx = 0x%x\n", newthr->regs.r_ebx);
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1011 print_debug("\tecx = 0x%x\n", newthr->regs.r_ecx);
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1012 print_debug("\tedx = 0x%x\n", newthr->regs.r_edx);
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1013 print_debug("\tesp = 0x%x\n", newthr->regs.r_esp);
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1014 print_debug("\tebp = 0x%x\n", newthr->regs.r_ebp);
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1015 print_debug("\tesi = 0x%x\n", newthr->regs.r_esi);
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1016 print_debug("\tedi = 0x%x\n", newthr->regs.r_edi);
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1017 print_debug("\teip = 0x%x\n", newthr->regs.r_eip);
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1018 #endif
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1019
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1020 #if defined(amd64) || defined(x86_64)
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1021 // print the regset
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1022 print_debug("\tr15 = 0x%lx\n", newthr->regs.r_r15);
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1023 print_debug("\tr14 = 0x%lx\n", newthr->regs.r_r14);
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1024 print_debug("\tr13 = 0x%lx\n", newthr->regs.r_r13);
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1025 print_debug("\tr12 = 0x%lx\n", newthr->regs.r_r12);
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1026 print_debug("\trbp = 0x%lx\n", newthr->regs.r_rbp);
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1027 print_debug("\trbx = 0x%lx\n", newthr->regs.r_rbx);
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1028 print_debug("\tr11 = 0x%lx\n", newthr->regs.r_r11);
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1029 print_debug("\tr10 = 0x%lx\n", newthr->regs.r_r10);
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1030 print_debug("\tr9 = 0x%lx\n", newthr->regs.r_r9);
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1031 print_debug("\tr8 = 0x%lx\n", newthr->regs.r_r8);
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1032 print_debug("\trax = 0x%lx\n", newthr->regs.r_rax);
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1033 print_debug("\trcx = 0x%lx\n", newthr->regs.r_rcx);
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1034 print_debug("\trdx = 0x%lx\n", newthr->regs.r_rdx);
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1035 print_debug("\trsi = 0x%lx\n", newthr->regs.r_rsi);
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1036 print_debug("\trdi = 0x%lx\n", newthr->regs.r_rdi);
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1037 //print_debug("\torig_rax = 0x%lx\n", newthr->regs.orig_rax);
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1038 print_debug("\trip = 0x%lx\n", newthr->regs.r_rip);
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1039 print_debug("\tcs = 0x%lx\n", newthr->regs.r_cs);
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1040 //print_debug("\teflags = 0x%lx\n", newthr->regs.eflags);
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1041 print_debug("\trsp = 0x%lx\n", newthr->regs.r_rsp);
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1042 print_debug("\tss = 0x%lx\n", newthr->regs.r_ss);
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1043 //print_debug("\tfs_base = 0x%lx\n", newthr->regs.fs_base);
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1044 //print_debug("\tgs_base = 0x%lx\n", newthr->regs.gs_base);
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1045 //print_debug("\tds = 0x%lx\n", newthr->regs.ds);
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1046 //print_debug("\tes = 0x%lx\n", newthr->regs.es);
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1047 //print_debug("\tfs = 0x%lx\n", newthr->regs.fs);
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1048 //print_debug("\tgs = 0x%lx\n", newthr->regs.gs);
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1049 #endif
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1050 }
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1051
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1052 return true;
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1053 }
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1054
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1055 #define ROUNDUP(x, y) ((((x)+((y)-1))/(y))*(y))
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1056
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1057 // read NT_PRSTATUS entries from core NOTE segment
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1058 static bool core_handle_note(struct ps_prochandle* ph, ELF_PHDR* note_phdr) {
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1059 char* buf = NULL;
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1060 char* p = NULL;
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1061 size_t size = note_phdr->p_filesz;
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1062
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1063 // we are interested in just prstatus entries. we will ignore the rest.
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1064 // Advance the seek pointer to the start of the PT_NOTE data
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1065 if (lseek(ph->core->core_fd, note_phdr->p_offset, SEEK_SET) == (off_t)-1) {
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1066 print_debug("failed to lseek to PT_NOTE data\n");
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1067 return false;
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1068 }
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1069
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1070 // Now process the PT_NOTE structures. Each one is preceded by
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1071 // an Elf{32/64}_Nhdr structure describing its type and size.
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1072 if ( (buf = (char*) malloc(size)) == NULL) {
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1073 print_debug("can't allocate memory for reading core notes\n");
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1074 goto err;
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1075 }
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1076
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1077 // read notes into buffer
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1078 if (read(ph->core->core_fd, buf, size) != size) {
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1079 print_debug("failed to read notes, core file must have been truncated\n");
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1080 goto err;
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1081 }
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1082
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1083 p = buf;
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1084 while (p < buf + size) {
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1085 ELF_NHDR* notep = (ELF_NHDR*) p;
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1086 char* descdata = p + sizeof(ELF_NHDR) + ROUNDUP(notep->n_namesz, 4);
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1087 print_debug("Note header with n_type = %d and n_descsz = %u\n",
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1088 notep->n_type, notep->n_descsz);
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1089
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1090 if (notep->n_type == NT_PRSTATUS) {
12807
5705c7ee6dd7 8025250: SA: Sync linux and bsd versions of ps_core file
dsamersoff
parents: 10229
diff changeset
1091 if (core_handle_prstatus(ph, descdata, notep->n_descsz) != true) {
5705c7ee6dd7 8025250: SA: Sync linux and bsd versions of ps_core file
dsamersoff
parents: 10229
diff changeset
1092 return false;
5705c7ee6dd7 8025250: SA: Sync linux and bsd versions of ps_core file
dsamersoff
parents: 10229
diff changeset
1093 }
3960
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1094 }
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1095 p = descdata + ROUNDUP(notep->n_descsz, 4);
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1096 }
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1097
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1098 free(buf);
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1099 return true;
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1100
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1101 err:
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1102 if (buf) free(buf);
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1103 return false;
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1104 }
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1105
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1106 // read all segments from core file
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1107 static bool read_core_segments(struct ps_prochandle* ph, ELF_EHDR* core_ehdr) {
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1108 int i = 0;
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1109 ELF_PHDR* phbuf = NULL;
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1110 ELF_PHDR* core_php = NULL;
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1111
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1112 if ((phbuf = read_program_header_table(ph->core->core_fd, core_ehdr)) == NULL)
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1113 return false;
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1114
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1115 /*
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1116 * Now iterate through the program headers in the core file.
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1117 * We're interested in two types of Phdrs: PT_NOTE (which
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1118 * contains a set of saved /proc structures), and PT_LOAD (which
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1119 * represents a memory mapping from the process's address space).
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1120 *
12807
5705c7ee6dd7 8025250: SA: Sync linux and bsd versions of ps_core file
dsamersoff
parents: 10229
diff changeset
1121 * Difference b/w Solaris PT_NOTE and Linux/BSD PT_NOTE:
3960
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1122 *
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1123 * In Solaris there are two PT_NOTE segments the first PT_NOTE (if present)
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1124 * contains /proc structs in the pre-2.6 unstructured /proc format. the last
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1125 * PT_NOTE has data in new /proc format.
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1126 *
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1127 * In Solaris, there is only one pstatus (process status). pstatus contains
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1128 * integer register set among other stuff. For each LWP, we have one lwpstatus
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1129 * entry that has integer regset for that LWP.
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1130 *
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1131 * Linux threads are actually 'clone'd processes. To support core analysis
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1132 * of "multithreaded" process, Linux creates more than one pstatus (called
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1133 * "prstatus") entry in PT_NOTE. Each prstatus entry has integer regset for one
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1134 * "thread". Please refer to Linux kernel src file 'fs/binfmt_elf.c', in particular
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1135 * function "elf_core_dump".
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1136 */
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1137
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1138 for (core_php = phbuf, i = 0; i < core_ehdr->e_phnum; i++) {
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1139 switch (core_php->p_type) {
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1140 case PT_NOTE:
8750
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
1141 if (core_handle_note(ph, core_php) != true) {
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
1142 goto err;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
1143 }
3960
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1144 break;
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1145
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1146 case PT_LOAD: {
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1147 if (core_php->p_filesz != 0) {
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1148 if (add_map_info(ph, ph->core->core_fd, core_php->p_offset,
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1149 core_php->p_vaddr, core_php->p_filesz) == NULL) goto err;
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1150 }
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1151 break;
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1152 }
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1153 }
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1154
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1155 core_php++;
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1156 }
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1157
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1158 free(phbuf);
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1159 return true;
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1160 err:
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1161 free(phbuf);
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1162 return false;
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1163 }
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1164
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1165 // read segments of a shared object
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1166 static bool read_lib_segments(struct ps_prochandle* ph, int lib_fd, ELF_EHDR* lib_ehdr, uintptr_t lib_base) {
12807
5705c7ee6dd7 8025250: SA: Sync linux and bsd versions of ps_core file
dsamersoff
parents: 10229
diff changeset
1167 int i = 0;
5705c7ee6dd7 8025250: SA: Sync linux and bsd versions of ps_core file
dsamersoff
parents: 10229
diff changeset
1168 ELF_PHDR* phbuf;
5705c7ee6dd7 8025250: SA: Sync linux and bsd versions of ps_core file
dsamersoff
parents: 10229
diff changeset
1169 ELF_PHDR* lib_php = NULL;
5705c7ee6dd7 8025250: SA: Sync linux and bsd versions of ps_core file
dsamersoff
parents: 10229
diff changeset
1170
5705c7ee6dd7 8025250: SA: Sync linux and bsd versions of ps_core file
dsamersoff
parents: 10229
diff changeset
1171 int page_size=sysconf(_SC_PAGE_SIZE);
3960
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1172
12807
5705c7ee6dd7 8025250: SA: Sync linux and bsd versions of ps_core file
dsamersoff
parents: 10229
diff changeset
1173 if ((phbuf = read_program_header_table(lib_fd, lib_ehdr)) == NULL) {
5705c7ee6dd7 8025250: SA: Sync linux and bsd versions of ps_core file
dsamersoff
parents: 10229
diff changeset
1174 return false;
5705c7ee6dd7 8025250: SA: Sync linux and bsd versions of ps_core file
dsamersoff
parents: 10229
diff changeset
1175 }
5705c7ee6dd7 8025250: SA: Sync linux and bsd versions of ps_core file
dsamersoff
parents: 10229
diff changeset
1176
5705c7ee6dd7 8025250: SA: Sync linux and bsd versions of ps_core file
dsamersoff
parents: 10229
diff changeset
1177 // we want to process only PT_LOAD segments that are not writable.
5705c7ee6dd7 8025250: SA: Sync linux and bsd versions of ps_core file
dsamersoff
parents: 10229
diff changeset
1178 // i.e., text segments. The read/write/exec (data) segments would
5705c7ee6dd7 8025250: SA: Sync linux and bsd versions of ps_core file
dsamersoff
parents: 10229
diff changeset
1179 // have been already added from core file segments.
5705c7ee6dd7 8025250: SA: Sync linux and bsd versions of ps_core file
dsamersoff
parents: 10229
diff changeset
1180 for (lib_php = phbuf, i = 0; i < lib_ehdr->e_phnum; i++) {
5705c7ee6dd7 8025250: SA: Sync linux and bsd versions of ps_core file
dsamersoff
parents: 10229
diff changeset
1181 if ((lib_php->p_type == PT_LOAD) && !(lib_php->p_flags & PF_W) && (lib_php->p_filesz != 0)) {
5705c7ee6dd7 8025250: SA: Sync linux and bsd versions of ps_core file
dsamersoff
parents: 10229
diff changeset
1182
5705c7ee6dd7 8025250: SA: Sync linux and bsd versions of ps_core file
dsamersoff
parents: 10229
diff changeset
1183 uintptr_t target_vaddr = lib_php->p_vaddr + lib_base;
5705c7ee6dd7 8025250: SA: Sync linux and bsd versions of ps_core file
dsamersoff
parents: 10229
diff changeset
1184 map_info *existing_map = core_lookup(ph, target_vaddr);
3960
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1185
12807
5705c7ee6dd7 8025250: SA: Sync linux and bsd versions of ps_core file
dsamersoff
parents: 10229
diff changeset
1186 if (existing_map == NULL){
5705c7ee6dd7 8025250: SA: Sync linux and bsd versions of ps_core file
dsamersoff
parents: 10229
diff changeset
1187 if (add_map_info(ph, lib_fd, lib_php->p_offset,
5705c7ee6dd7 8025250: SA: Sync linux and bsd versions of ps_core file
dsamersoff
parents: 10229
diff changeset
1188 target_vaddr, lib_php->p_filesz) == NULL) {
5705c7ee6dd7 8025250: SA: Sync linux and bsd versions of ps_core file
dsamersoff
parents: 10229
diff changeset
1189 goto err;
5705c7ee6dd7 8025250: SA: Sync linux and bsd versions of ps_core file
dsamersoff
parents: 10229
diff changeset
1190 }
5705c7ee6dd7 8025250: SA: Sync linux and bsd versions of ps_core file
dsamersoff
parents: 10229
diff changeset
1191 } else {
5705c7ee6dd7 8025250: SA: Sync linux and bsd versions of ps_core file
dsamersoff
parents: 10229
diff changeset
1192 if ((existing_map->memsz != page_size) &&
5705c7ee6dd7 8025250: SA: Sync linux and bsd versions of ps_core file
dsamersoff
parents: 10229
diff changeset
1193 (existing_map->fd != lib_fd) &&
5705c7ee6dd7 8025250: SA: Sync linux and bsd versions of ps_core file
dsamersoff
parents: 10229
diff changeset
1194 (existing_map->memsz != lib_php->p_filesz)){
5705c7ee6dd7 8025250: SA: Sync linux and bsd versions of ps_core file
dsamersoff
parents: 10229
diff changeset
1195
5705c7ee6dd7 8025250: SA: Sync linux and bsd versions of ps_core file
dsamersoff
parents: 10229
diff changeset
1196 print_debug("address conflict @ 0x%lx (size = %ld, flags = %d\n)",
5705c7ee6dd7 8025250: SA: Sync linux and bsd versions of ps_core file
dsamersoff
parents: 10229
diff changeset
1197 target_vaddr, lib_php->p_filesz, lib_php->p_flags);
5705c7ee6dd7 8025250: SA: Sync linux and bsd versions of ps_core file
dsamersoff
parents: 10229
diff changeset
1198 goto err;
5705c7ee6dd7 8025250: SA: Sync linux and bsd versions of ps_core file
dsamersoff
parents: 10229
diff changeset
1199 }
5705c7ee6dd7 8025250: SA: Sync linux and bsd versions of ps_core file
dsamersoff
parents: 10229
diff changeset
1200
5705c7ee6dd7 8025250: SA: Sync linux and bsd versions of ps_core file
dsamersoff
parents: 10229
diff changeset
1201 /* replace PT_LOAD segment with library segment */
5705c7ee6dd7 8025250: SA: Sync linux and bsd versions of ps_core file
dsamersoff
parents: 10229
diff changeset
1202 print_debug("overwrote with new address mapping (memsz %ld -> %ld)\n",
5705c7ee6dd7 8025250: SA: Sync linux and bsd versions of ps_core file
dsamersoff
parents: 10229
diff changeset
1203 existing_map->memsz, lib_php->p_filesz);
5705c7ee6dd7 8025250: SA: Sync linux and bsd versions of ps_core file
dsamersoff
parents: 10229
diff changeset
1204
5705c7ee6dd7 8025250: SA: Sync linux and bsd versions of ps_core file
dsamersoff
parents: 10229
diff changeset
1205 existing_map->fd = lib_fd;
5705c7ee6dd7 8025250: SA: Sync linux and bsd versions of ps_core file
dsamersoff
parents: 10229
diff changeset
1206 existing_map->offset = lib_php->p_offset;
5705c7ee6dd7 8025250: SA: Sync linux and bsd versions of ps_core file
dsamersoff
parents: 10229
diff changeset
1207 existing_map->memsz = lib_php->p_filesz;
3960
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1208 }
12807
5705c7ee6dd7 8025250: SA: Sync linux and bsd versions of ps_core file
dsamersoff
parents: 10229
diff changeset
1209 }
5705c7ee6dd7 8025250: SA: Sync linux and bsd versions of ps_core file
dsamersoff
parents: 10229
diff changeset
1210
5705c7ee6dd7 8025250: SA: Sync linux and bsd versions of ps_core file
dsamersoff
parents: 10229
diff changeset
1211 lib_php++;
5705c7ee6dd7 8025250: SA: Sync linux and bsd versions of ps_core file
dsamersoff
parents: 10229
diff changeset
1212 }
3960
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1213
12807
5705c7ee6dd7 8025250: SA: Sync linux and bsd versions of ps_core file
dsamersoff
parents: 10229
diff changeset
1214 free(phbuf);
5705c7ee6dd7 8025250: SA: Sync linux and bsd versions of ps_core file
dsamersoff
parents: 10229
diff changeset
1215 return true;
3960
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1216 err:
12807
5705c7ee6dd7 8025250: SA: Sync linux and bsd versions of ps_core file
dsamersoff
parents: 10229
diff changeset
1217 free(phbuf);
5705c7ee6dd7 8025250: SA: Sync linux and bsd versions of ps_core file
dsamersoff
parents: 10229
diff changeset
1218 return false;
3960
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1219 }
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1220
12807
5705c7ee6dd7 8025250: SA: Sync linux and bsd versions of ps_core file
dsamersoff
parents: 10229
diff changeset
1221 // process segments from interpreter (ld.so or ld-linux.so or ld-elf.so)
3960
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1222 static bool read_interp_segments(struct ps_prochandle* ph) {
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1223 ELF_EHDR interp_ehdr;
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1224
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1225 if (read_elf_header(ph->core->interp_fd, &interp_ehdr) != true) {
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1226 print_debug("interpreter is not a valid ELF file\n");
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1227 return false;
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1228 }
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1229
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1230 if (read_lib_segments(ph, ph->core->interp_fd, &interp_ehdr, ph->core->ld_base_addr) != true) {
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1231 print_debug("can't read segments of interpreter\n");
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1232 return false;
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1233 }
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1234
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1235 return true;
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1236 }
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1237
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1238 // process segments of a a.out
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1239 static bool read_exec_segments(struct ps_prochandle* ph, ELF_EHDR* exec_ehdr) {
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1240 int i = 0;
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1241 ELF_PHDR* phbuf = NULL;
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1242 ELF_PHDR* exec_php = NULL;
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1243
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1244 if ((phbuf = read_program_header_table(ph->core->exec_fd, exec_ehdr)) == NULL)
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1245 return false;
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1246
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1247 for (exec_php = phbuf, i = 0; i < exec_ehdr->e_phnum; i++) {
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1248 switch (exec_php->p_type) {
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1249
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1250 // add mappings for PT_LOAD segments
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1251 case PT_LOAD: {
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1252 // add only non-writable segments of non-zero filesz
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1253 if (!(exec_php->p_flags & PF_W) && exec_php->p_filesz != 0) {
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1254 if (add_map_info(ph, ph->core->exec_fd, exec_php->p_offset, exec_php->p_vaddr, exec_php->p_filesz) == NULL) goto err;
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1255 }
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1256 break;
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1257 }
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1258
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1259 // read the interpreter and it's segments
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1260 case PT_INTERP: {
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1261 char interp_name[BUF_SIZE];
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1262
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1263 pread(ph->core->exec_fd, interp_name, MIN(exec_php->p_filesz, BUF_SIZE), exec_php->p_offset);
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1264 print_debug("ELF interpreter %s\n", interp_name);
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1265 // read interpreter segments as well
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1266 if ((ph->core->interp_fd = pathmap_open(interp_name)) < 0) {
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1267 print_debug("can't open runtime loader\n");
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1268 goto err;
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1269 }
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1270 break;
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1271 }
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1272
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1273 // from PT_DYNAMIC we want to read address of first link_map addr
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1274 case PT_DYNAMIC: {
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1275 ph->core->dynamic_addr = exec_php->p_vaddr;
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1276 print_debug("address of _DYNAMIC is 0x%lx\n", ph->core->dynamic_addr);
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1277 break;
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1278 }
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1279
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1280 } // switch
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1281 exec_php++;
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1282 } // for
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1283
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1284 free(phbuf);
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1285 return true;
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1286 err:
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1287 free(phbuf);
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1288 return false;
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1289 }
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1290
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1291 #define FIRST_LINK_MAP_OFFSET offsetof(struct r_debug, r_map)
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1292 #define LD_BASE_OFFSET offsetof(struct r_debug, r_ldbase)
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1293 #define LINK_MAP_ADDR_OFFSET offsetof(struct link_map, l_addr)
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1294 #define LINK_MAP_NAME_OFFSET offsetof(struct link_map, l_name)
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1295 #define LINK_MAP_NEXT_OFFSET offsetof(struct link_map, l_next)
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1296
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1297 // read shared library info from runtime linker's data structures.
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1298 // This work is done by librtlb_db in Solaris
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1299 static bool read_shared_lib_info(struct ps_prochandle* ph) {
8750
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
1300 uintptr_t addr = ph->core->dynamic_addr;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
1301 uintptr_t debug_base;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
1302 uintptr_t first_link_map_addr;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
1303 uintptr_t ld_base_addr;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
1304 uintptr_t link_map_addr;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
1305 uintptr_t lib_base_diff;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
1306 uintptr_t lib_base;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
1307 uintptr_t lib_name_addr;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
1308 char lib_name[BUF_SIZE];
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
1309 ELF_DYN dyn;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
1310 ELF_EHDR elf_ehdr;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
1311 int lib_fd;
3960
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1312
8750
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
1313 // _DYNAMIC has information of the form
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
1314 // [tag] [data] [tag] [data] .....
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
1315 // Both tag and data are pointer sized.
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
1316 // We look for dynamic info with DT_DEBUG. This has shared object info.
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
1317 // refer to struct r_debug in link.h
3960
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1318
8750
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
1319 dyn.d_tag = DT_NULL;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
1320 while (dyn.d_tag != DT_DEBUG) {
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
1321 if (ps_pread(ph, (psaddr_t) addr, &dyn, sizeof(ELF_DYN)) != PS_OK) {
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
1322 print_debug("can't read debug info from _DYNAMIC\n");
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
1323 return false;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
1324 }
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
1325 addr += sizeof(ELF_DYN);
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
1326 }
3960
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1327
8750
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
1328 // we have got Dyn entry with DT_DEBUG
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
1329 debug_base = dyn.d_un.d_ptr;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
1330 // at debug_base we have struct r_debug. This has first link map in r_map field
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
1331 if (ps_pread(ph, (psaddr_t) debug_base + FIRST_LINK_MAP_OFFSET,
12807
5705c7ee6dd7 8025250: SA: Sync linux and bsd versions of ps_core file
dsamersoff
parents: 10229
diff changeset
1332 &first_link_map_addr, sizeof(uintptr_t)) != PS_OK) {
8750
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
1333 print_debug("can't read first link map address\n");
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
1334 return false;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
1335 }
3960
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1336
8750
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
1337 // read ld_base address from struct r_debug
12807
5705c7ee6dd7 8025250: SA: Sync linux and bsd versions of ps_core file
dsamersoff
parents: 10229
diff changeset
1338 #if 0 // There is no r_ldbase member on BSD
8750
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
1339 if (ps_pread(ph, (psaddr_t) debug_base + LD_BASE_OFFSET, &ld_base_addr,
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
1340 sizeof(uintptr_t)) != PS_OK) {
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
1341 print_debug("can't read ld base address\n");
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
1342 return false;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
1343 }
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
1344 ph->core->ld_base_addr = ld_base_addr;
12807
5705c7ee6dd7 8025250: SA: Sync linux and bsd versions of ps_core file
dsamersoff
parents: 10229
diff changeset
1345 #else
8750
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
1346 ph->core->ld_base_addr = 0;
12807
5705c7ee6dd7 8025250: SA: Sync linux and bsd versions of ps_core file
dsamersoff
parents: 10229
diff changeset
1347 #endif
3960
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1348
8750
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
1349 print_debug("interpreter base address is 0x%lx\n", ld_base_addr);
3960
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1350
12807
5705c7ee6dd7 8025250: SA: Sync linux and bsd versions of ps_core file
dsamersoff
parents: 10229
diff changeset
1351 // now read segments from interp (i.e ld.so or ld-linux.so or ld-elf.so)
5705c7ee6dd7 8025250: SA: Sync linux and bsd versions of ps_core file
dsamersoff
parents: 10229
diff changeset
1352 if (read_interp_segments(ph) != true) {
8750
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
1353 return false;
12807
5705c7ee6dd7 8025250: SA: Sync linux and bsd versions of ps_core file
dsamersoff
parents: 10229
diff changeset
1354 }
3960
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1355
8750
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
1356 // after adding interpreter (ld.so) mappings sort again
12807
5705c7ee6dd7 8025250: SA: Sync linux and bsd versions of ps_core file
dsamersoff
parents: 10229
diff changeset
1357 if (sort_map_array(ph) != true) {
8750
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
1358 return false;
12807
5705c7ee6dd7 8025250: SA: Sync linux and bsd versions of ps_core file
dsamersoff
parents: 10229
diff changeset
1359 }
3960
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1360
8750
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
1361 print_debug("first link map is at 0x%lx\n", first_link_map_addr);
3960
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1362
8750
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
1363 link_map_addr = first_link_map_addr;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
1364 while (link_map_addr != 0) {
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
1365 // read library base address of the .so. Note that even though <sys/link.h> calls
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
1366 // link_map->l_addr as "base address", this is * not * really base virtual
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
1367 // address of the shared object. This is actually the difference b/w the virtual
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
1368 // address mentioned in shared object and the actual virtual base where runtime
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
1369 // linker loaded it. We use "base diff" in read_lib_segments call below.
3960
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1370
8750
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
1371 if (ps_pread(ph, (psaddr_t) link_map_addr + LINK_MAP_ADDR_OFFSET,
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
1372 &lib_base_diff, sizeof(uintptr_t)) != PS_OK) {
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
1373 print_debug("can't read shared object base address diff\n");
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
1374 return false;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
1375 }
3960
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1376
8750
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
1377 // read address of the name
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
1378 if (ps_pread(ph, (psaddr_t) link_map_addr + LINK_MAP_NAME_OFFSET,
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
1379 &lib_name_addr, sizeof(uintptr_t)) != PS_OK) {
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
1380 print_debug("can't read address of shared object name\n");
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
1381 return false;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
1382 }
3960
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1383
8750
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
1384 // read name of the shared object
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
1385 if (read_string(ph, (uintptr_t) lib_name_addr, lib_name, sizeof(lib_name)) != true) {
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
1386 print_debug("can't read shared object name\n");
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
1387 return false;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
1388 }
3960
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1389
8750
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
1390 if (lib_name[0] != '\0') {
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
1391 // ignore empty lib names
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
1392 lib_fd = pathmap_open(lib_name);
3960
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1393
8750
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
1394 if (lib_fd < 0) {
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
1395 print_debug("can't open shared object %s\n", lib_name);
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
1396 // continue with other libraries...
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
1397 } else {
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
1398 if (read_elf_header(lib_fd, &elf_ehdr)) {
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
1399 lib_base = lib_base_diff + find_base_address(lib_fd, &elf_ehdr);
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
1400 print_debug("reading library %s @ 0x%lx [ 0x%lx ]\n",
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
1401 lib_name, lib_base, lib_base_diff);
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
1402 // while adding library mappings we need to use "base difference".
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
1403 if (! read_lib_segments(ph, lib_fd, &elf_ehdr, lib_base_diff)) {
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
1404 print_debug("can't read shared object's segments\n");
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
1405 close(lib_fd);
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
1406 return false;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
1407 }
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
1408 add_lib_info_fd(ph, lib_name, lib_fd, lib_base);
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
1409 // Map info is added for the library (lib_name) so
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
1410 // we need to re-sort it before calling the p_pdread.
12807
5705c7ee6dd7 8025250: SA: Sync linux and bsd versions of ps_core file
dsamersoff
parents: 10229
diff changeset
1411 if (sort_map_array(ph) != true) {
8750
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
1412 return false;
12807
5705c7ee6dd7 8025250: SA: Sync linux and bsd versions of ps_core file
dsamersoff
parents: 10229
diff changeset
1413 }
8750
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
1414 } else {
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
1415 print_debug("can't read ELF header for shared object %s\n", lib_name);
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
1416 close(lib_fd);
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
1417 // continue with other libraries...
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
1418 }
3960
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1419 }
8750
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
1420 }
3960
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1421
8750
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
1422 // read next link_map address
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
1423 if (ps_pread(ph, (psaddr_t) link_map_addr + LINK_MAP_NEXT_OFFSET,
12807
5705c7ee6dd7 8025250: SA: Sync linux and bsd versions of ps_core file
dsamersoff
parents: 10229
diff changeset
1424 &link_map_addr, sizeof(uintptr_t)) != PS_OK) {
8750
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
1425 print_debug("can't read next link in link_map\n");
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
1426 return false;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
1427 }
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
1428 }
3960
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1429
8750
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
1430 return true;
3960
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1431 }
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1432
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1433 // the one and only one exposed stuff from this file
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1434 struct ps_prochandle* Pgrab_core(const char* exec_file, const char* core_file) {
8750
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
1435 ELF_EHDR core_ehdr;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
1436 ELF_EHDR exec_ehdr;
3960
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1437
8750
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
1438 struct ps_prochandle* ph = (struct ps_prochandle*) calloc(1, sizeof(struct ps_prochandle));
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
1439 if (ph == NULL) {
12807
5705c7ee6dd7 8025250: SA: Sync linux and bsd versions of ps_core file
dsamersoff
parents: 10229
diff changeset
1440 print_debug("can't allocate ps_prochandle\n");
8750
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
1441 return NULL;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
1442 }
3960
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1443
8750
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
1444 if ((ph->core = (struct core_data*) calloc(1, sizeof(struct core_data))) == NULL) {
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
1445 free(ph);
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
1446 print_debug("can't allocate ps_prochandle\n");
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
1447 return NULL;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
1448 }
3960
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1449
8750
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
1450 // initialize ph
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
1451 ph->ops = &core_ops;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
1452 ph->core->core_fd = -1;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
1453 ph->core->exec_fd = -1;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
1454 ph->core->interp_fd = -1;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
1455
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
1456 print_debug("exec: %s core: %s", exec_file, core_file);
3960
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1457
8750
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
1458 // open the core file
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
1459 if ((ph->core->core_fd = open(core_file, O_RDONLY)) < 0) {
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
1460 print_debug("can't open core file\n");
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
1461 goto err;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
1462 }
3960
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1463
8750
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
1464 // read core file ELF header
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
1465 if (read_elf_header(ph->core->core_fd, &core_ehdr) != true || core_ehdr.e_type != ET_CORE) {
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
1466 print_debug("core file is not a valid ELF ET_CORE file\n");
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
1467 goto err;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
1468 }
3960
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1469
8750
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
1470 if ((ph->core->exec_fd = open(exec_file, O_RDONLY)) < 0) {
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
1471 print_debug("can't open executable file\n");
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
1472 goto err;
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
1473 }
3960
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1474
8750
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
1475 if (read_elf_header(ph->core->exec_fd, &exec_ehdr) != true || exec_ehdr.e_type != ET_EXEC) {
12807
5705c7ee6dd7 8025250: SA: Sync linux and bsd versions of ps_core file
dsamersoff
parents: 10229
diff changeset
1476 print_debug("executable file is not a valid ELF ET_EXEC file\n");
5705c7ee6dd7 8025250: SA: Sync linux and bsd versions of ps_core file
dsamersoff
parents: 10229
diff changeset
1477 goto err;
8750
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
1478 }
3960
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1479
8750
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
1480 // process core file segments
12807
5705c7ee6dd7 8025250: SA: Sync linux and bsd versions of ps_core file
dsamersoff
parents: 10229
diff changeset
1481 if (read_core_segments(ph, &core_ehdr) != true) {
5705c7ee6dd7 8025250: SA: Sync linux and bsd versions of ps_core file
dsamersoff
parents: 10229
diff changeset
1482 goto err;
5705c7ee6dd7 8025250: SA: Sync linux and bsd versions of ps_core file
dsamersoff
parents: 10229
diff changeset
1483 }
3960
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1484
8750
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
1485 // process exec file segments
12807
5705c7ee6dd7 8025250: SA: Sync linux and bsd versions of ps_core file
dsamersoff
parents: 10229
diff changeset
1486 if (read_exec_segments(ph, &exec_ehdr) != true) {
5705c7ee6dd7 8025250: SA: Sync linux and bsd versions of ps_core file
dsamersoff
parents: 10229
diff changeset
1487 goto err;
5705c7ee6dd7 8025250: SA: Sync linux and bsd versions of ps_core file
dsamersoff
parents: 10229
diff changeset
1488 }
3960
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1489
8750
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
1490 // exec file is also treated like a shared object for symbol search
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
1491 if (add_lib_info_fd(ph, exec_file, ph->core->exec_fd,
12807
5705c7ee6dd7 8025250: SA: Sync linux and bsd versions of ps_core file
dsamersoff
parents: 10229
diff changeset
1492 (uintptr_t)0 + find_base_address(ph->core->exec_fd, &exec_ehdr)) == NULL) {
5705c7ee6dd7 8025250: SA: Sync linux and bsd versions of ps_core file
dsamersoff
parents: 10229
diff changeset
1493 goto err;
5705c7ee6dd7 8025250: SA: Sync linux and bsd versions of ps_core file
dsamersoff
parents: 10229
diff changeset
1494 }
3960
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1495
8750
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
1496 // allocate and sort maps into map_array, we need to do this
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
1497 // here because read_shared_lib_info needs to read from debuggee
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
1498 // address space
12807
5705c7ee6dd7 8025250: SA: Sync linux and bsd versions of ps_core file
dsamersoff
parents: 10229
diff changeset
1499 if (sort_map_array(ph) != true) {
8750
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
1500 goto err;
12807
5705c7ee6dd7 8025250: SA: Sync linux and bsd versions of ps_core file
dsamersoff
parents: 10229
diff changeset
1501 }
3960
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1502
12807
5705c7ee6dd7 8025250: SA: Sync linux and bsd versions of ps_core file
dsamersoff
parents: 10229
diff changeset
1503 if (read_shared_lib_info(ph) != true) {
8750
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
1504 goto err;
12807
5705c7ee6dd7 8025250: SA: Sync linux and bsd versions of ps_core file
dsamersoff
parents: 10229
diff changeset
1505 }
3960
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1506
8750
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
1507 // sort again because we have added more mappings from shared objects
12807
5705c7ee6dd7 8025250: SA: Sync linux and bsd versions of ps_core file
dsamersoff
parents: 10229
diff changeset
1508 if (sort_map_array(ph) != true) {
8750
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
1509 goto err;
12807
5705c7ee6dd7 8025250: SA: Sync linux and bsd versions of ps_core file
dsamersoff
parents: 10229
diff changeset
1510 }
3960
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1511
12807
5705c7ee6dd7 8025250: SA: Sync linux and bsd versions of ps_core file
dsamersoff
parents: 10229
diff changeset
1512 if (init_classsharing_workaround(ph) != true) {
8750
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
1513 goto err;
12807
5705c7ee6dd7 8025250: SA: Sync linux and bsd versions of ps_core file
dsamersoff
parents: 10229
diff changeset
1514 }
3960
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1515
8750
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
1516 print_debug("Leave Pgrab_core\n");
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
1517 return ph;
3960
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1518
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1519 err:
8750
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
1520 Prelease(ph);
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
1521 return NULL;
3960
f08d439fab8c 7089790: integrate bsd-port changes
never
parents:
diff changeset
1522 }
8750
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
1523
39432a1cefdd 8003348: SA can not read core file on OS
minqi
parents: 6725
diff changeset
1524 #endif // __APPLE__