OpenCores
URL https://opencores.org/ocsvn/openrisc_me/openrisc_me/trunk

Subversion Repositories openrisc_me

[/] [openrisc/] [trunk/] [gnu-src/] [gdb-7.2/] [gdb/] [i387-tdep.c] - Blame information for rev 441

Go to most recent revision | Details | Compare with Previous | View Log

Line No. Rev Author Line
1 330 jeremybenn
/* Intel 387 floating point stuff.
2
 
3
   Copyright (C) 1988, 1989, 1991, 1992, 1993, 1994, 1998, 1999, 2000, 2001,
4
   2002, 2003, 2004, 2005, 2007, 2008, 2009, 2010
5
   Free Software Foundation, Inc.
6
 
7
   This file is part of GDB.
8
 
9
   This program is free software; you can redistribute it and/or modify
10
   it under the terms of the GNU General Public License as published by
11
   the Free Software Foundation; either version 3 of the License, or
12
   (at your option) any later version.
13
 
14
   This program is distributed in the hope that it will be useful,
15
   but WITHOUT ANY WARRANTY; without even the implied warranty of
16
   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
17
   GNU General Public License for more details.
18
 
19
   You should have received a copy of the GNU General Public License
20
   along with this program.  If not, see <http://www.gnu.org/licenses/>.  */
21
 
22
#include "defs.h"
23
#include "doublest.h"
24
#include "floatformat.h"
25
#include "frame.h"
26
#include "gdbcore.h"
27
#include "inferior.h"
28
#include "language.h"
29
#include "regcache.h"
30
#include "value.h"
31
 
32
#include "gdb_assert.h"
33
#include "gdb_string.h"
34
 
35
#include "i386-tdep.h"
36
#include "i387-tdep.h"
37
#include "i386-xstate.h"
38
 
39
/* Print the floating point number specified by RAW.  */
40
 
41
static void
42
print_i387_value (struct gdbarch *gdbarch,
43
                  const gdb_byte *raw, struct ui_file *file)
44
{
45
  DOUBLEST value;
46
 
47
  /* Using extract_typed_floating here might affect the representation
48
     of certain numbers such as NaNs, even if GDB is running natively.
49
     This is fine since our caller already detects such special
50
     numbers and we print the hexadecimal representation anyway.  */
51
  value = extract_typed_floating (raw, i387_ext_type (gdbarch));
52
 
53
  /* We try to print 19 digits.  The last digit may or may not contain
54
     garbage, but we'd better print one too many.  We need enough room
55
     to print the value, 1 position for the sign, 1 for the decimal
56
     point, 19 for the digits and 6 for the exponent adds up to 27.  */
57
#ifdef PRINTF_HAS_LONG_DOUBLE
58
  fprintf_filtered (file, " %-+27.19Lg", (long double) value);
59
#else
60
  fprintf_filtered (file, " %-+27.19g", (double) value);
61
#endif
62
}
63
 
64
/* Print the classification for the register contents RAW.  */
65
 
66
static void
67
print_i387_ext (struct gdbarch *gdbarch,
68
                const gdb_byte *raw, struct ui_file *file)
69
{
70
  int sign;
71
  int integer;
72
  unsigned int exponent;
73
  unsigned long fraction[2];
74
 
75
  sign = raw[9] & 0x80;
76
  integer = raw[7] & 0x80;
77
  exponent = (((raw[9] & 0x7f) << 8) | raw[8]);
78
  fraction[0] = ((raw[3] << 24) | (raw[2] << 16) | (raw[1] << 8) | raw[0]);
79
  fraction[1] = (((raw[7] & 0x7f) << 24) | (raw[6] << 16)
80
                 | (raw[5] << 8) | raw[4]);
81
 
82
  if (exponent == 0x7fff && integer)
83
    {
84
      if (fraction[0] == 0x00000000 && fraction[1] == 0x00000000)
85
        /* Infinity.  */
86
        fprintf_filtered (file, " %cInf", (sign ? '-' : '+'));
87
      else if (sign && fraction[0] == 0x00000000 && fraction[1] == 0x40000000)
88
        /* Real Indefinite (QNaN).  */
89
        fputs_unfiltered (" Real Indefinite (QNaN)", file);
90
      else if (fraction[1] & 0x40000000)
91
        /* QNaN.  */
92
        fputs_filtered (" QNaN", file);
93
      else
94
        /* SNaN.  */
95
        fputs_filtered (" SNaN", file);
96
    }
97
  else if (exponent < 0x7fff && exponent > 0x0000 && integer)
98
    /* Normal.  */
99
    print_i387_value (gdbarch, raw, file);
100
  else if (exponent == 0x0000)
101
    {
102
      /* Denormal or zero.  */
103
      print_i387_value (gdbarch, raw, file);
104
 
105
      if (integer)
106
        /* Pseudo-denormal.  */
107
        fputs_filtered (" Pseudo-denormal", file);
108
      else if (fraction[0] || fraction[1])
109
        /* Denormal.  */
110
        fputs_filtered (" Denormal", file);
111
    }
112
  else
113
    /* Unsupported.  */
114
    fputs_filtered (" Unsupported", file);
115
}
116
 
117
/* Print the status word STATUS.  */
118
 
119
static void
120
print_i387_status_word (unsigned int status, struct ui_file *file)
121
{
122
  fprintf_filtered (file, "Status Word:         %s",
123
                    hex_string_custom (status, 4));
124
  fputs_filtered ("  ", file);
125
  fprintf_filtered (file, " %s", (status & 0x0001) ? "IE" : "  ");
126
  fprintf_filtered (file, " %s", (status & 0x0002) ? "DE" : "  ");
127
  fprintf_filtered (file, " %s", (status & 0x0004) ? "ZE" : "  ");
128
  fprintf_filtered (file, " %s", (status & 0x0008) ? "OE" : "  ");
129
  fprintf_filtered (file, " %s", (status & 0x0010) ? "UE" : "  ");
130
  fprintf_filtered (file, " %s", (status & 0x0020) ? "PE" : "  ");
131
  fputs_filtered ("  ", file);
132
  fprintf_filtered (file, " %s", (status & 0x0080) ? "ES" : "  ");
133
  fputs_filtered ("  ", file);
134
  fprintf_filtered (file, " %s", (status & 0x0040) ? "SF" : "  ");
135
  fputs_filtered ("  ", file);
136
  fprintf_filtered (file, " %s", (status & 0x0100) ? "C0" : "  ");
137
  fprintf_filtered (file, " %s", (status & 0x0200) ? "C1" : "  ");
138
  fprintf_filtered (file, " %s", (status & 0x0400) ? "C2" : "  ");
139
  fprintf_filtered (file, " %s", (status & 0x4000) ? "C3" : "  ");
140
 
141
  fputs_filtered ("\n", file);
142
 
143
  fprintf_filtered (file,
144
                    "                       TOP: %d\n", ((status >> 11) & 7));
145
}
146
 
