1 /* Shared utility routines for GDB to interact with agent.
3 Copyright (C) 2009-2014 Free Software Foundation, Inc.
5 This file is part of GDB.
7 This program is free software; you can redistribute it and/or modify
8 it under the terms of the GNU General Public License as published by
9 the Free Software Foundation; either version 3 of the License, or
10 (at your option) any later version.
12 This program is distributed in the hope that it will be useful,
13 but WITHOUT ANY WARRANTY; without even the implied warranty of
14 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
15 GNU General Public License for more details.
17 You should have received a copy of the GNU General Public License
18 along with this program. If not, see <http://www.gnu.org/licenses/>. */
32 #include "filestuff.h"
37 #define DEBUG_AGENT(fmt, args...) \
39 fprintf (stderr, fmt, ##args);
41 #define DEBUG_AGENT(fmt, args...) \
43 fprintf_unfiltered (gdb_stdlog, fmt, ##args);
46 /* Global flag to determine using agent or not. */
49 /* Addresses of in-process agent's symbols both GDB and GDBserver cares
52 struct ipa_sym_addresses
54 CORE_ADDR addr_helper_thread_id
;
55 CORE_ADDR addr_cmd_buf
;
56 CORE_ADDR addr_capability
;
59 /* Cache of the helper thread id. FIXME: this global should be made
61 static unsigned int helper_thread_id
= 0;
69 IPA_SYM(helper_thread_id
),
74 static struct ipa_sym_addresses ipa_sym_addrs
;
76 static int all_agent_symbols_looked_up
= 0;
81 return all_agent_symbols_looked_up
;
84 /* Look up all symbols needed by agent. Return 0 if all the symbols are
85 found, return non-zero otherwise. */
88 agent_look_up_symbols (void *arg
)
92 all_agent_symbols_looked_up
= 0;
94 for (i
= 0; i
< sizeof (symbol_list
) / sizeof (symbol_list
[0]); i
++)
97 (CORE_ADDR
*) ((char *) &ipa_sym_addrs
+ symbol_list
[i
].offset
);
100 if (look_up_one_symbol (symbol_list
[i
].name
, addrp
, 1) == 0)
102 struct bound_minimal_symbol sym
=
103 lookup_minimal_symbol (symbol_list
[i
].name
, NULL
,
104 (struct objfile
*) arg
);
106 if (sym
.minsym
!= NULL
)
107 *addrp
= BMSYMBOL_VALUE_ADDRESS (sym
);
111 DEBUG_AGENT ("symbol `%s' not found\n", symbol_list
[i
].name
);
116 all_agent_symbols_looked_up
= 1;
121 agent_get_helper_thread_id (void)
123 if (helper_thread_id
== 0)
126 if (read_inferior_memory (ipa_sym_addrs
.addr_helper_thread_id
,
127 (unsigned char *) &helper_thread_id
,
128 sizeof helper_thread_id
))
130 enum bfd_endian byte_order
= gdbarch_byte_order (target_gdbarch ());
133 if (target_read_memory (ipa_sym_addrs
.addr_helper_thread_id
,
134 buf
, sizeof buf
) == 0)
135 helper_thread_id
= extract_unsigned_integer (buf
, sizeof buf
,
140 warning (_("Error reading helper thread's id in lib"));
144 return helper_thread_id
;
148 #include <sys/socket.h>
150 #define SOCK_DIR P_tmpdir
152 #ifndef UNIX_PATH_MAX
153 #define UNIX_PATH_MAX sizeof(((struct sockaddr_un *) NULL)->sun_path)
158 /* Connects to synchronization socket. PID is the pid of inferior, which is
159 used to set up the connection socket. */
162 gdb_connect_sync_socket (int pid
)
165 struct sockaddr_un addr
;
167 char path
[UNIX_PATH_MAX
];
169 res
= xsnprintf (path
, UNIX_PATH_MAX
, "%s/gdb_ust%d", P_tmpdir
, pid
);
170 if (res
>= UNIX_PATH_MAX
)
173 res
= fd
= gdb_socket_cloexec (PF_UNIX
, SOCK_STREAM
, 0);
176 warning (_("error opening sync socket: %s"), strerror (errno
));
180 addr
.sun_family
= AF_UNIX
;
182 res
= xsnprintf (addr
.sun_path
, UNIX_PATH_MAX
, "%s", path
);
183 if (res
>= UNIX_PATH_MAX
)
185 warning (_("string overflow allocating socket name"));
190 res
= connect (fd
, (struct sockaddr
*) &addr
, sizeof (addr
));
193 warning (_("error connecting sync socket (%s): %s. "
194 "Make sure the directory exists and that it is writable."),
195 path
, strerror (errno
));
206 /* Execute an agent command in the inferior. PID is the value of pid of the
207 inferior. CMD is the buffer for command. GDB or GDBserver will store the
208 command into it and fetch the return result from CMD. The interaction
209 between GDB/GDBserver and the agent is synchronized by a synchronization
210 socket. Return zero if success, otherwise return non-zero. */
213 agent_run_command (int pid
, const char *cmd
, int len
)
216 int tid
= agent_get_helper_thread_id ();
217 ptid_t ptid
= ptid_build (pid
, tid
, 0);
220 int ret
= write_inferior_memory (ipa_sym_addrs
.addr_cmd_buf
,
221 (const unsigned char *) cmd
, len
);
223 int ret
= target_write_memory (ipa_sym_addrs
.addr_cmd_buf
,
224 (gdb_byte
*) cmd
, len
);
229 warning (_("unable to write"));
233 DEBUG_AGENT ("agent: resumed helper thread\n");
235 /* Resume helper thread. */
238 struct thread_resume resume_info
;
240 resume_info
.thread
= ptid
;
241 resume_info
.kind
= resume_continue
;
242 resume_info
.sig
= GDB_SIGNAL_0
;
243 (*the_target
->resume
) (&resume_info
, 1);
246 target_resume (ptid
, 0, GDB_SIGNAL_0
);
249 fd
= gdb_connect_sync_socket (pid
);
255 DEBUG_AGENT ("agent: signalling helper thread\n");
259 ret
= write (fd
, buf
, 1);
260 } while (ret
== -1 && errno
== EINTR
);
262 DEBUG_AGENT ("agent: waiting for helper thread's response\n");
266 ret
= read (fd
, buf
, 1);
267 } while (ret
== -1 && errno
== EINTR
);
271 DEBUG_AGENT ("agent: helper thread's response received\n");
276 /* Need to read response with the inferior stopped. */
277 if (!ptid_equal (ptid
, null_ptid
))
279 struct target_waitstatus status
;
280 int was_non_stop
= non_stop
;
281 /* Stop thread PTID. */
282 DEBUG_AGENT ("agent: stop helper thread\n");
285 struct thread_resume resume_info
;
287 resume_info
.thread
= ptid
;
288 resume_info
.kind
= resume_stop
;
289 resume_info
.sig
= GDB_SIGNAL_0
;
290 (*the_target
->resume
) (&resume_info
, 1);
294 mywait (ptid
, &status
, 0, 0);
299 memset (&status
, 0, sizeof (status
));
300 target_wait (ptid
, &status
, 0);
302 non_stop
= was_non_stop
;
308 if (read_inferior_memory (ipa_sym_addrs
.addr_cmd_buf
,
309 (unsigned char *) cmd
, IPA_CMD_BUF_SIZE
))
311 if (target_read_memory (ipa_sym_addrs
.addr_cmd_buf
, (gdb_byte
*) cmd
,
315 warning (_("Error reading command response"));
323 /* Each bit of it stands for a capability of agent. */
324 static unsigned int agent_capability
= 0;
326 /* Return true if agent has capability AGENT_CAP, otherwise return false. */
329 agent_capability_check (enum agent_capa agent_capa
)
331 if (agent_capability
== 0)
334 if (read_inferior_memory (ipa_sym_addrs
.addr_capability
,
335 (unsigned char *) &agent_capability
,
336 sizeof agent_capability
))
338 enum bfd_endian byte_order
= gdbarch_byte_order (target_gdbarch ());
341 if (target_read_memory (ipa_sym_addrs
.addr_capability
,
342 buf
, sizeof buf
) == 0)
343 agent_capability
= extract_unsigned_integer (buf
, sizeof buf
,
347 warning (_("Error reading capability of agent"));
349 return agent_capability
& agent_capa
;
352 /* Invalidate the cache of agent capability, so we'll read it from inferior
353 again. Call it when launches a new program or reconnect to remote stub. */
356 agent_capability_invalidate (void)
358 agent_capability
= 0;