1/* Intel 387 floating point stuff. 2 3 Copyright 1988, 1989, 1991, 1992, 1993, 1994, 1998, 1999, 2000, 4 2001, 2002, 2003, 2004 Free Software Foundation, Inc. 5 6 This file is part of GDB. 7 8 This program is free software; you can redistribute it and/or modify 9 it under the terms of the GNU General Public License as published by 10 the Free Software Foundation; either version 2 of the License, or 11 (at your option) any later version. 12 13 This program is distributed in the hope that it will be useful, 14 but WITHOUT ANY WARRANTY; without even the implied warranty of 15 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 16 GNU General Public License for more details. 17 18 You should have received a copy of the GNU General Public License 19 along with this program; if not, write to the Free Software 20 Foundation, Inc., 59 Temple Place - Suite 330, 21 Boston, MA 02111-1307, USA. */ 22 23#include "defs.h" 24#include "doublest.h" 25#include "floatformat.h" 26#include "frame.h" 27#include "gdbcore.h" 28#include "inferior.h" 29#include "language.h" 30#include "regcache.h" 31#include "value.h" 32 33#include "gdb_assert.h" 34#include "gdb_string.h" 35 36#include "i386-tdep.h" 37#include "i387-tdep.h" 38 39/* Implement the `info float' layout based on the register definitions 40 in `tm-i386.h'. */ 41 42/* Print the floating point number specified by RAW. */ 43 44static void 45print_i387_value (char *raw, struct ui_file *file) 46{ 47 DOUBLEST value; 48 49 /* Using extract_typed_floating here might affect the representation 50 of certain numbers such as NaNs, even if GDB is running natively. 51 This is fine since our caller already detects such special 52 numbers and we print the hexadecimal representation anyway. */ 53 value = extract_typed_floating (raw, builtin_type_i387_ext); 54 55 /* We try to print 19 digits. The last digit may or may not contain 56 garbage, but we'd better print one too many. We need enough room 57 to print the value, 1 position for the sign, 1 for the decimal 58 point, 19 for the digits and 6 for the exponent adds up to 27. */ 59#ifdef PRINTF_HAS_LONG_DOUBLE 60 fprintf_filtered (file, " %-+27.19Lg", (long double) value); 61#else 62 fprintf_filtered (file, " %-+27.19g", (double) value); 63#endif 64} 65 66/* Print the classification for the register contents RAW. */ 67 68static void 69print_i387_ext (unsigned char *raw, struct ui_file *file) 70{ 71 int sign; 72 int integer; 73 unsigned int exponent; 74 unsigned long fraction[2]; 75 76 sign = raw[9] & 0x80; 77 integer = raw[7] & 0x80; 78 exponent = (((raw[9] & 0x7f) << 8) | raw[8]); 79 fraction[0] = ((raw[3] << 24) | (raw[2] << 16) | (raw[1] << 8) | raw[0]); 80 fraction[1] = (((raw[7] & 0x7f) << 24) | (raw[6] << 16) 81 | (raw[5] << 8) | raw[4]); 82 83 if (exponent == 0x7fff && integer) 84 { 85 if (fraction[0] == 0x00000000 && fraction[1] == 0x00000000) 86 /* Infinity. */ 87 fprintf_filtered (file, " %cInf", (sign ? '-' : '+')); 88 else if (sign && fraction[0] == 0x00000000 && fraction[1] == 0x40000000) 89 /* Real Indefinite (QNaN). */ 90 fputs_unfiltered (" Real Indefinite (QNaN)", file); 91 else if (fraction[1] & 0x40000000) 92 /* QNaN. */ 93 fputs_filtered (" QNaN", file); 94 else 95 /* SNaN. */ 96 fputs_filtered (" SNaN", file); 97 } 98 else if (exponent < 0x7fff && exponent > 0x0000 && integer) 99 /* Normal. */ 100 print_i387_value (raw, file); 101 else if (exponent == 0x0000) 102 { 103 /* Denormal or zero. */ 104 print_i387_value (raw, file); 105 106 if (integer) 107 /* Pseudo-denormal. */ 108 fputs_filtered (" Pseudo-denormal", file); 109 else if (fraction[0] || fraction[1]) 110 /* Denormal. */ 111 fputs_filtered (" Denormal", file); 112 } 113 else 114 /* Unsupported. */ 115 fputs_filtered (" Unsupported", file); 116} 117 118/* Print the status word STATUS. */ 119 120static void 121print_i387_status_word (unsigned int status, struct ui_file *file) 122{ 123 fprintf_filtered (file, "Status Word: %s", 124 local_hex_string_custom (status, "04")); 125 fputs_filtered (" ", file); 126 fprintf_filtered (file, " %s", (status & 0x0001) ? "IE" : " "); 127 fprintf_filtered (file, " %s", (status & 0x0002) ? "DE" : " "); 128 fprintf_filtered (file, " %s", (status & 0x0004) ? "ZE" : " "); 129 fprintf_filtered (file, " %s", (status & 0x0008) ? "OE" : " "); 130 fprintf_filtered (file, " %s", (status & 0x0010) ? "UE" : " "); 131 fprintf_filtered (file, " %s", (status & 0x0020) ? "PE" : " "); 132 fputs_filtered (" ", file); 133 fprintf_filtered (file, " %s", (status & 0x0080) ? "ES" : " "); 134 fputs_filtered (" ", file); 135 fprintf_filtered (file, " %s", (status & 0x0040) ? "SF" : " "); 136 fputs_filtered (" ", file); 137 fprintf_filtered (file, " %s", (status & 0x0100) ? "C0" : " "); 138 fprintf_filtered (file, " %s", (status & 0x0200) ? "C1" : " "); 139 fprintf_filtered (file, " %s", (status & 0x0400) ? "C2" : " "); 140 fprintf_filtered (file, " %s", (status & 0x4000) ? "C3" : " "); 141 142 fputs_filtered ("\n", file); 143 144 fprintf_filtered (file, 145 " TOP: %d\n", ((status >> 11) & 7)); 146} 147 148/* Print the control word CONTROL. */ 149 150static void 151print_i387_control_word (unsigned int control, struct ui_file *file) 152{ 153 fprintf_filtered (file, "Control Word: %s", 154 local_hex_string_custom (control, "04")); 155 fputs_filtered (" ", file); 156 fprintf_filtered (file, " %s", (control & 0x0001) ? "IM" : " "); 157 fprintf_filtered (file, " %s", (control & 0x0002) ? "DM" : " "); 158 fprintf_filtered (file, " %s", (control & 0x0004) ? "ZM" : " "); 159 fprintf_filtered (file, " %s", (control & 0x0008) ? "OM" : " "); 160 fprintf_filtered (file, " %s", (control & 0x0010) ? "UM" : " "); 161 fprintf_filtered (file, " %s", (control & 0x0020) ? "PM" : " "); 162 163 fputs_filtered ("\n", file); 164 165 fputs_filtered (" PC: ", file); 166 switch ((control >> 8) & 3) 167 { 168 case 0: 169 fputs_filtered ("Single Precision (24-bits)\n", file); 170 break; 171 case 1: 172 fputs_filtered ("Reserved\n", file); 173 break; 174 case 2: 175 fputs_filtered ("Double Precision (53-bits)\n", file); 176 break; 177 case 3: 178 fputs_filtered ("Extended Precision (64-bits)\n", file); 179 break; 180 } 181 182 fputs_filtered (" RC: ", file); 183 switch ((control >> 10) & 3) 184 { 185 case 0: 186 fputs_filtered ("Round to nearest\n", file); 187 break; 188 case 1: 189 fputs_filtered ("Round down\n", file); 190 break; 191 case 2: 192 fputs_filtered ("Round up\n", file); 193 break; 194 case 3: 195 fputs_filtered ("Round toward zero\n", file); 196 break; 197 } 198} 199 200/* Print out the i387 floating point state. Note that we ignore FRAME 201 in the code below. That's OK since floating-point registers are 202 never saved on the stack. */ 203 204void 205i387_print_float_info (struct gdbarch *gdbarch, struct ui_file *file, 206 struct frame_info *frame, const char *args) 207{ 208 struct gdbarch_tdep *tdep = gdbarch_tdep (get_frame_arch (frame)); 209 char buf[4]; 210 ULONGEST fctrl; 211 ULONGEST fstat; 212 ULONGEST ftag; 213 ULONGEST fiseg; 214 ULONGEST fioff; 215 ULONGEST foseg; 216 ULONGEST fooff; 217 ULONGEST fop; 218 int fpreg; 219 int top; 220 221 gdb_assert (gdbarch == get_frame_arch (frame)); 222 223 /* Define I387_ST0_REGNUM such that we use the proper definitions 224 for FRAME's architecture. */ 225#define I387_ST0_REGNUM tdep->st0_regnum 226 227 fctrl = get_frame_register_unsigned (frame, I387_FCTRL_REGNUM); 228 fstat = get_frame_register_unsigned (frame, I387_FSTAT_REGNUM); 229 ftag = get_frame_register_unsigned (frame, I387_FTAG_REGNUM); 230 fiseg = get_frame_register_unsigned (frame, I387_FISEG_REGNUM); 231 fioff = get_frame_register_unsigned (frame, I387_FIOFF_REGNUM); 232 foseg = get_frame_register_unsigned (frame, I387_FOSEG_REGNUM); 233 fooff = get_frame_register_unsigned (frame, I387_FOOFF_REGNUM); 234 fop = get_frame_register_unsigned (frame, I387_FOP_REGNUM); 235 236 top = ((fstat >> 11) & 7); 237 238 for (fpreg = 7; fpreg >= 0; fpreg--) 239 { 240 unsigned char raw[I386_MAX_REGISTER_SIZE]; 241 int tag = (ftag >> (fpreg * 2)) & 3; 242 int i; 243 244 fprintf_filtered (file, "%sR%d: ", fpreg == top ? "=>" : " ", fpreg); 245 246 switch (tag) 247 { 248 case 0: 249 fputs_filtered ("Valid ", file); 250 break; 251 case 1: 252 fputs_filtered ("Zero ", file); 253 break; 254 case 2: 255 fputs_filtered ("Special ", file); 256 break; 257 case 3: 258 fputs_filtered ("Empty ", file); 259 break; 260 } 261 262 get_frame_register (frame, (fpreg + 8 - top) % 8 + I387_ST0_REGNUM, raw); 263 264 fputs_filtered ("0x", file); 265 for (i = 9; i >= 0; i--) 266 fprintf_filtered (file, "%02x", raw[i]); 267 268 if (tag != 3) 269 print_i387_ext (raw, file); 270 271 fputs_filtered ("\n", file); 272 } 273 274 fputs_filtered ("\n", file); 275 276 print_i387_status_word (fstat, file); 277 print_i387_control_word (fctrl, file); 278 fprintf_filtered (file, "Tag Word: %s\n", 279 local_hex_string_custom (ftag, "04")); 280 fprintf_filtered (file, "Instruction Pointer: %s:", 281 local_hex_string_custom (fiseg, "02")); 282 fprintf_filtered (file, "%s\n", local_hex_string_custom (fioff, "08")); 283 fprintf_filtered (file, "Operand Pointer: %s:", 284 local_hex_string_custom (foseg, "02")); 285 fprintf_filtered (file, "%s\n", local_hex_string_custom (fooff, "08")); 286 fprintf_filtered (file, "Opcode: %s\n", 287 local_hex_string_custom (fop ? (fop | 0xd800) : 0, "04")); 288 289#undef I387_ST0_REGNUM 290} 291 292 293/* Read a value of type TYPE from register REGNUM in frame FRAME, and 294 return its contents in TO. */ 295 296void 297i387_register_to_value (struct frame_info *frame, int regnum, 298 struct type *type, void *to) 299{ 300 char from[I386_MAX_REGISTER_SIZE]; 301 302 gdb_assert (i386_fp_regnum_p (regnum)); 303 304 /* We only support floating-point values. */ 305 if (TYPE_CODE (type) != TYPE_CODE_FLT) 306 { 307 warning ("Cannot convert floating-point register value " 308 "to non-floating-point type."); 309 return; 310 } 311 312 /* Convert to TYPE. This should be a no-op if TYPE is equivalent to 313 the extended floating-point format used by the FPU. */ 314 get_frame_register (frame, regnum, from); 315 convert_typed_floating (from, builtin_type_i387_ext, to, type); 316} 317 318/* Write the contents FROM of a value of type TYPE into register 319 REGNUM in frame FRAME. */ 320 321void 322i387_value_to_register (struct frame_info *frame, int regnum, 323 struct type *type, const void *from) 324{ 325 char to[I386_MAX_REGISTER_SIZE]; 326 327 gdb_assert (i386_fp_regnum_p (regnum)); 328 329 /* We only support floating-point values. */ 330 if (TYPE_CODE (type) != TYPE_CODE_FLT) 331 { 332 warning ("Cannot convert non-floating-point type " 333 "to floating-point register value."); 334 return; 335 } 336 337 /* Convert from TYPE. This should be a no-op if TYPE is equivalent 338 to the extended floating-point format used by the FPU. */ 339 convert_typed_floating (from, type, to, builtin_type_i387_ext); 340 put_frame_register (frame, regnum, to); 341} 342 343 344 345/* Handle FSAVE and FXSAVE formats. */ 346 347/* FIXME: kettenis/20030927: The functions below should accept a 348 `regcache' argument, but I don't want to change the function 349 signature just yet. There's some band-aid in the functions below 350 in the form of the `regcache' local variables. This will ease the 351 transition later on. */ 352 353/* At fsave_offset[REGNUM] you'll find the offset to the location in 354 the data structure used by the "fsave" instruction where GDB 355 register REGNUM is stored. */ 356 357static int fsave_offset[] = 358{ 359 28 + 0 * 10, /* %st(0) ... */ 360 28 + 1 * 10, 361 28 + 2 * 10, 362 28 + 3 * 10, 363 28 + 4 * 10, 364 28 + 5 * 10, 365 28 + 6 * 10, 366 28 + 7 * 10, /* ... %st(7). */ 367 0, /* `fctrl' (16 bits). */ 368 4, /* `fstat' (16 bits). */ 369 8, /* `ftag' (16 bits). */ 370 16, /* `fiseg' (16 bits). */ 371 12, /* `fioff'. */ 372 24, /* `foseg' (16 bits). */ 373 20, /* `fooff'. */ 374 18 /* `fop' (bottom 11 bits). */ 375}; 376 377#define FSAVE_ADDR(fsave, regnum) \ 378 (fsave + fsave_offset[regnum - I387_ST0_REGNUM]) 379 380 381/* Fill register REGNUM in REGCACHE with the appropriate value from 382 *FSAVE. This function masks off any of the reserved bits in 383 *FSAVE. */ 384 385void 386i387_supply_fsave (struct regcache *regcache, int regnum, const void *fsave) 387{ 388 struct gdbarch_tdep *tdep = gdbarch_tdep (get_regcache_arch (regcache)); 389 const char *regs = fsave; 390 int i; 391 392 gdb_assert (tdep->st0_regnum >= I386_ST0_REGNUM); 393 394 /* Define I387_ST0_REGNUM such that we use the proper definitions 395 for REGCACHE's architecture. */ 396#define I387_ST0_REGNUM tdep->st0_regnum 397 398 for (i = I387_ST0_REGNUM; i < I387_XMM0_REGNUM; i++) 399 if (regnum == -1 || regnum == i) 400 { 401 if (fsave == NULL) 402 { 403 regcache_raw_supply (regcache, i, NULL); 404 continue; 405 } 406 407 /* Most of the FPU control registers occupy only 16 bits in the 408 fsave area. Give those a special treatment. */ 409 if (i >= I387_FCTRL_REGNUM 410 && i != I387_FIOFF_REGNUM && i != I387_FOOFF_REGNUM) 411 { 412 unsigned char val[4]; 413 414 memcpy (val, FSAVE_ADDR (regs, i), 2); 415 val[2] = val[3] = 0; 416 if (i == I387_FOP_REGNUM) 417 val[1] &= ((1 << 3) - 1); 418 regcache_raw_supply (regcache, i, val); 419 } 420 else 421 regcache_raw_supply (regcache, i, FSAVE_ADDR (regs, i)); 422 } 423#undef I387_ST0_REGNUM 424} 425 426/* Fill register REGNUM (if it is a floating-point register) in *FSAVE 427 with the value in GDB's register cache. If REGNUM is -1, do this 428 for all registers. This function doesn't touch any of the reserved 429 bits in *FSAVE. */ 430 431void 432i387_fill_fsave (void *fsave, int regnum) 433{ 434 struct regcache *regcache = current_regcache; 435 struct gdbarch_tdep *tdep = gdbarch_tdep (current_gdbarch); 436 char *regs = fsave; 437 int i; 438 439 gdb_assert (tdep->st0_regnum >= I386_ST0_REGNUM); 440 441 /* Define I387_ST0_REGNUM such that we use the proper definitions 442 for REGCACHE's architecture. */ 443#define I387_ST0_REGNUM tdep->st0_regnum 444 445 for (i = I387_ST0_REGNUM; i < I387_XMM0_REGNUM; i++) 446 if (regnum == -1 || regnum == i) 447 { 448 /* Most of the FPU control registers occupy only 16 bits in 449 the fsave area. Give those a special treatment. */ 450 if (i >= I387_FCTRL_REGNUM 451 && i != I387_FIOFF_REGNUM && i != I387_FOOFF_REGNUM) 452 { 453 unsigned char buf[4]; 454 455 regcache_raw_collect (regcache, i, buf); 456 457 if (i == I387_FOP_REGNUM) 458 { 459 /* The opcode occupies only 11 bits. Make sure we 460 don't touch the other bits. */ 461 buf[1] &= ((1 << 3) - 1); 462 buf[1] |= ((FSAVE_ADDR (regs, i))[1] & ~((1 << 3) - 1)); 463 } 464 memcpy (FSAVE_ADDR (regs, i), buf, 2); 465 } 466 else 467 regcache_raw_collect (regcache, i, FSAVE_ADDR (regs, i)); 468 } 469#undef I387_ST0_REGNUM 470} 471 472 473/* At fxsave_offset[REGNUM] you'll find the offset to the location in 474 the data structure used by the "fxsave" instruction where GDB 475 register REGNUM is stored. */ 476 477static int fxsave_offset[] = 478{ 479 32, /* %st(0) through ... */ 480 48, 481 64, 482 80, 483 96, 484 112, 485 128, 486 144, /* ... %st(7) (80 bits each). */ 487 0, /* `fctrl' (16 bits). */ 488 2, /* `fstat' (16 bits). */ 489 4, /* `ftag' (16 bits). */ 490 12, /* `fiseg' (16 bits). */ 491 8, /* `fioff'. */ 492 20, /* `foseg' (16 bits). */ 493 16, /* `fooff'. */ 494 6, /* `fop' (bottom 11 bits). */ 495 160 + 0 * 16, /* %xmm0 through ... */ 496 160 + 1 * 16, 497 160 + 2 * 16, 498 160 + 3 * 16, 499 160 + 4 * 16, 500 160 + 5 * 16, 501 160 + 6 * 16, 502 160 + 7 * 16, 503 160 + 8 * 16, 504 160 + 9 * 16, 505 160 + 10 * 16, 506 160 + 11 * 16, 507 160 + 12 * 16, 508 160 + 13 * 16, 509 160 + 14 * 16, 510 160 + 15 * 16, /* ... %xmm15 (128 bits each). */ 511}; 512 513#define FXSAVE_ADDR(fxsave, regnum) \ 514 (fxsave + fxsave_offset[regnum - I387_ST0_REGNUM]) 515 516/* We made an unfortunate choice in putting %mxcsr after the SSE 517 registers %xmm0-%xmm7 instead of before, since it makes supporting 518 the registers %xmm8-%xmm15 on AMD64 a bit involved. Therefore we 519 don't include the offset for %mxcsr here above. */ 520 521#define FXSAVE_MXCSR_ADDR(fxsave) (fxsave + 24) 522 523static int i387_tag (const unsigned char *raw); 524 525 526/* Fill register REGNUM in REGCACHE with the appropriate 527 floating-point or SSE register value from *FXSAVE. This function 528 masks off any of the reserved bits in *FXSAVE. */ 529 530void 531i387_supply_fxsave (struct regcache *regcache, int regnum, const void *fxsave) 532{ 533 struct gdbarch_tdep *tdep = gdbarch_tdep (get_regcache_arch (regcache)); 534 const char *regs = fxsave; 535 int i; 536 537 gdb_assert (tdep->st0_regnum >= I386_ST0_REGNUM); 538 gdb_assert (tdep->num_xmm_regs > 0); 539 540 /* Define I387_ST0_REGNUM and I387_NUM_XMM_REGS such that we use the 541 proper definitions for REGCACHE's architecture. */ 542 543#define I387_ST0_REGNUM tdep->st0_regnum 544#define I387_NUM_XMM_REGS tdep->num_xmm_regs 545 546 for (i = I387_ST0_REGNUM; i < I387_MXCSR_REGNUM; i++) 547 if (regnum == -1 || regnum == i) 548 { 549 if (regs == NULL) 550 { 551 regcache_raw_supply (regcache, i, NULL); 552 continue; 553 } 554 555 /* Most of the FPU control registers occupy only 16 bits in 556 the fxsave area. Give those a special treatment. */ 557 if (i >= I387_FCTRL_REGNUM && i < I387_XMM0_REGNUM 558 && i != I387_FIOFF_REGNUM && i != I387_FOOFF_REGNUM) 559 { 560 unsigned char val[4]; 561 562 memcpy (val, FXSAVE_ADDR (regs, i), 2); 563 val[2] = val[3] = 0; 564 if (i == I387_FOP_REGNUM) 565 val[1] &= ((1 << 3) - 1); 566 else if (i== I387_FTAG_REGNUM) 567 { 568 /* The fxsave area contains a simplified version of 569 the tag word. We have to look at the actual 80-bit 570 FP data to recreate the traditional i387 tag word. */ 571 572 unsigned long ftag = 0; 573 int fpreg; 574 int top; 575 576 top = ((FXSAVE_ADDR (regs, I387_FSTAT_REGNUM))[1] >> 3); 577 top &= 0x7; 578 579 for (fpreg = 7; fpreg >= 0; fpreg--) 580 { 581 int tag; 582 583 if (val[0] & (1 << fpreg)) 584 { 585 int regnum = (fpreg + 8 - top) % 8 + I387_ST0_REGNUM; 586 tag = i387_tag (FXSAVE_ADDR (regs, regnum)); 587 } 588 else 589 tag = 3; /* Empty */ 590 591 ftag |= tag << (2 * fpreg); 592 } 593 val[0] = ftag & 0xff; 594 val[1] = (ftag >> 8) & 0xff; 595 } 596 regcache_raw_supply (regcache, i, val); 597 } 598 else 599 regcache_raw_supply (regcache, i, FXSAVE_ADDR (regs, i)); 600 } 601 602 if (regnum == I387_MXCSR_REGNUM || regnum == -1) 603 { 604 if (regs == NULL) 605 regcache_raw_supply (regcache, I387_MXCSR_REGNUM, NULL); 606 else 607 regcache_raw_supply (regcache, I387_MXCSR_REGNUM, 608 FXSAVE_MXCSR_ADDR (regs)); 609 } 610 611#undef I387_ST0_REGNUM 612#undef I387_NUM_XMM_REGS 613} 614 615/* Fill register REGNUM (if it is a floating-point or SSE register) in 616 *FXSAVE with the value from REGCACHE. If REGNUM is -1, do this for 617 all registers. This function doesn't touch any of the reserved 618 bits in *FXSAVE. */ 619 620void 621i387_collect_fxsave (const struct regcache *regcache, int regnum, void *fxsave) 622{ 623 struct gdbarch_tdep *tdep = gdbarch_tdep (current_gdbarch); 624 char *regs = fxsave; 625 int i; 626 627 gdb_assert (tdep->st0_regnum >= I386_ST0_REGNUM); 628 gdb_assert (tdep->num_xmm_regs > 0); 629 630 /* Define I387_ST0_REGNUM and I387_NUM_XMM_REGS such that we use the 631 proper definitions for REGCACHE's architecture. */ 632 633#define I387_ST0_REGNUM tdep->st0_regnum 634#define I387_NUM_XMM_REGS tdep->num_xmm_regs 635 636 for (i = I387_ST0_REGNUM; i < I387_MXCSR_REGNUM; i++) 637 if (regnum == -1 || regnum == i) 638 { 639 /* Most of the FPU control registers occupy only 16 bits in 640 the fxsave area. Give those a special treatment. */ 641 if (i >= I387_FCTRL_REGNUM && i < I387_XMM0_REGNUM 642 && i != I387_FIOFF_REGNUM && i != I387_FOOFF_REGNUM) 643 { 644 unsigned char buf[4]; 645 646 regcache_raw_collect (regcache, i, buf); 647 648 if (i == I387_FOP_REGNUM) 649 { 650 /* The opcode occupies only 11 bits. Make sure we 651 don't touch the other bits. */ 652 buf[1] &= ((1 << 3) - 1); 653 buf[1] |= ((FXSAVE_ADDR (regs, i))[1] & ~((1 << 3) - 1)); 654 } 655 else if (i == I387_FTAG_REGNUM) 656 { 657 /* Converting back is much easier. */ 658 659 unsigned short ftag; 660 int fpreg; 661 662 ftag = (buf[1] << 8) | buf[0]; 663 buf[0] = 0; 664 buf[1] = 0; 665 666 for (fpreg = 7; fpreg >= 0; fpreg--) 667 { 668 int tag = (ftag >> (fpreg * 2)) & 3; 669 670 if (tag != 3) 671 buf[0] |= (1 << fpreg); 672 } 673 } 674 memcpy (FXSAVE_ADDR (regs, i), buf, 2); 675 } 676 else 677 regcache_raw_collect (regcache, i, FXSAVE_ADDR (regs, i)); 678 } 679 680 if (regnum == I387_MXCSR_REGNUM || regnum == -1) 681 regcache_raw_collect (regcache, I387_MXCSR_REGNUM, 682 FXSAVE_MXCSR_ADDR (regs)); 683 684#undef I387_ST0_REGNUM 685#undef I387_NUM_XMM_REGS 686} 687 688/* Fill register REGNUM (if it is a floating-point or SSE register) in 689 *FXSAVE with the value in GDB's register cache. If REGNUM is -1, do 690 this for all registers. This function doesn't touch any of the 691 reserved bits in *FXSAVE. */ 692 693void 694i387_fill_fxsave (void *fxsave, int regnum) 695{ 696 i387_collect_fxsave (current_regcache, regnum, fxsave); 697} 698 699/* Recreate the FTW (tag word) valid bits from the 80-bit FP data in 700 *RAW. */ 701 702static int 703i387_tag (const unsigned char *raw) 704{ 705 int integer; 706 unsigned int exponent; 707 unsigned long fraction[2]; 708 709 integer = raw[7] & 0x80; 710 exponent = (((raw[9] & 0x7f) << 8) | raw[8]); 711 fraction[0] = ((raw[3] << 24) | (raw[2] << 16) | (raw[1] << 8) | raw[0]); 712 fraction[1] = (((raw[7] & 0x7f) << 24) | (raw[6] << 16) 713 | (raw[5] << 8) | raw[4]); 714 715 if (exponent == 0x7fff) 716 { 717 /* Special. */ 718 return (2); 719 } 720 else if (exponent == 0x0000) 721 { 722 if (fraction[0] == 0x0000 && fraction[1] == 0x0000 && !integer) 723 { 724 /* Zero. */ 725 return (1); 726 } 727 else 728 { 729 /* Special. */ 730 return (2); 731 } 732 } 733 else 734 { 735 if (integer) 736 { 737 /* Valid. */ 738 return (0); 739 } 740 else 741 { 742 /* Special. */ 743 return (2); 744 } 745 } 746} 747 748/* Prepare the FPU stack in REGCACHE for a function return. */ 749 750void 751i387_return_value (struct gdbarch *gdbarch, struct regcache *regcache) 752{ 753 struct gdbarch_tdep *tdep = gdbarch_tdep (gdbarch); 754 ULONGEST fstat; 755 756 /* Define I387_ST0_REGNUM such that we use the proper 757 definitions for the architecture. */ 758#define I387_ST0_REGNUM tdep->st0_regnum 759 760 /* Set the top of the floating-point register stack to 7. The 761 actual value doesn't really matter, but 7 is what a normal 762 function return would end up with if the program started out with 763 a freshly initialized FPU. */ 764 regcache_raw_read_unsigned (regcache, I387_FSTAT_REGNUM, &fstat); 765 fstat |= (7 << 11); 766 regcache_raw_write_unsigned (regcache, I387_FSTAT_REGNUM, fstat); 767 768 /* Mark %st(1) through %st(7) as empty. Since we set the top of the 769 floating-point register stack to 7, the appropriate value for the 770 tag word is 0x3fff. */ 771 regcache_raw_write_unsigned (regcache, I387_FTAG_REGNUM, 0x3fff); 772 773#undef I387_ST0_REGNUM 774} 775