147
/* Print the control word CONTROL.  */
148
 
149
static void
150
print_i387_control_word (unsigned int control, struct ui_file *file)
151
{
152
  fprintf_filtered (file, "Control Word:        %s",
153
                    hex_string_custom (control, 4));
154
  fputs_filtered ("  ", file);
155
  fprintf_filtered (file, " %s", (control & 0x0001) ? "IM" : "  ");
156
  fprintf_filtered (file, " %s", (control & 0x0002) ? "DM" : "  ");
157
  fprintf_filtered (file, " %s", (control & 0x0004) ? "ZM" : "  ");
158
  fprintf_filtered (file, " %s", (control & 0x0008) ? "OM" : "  ");
159
  fprintf_filtered (file, " %s", (control & 0x0010) ? "UM" : "  ");
160
  fprintf_filtered (file, " %s", (control & 0x0020) ? "PM" : "  ");
161
 
162
  fputs_filtered ("\n", file);
163
 
164
  fputs_filtered ("                       PC: ", file);
165
  switch ((control >> 8) & 3)
166
    {
167
    case 0:
168
      fputs_filtered ("Single Precision (24-bits)\n", file);
169
      break;
170
    case 1:
171
      fputs_filtered ("Reserved\n", file);
172
      break;
173
    case 2:
174
      fputs_filtered ("Double Precision (53-bits)\n", file);
175
      break;
176
    case 3:
177
      fputs_filtered ("Extended Precision (64-bits)\n", file);
178
      break;
179
    }
180
 
181
  fputs_filtered ("                       RC: ", file);
182
  switch ((control >> 10) & 3)
183
    {
184
    case 0:
185
      fputs_filtered ("Round to nearest\n", file);
186
      break;
187
    case 1:
188
      fputs_filtered ("Round down\n", file);
189
      break;
190
    case 2:
191
      fputs_filtered ("Round up\n", file);
192
      break;
193
    case 3:
194
      fputs_filtered ("Round toward zero\n", file);
195
      break;
196
    }
197
}
198
 
199
/* Print out the i387 floating point state.  Note that we ignore FRAME
200
   in the code below.  That's OK since floating-point registers are
201
   never saved on the stack.  */
202
 
203
void
204
i387_print_float_info (struct gdbarch *gdbarch, struct ui_file *file,
205
                       struct frame_info *frame, const char *args)
206
{
207
  struct gdbarch_tdep *tdep = gdbarch_tdep (get_frame_arch (frame));
208
  ULONGEST fctrl;
209
  ULONGEST fstat;
210
  ULONGEST ftag;
211
  ULONGEST fiseg;
212
  ULONGEST fioff;
213
  ULONGEST foseg;
214
  ULONGEST fooff;
215
  ULONGEST fop;
216
  int fpreg;
217
  int top;
218
 
219
  gdb_assert (gdbarch == get_frame_arch (frame));
220
 
221
  fctrl = get_frame_register_unsigned (frame, I387_FCTRL_REGNUM (tdep));
222
  fstat = get_frame_register_unsigned (frame, I387_FSTAT_REGNUM (tdep));
223
  ftag = get_frame_register_unsigned (frame, I387_FTAG_REGNUM (tdep));
224
  fiseg = get_frame_register_unsigned (frame, I387_FISEG_REGNUM (tdep));
225
  fioff = get_frame_register_unsigned (frame, I387_FIOFF_REGNUM (tdep));
226
  foseg = get_frame_register_unsigned (frame, I387_FOSEG_REGNUM (tdep));
227
  fooff = get_frame_register_unsigned (frame, I387_FOOFF_REGNUM (tdep));
228
  fop = get_frame_register_unsigned (frame, I387_FOP_REGNUM (tdep));
229
 
230
  top = ((fstat >> 11) & 7);
231
 
232
  for (fpreg = 7; fpreg >= 0; fpreg--)
233
    {
234
      gdb_byte raw[I386_MAX_REGISTER_SIZE];
235
      int tag = (ftag >> (fpreg * 2)) & 3;
236
      int i;
237
 
238
      fprintf_filtered (file, "%sR%d: ", fpreg == top ? "=>" : "  ", fpreg);
239
 
240
      switch (tag)
241
        {
242
        case 0:
243
          fputs_filtered ("Valid   ", file);
244
          break;
245
        case 1:
246
          fputs_filtered ("Zero    ", file);
247
          break;
248
        case 2:
249
          fputs_filtered ("Special ", file);
250
          break;
251
        case 3:
252
          fputs_filtered ("Empty   ", file);
253
          break;
254
        }
255
 
256
      get_frame_register (frame, (fpreg + 8 - top) % 8 + I387_ST0_REGNUM (tdep),
257
                          raw);
258
 
259
      fputs_filtered ("0x", file);
260
      for (i = 9; i >= 0; i--)
261
        fprintf_filtered (file, "%02x", raw[i]);
262
 
263
      if (tag != 3)
264
        print_i387_ext (gdbarch, raw, file);
265
 
266
      fputs_filtered ("\n", file);
267
    }
268
 
269
  fputs_filtered ("\n", file);
270
 
271
  print_i387_status_word (fstat, file);
272
  print_i387_control_word (fctrl, file);
273
  fprintf_filtered (file, "Tag Word:            %s\n",
274
                    hex_string_custom (ftag, 4));
275
  fprintf_filtered (file, "Instruction Pointer: %s:",
276
                    hex_string_custom (fiseg, 2));
277
  fprintf_filtered (file, "%s\n", hex_string_custom (fioff, 8));
278
  fprintf_filtered (file, "Operand Pointer:     %s:",
279
                    hex_string_custom (foseg, 2));
280
  fprintf_filtered (file, "%s\n", hex_string_custom (fooff, 8));
281
  fprintf_filtered (file, "Opcode:              %s\n",
282
                    hex_string_custom (fop ? (fop | 0xd800) : 0, 4));
283
}
284
 
285
 
286
/* Return nonzero if a value of type TYPE stored in register REGNUM
287
   needs any special handling.  */
