i386-gnu-nat.c 12 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446
  1. /* Low level interface to i386 running the GNU Hurd.
  2. Copyright (C) 1992-2022 Free Software Foundation, Inc.
  3. This file is part of GDB.
  4. This program is free software; you can redistribute it and/or modify
  5. it under the terms of the GNU General Public License as published by
  6. the Free Software Foundation; either version 3 of the License, or
  7. (at your option) any later version.
  8. This program is distributed in the hope that it will be useful,
  9. but WITHOUT ANY WARRANTY; without even the implied warranty of
  10. MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
  11. GNU General Public License for more details.
  12. You should have received a copy of the GNU General Public License
  13. along with this program. If not, see <http://www.gnu.org/licenses/>. */
  14. /* Include this first, to pick up the <mach.h> 'thread_info' diversion. */
  15. #include "gnu-nat.h"
  16. /* Mach/Hurd headers are not yet ready for C++ compilation. */
  17. extern "C"
  18. {
  19. #include <mach.h>
  20. #include <mach_error.h>
  21. #include <mach/message.h>
  22. #include <mach/exception.h>
  23. }
  24. #include "defs.h"
  25. #include "x86-nat.h"
  26. #include "inferior.h"
  27. #include "floatformat.h"
  28. #include "regcache.h"
  29. #include "i386-tdep.h"
  30. #include "inf-child.h"
  31. #include "i387-tdep.h"
  32. /* Offset to the thread_state_t location where REG is stored. */
  33. #define REG_OFFSET(reg) offsetof (struct i386_thread_state, reg)
  34. /* At REG_OFFSET[N] is the offset to the thread_state_t location where
  35. the GDB register N is stored. */
  36. static int reg_offset[] =
  37. {
  38. REG_OFFSET (eax), REG_OFFSET (ecx), REG_OFFSET (edx), REG_OFFSET (ebx),
  39. REG_OFFSET (uesp), REG_OFFSET (ebp), REG_OFFSET (esi), REG_OFFSET (edi),
  40. REG_OFFSET (eip), REG_OFFSET (efl), REG_OFFSET (cs), REG_OFFSET (ss),
  41. REG_OFFSET (ds), REG_OFFSET (es), REG_OFFSET (fs), REG_OFFSET (gs)
  42. };
  43. #define REG_ADDR(state, regnum) ((char *)(state) + reg_offset[regnum])
  44. /* The i386 GNU Hurd target. */
  45. #ifdef i386_DEBUG_STATE
  46. using gnu_base_target = x86_nat_target<gnu_nat_target>;
  47. #else
  48. using gnu_base_target = gnu_nat_target;
  49. #endif
  50. struct i386_gnu_nat_target final : public gnu_base_target
  51. {
  52. void fetch_registers (struct regcache *, int) override;
  53. void store_registers (struct regcache *, int) override;
  54. };
  55. static i386_gnu_nat_target the_i386_gnu_nat_target;
  56. /* Get the whole floating-point state of THREAD and record the values
  57. of the corresponding (pseudo) registers. */
  58. static void
  59. fetch_fpregs (struct regcache *regcache, struct proc *thread)
  60. {
  61. mach_msg_type_number_t count = i386_FLOAT_STATE_COUNT;
  62. struct i386_float_state state;
  63. kern_return_t err;
  64. err = thread_get_state (thread->port, i386_FLOAT_STATE,
  65. (thread_state_t) &state, &count);
  66. if (err)
  67. {
  68. warning (_("Couldn't fetch floating-point state from %s"),
  69. proc_string (thread));
  70. return;
  71. }
  72. if (!state.initialized)
  73. {
  74. /* The floating-point state isn't initialized. */
  75. i387_supply_fsave (regcache, -1, NULL);
  76. }
  77. else
  78. {
  79. /* Supply the floating-point registers. */
  80. i387_supply_fsave (regcache, -1, state.hw_state);
  81. }
  82. }
  83. /* Fetch register REGNO, or all regs if REGNO is -1. */
  84. void
  85. i386_gnu_nat_target::fetch_registers (struct regcache *regcache, int regno)
  86. {
  87. struct proc *thread;
  88. ptid_t ptid = regcache->ptid ();
  89. /* Make sure we know about new threads. */
  90. inf_update_procs (gnu_current_inf);
  91. thread = inf_tid_to_thread (gnu_current_inf, ptid.lwp ());
  92. if (!thread)
  93. error (_("Can't fetch registers from thread %s: No such thread"),
  94. target_pid_to_str (ptid).c_str ());
  95. if (regno < I386_NUM_GREGS || regno == -1)
  96. {
  97. thread_state_t state;
  98. /* This does the dirty work for us. */
  99. state = proc_get_state (thread, 0);
  100. if (!state)
  101. {
  102. warning (_("Couldn't fetch registers from %s"),
  103. proc_string (thread));
  104. return;
  105. }
  106. if (regno == -1)
  107. {
  108. int i;
  109. proc_debug (thread, "fetching all register");
  110. for (i = 0; i < I386_NUM_GREGS; i++)
  111. regcache->raw_supply (i, REG_ADDR (state, i));
  112. thread->fetched_regs = ~0;
  113. }
  114. else
  115. {
  116. proc_debug (thread, "fetching register %s",
  117. gdbarch_register_name (regcache->arch (),
  118. regno));
  119. regcache->raw_supply (regno, REG_ADDR (state, regno));
  120. thread->fetched_regs |= (1 << regno);
  121. }
  122. }
  123. if (regno >= I386_NUM_GREGS || regno == -1)
  124. {
  125. proc_debug (thread, "fetching floating-point registers");
  126. fetch_fpregs (regcache, thread);
  127. }
  128. }
  129. /* Store the whole floating-point state into THREAD using information
  130. from the corresponding (pseudo) registers. */
  131. static void
  132. store_fpregs (const struct regcache *regcache, struct proc *thread, int regno)
  133. {
  134. mach_msg_type_number_t count = i386_FLOAT_STATE_COUNT;
  135. struct i386_float_state state;
  136. kern_return_t err;
  137. err = thread_get_state (thread->port, i386_FLOAT_STATE,
  138. (thread_state_t) &state, &count);
  139. if (err)
  140. {
  141. warning (_("Couldn't fetch floating-point state from %s"),
  142. proc_string (thread));
  143. return;
  144. }
  145. /* FIXME: kettenis/2001-07-15: Is this right? Should we somehow
  146. take into account DEPRECATED_REGISTER_VALID like the old code did? */
  147. i387_collect_fsave (regcache, regno, state.hw_state);
  148. err = thread_set_state (thread->port, i386_FLOAT_STATE,
  149. (thread_state_t) &state, i386_FLOAT_STATE_COUNT);
  150. if (err)
  151. {
  152. warning (_("Couldn't store floating-point state into %s"),
  153. proc_string (thread));
  154. return;
  155. }
  156. }
  157. /* Store at least register REGNO, or all regs if REGNO == -1. */
  158. void
  159. i386_gnu_nat_target::store_registers (struct regcache *regcache, int regno)
  160. {
  161. struct proc *thread;
  162. struct gdbarch *gdbarch = regcache->arch ();
  163. ptid_t ptid = regcache->ptid ();
  164. /* Make sure we know about new threads. */
  165. inf_update_procs (gnu_current_inf);
  166. thread = inf_tid_to_thread (gnu_current_inf, ptid.lwp ());
  167. if (!thread)
  168. error (_("Couldn't store registers into thread %s: No such thread"),
  169. target_pid_to_str (ptid).c_str ());
  170. if (regno < I386_NUM_GREGS || regno == -1)
  171. {
  172. thread_state_t state;
  173. thread_state_data_t old_state;
  174. int was_aborted = thread->aborted;
  175. int was_valid = thread->state_valid;
  176. int trace;
  177. if (!was_aborted && was_valid)
  178. memcpy (&old_state, &thread->state, sizeof (old_state));
  179. state = proc_get_state (thread, 1);
  180. if (!state)
  181. {
  182. warning (_("Couldn't store registers into %s"),
  183. proc_string (thread));
  184. return;
  185. }
  186. /* Save the T bit. We might try to restore the %eflags register
  187. below, but changing the T bit would seriously confuse GDB. */
  188. trace = ((struct i386_thread_state *)state)->efl & 0x100;
  189. if (!was_aborted && was_valid)
  190. /* See which registers have changed after aborting the thread. */
  191. {
  192. int check_regno;
  193. for (check_regno = 0; check_regno < I386_NUM_GREGS; check_regno++)
  194. if ((thread->fetched_regs & (1 << check_regno))
  195. && memcpy (REG_ADDR (&old_state, check_regno),
  196. REG_ADDR (state, check_regno),
  197. register_size (gdbarch, check_regno)))
  198. /* Register CHECK_REGNO has changed! Ack! */
  199. {
  200. warning (_("Register %s changed after the thread was aborted"),
  201. gdbarch_register_name (gdbarch, check_regno));
  202. if (regno >= 0 && regno != check_regno)
  203. /* Update GDB's copy of the register. */
  204. regcache->raw_supply (check_regno,
  205. REG_ADDR (state, check_regno));
  206. else
  207. warning (_("... also writing this register! "
  208. "Suspicious..."));
  209. }
  210. }
  211. if (regno == -1)
  212. {
  213. int i;
  214. proc_debug (thread, "storing all registers");
  215. for (i = 0; i < I386_NUM_GREGS; i++)
  216. if (REG_VALID == regcache->get_register_status (i))
  217. regcache->raw_collect (i, REG_ADDR (state, i));
  218. }
  219. else
  220. {
  221. proc_debug (thread, "storing register %s",
  222. gdbarch_register_name (gdbarch, regno));
  223. gdb_assert (REG_VALID == regcache->get_register_status (regno));
  224. regcache->raw_collect (regno, REG_ADDR (state, regno));
  225. }
  226. /* Restore the T bit. */
  227. ((struct i386_thread_state *)state)->efl &= ~0x100;
  228. ((struct i386_thread_state *)state)->efl |= trace;
  229. }
  230. if (regno >= I386_NUM_GREGS || regno == -1)
  231. {
  232. proc_debug (thread, "storing floating-point registers");
  233. store_fpregs (regcache, thread, regno);
  234. }
  235. }
  236. /* Support for debug registers. */
  237. #ifdef i386_DEBUG_STATE
  238. /* Get debug registers for thread THREAD. */
  239. static void
  240. i386_gnu_dr_get (struct i386_debug_state *regs, struct proc *thread)
  241. {
  242. mach_msg_type_number_t count = i386_DEBUG_STATE_COUNT;
  243. kern_return_t err;
  244. err = thread_get_state (thread->port, i386_DEBUG_STATE,
  245. (thread_state_t) regs, &count);
  246. if (err != 0 || count != i386_DEBUG_STATE_COUNT)
  247. warning (_("Couldn't fetch debug state from %s"),
  248. proc_string (thread));
  249. }
  250. /* Set debug registers for thread THREAD. */
  251. static void
  252. i386_gnu_dr_set (const struct i386_debug_state *regs, struct proc *thread)
  253. {
  254. kern_return_t err;
  255. err = thread_set_state (thread->port, i386_DEBUG_STATE,
  256. (thread_state_t) regs, i386_DEBUG_STATE_COUNT);
  257. if (err != 0)
  258. warning (_("Couldn't store debug state into %s"),
  259. proc_string (thread));
  260. }
  261. /* Set DR_CONTROL in THREAD. */
  262. static void
  263. i386_gnu_dr_set_control_one (struct proc *thread, void *arg)
  264. {
  265. unsigned long *control = (unsigned long *) arg;
  266. struct i386_debug_state regs;
  267. i386_gnu_dr_get (&regs, thread);
  268. regs.dr[DR_CONTROL] = *control;
  269. i386_gnu_dr_set (&regs, thread);
  270. }
  271. /* Set DR_CONTROL to CONTROL in all threads. */
  272. static void
  273. i386_gnu_dr_set_control (unsigned long control)
  274. {
  275. inf_update_procs (gnu_current_inf);
  276. inf_threads (gnu_current_inf, i386_gnu_dr_set_control_one, &control);
  277. }
  278. /* Parameters to set a debugging address. */
  279. struct reg_addr
  280. {
  281. int regnum; /* Register number (zero based). */
  282. CORE_ADDR addr; /* Address. */
  283. };
  284. /* Set address REGNUM (zero based) to ADDR in THREAD. */
  285. static void
  286. i386_gnu_dr_set_addr_one (struct proc *thread, void *arg)
  287. {
  288. struct reg_addr *reg_addr = (struct reg_addr *) arg;
  289. struct i386_debug_state regs;
  290. i386_gnu_dr_get (&regs, thread);
  291. regs.dr[reg_addr->regnum] = reg_addr->addr;
  292. i386_gnu_dr_set (&regs, thread);
  293. }
  294. /* Set address REGNUM (zero based) to ADDR in all threads. */
  295. static void
  296. i386_gnu_dr_set_addr (int regnum, CORE_ADDR addr)
  297. {
  298. struct reg_addr reg_addr;
  299. gdb_assert (DR_FIRSTADDR <= regnum && regnum <= DR_LASTADDR);
  300. reg_addr.regnum = regnum;
  301. reg_addr.addr = addr;
  302. inf_update_procs (gnu_current_inf);
  303. inf_threads (gnu_current_inf, i386_gnu_dr_set_addr_one, &reg_addr);
  304. }
  305. /* Get debug register REGNUM value from only the one LWP of PTID. */
  306. static unsigned long
  307. i386_gnu_dr_get_reg (ptid_t ptid, int regnum)
  308. {
  309. struct i386_debug_state regs;
  310. struct proc *thread;
  311. /* Make sure we know about new threads. */
  312. inf_update_procs (gnu_current_inf);
  313. thread = inf_tid_to_thread (gnu_current_inf, ptid.lwp ());
  314. i386_gnu_dr_get (&regs, thread);
  315. return regs.dr[regnum];
  316. }
  317. /* Return the inferior's debug register REGNUM. */
  318. static CORE_ADDR
  319. i386_gnu_dr_get_addr (int regnum)
  320. {
  321. gdb_assert (DR_FIRSTADDR <= regnum && regnum <= DR_LASTADDR);
  322. return i386_gnu_dr_get_reg (inferior_ptid, regnum);
  323. }
  324. /* Get DR_STATUS from only the one thread of INFERIOR_PTID. */
  325. static unsigned long
  326. i386_gnu_dr_get_status (void)
  327. {
  328. return i386_gnu_dr_get_reg (inferior_ptid, DR_STATUS);
  329. }
  330. /* Return the inferior's DR7 debug control register. */
  331. static unsigned long
  332. i386_gnu_dr_get_control (void)
  333. {
  334. return i386_gnu_dr_get_reg (inferior_ptid, DR_CONTROL);
  335. }
  336. #endif /* i386_DEBUG_STATE */
  337. void _initialize_i386gnu_nat ();
  338. void
  339. _initialize_i386gnu_nat ()
  340. {
  341. #ifdef i386_DEBUG_STATE
  342. x86_dr_low.set_control = i386_gnu_dr_set_control;
  343. gdb_assert (DR_FIRSTADDR == 0 && DR_LASTADDR < i386_DEBUG_STATE_COUNT);
  344. x86_dr_low.set_addr = i386_gnu_dr_set_addr;
  345. x86_dr_low.get_addr = i386_gnu_dr_get_addr;
  346. x86_dr_low.get_status = i386_gnu_dr_get_status;
  347. x86_dr_low.get_control = i386_gnu_dr_get_control;
  348. x86_set_debug_register_length (4);
  349. #endif /* i386_DEBUG_STATE */
  350. gnu_target = &the_i386_gnu_nat_target;
  351. /* Register the target. */
  352. add_inf_child_target (&the_i386_gnu_nat_target);
  353. }