288
 
289
int
290
i387_convert_register_p (struct gdbarch *gdbarch, int regnum, struct type *type)
291
{
292
  if (i386_fp_regnum_p (gdbarch, regnum))
293
    {
294
      /* Floating point registers must be converted unless we are
295
         accessing them in their hardware type.  */
296
      if (type == i387_ext_type (gdbarch))
297
        return 0;
298
      else
299
        return 1;
300
    }
301
 
302
  return 0;
303
}
304
 
305
/* Read a value of type TYPE from register REGNUM in frame FRAME, and
306
   return its contents in TO.  */
307
 
308
void
309
i387_register_to_value (struct frame_info *frame, int regnum,
310
                        struct type *type, gdb_byte *to)
311
{
312
  struct gdbarch *gdbarch = get_frame_arch (frame);
313
  gdb_byte from[I386_MAX_REGISTER_SIZE];
314
 
315
  gdb_assert (i386_fp_regnum_p (gdbarch, regnum));
316
 
317
  /* We only support floating-point values.  */
318
  if (TYPE_CODE (type) != TYPE_CODE_FLT)
319
    {
320
      warning (_("Cannot convert floating-point register value "
321
               "to non-floating-point type."));
322
      return;
323
    }
324
 
325
  /* Convert to TYPE.  */
326
  get_frame_register (frame, regnum, from);
327
  convert_typed_floating (from, i387_ext_type (gdbarch), to, type);
328
}
329
 
330
/* Write the contents FROM of a value of type TYPE into register
331
   REGNUM in frame FRAME.  */
332
 
333
void
334
i387_value_to_register (struct frame_info *frame, int regnum,
335
                        struct type *type, const gdb_byte *from)
336
{
337
  struct gdbarch *gdbarch = get_frame_arch (frame);
338
  gdb_byte to[I386_MAX_REGISTER_SIZE];
339
 
340
  gdb_assert (i386_fp_regnum_p (gdbarch, regnum));
341
 
342
  /* We only support floating-point values.  */
343
  if (TYPE_CODE (type) != TYPE_CODE_FLT)
344
    {
345
      warning (_("Cannot convert non-floating-point type "
346
               "to floating-point register value."));
347
      return;
348
    }
349
 
350
  /* Convert from TYPE.  */
351
  convert_typed_floating (from, type, to, i387_ext_type (gdbarch));
352
  put_frame_register (frame, regnum, to);
353
}
354
 
355
 
356
/* Handle FSAVE and FXSAVE formats.  */
357
 
358
/* At fsave_offset[REGNUM] you'll find the offset to the location in
359
   the data structure used by the "fsave" instruction where GDB
360
   register REGNUM is stored.  */
361
 
362
static int fsave_offset[] =
363
{
364
  28 + 0 * 10,                   /* %st(0) ...  */
365
  28 + 1 * 10,
366
  28 + 2 * 10,
367
  28 + 3 * 10,
368
  28 + 4 * 10,
369
  28 + 5 * 10,
370
  28 + 6 * 10,
371
  28 + 7 * 10,                  /* ... %st(7).  */
372
  0,                             /* `fctrl' (16 bits).  */
373
  4,                            /* `fstat' (16 bits).  */
374
  8,                            /* `ftag' (16 bits).  */
375
  16,                           /* `fiseg' (16 bits).  */
376
  12,                           /* `fioff'.  */
377
  24,                           /* `foseg' (16 bits).  */
378
  20,                           /* `fooff'.  */
379
  18                            /* `fop' (bottom 11 bits).  */
380
};
381
 
382
#define FSAVE_ADDR(tdep, fsave, regnum) \
383
  (fsave + fsave_offset[regnum - I387_ST0_REGNUM (tdep)])
384
 
385
 
386
/* Fill register REGNUM in REGCACHE with the appropriate value from
387
   *FSAVE.  This function masks off any of the reserved bits in
388
   *FSAVE.  */
389
 
390
void
391
i387_supply_fsave (struct regcache *regcache, int regnum, const void *fsave)
392
{
393
  struct gdbarch *gdbarch = get_regcache_arch (regcache);
394
  struct gdbarch_tdep *tdep = gdbarch_tdep (gdbarch);
395
  enum bfd_endian byte_order = gdbarch_byte_order (gdbarch);
396
  const gdb_byte *regs = fsave;
397
  int i;
398
 
399
  gdb_assert (tdep->st0_regnum >= I386_ST0_REGNUM);
400
 
401
  for (i = I387_ST0_REGNUM (tdep); i < I387_XMM0_REGNUM (tdep); i++)
402
    if (regnum == -1 || regnum == i)
403
      {
404
        if (fsave == NULL)
405
          {
406
            regcache_raw_supply (regcache, i, NULL);
407
            continue;
408
          }
409
 
410
        /* Most of the FPU control registers occupy only 16 bits in the
411
           fsave area.  Give those a special treatment.  */
412
        if (i >= I387_FCTRL_REGNUM (tdep)
413
            && i != I387_FIOFF_REGNUM (tdep) && i != I387_FOOFF_REGNUM (tdep))
414
          {
415
            gdb_byte val[4];
416
 
417
            memcpy (val, FSAVE_ADDR (tdep, regs, i), 2);
418
            val[2] = val[3] = 0;
419
            if (i == I387_FOP_REGNUM (tdep))
420
              val[1] &= ((1 << 3) - 1);
421
            regcache_raw_supply (regcache, i, val);
422
          }
423
        else
424
          regcache_raw_supply (regcache, i, FSAVE_ADDR (tdep, regs, i));
425
      }
426
 
427
  /* Provide dummy values for the SSE registers.  */
428
  for (i = I387_XMM0_REGNUM (tdep); i < I387_MXCSR_REGNUM (tdep); i++)
429
    if (regnum == -1 || regnum == i)
430
      regcache_raw_supply (regcache, i, NULL);
431
  if (regnum == -1 || regnum == I387_MXCSR_REGNUM (tdep))
432
    {
433
      gdb_byte buf[4];
434
 
435
      store_unsigned_integer (buf, 4, byte_order, 0x1f80);
436
      regcache_raw_supply (regcache, I387_MXCSR_REGNUM (tdep), buf);
437
    }
438
}
439
 
440
/* Fill register REGNUM (if it is a floating-point register) in *FSAVE
441
   with the value from REGCACHE.  If REGNUM is -1, do this for all
442
   registers.  This function doesn't touch any of the reserved bits in
443
   *FSAVE.  */
444
 
445
void
446
i387_collect_fsave (const struct regcache *regcache, int regnum, void *fsave)
447
{
448
  struct gdbarch_tdep *tdep = gdbarch_tdep (get_regcache_arch (regcache));
449
  gdb_byte *regs = fsave;
450
  int i;
451
 
452
  gdb_assert (tdep->st0_regnum >= I386_ST0_REGNUM);
453
 
454
  for (i = I387_ST0_REGNUM (tdep); i < I387_XMM0_REGNUM (tdep); i++)
455
    if (regnum == -1 || regnum == i)
456
      {
457
        /* Most of the FPU control registers occupy only 16 bits in
458
           the fsave area.  Give those a special treatment.  */
459
        if (i >= I387_FCTRL_REGNUM (tdep)
460
            && i != I387_FIOFF_REGNUM (tdep) && i != I387_FOOFF_REGNUM (tdep))
461
          {
462
            gdb_byte buf[4];
463
 
464
            regcache_raw_collect (regcache, i, buf);
465
 
466
            if (i == I387_FOP_REGNUM (tdep))
467
              {
468
                /* The opcode occupies only 11 bits.  Make sure we
469
                   don't touch the other bits.  */
470
                buf[1] &= ((1 << 3) - 1);
471
                buf[1] |= ((FSAVE_ADDR (tdep, regs, i))[1] & ~((1 << 3) - 1));
472
              }
473
            memcpy (FSAVE_ADDR (tdep, regs, i), buf, 2);
474
          }
475
        else
476
          regcache_raw_collect (regcache, i, FSAVE_ADDR (tdep, regs, i));
477
      }
478
}
479
 
480
 
481
/* At fxsave_offset[REGNUM] you'll find the offset to the location in
482
   the data structure used by the "fxsave" instruction where GDB
483
   register REGNUM is stored.  */
484
 
485
static int fxsave_offset[] =
486
{
487
  32,                           /* %st(0) through ...  */
488
  48,
489
  64,
490
  80,
491
  96,
492
  112,
493
  128,
494
  144,                          /* ... %st(7) (80 bits each).  */
495
  0,                             /* `fctrl' (16 bits).  */
496
  2,                            /* `fstat' (16 bits).  */
497
  4,                            /* `ftag' (16 bits).  */
498
  12,                           /* `fiseg' (16 bits).  */
499
  8,                            /* `fioff'.  */
500
  20,                           /* `foseg' (16 bits).  */
501
  16,                           /* `fooff'.  */
502
  6,                            /* `fop' (bottom 11 bits).  */
503
  160 + 0 * 16,                  /* %xmm0 through ...  */
504
  160 + 1 * 16,
505
  160 + 2 * 16,
506
  160 + 3 * 16,
507
  160 + 4 * 16,
508
  160 + 5 * 16,
509
  160 + 6 * 16,
510
  160 + 7 * 16,
511
  160 + 8 * 16,
512
  160 + 9 * 16,
513
  160 + 10 * 16,
514
  160 + 11 * 16,
515
  160 + 12 * 16,
516
  160 + 13 * 16,
517
  160 + 14 * 16,
518
  160 + 15 * 16,                /* ... %xmm15 (128 bits each).  */
519
};
520
 
521
#define FXSAVE_ADDR(tdep, fxsave, regnum) \
522
  (fxsave + fxsave_offset[regnum - I387_ST0_REGNUM (tdep)])
523
 
524
/* We made an unfortunate choice in putting %mxcsr after the SSE
525
   registers %xmm0-%xmm7 instead of before, since it makes supporting
526
   the registers %xmm8-%xmm15 on AMD64 a bit involved.  Therefore we
527
   don't include the offset for %mxcsr here above.  */
528
 
529
#define FXSAVE_MXCSR_ADDR(fxsave) (fxsave + 24)
530
 
531
static int i387_tag (const gdb_byte *raw);
532
 
533
 
534
/* Fill register REGNUM in REGCACHE with the appropriate
535
   floating-point or SSE register value from *FXSAVE.  This function
536
   masks off any of the reserved bits in *FXSAVE.  */
537
 
538
void
539
i387_supply_fxsave (struct regcache *regcache, int regnum, const void *fxsave)
540
{
541
  struct gdbarch_tdep *tdep = gdbarch_tdep (get_regcache_arch (regcache));
542
  const gdb_byte *regs = fxsave;
543
  int i;
544
 
545
  gdb_assert (tdep->st0_regnum >= I386_ST0_REGNUM);
546
  gdb_assert (tdep->num_xmm_regs > 0);
547
 
548
  for (i = I387_ST0_REGNUM (tdep); i < I387_MXCSR_REGNUM (tdep); i++)
549
    if (regnum == -1 || regnum == i)
550
      {
551
        if (regs == NULL)
552
          {
553
            regcache_raw_supply (regcache, i, NULL);
554
            continue;
555
          }
556
 
557
        /* Most of the FPU control registers occupy only 16 bits in
558
           the fxsave area.  Give those a special treatment.  */
559
        if (i >= I387_FCTRL_REGNUM (tdep) && i < I387_XMM0_REGNUM (tdep)
560
            && i != I387_FIOFF_REGNUM (tdep) && i != I387_FOOFF_REGNUM (tdep))
561
          {
562
            gdb_byte val[4];
563
 
564
            memcpy (val, FXSAVE_ADDR (tdep, regs, i), 2);
565
            val[2] = val[3] = 0;
566
            if (i == I387_FOP_REGNUM (tdep))
567
              val[1] &= ((1 << 3) - 1);
568
            else if (i== I387_FTAG_REGNUM (tdep))
569
              {
570
                /* The fxsave area contains a simplified version of
571
                   the tag word.  We have to look at the actual 80-bit
572
                   FP data to recreate the traditional i387 tag word.  */
573
 
574
                unsigned long ftag = 0;
575
                int fpreg;
576
                int top;
577
 
578
                top = ((FXSAVE_ADDR (tdep, regs,
579
                                     I387_FSTAT_REGNUM (tdep)))[1] >> 3);
580
                top &= 0x7;
581
 
582
                for (fpreg = 7; fpreg >= 0; fpreg--)
583
                  {
584
                    int tag;
585
 
586
                    if (val[0] & (1 << fpreg))
587
                      {
588
                        int regnum = (fpreg + 8 - top) % 8
589
                                       + I387_ST0_REGNUM (tdep);
590
                        tag = i387_tag (FXSAVE_ADDR (tdep, regs, regnum));
591
                      }
592
                    else
593
                      tag = 3;          /* Empty */
594
 
595
                    ftag |= tag << (2 * fpreg);
596
                  }
597
                val[0] = ftag & 0xff;
598
                val[1] = (ftag >> 8) & 0xff;
599
              }
600
            regcache_raw_supply (regcache, i, val);
601
          }
602
        else
603
          regcache_raw_supply (regcache, i, FXSAVE_ADDR (tdep, regs, i));
604
      }
605
 
606
  if (regnum == I387_MXCSR_REGNUM (tdep) || regnum == -1)
607
    {
608
      if (regs == NULL)
609
        regcache_raw_supply (regcache, I387_MXCSR_REGNUM (tdep), NULL);
610
      else
611
        regcache_raw_supply (regcache, I387_MXCSR_REGNUM (tdep),
612
                             FXSAVE_MXCSR_ADDR (regs));
613
    }
614
}
615
 
616
/* Fill register REGNUM (if it is a floating-point or SSE register) in
617
   *FXSAVE with the value from REGCACHE.  If REGNUM is -1, do this for
618
   all registers.  This function doesn't touch any of the reserved
619
   bits in *FXSAVE.  */
620
 
621
void
622
i387_collect_fxsave (const struct regcache *regcache, int regnum, void *fxsave)
623
{
624
  struct gdbarch_tdep *tdep = gdbarch_tdep (get_regcache_arch (regcache));
625
  gdb_byte *regs = fxsave;
626
  int i;
627
 
628
  gdb_assert (tdep->st0_regnum >= I386_ST0_REGNUM);
629
  gdb_assert (tdep->num_xmm_regs > 0);
630
 
631
  for (i = I387_ST0_REGNUM (tdep); i < I387_MXCSR_REGNUM (tdep); i++)
632
    if (regnum == -1 || regnum == i)
633
      {
634
        /* Most of the FPU control registers occupy only 16 bits in
635
           the fxsave area.  Give those a special treatment.  */
636
        if (i >= I387_FCTRL_REGNUM (tdep) && i < I387_XMM0_REGNUM (tdep)
637
            && i != I387_FIOFF_REGNUM (tdep) && i != I387_FOOFF_REGNUM (tdep))
638
          {
639
            gdb_byte buf[4];
640
 
641
            regcache_raw_collect (regcache, i, buf);
642
 
643
            if (i == I387_FOP_REGNUM (tdep))
644
              {
645
                /* The opcode occupies only 11 bits.  Make sure we
646
                   don't touch the other bits.  */
647
                buf[1] &= ((1 << 3) - 1);
648
                buf[1] |= ((FXSAVE_ADDR (tdep, regs, i))[1] & ~((1 << 3) - 1));
649
              }
650
            else if (i == I387_FTAG_REGNUM (tdep))
651
              {
652
                /* Converting back is much easier.  */
653
 
654
                unsigned short ftag;
655
                int fpreg;
656
 
657
                ftag = (buf[1] << 8) | buf[0];
658
                buf[0] = 0;
659
                buf[1] = 0;
660
 
661
                for (fpreg = 7; fpreg >= 0; fpreg--)
662
                  {
663
                    int tag = (ftag >> (fpreg * 2)) & 3;
664
 
665
                    if (tag != 3)
666
                      buf[0] |= (1 << fpreg);
667
                  }
668
              }
669
            memcpy (FXSAVE_ADDR (tdep, regs, i), buf, 2);
670
          }
671
        else
672
          regcache_raw_collect (regcache, i, FXSAVE_ADDR (tdep, regs, i));
673
      }
674
 
675
  if (regnum == I387_MXCSR_REGNUM (tdep) || regnum == -1)
676
    regcache_raw_collect (regcache, I387_MXCSR_REGNUM (tdep),
677
                          FXSAVE_MXCSR_ADDR (regs));
678
}
679
 
680
/* `xstate_bv' is at byte offset 512.  */
681
#define XSAVE_XSTATE_BV_ADDR(xsave) (xsave + 512)
682
 
683
/* At xsave_avxh_offset[REGNUM] you'll find the offset to the location in
684
   the upper 128bit of AVX register data structure used by the "xsave"
685
   instruction where GDB register REGNUM is stored.  */
686
 
687
static int xsave_avxh_offset[] =
688
{
689
  576 + 0 * 16,          /* Upper 128bit of %ymm0 through ...  */
690
  576 + 1 * 16,
691
  576 + 2 * 16,
692
  576 + 3 * 16,
693
  576 + 4 * 16,
694
  576 + 5 * 16,
695
  576 + 6 * 16,
696
  576 + 7 * 16,
697
  576 + 8 * 16,
698
  576 + 9 * 16,
699
  576 + 10 * 16,
700
  576 + 11 * 16,
701
  576 + 12 * 16,
702
  576 + 13 * 16,
703
  576 + 14 * 16,
704
  576 + 15 * 16         /* Upper 128bit of ... %ymm15 (128 bits each).  */
705
};
706
 
707
#define XSAVE_AVXH_ADDR(tdep, xsave, regnum) \
708
  (xsave + xsave_avxh_offset[regnum - I387_YMM0H_REGNUM (tdep)])
709
 
710
/* Similar to i387_supply_fxsave, but use XSAVE extended state.  */
711
 
712
void
713
i387_supply_xsave (struct regcache *regcache, int regnum,
714
                   const void *xsave)
715
{
716
  struct gdbarch_tdep *tdep = gdbarch_tdep (get_regcache_arch (regcache));
717
  const gdb_byte *regs = xsave;
718
  int i;
719
  unsigned int clear_bv;
720
  const gdb_byte *p;
721
  enum
722
    {
723
      none = 0x0,
724
      x87 = 0x1,
725
      sse = 0x2,
726
      avxh = 0x4,
727
      all = x87 | sse | avxh
728
    } regclass;
729
 
730
  gdb_assert (tdep->st0_regnum >= I386_ST0_REGNUM);
731
  gdb_assert (tdep->num_xmm_regs > 0);
732
 
733
  if (regnum == -1)
734
    regclass = all;
735
  else if (regnum >= I387_YMM0H_REGNUM (tdep)
736
           && regnum < I387_YMMENDH_REGNUM (tdep))
737
    regclass = avxh;
738
  else if (regnum >= I387_XMM0_REGNUM(tdep)
739
           && regnum < I387_MXCSR_REGNUM (tdep))
740
    regclass = sse;
741
  else if (regnum >= I387_ST0_REGNUM (tdep)
742
           && regnum < I387_FCTRL_REGNUM (tdep))
743
    regclass = x87;
744
  else
745
    regclass = none;
746
 
747
  if (regs != NULL && regclass != none)
748
    {
749
      /* Get `xstat_bv'.  */
750
      const gdb_byte *xstate_bv_p = XSAVE_XSTATE_BV_ADDR (regs);
751
 
752
      /* The supported bits in `xstat_bv' are 1 byte.  Clear part in
753
         vector registers if its bit in xstat_bv is zero.  */
754
      clear_bv = (~(*xstate_bv_p)) & tdep->xcr0;
755
    }
756
  else
757
    clear_bv = I386_XSTATE_AVX_MASK;
758
 
759
  switch (regclass)
760
    {
761
    case none:
762
      break;
763
 
764
    case avxh:
765
      if ((clear_bv & I386_XSTATE_AVX))
766
        p = NULL;
767
      else
768
        p = XSAVE_AVXH_ADDR (tdep, regs, regnum);
769
      regcache_raw_supply (regcache, regnum, p);
770
      return;
771
 
772
    case sse:
773
      if ((clear_bv & I386_XSTATE_SSE))
774
        p = NULL;
775
      else
776
        p = FXSAVE_ADDR (tdep, regs, regnum);
777
      regcache_raw_supply (regcache, regnum, p);
778
      return;
779
 
780
    case x87:
781
      if ((clear_bv & I386_XSTATE_X87))
782
        p = NULL;
783
      else
784
        p = FXSAVE_ADDR (tdep, regs, regnum);
785
      regcache_raw_supply (regcache, regnum, p);
786
      return;
787
 
788
    case all:
789
      /* Hanle the upper YMM registers.  */
790
      if ((tdep->xcr0 & I386_XSTATE_AVX))
791
        {
792
          if ((clear_bv & I386_XSTATE_AVX))
793
            p = NULL;
794
          else
795
            p = regs;
796
 
797
          for (i = I387_YMM0H_REGNUM (tdep);
798
               i < I387_YMMENDH_REGNUM (tdep); i++)
799
            {
800
              if (p != NULL)
801
                p = XSAVE_AVXH_ADDR (tdep, regs, i);
802
              regcache_raw_supply (regcache, i, p);
803
            }
804
        }
805
 
806
      /* Handle the XMM registers.  */
807
      if ((tdep->xcr0 & I386_XSTATE_SSE))
808
        {
809
          if ((clear_bv & I386_XSTATE_SSE))
810
            p = NULL;
811
          else
812
            p = regs;
813
 
814
          for (i = I387_XMM0_REGNUM (tdep);
815
               i < I387_MXCSR_REGNUM (tdep); i++)
816
            {
817
              if (p != NULL)
818
                p = FXSAVE_ADDR (tdep, regs, i);
819
              regcache_raw_supply (regcache, i, p);
820
            }
821
        }
822
 
823
      /* Handle the x87 registers.  */
824
      if ((tdep->xcr0 & I386_XSTATE_X87))
825
        {
826
          if ((clear_bv & I386_XSTATE_X87))
827
            p = NULL;
828
          else
829
            p = regs;
830
 
831
          for (i = I387_ST0_REGNUM (tdep);
832
               i < I387_FCTRL_REGNUM (tdep); i++)
833
            {
834
              if (p != NULL)
835
                p = FXSAVE_ADDR (tdep, regs, i);
836
              regcache_raw_supply (regcache, i, p);
837
            }
838
        }
839
      break;
840
    }
841
 
842
  /* Only handle x87 control registers.  */
843
  for (i = I387_FCTRL_REGNUM (tdep); i < I387_XMM0_REGNUM (tdep); i++)
844
    if (regnum == -1 || regnum == i)
845
      {
846
        if (regs == NULL)
847
          {
848
            regcache_raw_supply (regcache, i, NULL);
849
            continue;
850
          }
851
 
852
        /* Most of the FPU control registers occupy only 16 bits in
853
           the xsave extended state.  Give those a special treatment.  */
854
        if (i != I387_FIOFF_REGNUM (tdep)
855
            && i != I387_FOOFF_REGNUM (tdep))
856
          {
857
            gdb_byte val[4];
858
 
859
            memcpy (val, FXSAVE_ADDR (tdep, regs, i), 2);
860
            val[2] = val[3] = 0;
861
            if (i == I387_FOP_REGNUM (tdep))
862
              val[1] &= ((1 << 3) - 1);
863
            else if (i== I387_FTAG_REGNUM (tdep))
864
              {
865
                /* The fxsave area contains a simplified version of
866
                   the tag word.  We have to look at the actual 80-bit
867
                   FP data to recreate the traditional i387 tag word.  */
868
 
869
                unsigned long ftag = 0;
870
                int fpreg;
871
                int top;
872
 
873
                top = ((FXSAVE_ADDR (tdep, regs,
874
                                     I387_FSTAT_REGNUM (tdep)))[1] >> 3);
875
                top &= 0x7;
876
 
877
                for (fpreg = 7; fpreg >= 0; fpreg--)
878
                  {
879
                    int tag;
880
 
881
                    if (val[0] & (1 << fpreg))
882
                      {
883
                        int regnum = (fpreg + 8 - top) % 8
884
                                       + I387_ST0_REGNUM (tdep);
885
                        tag = i387_tag (FXSAVE_ADDR (tdep, regs, regnum));
886
                      }
887
                    else
888
                      tag = 3;          /* Empty */
889
 
890
                    ftag |= tag << (2 * fpreg);
891
                  }
892
                val[0] = ftag & 0xff;
893
                val[1] = (ftag >> 8) & 0xff;
894
              }
895
            regcache_raw_supply (regcache, i, val);
896
          }
897
        else
898
          regcache_raw_supply (regcache, i, FXSAVE_ADDR (tdep, regs, i));
899
      }
900
 
901
  if (regnum == I387_MXCSR_REGNUM (tdep) || regnum == -1)
902
    {
903
      p = regs == NULL ? NULL : FXSAVE_MXCSR_ADDR (regs);
904
      regcache_raw_supply (regcache, I387_MXCSR_REGNUM (tdep), p);
905
    }
906
}
907
 
908
/* Similar to i387_collect_fxsave, but use XSAVE extended state.  */
909
 
910
void
911
i387_collect_xsave (const struct regcache *regcache, int regnum,
912
                    void *xsave, int gcore)
913
{
914
  struct gdbarch_tdep *tdep = gdbarch_tdep (get_regcache_arch (regcache));
915
  gdb_byte *regs = xsave;
916
  int i;
917
  enum
918
    {
919
      none = 0x0,
920
      check = 0x1,
921
      x87 = 0x2 | check,
922
      sse = 0x4 | check,
923
      avxh = 0x8 | check,
924
      all = x87 | sse | avxh
925
    } regclass;
926
 
927
  gdb_assert (tdep->st0_regnum >= I386_ST0_REGNUM);
928
  gdb_assert (tdep->num_xmm_regs > 0);
929
 
930
  if (regnum == -1)
931
    regclass = all;
932
  else if (regnum >= I387_YMM0H_REGNUM (tdep)
933
           && regnum < I387_YMMENDH_REGNUM (tdep))
934
    regclass = avxh;
935
  else if (regnum >= I387_XMM0_REGNUM(tdep)
936
           && regnum < I387_MXCSR_REGNUM (tdep))
937
    regclass = sse;
938
  else if (regnum >= I387_ST0_REGNUM (tdep)
939
           && regnum < I387_FCTRL_REGNUM (tdep))
940
    regclass = x87;
941
  else
942
    regclass = none;
943
 
944
  if (gcore)
945
    {
946
      /* Clear XSAVE extended state.  */
947
      memset (regs, 0, I386_XSTATE_SIZE (tdep->xcr0));
948
 
949
      /* Update XCR0 and `xstate_bv' with XCR0 for gcore.  */
950
      if (tdep->xsave_xcr0_offset != -1)
951
        memcpy (regs + tdep->xsave_xcr0_offset, &tdep->xcr0, 8);
952
      memcpy (XSAVE_XSTATE_BV_ADDR (regs), &tdep->xcr0, 8);
953
    }
954
 
955
  if ((regclass & check))
956
    {
957
      gdb_byte raw[I386_MAX_REGISTER_SIZE];
958
      gdb_byte *xstate_bv_p = XSAVE_XSTATE_BV_ADDR (regs);
959
      unsigned int xstate_bv = 0;
960
      /* The supported bits in `xstat_bv' are 1 byte. */
961
      unsigned int clear_bv = (~(*xstate_bv_p)) & tdep->xcr0;
962
      gdb_byte *p;
963
 
964
      /* Clear register set if its bit in xstat_bv is zero.  */
965
      if (clear_bv)
966
        {
967
          if ((clear_bv & I386_XSTATE_AVX))
968
            for (i = I387_YMM0H_REGNUM (tdep);
969
                 i < I387_YMMENDH_REGNUM (tdep); i++)
970
              memset (XSAVE_AVXH_ADDR (tdep, regs, i), 0, 16);
971
 
972
          if ((clear_bv & I386_XSTATE_SSE))
973
            for (i = I387_XMM0_REGNUM (tdep);
974
                 i < I387_MXCSR_REGNUM (tdep); i++)
975
              memset (FXSAVE_ADDR (tdep, regs, i), 0, 16);
976
 
977
          if ((clear_bv & I386_XSTATE_X87))
978
            for (i = I387_ST0_REGNUM (tdep);
979
                 i < I387_FCTRL_REGNUM (tdep); i++)
980
              memset (FXSAVE_ADDR (tdep, regs, i), 0, 10);
981
        }
982
 
983
      if (regclass == all)
984
        {
985
          /* Check if any upper YMM registers are changed.  */
986
          if ((tdep->xcr0 & I386_XSTATE_AVX))
987
            for (i = I387_YMM0H_REGNUM (tdep);
988
                 i < I387_YMMENDH_REGNUM (tdep); i++)
989
              {
990
                regcache_raw_collect (regcache, i, raw);
991
                p = XSAVE_AVXH_ADDR (tdep, regs, i);
992
                if (memcmp (raw, p, 16))
993
                  {
994
                    xstate_bv |= I386_XSTATE_AVX;
995
                    memcpy (p, raw, 16);
996
                  }
997
              }
998
 
999
          /* Check if any SSE registers are changed.  */
1000
          if ((tdep->xcr0 & I386_XSTATE_SSE))
1001
            for (i = I387_XMM0_REGNUM (tdep);
1002
                 i < I387_MXCSR_REGNUM (tdep); i++)
1003
              {
1004
                regcache_raw_collect (regcache, i, raw);
1005
                p = FXSAVE_ADDR (tdep, regs, i);
1006
                if (memcmp (raw, p, 16))
1007
                  {
1008
                    xstate_bv |= I386_XSTATE_SSE;
1009
                    memcpy (p, raw, 16);
1010
                  }
1011
              }
1012
 
1013
          /* Check if any X87 registers are changed.  */
1014
          if ((tdep->xcr0 & I386_XSTATE_X87))
1015
            for (i = I387_ST0_REGNUM (tdep);
1016
                 i < I387_FCTRL_REGNUM (tdep); i++)
1017
              {
1018
                regcache_raw_collect (regcache, i, raw);
1019
                p = FXSAVE_ADDR (tdep, regs, i);
1020
                if (memcmp (raw, p, 10))
1021
                  {
1022
                    xstate_bv |= I386_XSTATE_X87;
1023
                    memcpy (p, raw, 10);
1024
                  }
1025
              }
1026
        }
1027
      else
1028
        {
1029
          /* Check if REGNUM is changed.  */
1030
          regcache_raw_collect (regcache, regnum, raw);
1031
 
1032
          switch (regclass)
1033
            {
1034
            default:
1035
              internal_error (__FILE__, __LINE__,
1036
                              _("invalid i387 regclass"));
1037
 
1038
            case avxh:
1039
              /* This is an upper YMM register.  */
1040
              p = XSAVE_AVXH_ADDR (tdep, regs, regnum);
1041
              if (memcmp (raw, p, 16))
1042
                {
1043
                  xstate_bv |= I386_XSTATE_AVX;
1044
                  memcpy (p, raw, 16);
1045
                }
1046
              break;
1047
 
1048
            case sse:
1049
              /* This is an SSE register.  */
1050
              p = FXSAVE_ADDR (tdep, regs, regnum);
1051
              if (memcmp (raw, p, 16))
1052
                {
1053
                  xstate_bv |= I386_XSTATE_SSE;
1054
                  memcpy (p, raw, 16);
1055
                }
1056
              break;
1057
 
1058
            case x87:
1059
              /* This is an x87 register.  */
1060
              p = FXSAVE_ADDR (tdep, regs, regnum);
1061
              if (memcmp (raw, p, 10))
1062
                {
1063
                  xstate_bv |= I386_XSTATE_X87;
1064
                  memcpy (p, raw, 10);
1065
                }
1066
              break;
1067
            }
1068
        }
1069
 
1070
      /* Update the corresponding bits in `xstate_bv' if any SSE/AVX
1071
         registers are changed.  */
1072
      if (xstate_bv)
1073
        {
1074
          /* The supported bits in `xstat_bv' are 1 byte.  */
1075
          *xstate_bv_p |= (gdb_byte) xstate_bv;
1076
 
1077
          switch (regclass)
1078
            {
1079
            default:
1080
              internal_error (__FILE__, __LINE__,
1081
                              _("invalid i387 regclass"));
1082
 
1083
            case all:
1084
              break;
1085
 
1086
            case x87:
1087
            case sse:
1088
            case avxh:
1089
              /* Register REGNUM has been updated.  Return.  */
1090
              return;
1091
            }
1092
        }
1093
      else
1094
        {
1095
          /* Return if REGNUM isn't changed.  */
1096
          if (regclass != all)
1097
            return;
1098
        }
1099
    }
1100
 
1101
  /* Only handle x87 control registers.  */
1102
  for (i = I387_FCTRL_REGNUM (tdep); i < I387_XMM0_REGNUM (tdep); i++)
1103
    if (regnum == -1 || regnum == i)
1104
      {
1105
        /* Most of the FPU control registers occupy only 16 bits in
1106
           the xsave extended state.  Give those a special treatment.  */
1107
        if (i != I387_FIOFF_REGNUM (tdep)
1108
            && i != I387_FOOFF_REGNUM (tdep))
1109
          {
1110
            gdb_byte buf[4];
1111
 
1112
            regcache_raw_collect (regcache, i, buf);
1113
 
1114
            if (i == I387_FOP_REGNUM (tdep))
1115
              {
1116
                /* The opcode occupies only 11 bits.  Make sure we
1117
                   don't touch the other bits.  */
1118
                buf[1] &= ((1 << 3) - 1);
1119
                buf[1] |= ((FXSAVE_ADDR (tdep, regs, i))[1] & ~((1 << 3) - 1));
1120
              }
1121
            else if (i == I387_FTAG_REGNUM (tdep))
1122
              {
1123
                /* Converting back is much easier.  */
1124
 
1125
                unsigned short ftag;
1126
                int fpreg;
1127
 
1128
                ftag = (buf[1] << 8) | buf[0];
1129
                buf[0] = 0;
1130
                buf[1] = 0;
1131
 
1132
                for (fpreg = 7; fpreg >= 0; fpreg--)
1133
                  {
1134
                    int tag = (ftag >> (fpreg * 2)) & 3;
1135
 
1136
                    if (tag != 3)
1137
                      buf[0] |= (1 << fpreg);
1138
                  }
1139
              }
1140
            memcpy (FXSAVE_ADDR (tdep, regs, i), buf, 2);
1141
          }
1142
        else
1143
          regcache_raw_collect (regcache, i, FXSAVE_ADDR (tdep, regs, i));
1144
      }
1145
 
1146
  if (regnum == I387_MXCSR_REGNUM (tdep) || regnum == -1)
1147
    regcache_raw_collect (regcache, I387_MXCSR_REGNUM (tdep),
1148
                          FXSAVE_MXCSR_ADDR (regs));
1149
}
1150
 
1151
/* Recreate the FTW (tag word) valid bits from the 80-bit FP data in
1152
   *RAW.  */
1153
 
1154
static int
1155
i387_tag (const gdb_byte *raw)
1156
{
1157
  int integer;
1158
  unsigned int exponent;
1159
  unsigned long fraction[2];
1160
 
1161
  integer = raw[7] & 0x80;
1162
  exponent = (((raw[9] & 0x7f) << 8) | raw[8]);
1163
  fraction[0] = ((raw[3] << 24) | (raw[2] << 16) | (raw[1] << 8) | raw[0]);
1164
  fraction[1] = (((raw[7] & 0x7f) << 24) | (raw[6] << 16)
1165
                 | (raw[5] << 8) | raw[4]);
1166
 
1167
  if (exponent == 0x7fff)
1168
    {
1169
      /* Special.  */
1170
      return (2);
1171
    }
1172
  else if (exponent == 0x0000)
1173
    {
1174
      if (fraction[0] == 0x0000 && fraction[1] == 0x0000 && !integer)
1175
        {
1176
          /* Zero.  */
1177
          return (1);
1178
        }
1179
      else
1180
        {
1181
          /* Special.  */
1182
          return (2);
1183
        }
1184
    }
1185
  else
1186
    {
1187
      if (integer)
1188
        {
1189
          /* Valid.  */
1190
          return (0);
1191
        }
1192
      else
1193
        {
1194
          /* Special.  */
1195
          return (2);
1196
        }
1197
    }
1198
}
1199
 
1200
/* Prepare the FPU stack in REGCACHE for a function return.  */
1201
 
1202
void
1203
i387_return_value (struct gdbarch *gdbarch, struct regcache *regcache)
1204
{
1205
  struct gdbarch_tdep *tdep = gdbarch_tdep (gdbarch);
1206
  ULONGEST fstat;
1207
 
1208
  /* Set the top of the floating-point register stack to 7.  The
1209
     actual value doesn't really matter, but 7 is what a normal
1210
     function return would end up with if the program started out with
1211
     a freshly initialized FPU.  */
1212
  regcache_raw_read_unsigned (regcache, I387_FSTAT_REGNUM (tdep), &fstat);
1213
  fstat |= (7 << 11);
1214
  regcache_raw_write_unsigned (regcache, I387_FSTAT_REGNUM (tdep), fstat);
1215
 
1216
  /* Mark %st(1) through %st(7) as empty.  Since we set the top of the
1217
     floating-point register stack to 7, the appropriate value for the
1218
     tag word is 0x3fff.  */
1219
  regcache_raw_write_unsigned (regcache, I387_FTAG_REGNUM (tdep), 0x3fff);
1220
 
1221
}

powered by: WebSVN 2.1.0

© copyright 1999-2024 OpenCores.org, equivalent to Oliscience, all rights reserved. OpenCores®, registered trademark.