1 /* Subroutines needed for unwinding IA-64 standard format stack frame
2 info for exception handling.
3 Copyright (C) 1997, 1998, 1999, 2000, 2001, 2002, 2004, 2005, 2006,
4 2009, 2011 Free Software Foundation, Inc.
5 Contributed by Andrew MacLeod <amacleod@cygnus.com>
6 Andrew Haley <aph@cygnus.com>
7 David Mosberger-Tang <davidm@hpl.hp.com>
9 This file is part of GCC.
11 GCC is free software; you can redistribute it and/or modify
12 it under the terms of the GNU General Public License as published by
13 the Free Software Foundation; either version 3, or (at your option)
16 GCC is distributed in the hope that it will be useful,
17 but WITHOUT ANY WARRANTY; without even the implied warranty of
18 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
19 GNU General Public License for more details.
21 Under Section 7 of GPL version 3, you are granted additional
22 permissions described in the GCC Runtime Library Exception, version
23 3.1, as published by the Free Software Foundation.
25 You should have received a copy of the GNU General Public License and
26 a copy of the GCC Runtime Library Exception along with this program;
27 see the files COPYING3 and COPYING.RUNTIME respectively. If not, see
28 <http://www.gnu.org/licenses/>. */
32 #include "coretypes.h"
35 #include "unwind-ia64.h"
36 #include "unwind-compat.h"
37 #include "ia64intrin.h"
39 /* This isn't thread safe, but nice for occasional tests. */
40 #undef ENABLE_MALLOC_CHECKING
42 #ifndef __USING_SJLJ_EXCEPTIONS__
45 /* By default, assume personality routine interface compatibility with
47 #ifndef MD_UNW_COMPATIBLE_PERSONALITY_P
48 #define MD_UNW_COMPATIBLE_PERSONALITY_P(HEADER) 1
51 enum unw_application_register
65 enum unw_register_index
72 UNW_REG_PSP
, /* previous memory stack pointer */
75 UNW_REG_BSP
, /* register stack pointer */
77 UNW_REG_PFS
, /* previous function state */
82 /* Special preserved registers. */
83 UNW_REG_UNAT
, UNW_REG_PR
, UNW_REG_LC
, UNW_REG_FPSR
,
85 /* Non-stacked general registers. */
87 UNW_REG_R4
= UNW_REG_R2
+ 2,
88 UNW_REG_R7
= UNW_REG_R2
+ 5,
89 UNW_REG_R31
= UNW_REG_R2
+ 29,
91 /* Non-stacked floating point registers. */
93 UNW_REG_F5
= UNW_REG_F2
+ 3,
94 UNW_REG_F16
= UNW_REG_F2
+ 14,
95 UNW_REG_F31
= UNW_REG_F2
+ 29,
97 /* Branch registers. */
98 UNW_REG_B0
, UNW_REG_B1
,
99 UNW_REG_B5
= UNW_REG_B1
+ 4,
106 UNW_WHERE_NONE
, /* register isn't saved at all */
107 UNW_WHERE_GR
, /* register is saved in a general register */
108 UNW_WHERE_FR
, /* register is saved in a floating-point register */
109 UNW_WHERE_BR
, /* register is saved in a branch register */
110 UNW_WHERE_SPREL
, /* register is saved on memstack (sp-relative) */
111 UNW_WHERE_PSPREL
, /* register is saved on memstack (psp-relative) */
113 /* At the end of each prologue these locations get resolved to
114 UNW_WHERE_PSPREL and UNW_WHERE_GR, respectively. */
115 UNW_WHERE_SPILL_HOME
, /* register is saved in its spill home */
116 UNW_WHERE_GR_SAVE
/* register is saved in next general register */
119 #define UNW_WHEN_NEVER 0x7fffffff
123 unsigned long val
; /* save location: register number or offset */
124 enum unw_where where
; /* where the register gets saved */
125 int when
; /* when the register gets saved */
128 struct unw_reg_state
{
129 struct unw_reg_state
*next
; /* next (outer) element on state stack */
130 struct unw_reg_info reg
[UNW_NUM_REGS
]; /* register save locations */
133 struct unw_labeled_state
{
134 struct unw_labeled_state
*next
; /* next labeled state (or NULL) */
135 unsigned long label
; /* label for this state */
136 struct unw_reg_state saved_state
;
139 typedef struct unw_state_record
141 unsigned int first_region
: 1; /* is this the first region? */
142 unsigned int done
: 1; /* are we done scanning descriptors? */
143 unsigned int any_spills
: 1; /* got any register spills? */
144 unsigned int in_body
: 1; /* are we inside a body? */
145 unsigned int no_reg_stack_frame
: 1; /* Don't adjust bsp for i&l regs */
146 unsigned char *imask
; /* imask of spill_mask record or NULL */
147 unsigned long pr_val
; /* predicate values */
148 unsigned long pr_mask
; /* predicate mask */
149 long spill_offset
; /* psp-relative offset for spill base */
156 unsigned char gr_save_loc
; /* next general register to use for saving */
157 unsigned char return_link_reg
; /* branch register for return link */
158 unsigned short unwabi
;
160 struct unw_labeled_state
*labeled_states
; /* list of all labeled states */
161 struct unw_reg_state curr
; /* current state */
163 _Unwind_Personality_Fn personality
;
165 } _Unwind_FrameState
;
169 UNW_NAT_NONE
, /* NaT not represented */
170 UNW_NAT_VAL
, /* NaT represented by NaT value (fp reg) */
171 UNW_NAT_MEMSTK
, /* NaT value is in unat word at offset OFF */
172 UNW_NAT_REGSTK
/* NaT is in rnat */
181 struct _Unwind_Context
183 /* Initial frame info. */
184 unsigned long rnat
; /* rse nat collection */
185 unsigned long regstk_top
; /* lowest address of rbs stored register
186 which uses context->rnat collection */
188 /* Current frame info. */
189 unsigned long bsp
; /* backing store pointer value
190 corresponding to psp. */
191 unsigned long sp
; /* stack pointer value */
192 unsigned long psp
; /* previous sp value */
193 unsigned long rp
; /* return pointer */
194 unsigned long pr
; /* predicate collection */
196 unsigned long region_start
; /* start of unwind region */
197 unsigned long gp
; /* global pointer value */
198 void *lsda
; /* language specific data area */
200 /* Preserved state. */
201 unsigned long *bsp_loc
; /* previous bsp save location
202 Appears to be write-only? */
203 unsigned long *bspstore_loc
;
204 unsigned long *pfs_loc
; /* Save location for pfs in current
205 (corr. to sp) frame. Target
206 contains cfm for caller. */
207 unsigned long *signal_pfs_loc
;/* Save location for pfs in current
208 signal frame. Target contains
210 unsigned long *pri_unat_loc
;
211 unsigned long *unat_loc
;
212 unsigned long *lc_loc
;
213 unsigned long *fpsr_loc
;
215 unsigned long eh_data
[4];
222 enum unw_nat_type type
: 3;
223 signed long off
: 61; /* NaT word is at loc+nat.off */
225 } ireg
[32 - 2]; /* Indexed by <register number> - 2 */
227 unsigned long *br_loc
[8];
228 void *fr_loc
[32 - 2];
230 /* ??? We initially point pri_unat_loc here. The entire NAT bit
232 unsigned long initial_unat
;
235 typedef unsigned long unw_word
;
237 /* Implicit register save order. See section 11.4.2.3 Rules for Using
238 Unwind Descriptors, rule 3. */
240 static unsigned char const save_order
[] =
242 UNW_REG_RP
, UNW_REG_PFS
, UNW_REG_PSP
, UNW_REG_PR
,
243 UNW_REG_UNAT
, UNW_REG_LC
, UNW_REG_FPSR
, UNW_REG_PRI_UNAT_GR
247 #define MIN(X, Y) ((X) < (Y) ? (X) : (Y))
249 /* MASK is a bitmap describing the allocation state of emergency buffers,
250 with bit set indicating free. Return >= 0 if allocation is successful;
254 atomic_alloc (unsigned int *mask
)
256 unsigned int old
= *mask
, ret
, new;
264 new = __sync_val_compare_and_swap (mask
, old
, new);
270 return __builtin_ffs (ret
) - 1;
273 /* Similarly, free an emergency buffer. */
276 atomic_free (unsigned int *mask
, int bit
)
278 __sync_xor_and_fetch (mask
, 1 << bit
);
282 #define SIZE(X) (sizeof(X) / sizeof(*(X)))
283 #define MASK_FOR(X) ((2U << (SIZE (X) - 1)) - 1)
284 #define PTR_IN(X, P) ((P) >= (X) && (P) < (X) + SIZE (X))
286 static struct unw_reg_state emergency_reg_state
[32];
287 static unsigned int emergency_reg_state_free
= MASK_FOR (emergency_reg_state
);
289 static struct unw_labeled_state emergency_labeled_state
[8];
290 static unsigned int emergency_labeled_state_free
= MASK_FOR (emergency_labeled_state
);
292 #ifdef ENABLE_MALLOC_CHECKING
293 static int reg_state_alloced
;
294 static int labeled_state_alloced
;
297 /* Allocation and deallocation of structures. */
299 static struct unw_reg_state
*
300 alloc_reg_state (void)
302 struct unw_reg_state
*rs
;
304 #ifdef ENABLE_MALLOC_CHECKING
308 rs
= malloc (sizeof (struct unw_reg_state
));
311 int n
= atomic_alloc (&emergency_reg_state_free
);
313 rs
= &emergency_reg_state
[n
];
320 free_reg_state (struct unw_reg_state
*rs
)
322 #ifdef ENABLE_MALLOC_CHECKING
326 if (PTR_IN (emergency_reg_state
, rs
))
327 atomic_free (&emergency_reg_state_free
, rs
- emergency_reg_state
);
332 static struct unw_labeled_state
*
333 alloc_label_state (void)
335 struct unw_labeled_state
*ls
;
337 #ifdef ENABLE_MALLOC_CHECKING
338 labeled_state_alloced
++;
341 ls
= malloc(sizeof(struct unw_labeled_state
));
344 int n
= atomic_alloc (&emergency_labeled_state_free
);
346 ls
= &emergency_labeled_state
[n
];
353 free_label_state (struct unw_labeled_state
*ls
)
355 #ifdef ENABLE_MALLOC_CHECKING
356 labeled_state_alloced
--;
359 if (PTR_IN (emergency_labeled_state
, ls
))
360 atomic_free (&emergency_labeled_state_free
, emergency_labeled_state
- ls
);
365 /* Routines to manipulate the state stack. */
368 push (struct unw_state_record
*sr
)
370 struct unw_reg_state
*rs
= alloc_reg_state ();
371 memcpy (rs
, &sr
->curr
, sizeof (*rs
));
376 pop (struct unw_state_record
*sr
)
378 struct unw_reg_state
*rs
= sr
->curr
.next
;
382 memcpy (&sr
->curr
, rs
, sizeof(*rs
));
386 /* Make a copy of the state stack. Non-recursive to avoid stack overflows. */
388 static struct unw_reg_state
*
389 dup_state_stack (struct unw_reg_state
*rs
)
391 struct unw_reg_state
*copy
, *prev
= NULL
, *first
= NULL
;
395 copy
= alloc_reg_state ();
396 memcpy (copy
, rs
, sizeof(*copy
));
408 /* Free all stacked register states (but not RS itself). */
410 free_state_stack (struct unw_reg_state
*rs
)
412 struct unw_reg_state
*p
, *next
;
414 for (p
= rs
->next
; p
!= NULL
; p
= next
)
422 /* Free all labeled states. */
425 free_label_states (struct unw_labeled_state
*ls
)
427 struct unw_labeled_state
*next
;
429 for (; ls
; ls
= next
)
433 free_state_stack (&ls
->saved_state
);
434 free_label_state (ls
);
438 /* Unwind decoder routines */
440 static enum unw_register_index
__attribute__((const))
441 decode_abreg (unsigned char abreg
, int memory
)
445 #if TARGET_ABI_OPEN_VMS
446 /* OpenVMS Calling Standard specifies R3 - R31. */
447 case 0x03 ... 0x1f: return UNW_REG_R2
+ (abreg
- 0x02);
449 /* Standard Intel ABI specifies GR 4 - 7. */
450 case 0x04 ... 0x07: return UNW_REG_R4
+ (abreg
- 0x04);
452 case 0x22 ... 0x25: return UNW_REG_F2
+ (abreg
- 0x22);
453 case 0x30 ... 0x3f: return UNW_REG_F16
+ (abreg
- 0x30);
454 case 0x41 ... 0x45: return UNW_REG_B1
+ (abreg
- 0x41);
455 case 0x60: return UNW_REG_PR
;
456 case 0x61: return UNW_REG_PSP
;
457 case 0x62: return memory
? UNW_REG_PRI_UNAT_MEM
: UNW_REG_PRI_UNAT_GR
;
458 case 0x63: return UNW_REG_RP
;
459 case 0x64: return UNW_REG_BSP
;
460 case 0x65: return UNW_REG_BSPSTORE
;
461 case 0x66: return UNW_REG_RNAT
;
462 case 0x67: return UNW_REG_UNAT
;
463 case 0x68: return UNW_REG_FPSR
;
464 case 0x69: return UNW_REG_PFS
;
465 case 0x6a: return UNW_REG_LC
;
472 set_reg (struct unw_reg_info
*reg
, enum unw_where where
,
473 int when
, unsigned long val
)
477 if (reg
->when
== UNW_WHEN_NEVER
)
482 alloc_spill_area (unsigned long *offp
, unsigned long regsize
,
483 struct unw_reg_info
*lo
, struct unw_reg_info
*hi
)
485 struct unw_reg_info
*reg
;
487 for (reg
= hi
; reg
>= lo
; --reg
)
489 if (reg
->where
== UNW_WHERE_SPILL_HOME
)
491 reg
->where
= UNW_WHERE_PSPREL
;
499 spill_next_when (struct unw_reg_info
**regp
, struct unw_reg_info
*lim
,
502 struct unw_reg_info
*reg
;
504 for (reg
= *regp
; reg
<= lim
; ++reg
)
506 if (reg
->where
== UNW_WHERE_SPILL_HOME
)
518 finish_prologue (struct unw_state_record
*sr
)
520 struct unw_reg_info
*reg
;
524 /* First, resolve implicit register save locations
525 (see Section "11.4.2.3 Rules for Using Unwind Descriptors", rule 3). */
527 for (i
= 0; i
< (int) sizeof (save_order
); ++i
)
529 reg
= sr
->curr
.reg
+ save_order
[i
];
530 if (reg
->where
== UNW_WHERE_GR_SAVE
)
532 reg
->where
= UNW_WHERE_GR
;
533 reg
->val
= sr
->gr_save_loc
++;
537 /* Next, compute when the fp, general, and branch registers get saved.
538 This must come before alloc_spill_area() because we need to know
539 which registers are spilled to their home locations. */
542 static unsigned char const limit
[3] = {
543 UNW_REG_F31
, UNW_REG_R7
, UNW_REG_B5
546 unsigned char kind
, mask
= 0, *cp
= sr
->imask
;
548 struct unw_reg_info
*(regs
[3]);
550 regs
[0] = sr
->curr
.reg
+ UNW_REG_F2
;
551 regs
[1] = sr
->curr
.reg
+ UNW_REG_R4
;
552 regs
[2] = sr
->curr
.reg
+ UNW_REG_B1
;
554 for (t
= 0; t
< sr
->region_len
; ++t
)
558 kind
= (mask
>> 2*(3-(t
& 3))) & 3;
560 spill_next_when (®s
[kind
- 1], sr
->curr
.reg
+ limit
[kind
- 1],
561 sr
->region_start
+ t
);
565 /* Next, lay out the memory stack spill area. */
568 off
= sr
->spill_offset
;
569 alloc_spill_area (&off
, 16, sr
->curr
.reg
+ UNW_REG_F2
,
570 sr
->curr
.reg
+ UNW_REG_F31
);
571 alloc_spill_area (&off
, 8, sr
->curr
.reg
+ UNW_REG_B1
,
572 sr
->curr
.reg
+ UNW_REG_B5
);
573 alloc_spill_area (&off
, 8, sr
->curr
.reg
+ UNW_REG_R4
,
574 sr
->curr
.reg
+ UNW_REG_R7
);
579 * Region header descriptors.
583 desc_prologue (int body
, unw_word rlen
, unsigned char mask
,
584 unsigned char grsave
, struct unw_state_record
*sr
)
588 if (!(sr
->in_body
|| sr
->first_region
))
589 finish_prologue (sr
);
590 sr
->first_region
= 0;
592 /* Check if we're done. */
593 if (sr
->when_target
< sr
->region_start
+ sr
->region_len
)
599 for (i
= 0; i
< sr
->epilogue_count
; ++i
)
602 sr
->epilogue_count
= 0;
603 sr
->epilogue_start
= UNW_WHEN_NEVER
;
608 sr
->region_start
+= sr
->region_len
;
609 sr
->region_len
= rlen
;
614 for (i
= 0; i
< 4; ++i
)
617 set_reg (sr
->curr
.reg
+ save_order
[i
], UNW_WHERE_GR
,
618 sr
->region_start
+ sr
->region_len
- 1, grsave
++);
621 sr
->gr_save_loc
= grsave
;
624 sr
->spill_offset
= 0x10; /* default to psp+16 */
629 * Prologue descriptors.
633 desc_abi (unsigned char abi
,
634 unsigned char context
,
635 struct unw_state_record
*sr
)
637 sr
->unwabi
= (abi
<< 8) | context
;
641 desc_br_gr (unsigned char brmask
, unsigned char gr
,
642 struct unw_state_record
*sr
)
646 for (i
= 0; i
< 5; ++i
)
649 set_reg (sr
->curr
.reg
+ UNW_REG_B1
+ i
, UNW_WHERE_GR
,
650 sr
->region_start
+ sr
->region_len
- 1, gr
++);
656 desc_br_mem (unsigned char brmask
, struct unw_state_record
*sr
)
660 for (i
= 0; i
< 5; ++i
)
664 set_reg (sr
->curr
.reg
+ UNW_REG_B1
+ i
, UNW_WHERE_SPILL_HOME
,
665 sr
->region_start
+ sr
->region_len
- 1, 0);
673 desc_frgr_mem (unsigned char grmask
, unw_word frmask
,
674 struct unw_state_record
*sr
)
678 for (i
= 0; i
< 4; ++i
)
680 if ((grmask
& 1) != 0)
682 set_reg (sr
->curr
.reg
+ UNW_REG_R4
+ i
, UNW_WHERE_SPILL_HOME
,
683 sr
->region_start
+ sr
->region_len
- 1, 0);
688 for (i
= 0; i
< 20; ++i
)
690 if ((frmask
& 1) != 0)
692 enum unw_register_index base
= i
< 4 ? UNW_REG_F2
: UNW_REG_F16
- 4;
693 set_reg (sr
->curr
.reg
+ base
+ i
, UNW_WHERE_SPILL_HOME
,
694 sr
->region_start
+ sr
->region_len
- 1, 0);
702 desc_fr_mem (unsigned char frmask
, struct unw_state_record
*sr
)
706 for (i
= 0; i
< 4; ++i
)
708 if ((frmask
& 1) != 0)
710 set_reg (sr
->curr
.reg
+ UNW_REG_F2
+ i
, UNW_WHERE_SPILL_HOME
,
711 sr
->region_start
+ sr
->region_len
- 1, 0);
719 desc_gr_gr (unsigned char grmask
, unsigned char gr
,
720 struct unw_state_record
*sr
)
724 for (i
= 0; i
< 4; ++i
)
726 if ((grmask
& 1) != 0)
727 set_reg (sr
->curr
.reg
+ UNW_REG_R4
+ i
, UNW_WHERE_GR
,
728 sr
->region_start
+ sr
->region_len
- 1, gr
++);
734 desc_gr_mem (unsigned char grmask
, struct unw_state_record
*sr
)
738 for (i
= 0; i
< 4; ++i
)
740 if ((grmask
& 1) != 0)
742 set_reg (sr
->curr
.reg
+ UNW_REG_R4
+ i
, UNW_WHERE_SPILL_HOME
,
743 sr
->region_start
+ sr
->region_len
- 1, 0);
751 desc_mem_stack_f (unw_word t
, unw_word size
, struct unw_state_record
*sr
)
753 set_reg (sr
->curr
.reg
+ UNW_REG_PSP
, UNW_WHERE_NONE
,
754 sr
->region_start
+ MIN ((int)t
, sr
->region_len
- 1), 16*size
);
758 desc_mem_stack_v (unw_word t
, struct unw_state_record
*sr
)
760 sr
->curr
.reg
[UNW_REG_PSP
].when
761 = sr
->region_start
+ MIN ((int)t
, sr
->region_len
- 1);
765 desc_reg_gr (unsigned char reg
, unsigned char dst
, struct unw_state_record
*sr
)
767 set_reg (sr
->curr
.reg
+ reg
, UNW_WHERE_GR
,
768 sr
->region_start
+ sr
->region_len
- 1, dst
);
772 desc_reg_psprel (unsigned char reg
, unw_word pspoff
,
773 struct unw_state_record
*sr
)
775 set_reg (sr
->curr
.reg
+ reg
, UNW_WHERE_PSPREL
,
776 sr
->region_start
+ sr
->region_len
- 1,
781 desc_reg_sprel (unsigned char reg
, unw_word spoff
, struct unw_state_record
*sr
)
783 set_reg (sr
->curr
.reg
+ reg
, UNW_WHERE_SPREL
,
784 sr
->region_start
+ sr
->region_len
- 1,
789 desc_rp_br (unsigned char dst
, struct unw_state_record
*sr
)
791 sr
->return_link_reg
= dst
;
795 desc_reg_when (unsigned char regnum
, unw_word t
, struct unw_state_record
*sr
)
797 struct unw_reg_info
*reg
= sr
->curr
.reg
+ regnum
;
799 if (reg
->where
== UNW_WHERE_NONE
)
800 reg
->where
= UNW_WHERE_GR_SAVE
;
801 reg
->when
= sr
->region_start
+ MIN ((int)t
, sr
->region_len
- 1);
805 desc_spill_base (unw_word pspoff
, struct unw_state_record
*sr
)
807 sr
->spill_offset
= 0x10 - 4*pspoff
;
810 static inline unsigned char *
811 desc_spill_mask (unsigned char *imaskp
, struct unw_state_record
*sr
)
814 return imaskp
+ (2*sr
->region_len
+ 7)/8;
821 desc_epilogue (unw_word t
, unw_word ecount
, struct unw_state_record
*sr
)
823 sr
->epilogue_start
= sr
->region_start
+ sr
->region_len
- 1 - t
;
824 sr
->epilogue_count
= ecount
+ 1;
828 desc_copy_state (unw_word label
, struct unw_state_record
*sr
)
830 struct unw_labeled_state
*ls
;
832 for (ls
= sr
->labeled_states
; ls
; ls
= ls
->next
)
834 if (ls
->label
== label
)
836 free_state_stack (&sr
->curr
);
837 memcpy (&sr
->curr
, &ls
->saved_state
, sizeof (sr
->curr
));
838 sr
->curr
.next
= dup_state_stack (ls
->saved_state
.next
);
846 desc_label_state (unw_word label
, struct unw_state_record
*sr
)
848 struct unw_labeled_state
*ls
= alloc_label_state ();
851 memcpy (&ls
->saved_state
, &sr
->curr
, sizeof (ls
->saved_state
));
852 ls
->saved_state
.next
= dup_state_stack (sr
->curr
.next
);
854 /* Insert into list of labeled states. */
855 ls
->next
= sr
->labeled_states
;
856 sr
->labeled_states
= ls
;
860 * General descriptors.
864 desc_is_active (unsigned char qp
, unw_word t
, struct unw_state_record
*sr
)
866 if (sr
->when_target
<= sr
->region_start
+ MIN ((int)t
, sr
->region_len
- 1))
870 if ((sr
->pr_val
& (1UL << qp
)) == 0)
872 sr
->pr_mask
|= (1UL << qp
);
878 desc_restore_p (unsigned char qp
, unw_word t
, unsigned char abreg
,
879 struct unw_state_record
*sr
)
881 struct unw_reg_info
*r
;
883 if (! desc_is_active (qp
, t
, sr
))
886 r
= sr
->curr
.reg
+ decode_abreg (abreg
, 0);
887 r
->where
= UNW_WHERE_NONE
;
888 r
->when
= sr
->region_start
+ MIN ((int)t
, sr
->region_len
- 1);
893 desc_spill_reg_p (unsigned char qp
, unw_word t
, unsigned char abreg
,
894 unsigned char x
, unsigned char ytreg
,
895 struct unw_state_record
*sr
)
897 enum unw_where where
= UNW_WHERE_GR
;
898 struct unw_reg_info
*r
;
900 if (! desc_is_active (qp
, t
, sr
))
904 where
= UNW_WHERE_BR
;
905 else if (ytreg
& 0x80)
906 where
= UNW_WHERE_FR
;
908 r
= sr
->curr
.reg
+ decode_abreg (abreg
, 0);
910 r
->when
= sr
->region_start
+ MIN ((int)t
, sr
->region_len
- 1);
911 r
->val
= ytreg
& 0x7f;
915 desc_spill_psprel_p (unsigned char qp
, unw_word t
, unsigned char abreg
,
916 unw_word pspoff
, struct unw_state_record
*sr
)
918 struct unw_reg_info
*r
;
920 if (! desc_is_active (qp
, t
, sr
))
923 r
= sr
->curr
.reg
+ decode_abreg (abreg
, 1);
924 r
->where
= UNW_WHERE_PSPREL
;
925 r
->when
= sr
->region_start
+ MIN((int)t
, sr
->region_len
- 1);
926 r
->val
= 0x10 - 4*pspoff
;
930 desc_spill_sprel_p (unsigned char qp
, unw_word t
, unsigned char abreg
,
931 unw_word spoff
, struct unw_state_record
*sr
)
933 struct unw_reg_info
*r
;
935 if (! desc_is_active (qp
, t
, sr
))
938 r
= sr
->curr
.reg
+ decode_abreg (abreg
, 1);
939 r
->where
= UNW_WHERE_SPREL
;
940 r
->when
= sr
->region_start
+ MIN ((int)t
, sr
->region_len
- 1);
945 #define UNW_DEC_BAD_CODE(code) abort ();
947 /* Region headers. */
948 #define UNW_DEC_PROLOGUE_GR(fmt,r,m,gr,arg) desc_prologue(0,r,m,gr,arg)
949 #define UNW_DEC_PROLOGUE(fmt,b,r,arg) desc_prologue(b,r,0,32,arg)
951 /* Prologue descriptors. */
952 #define UNW_DEC_ABI(fmt,a,c,arg) desc_abi(a,c,arg)
953 #define UNW_DEC_BR_GR(fmt,b,g,arg) desc_br_gr(b,g,arg)
954 #define UNW_DEC_BR_MEM(fmt,b,arg) desc_br_mem(b,arg)
955 #define UNW_DEC_FRGR_MEM(fmt,g,f,arg) desc_frgr_mem(g,f,arg)
956 #define UNW_DEC_FR_MEM(fmt,f,arg) desc_fr_mem(f,arg)
957 #define UNW_DEC_GR_GR(fmt,m,g,arg) desc_gr_gr(m,g,arg)
958 #define UNW_DEC_GR_MEM(fmt,m,arg) desc_gr_mem(m,arg)
959 #define UNW_DEC_MEM_STACK_F(fmt,t,s,arg) desc_mem_stack_f(t,s,arg)
960 #define UNW_DEC_MEM_STACK_V(fmt,t,arg) desc_mem_stack_v(t,arg)
961 #define UNW_DEC_REG_GR(fmt,r,d,arg) desc_reg_gr(r,d,arg)
962 #define UNW_DEC_REG_PSPREL(fmt,r,o,arg) desc_reg_psprel(r,o,arg)
963 #define UNW_DEC_REG_SPREL(fmt,r,o,arg) desc_reg_sprel(r,o,arg)
964 #define UNW_DEC_REG_WHEN(fmt,r,t,arg) desc_reg_when(r,t,arg)
965 #define UNW_DEC_PRIUNAT_WHEN_GR(fmt,t,arg) desc_reg_when(UNW_REG_PRI_UNAT_GR,t,arg)
966 #define UNW_DEC_PRIUNAT_WHEN_MEM(fmt,t,arg) desc_reg_when(UNW_REG_PRI_UNAT_MEM,t,arg)
967 #define UNW_DEC_PRIUNAT_GR(fmt,r,arg) desc_reg_gr(UNW_REG_PRI_UNAT_GR,r,arg)
968 #define UNW_DEC_PRIUNAT_PSPREL(fmt,o,arg) desc_reg_psprel(UNW_REG_PRI_UNAT_MEM,o,arg)
969 #define UNW_DEC_PRIUNAT_SPREL(fmt,o,arg) desc_reg_sprel(UNW_REG_PRI_UNAT_MEM,o,arg)
970 #define UNW_DEC_RP_BR(fmt,d,arg) desc_rp_br(d,arg)
971 #define UNW_DEC_SPILL_BASE(fmt,o,arg) desc_spill_base(o,arg)
972 #define UNW_DEC_SPILL_MASK(fmt,m,arg) (m = desc_spill_mask(m,arg))
974 /* Body descriptors. */
975 #define UNW_DEC_EPILOGUE(fmt,t,c,arg) desc_epilogue(t,c,arg)
976 #define UNW_DEC_COPY_STATE(fmt,l,arg) desc_copy_state(l,arg)
977 #define UNW_DEC_LABEL_STATE(fmt,l,arg) desc_label_state(l,arg)
979 /* General unwind descriptors. */
980 #define UNW_DEC_SPILL_REG_P(f,p,t,a,x,y,arg) desc_spill_reg_p(p,t,a,x,y,arg)
981 #define UNW_DEC_SPILL_REG(f,t,a,x,y,arg) desc_spill_reg_p(0,t,a,x,y,arg)
982 #define UNW_DEC_SPILL_PSPREL_P(f,p,t,a,o,arg) desc_spill_psprel_p(p,t,a,o,arg)
983 #define UNW_DEC_SPILL_PSPREL(f,t,a,o,arg) desc_spill_psprel_p(0,t,a,o,arg)
984 #define UNW_DEC_SPILL_SPREL_P(f,p,t,a,o,arg) desc_spill_sprel_p(p,t,a,o,arg)
985 #define UNW_DEC_SPILL_SPREL(f,t,a,o,arg) desc_spill_sprel_p(0,t,a,o,arg)
986 #define UNW_DEC_RESTORE_P(f,p,t,a,arg) desc_restore_p(p,t,a,arg)
987 #define UNW_DEC_RESTORE(f,t,a,arg) desc_restore_p(0,t,a,arg)
991 * Generic IA-64 unwind info decoder.
993 * This file is used both by the Linux kernel and objdump. Please keep
994 * the copies of this file in sync.
996 * You need to customize the decoder by defining the following
997 * macros/constants before including this file:
1000 * unw_word Unsigned integer type with at least 64 bits
1014 * Decoder action macros:
1015 * UNW_DEC_BAD_CODE(code)
1016 * UNW_DEC_ABI(fmt,abi,context,arg)
1017 * UNW_DEC_BR_GR(fmt,brmask,gr,arg)
1018 * UNW_DEC_BR_MEM(fmt,brmask,arg)
1019 * UNW_DEC_COPY_STATE(fmt,label,arg)
1020 * UNW_DEC_EPILOGUE(fmt,t,ecount,arg)
1021 * UNW_DEC_FRGR_MEM(fmt,grmask,frmask,arg)
1022 * UNW_DEC_FR_MEM(fmt,frmask,arg)
1023 * UNW_DEC_GR_GR(fmt,grmask,gr,arg)
1024 * UNW_DEC_GR_MEM(fmt,grmask,arg)
1025 * UNW_DEC_LABEL_STATE(fmt,label,arg)
1026 * UNW_DEC_MEM_STACK_F(fmt,t,size,arg)
1027 * UNW_DEC_MEM_STACK_V(fmt,t,arg)
1028 * UNW_DEC_PRIUNAT_GR(fmt,r,arg)
1029 * UNW_DEC_PRIUNAT_WHEN_GR(fmt,t,arg)
1030 * UNW_DEC_PRIUNAT_WHEN_MEM(fmt,t,arg)
1031 * UNW_DEC_PRIUNAT_WHEN_PSPREL(fmt,pspoff,arg)
1032 * UNW_DEC_PRIUNAT_WHEN_SPREL(fmt,spoff,arg)
1033 * UNW_DEC_PROLOGUE(fmt,body,rlen,arg)
1034 * UNW_DEC_PROLOGUE_GR(fmt,rlen,mask,grsave,arg)
1035 * UNW_DEC_REG_PSPREL(fmt,reg,pspoff,arg)
1036 * UNW_DEC_REG_REG(fmt,src,dst,arg)
1037 * UNW_DEC_REG_SPREL(fmt,reg,spoff,arg)
1038 * UNW_DEC_REG_WHEN(fmt,reg,t,arg)
1039 * UNW_DEC_RESTORE(fmt,t,abreg,arg)
1040 * UNW_DEC_RESTORE_P(fmt,qp,t,abreg,arg)
1041 * UNW_DEC_SPILL_BASE(fmt,pspoff,arg)
1042 * UNW_DEC_SPILL_MASK(fmt,imaskp,arg)
1043 * UNW_DEC_SPILL_PSPREL(fmt,t,abreg,pspoff,arg)
1044 * UNW_DEC_SPILL_PSPREL_P(fmt,qp,t,abreg,pspoff,arg)
1045 * UNW_DEC_SPILL_REG(fmt,t,abreg,x,ytreg,arg)
1046 * UNW_DEC_SPILL_REG_P(fmt,qp,t,abreg,x,ytreg,arg)
1047 * UNW_DEC_SPILL_SPREL(fmt,t,abreg,spoff,arg)
1048 * UNW_DEC_SPILL_SPREL_P(fmt,qp,t,abreg,pspoff,arg)
1052 unw_decode_uleb128 (unsigned char **dpp
)
1055 unw_word byte
, result
= 0;
1056 unsigned char *bp
= *dpp
;
1061 result
|= (byte
& 0x7f) << shift
;
1062 if ((byte
& 0x80) == 0)
1070 static unsigned char *
1071 unw_decode_x1 (unsigned char *dp
,
1072 unsigned char code
__attribute__((unused
)),
1075 unsigned char byte1
, abreg
;
1079 t
= unw_decode_uleb128 (&dp
);
1080 off
= unw_decode_uleb128 (&dp
);
1081 abreg
= (byte1
& 0x7f);
1083 UNW_DEC_SPILL_SPREL(X1
, t
, abreg
, off
, arg
);
1085 UNW_DEC_SPILL_PSPREL(X1
, t
, abreg
, off
, arg
);
1089 static unsigned char *
1090 unw_decode_x2 (unsigned char *dp
,
1091 unsigned char code
__attribute__((unused
)),
1094 unsigned char byte1
, byte2
, abreg
, x
, ytreg
;
1097 byte1
= *dp
++; byte2
= *dp
++;
1098 t
= unw_decode_uleb128 (&dp
);
1099 abreg
= (byte1
& 0x7f);
1101 x
= (byte1
>> 7) & 1;
1102 if ((byte1
& 0x80) == 0 && ytreg
== 0)
1103 UNW_DEC_RESTORE(X2
, t
, abreg
, arg
);
1105 UNW_DEC_SPILL_REG(X2
, t
, abreg
, x
, ytreg
, arg
);
1109 static unsigned char *
1110 unw_decode_x3 (unsigned char *dp
,
1111 unsigned char code
__attribute__((unused
)),
1114 unsigned char byte1
, byte2
, abreg
, qp
;
1117 byte1
= *dp
++; byte2
= *dp
++;
1118 t
= unw_decode_uleb128 (&dp
);
1119 off
= unw_decode_uleb128 (&dp
);
1121 qp
= (byte1
& 0x3f);
1122 abreg
= (byte2
& 0x7f);
1125 UNW_DEC_SPILL_SPREL_P(X3
, qp
, t
, abreg
, off
, arg
);
1127 UNW_DEC_SPILL_PSPREL_P(X3
, qp
, t
, abreg
, off
, arg
);
1131 static unsigned char *
1132 unw_decode_x4 (unsigned char *dp
,
1133 unsigned char code
__attribute__((unused
)),
1136 unsigned char byte1
, byte2
, byte3
, qp
, abreg
, x
, ytreg
;
1139 byte1
= *dp
++; byte2
= *dp
++; byte3
= *dp
++;
1140 t
= unw_decode_uleb128 (&dp
);
1142 qp
= (byte1
& 0x3f);
1143 abreg
= (byte2
& 0x7f);
1144 x
= (byte2
>> 7) & 1;
1147 if ((byte2
& 0x80) == 0 && byte3
== 0)
1148 UNW_DEC_RESTORE_P(X4
, qp
, t
, abreg
, arg
);
1150 UNW_DEC_SPILL_REG_P(X4
, qp
, t
, abreg
, x
, ytreg
, arg
);
1154 static unsigned char *
1155 unw_decode_r1 (unsigned char *dp
, unsigned char code
, void *arg
)
1157 int body
= (code
& 0x20) != 0;
1160 rlen
= (code
& 0x1f);
1161 UNW_DEC_PROLOGUE(R1
, body
, rlen
, arg
);
1165 static unsigned char *
1166 unw_decode_r2 (unsigned char *dp
, unsigned char code
, void *arg
)
1168 unsigned char byte1
, mask
, grsave
;
1173 mask
= ((code
& 0x7) << 1) | ((byte1
>> 7) & 1);
1174 grsave
= (byte1
& 0x7f);
1175 rlen
= unw_decode_uleb128 (&dp
);
1176 UNW_DEC_PROLOGUE_GR(R2
, rlen
, mask
, grsave
, arg
);
1180 static unsigned char *
1181 unw_decode_r3 (unsigned char *dp
, unsigned char code
, void *arg
)
1185 rlen
= unw_decode_uleb128 (&dp
);
1186 UNW_DEC_PROLOGUE(R3
, ((code
& 0x3) == 1), rlen
, arg
);
1190 static unsigned char *
1191 unw_decode_p1 (unsigned char *dp
, unsigned char code
, void *arg
)
1193 unsigned char brmask
= (code
& 0x1f);
1195 UNW_DEC_BR_MEM(P1
, brmask
, arg
);
1199 static unsigned char *
1200 unw_decode_p2_p5 (unsigned char *dp
, unsigned char code
, void *arg
)
1202 if ((code
& 0x10) == 0)
1204 unsigned char byte1
= *dp
++;
1206 UNW_DEC_BR_GR(P2
, ((code
& 0xf) << 1) | ((byte1
>> 7) & 1),
1207 (byte1
& 0x7f), arg
);
1209 else if ((code
& 0x08) == 0)
1211 unsigned char byte1
= *dp
++, r
, dst
;
1213 r
= ((code
& 0x7) << 1) | ((byte1
>> 7) & 1);
1214 dst
= (byte1
& 0x7f);
1217 case 0: UNW_DEC_REG_GR(P3
, UNW_REG_PSP
, dst
, arg
); break;
1218 case 1: UNW_DEC_REG_GR(P3
, UNW_REG_RP
, dst
, arg
); break;
1219 case 2: UNW_DEC_REG_GR(P3
, UNW_REG_PFS
, dst
, arg
); break;
1220 case 3: UNW_DEC_REG_GR(P3
, UNW_REG_PR
, dst
, arg
); break;
1221 case 4: UNW_DEC_REG_GR(P3
, UNW_REG_UNAT
, dst
, arg
); break;
1222 case 5: UNW_DEC_REG_GR(P3
, UNW_REG_LC
, dst
, arg
); break;
1223 case 6: UNW_DEC_RP_BR(P3
, dst
, arg
); break;
1224 case 7: UNW_DEC_REG_GR(P3
, UNW_REG_RNAT
, dst
, arg
); break;
1225 case 8: UNW_DEC_REG_GR(P3
, UNW_REG_BSP
, dst
, arg
); break;
1226 case 9: UNW_DEC_REG_GR(P3
, UNW_REG_BSPSTORE
, dst
, arg
); break;
1227 case 10: UNW_DEC_REG_GR(P3
, UNW_REG_FPSR
, dst
, arg
); break;
1228 case 11: UNW_DEC_PRIUNAT_GR(P3
, dst
, arg
); break;
1229 default: UNW_DEC_BAD_CODE(r
); break;
1232 else if ((code
& 0x7) == 0)
1233 UNW_DEC_SPILL_MASK(P4
, dp
, arg
);
1234 else if ((code
& 0x7) == 1)
1236 unw_word grmask
, frmask
, byte1
, byte2
, byte3
;
1238 byte1
= *dp
++; byte2
= *dp
++; byte3
= *dp
++;
1239 grmask
= ((byte1
>> 4) & 0xf);
1240 frmask
= ((byte1
& 0xf) << 16) | (byte2
<< 8) | byte3
;
1241 UNW_DEC_FRGR_MEM(P5
, grmask
, frmask
, arg
);
1244 UNW_DEC_BAD_CODE(code
);
1248 static unsigned char *
1249 unw_decode_p6 (unsigned char *dp
, unsigned char code
, void *arg
)
1251 int gregs
= (code
& 0x10) != 0;
1252 unsigned char mask
= (code
& 0x0f);
1255 UNW_DEC_GR_MEM(P6
, mask
, arg
);
1257 UNW_DEC_FR_MEM(P6
, mask
, arg
);
1261 static unsigned char *
1262 unw_decode_p7_p10 (unsigned char *dp
, unsigned char code
, void *arg
)
1264 unsigned char r
, byte1
, byte2
;
1267 if ((code
& 0x10) == 0)
1270 t
= unw_decode_uleb128 (&dp
);
1274 size
= unw_decode_uleb128 (&dp
);
1275 UNW_DEC_MEM_STACK_F(P7
, t
, size
, arg
);
1278 case 1: UNW_DEC_MEM_STACK_V(P7
, t
, arg
); break;
1279 case 2: UNW_DEC_SPILL_BASE(P7
, t
, arg
); break;
1280 case 3: UNW_DEC_REG_SPREL(P7
, UNW_REG_PSP
, t
, arg
); break;
1281 case 4: UNW_DEC_REG_WHEN(P7
, UNW_REG_RP
, t
, arg
); break;
1282 case 5: UNW_DEC_REG_PSPREL(P7
, UNW_REG_RP
, t
, arg
); break;
1283 case 6: UNW_DEC_REG_WHEN(P7
, UNW_REG_PFS
, t
, arg
); break;
1284 case 7: UNW_DEC_REG_PSPREL(P7
, UNW_REG_PFS
, t
, arg
); break;
1285 case 8: UNW_DEC_REG_WHEN(P7
, UNW_REG_PR
, t
, arg
); break;
1286 case 9: UNW_DEC_REG_PSPREL(P7
, UNW_REG_PR
, t
, arg
); break;
1287 case 10: UNW_DEC_REG_WHEN(P7
, UNW_REG_LC
, t
, arg
); break;
1288 case 11: UNW_DEC_REG_PSPREL(P7
, UNW_REG_LC
, t
, arg
); break;
1289 case 12: UNW_DEC_REG_WHEN(P7
, UNW_REG_UNAT
, t
, arg
); break;
1290 case 13: UNW_DEC_REG_PSPREL(P7
, UNW_REG_UNAT
, t
, arg
); break;
1291 case 14: UNW_DEC_REG_WHEN(P7
, UNW_REG_FPSR
, t
, arg
); break;
1292 case 15: UNW_DEC_REG_PSPREL(P7
, UNW_REG_FPSR
, t
, arg
); break;
1293 default: UNW_DEC_BAD_CODE(r
); break;
1303 t
= unw_decode_uleb128 (&dp
);
1306 case 1: UNW_DEC_REG_SPREL(P8
, UNW_REG_RP
, t
, arg
); break;
1307 case 2: UNW_DEC_REG_SPREL(P8
, UNW_REG_PFS
, t
, arg
); break;
1308 case 3: UNW_DEC_REG_SPREL(P8
, UNW_REG_PR
, t
, arg
); break;
1309 case 4: UNW_DEC_REG_SPREL(P8
, UNW_REG_LC
, t
, arg
); break;
1310 case 5: UNW_DEC_REG_SPREL(P8
, UNW_REG_UNAT
, t
, arg
); break;
1311 case 6: UNW_DEC_REG_SPREL(P8
, UNW_REG_FPSR
, t
, arg
); break;
1312 case 7: UNW_DEC_REG_WHEN(P8
, UNW_REG_BSP
, t
, arg
); break;
1313 case 8: UNW_DEC_REG_PSPREL(P8
, UNW_REG_BSP
, t
, arg
); break;
1314 case 9: UNW_DEC_REG_SPREL(P8
, UNW_REG_BSP
, t
, arg
); break;
1315 case 10: UNW_DEC_REG_WHEN(P8
, UNW_REG_BSPSTORE
, t
, arg
); break;
1316 case 11: UNW_DEC_REG_PSPREL(P8
, UNW_REG_BSPSTORE
, t
, arg
); break;
1317 case 12: UNW_DEC_REG_SPREL(P8
, UNW_REG_BSPSTORE
, t
, arg
); break;
1318 case 13: UNW_DEC_REG_WHEN(P8
, UNW_REG_RNAT
, t
, arg
); break;
1319 case 14: UNW_DEC_REG_PSPREL(P8
, UNW_REG_RNAT
, t
, arg
); break;
1320 case 15: UNW_DEC_REG_SPREL(P8
, UNW_REG_RNAT
, t
, arg
); break;
1321 case 16: UNW_DEC_PRIUNAT_WHEN_GR(P8
, t
, arg
); break;
1322 case 17: UNW_DEC_PRIUNAT_PSPREL(P8
, t
, arg
); break;
1323 case 18: UNW_DEC_PRIUNAT_SPREL(P8
, t
, arg
); break;
1324 case 19: UNW_DEC_PRIUNAT_WHEN_MEM(P8
, t
, arg
); break;
1325 default: UNW_DEC_BAD_CODE(r
); break;
1331 byte1
= *dp
++; byte2
= *dp
++;
1332 UNW_DEC_GR_GR(P9
, (byte1
& 0xf), (byte2
& 0x7f), arg
);
1336 byte1
= *dp
++; byte2
= *dp
++;
1337 UNW_DEC_ABI(P10
, byte1
, byte2
, arg
);
1341 return unw_decode_x1 (dp
, code
, arg
);
1344 return unw_decode_x2 (dp
, code
, arg
);
1347 return unw_decode_x3 (dp
, code
, arg
);
1350 return unw_decode_x4 (dp
, code
, arg
);
1353 UNW_DEC_BAD_CODE(code
);
1360 static unsigned char *
1361 unw_decode_b1 (unsigned char *dp
, unsigned char code
, void *arg
)
1363 unw_word label
= (code
& 0x1f);
1365 if ((code
& 0x20) != 0)
1366 UNW_DEC_COPY_STATE(B1
, label
, arg
);
1368 UNW_DEC_LABEL_STATE(B1
, label
, arg
);
1372 static unsigned char *
1373 unw_decode_b2 (unsigned char *dp
, unsigned char code
, void *arg
)
1377 t
= unw_decode_uleb128 (&dp
);
1378 UNW_DEC_EPILOGUE(B2
, t
, (code
& 0x1f), arg
);
1382 static unsigned char *
1383 unw_decode_b3_x4 (unsigned char *dp
, unsigned char code
, void *arg
)
1385 unw_word t
, ecount
, label
;
1387 if ((code
& 0x10) == 0)
1389 t
= unw_decode_uleb128 (&dp
);
1390 ecount
= unw_decode_uleb128 (&dp
);
1391 UNW_DEC_EPILOGUE(B3
, t
, ecount
, arg
);
1393 else if ((code
& 0x07) == 0)
1395 label
= unw_decode_uleb128 (&dp
);
1396 if ((code
& 0x08) != 0)
1397 UNW_DEC_COPY_STATE(B4
, label
, arg
);
1399 UNW_DEC_LABEL_STATE(B4
, label
, arg
);
1404 case 1: return unw_decode_x1 (dp
, code
, arg
);
1405 case 2: return unw_decode_x2 (dp
, code
, arg
);
1406 case 3: return unw_decode_x3 (dp
, code
, arg
);
1407 case 4: return unw_decode_x4 (dp
, code
, arg
);
1408 default: UNW_DEC_BAD_CODE(code
); break;
1413 typedef unsigned char *(*unw_decoder
) (unsigned char *, unsigned char, void *);
1415 static const unw_decoder unw_decode_table
[2][8] =
1417 /* prologue table: */
1419 unw_decode_r1
, /* 0 */
1423 unw_decode_p1
, /* 4 */
1429 unw_decode_r1
, /* 0 */
1433 unw_decode_b1
, /* 4 */
1441 * Decode one descriptor and return address of next descriptor.
1443 static inline unsigned char *
1444 unw_decode (unsigned char *dp
, int inside_body
, void *arg
)
1446 unw_decoder decoder
;
1450 decoder
= unw_decode_table
[inside_body
][code
>> 5];
1451 dp
= (*decoder
) (dp
, code
, arg
);
1456 /* RSE helper functions. */
1458 static inline unsigned long
1459 ia64_rse_slot_num (unsigned long *addr
)
1461 return (((unsigned long) addr
) >> 3) & 0x3f;
1464 /* Return TRUE if ADDR is the address of an RNAT slot. */
1465 static inline unsigned long
1466 ia64_rse_is_rnat_slot (unsigned long *addr
)
1468 return ia64_rse_slot_num (addr
) == 0x3f;
1471 /* Returns the address of the RNAT slot that covers the slot at
1472 address SLOT_ADDR. */
1473 static inline unsigned long *
1474 ia64_rse_rnat_addr (unsigned long *slot_addr
)
1476 return (unsigned long *) ((unsigned long) slot_addr
| (0x3f << 3));
1479 /* Calculate the number of registers in the dirty partition starting at
1480 BSPSTORE with a size of DIRTY bytes. This isn't simply DIRTY
1481 divided by eight because the 64th slot is used to store ar.rnat. */
1482 static inline unsigned long
1483 ia64_rse_num_regs (unsigned long *bspstore
, unsigned long *bsp
)
1485 unsigned long slots
= (bsp
- bspstore
);
1487 return slots
- (ia64_rse_slot_num (bspstore
) + slots
)/0x40;
1490 /* The inverse of the above: given bspstore and the number of
1491 registers, calculate ar.bsp. */
1492 static inline unsigned long *
1493 ia64_rse_skip_regs (unsigned long *addr
, long num_regs
)
1495 long delta
= ia64_rse_slot_num (addr
) + num_regs
;
1499 return addr
+ num_regs
+ delta
/0x3f;
1503 /* Copy register backing store from SRC to DST, LEN words
1504 (which include both saved registers and nat collections).
1505 DST_RNAT is a partial nat collection for DST. SRC and DST
1506 don't have to be equal modulo 64 slots, so it cannot be
1507 done with a simple memcpy as the nat collections will be
1508 at different relative offsets and need to be combined together. */
1510 ia64_copy_rbs (struct _Unwind_Context
*info
, unsigned long dst
,
1511 unsigned long src
, long len
, unsigned long dst_rnat
)
1514 unsigned long src_rnat
;
1515 unsigned long shift1
, shift2
;
1518 dst_rnat
&= (1UL << ((dst
>> 3) & 0x3f)) - 1;
1519 src_rnat
= src
>= info
->regstk_top
1520 ? info
->rnat
: *(unsigned long *) (src
| 0x1f8);
1521 src_rnat
&= ~((1UL << ((src
>> 3) & 0x3f)) - 1);
1522 /* Just to make sure. */
1523 src_rnat
&= ~(1UL << 63);
1524 shift1
= ((dst
- src
) >> 3) & 0x3f;
1525 if ((dst
& 0x1f8) < (src
& 0x1f8))
1527 shift2
= 0x3f - shift1
;
1528 if ((dst
& 0x1f8) >= (src
& 0x1f8))
1530 count
= ~dst
& 0x1f8;
1533 count
= ~src
& 0x1f8;
1537 src_rnat
= src
>= info
->regstk_top
1538 ? info
->rnat
: *(unsigned long *) (src
| 0x1f8);
1539 /* Just to make sure. */
1540 src_rnat
&= ~(1UL << 63);
1541 count
= shift2
<< 3;
1545 memcpy ((char *) dst
, (char *) src
, count
);
1549 dst_rnat
|= (src_rnat
<< shift1
) & ~(1UL << 63);
1552 *(long *) dst
= dst_rnat
;
1555 count
= shift1
<< 3;
1559 memcpy ((char *) dst
, (char *) src
, count
);
1563 dst_rnat
|= (src_rnat
>> shift2
);
1565 if ((dst
& 0x1f8) == 0x1f8)
1567 *(long *) dst
= dst_rnat
;
1571 /* Set info->regstk_top to lowest rbs address which will use
1572 info->rnat collection. */
1573 info
->regstk_top
= dst
& ~0x1ffUL
;
1574 info
->rnat
= dst_rnat
;
1577 /* Unwind accessors. */
1580 unw_access_gr (struct _Unwind_Context
*info
, int regnum
,
1581 unsigned long *val
, char *nat
, int write
)
1583 unsigned long *addr
, *nat_addr
= 0, nat_mask
= 0, dummy_nat
;
1584 struct unw_ireg
*ireg
;
1586 if ((unsigned) regnum
- 1 >= 127)
1591 nat_addr
= addr
= &dummy_nat
;
1594 else if (regnum
< 32)
1596 /* Access a non-stacked register. */
1597 ireg
= &info
->ireg
[regnum
- 2];
1601 nat_addr
= addr
+ ireg
->nat
.off
;
1602 switch (ireg
->nat
.type
)
1605 /* Simulate getf.sig/setf.sig. */
1610 /* Write NaTVal and be done with it. */
1617 else if (addr
[0] == 0 && addr
[1] == 0x1ffe)
1619 /* Return NaT and be done with it. */
1628 nat_addr
= &dummy_nat
;
1631 case UNW_NAT_MEMSTK
:
1632 nat_mask
= 1UL << ((long) addr
& 0x1f8)/8;
1635 case UNW_NAT_REGSTK
:
1636 if ((unsigned long) addr
>= info
->regstk_top
)
1637 nat_addr
= &info
->rnat
;
1639 nat_addr
= ia64_rse_rnat_addr (addr
);
1640 nat_mask
= 1UL << ia64_rse_slot_num (addr
);
1647 /* Access a stacked register. */
1648 addr
= ia64_rse_skip_regs ((unsigned long *) info
->bsp
, regnum
- 32);
1649 if ((unsigned long) addr
>= info
->regstk_top
)
1650 nat_addr
= &info
->rnat
;
1652 nat_addr
= ia64_rse_rnat_addr (addr
);
1653 nat_mask
= 1UL << ia64_rse_slot_num (addr
);
1660 *nat_addr
|= nat_mask
;
1662 *nat_addr
&= ~nat_mask
;
1667 *nat
= (*nat_addr
& nat_mask
) != 0;
1671 /* Get the value of register REG as saved in CONTEXT. */
1674 _Unwind_GetGR (struct _Unwind_Context
*context
, int index
)
1681 else if (index
>= 15 && index
<= 18)
1682 return context
->eh_data
[index
- 15];
1684 unw_access_gr (context
, index
, &ret
, &nat
, 0);
1689 /* Overwrite the saved value for register REG in CONTEXT with VAL. */
1692 _Unwind_SetGR (struct _Unwind_Context
*context
, int index
, _Unwind_Word val
)
1698 else if (index
>= 15 && index
<= 18)
1699 context
->eh_data
[index
- 15] = val
;
1701 unw_access_gr (context
, index
, &val
, &nat
, 1);
1704 /* Retrieve the return address for CONTEXT. */
1707 _Unwind_GetIP (struct _Unwind_Context
*context
)
1713 _Unwind_GetIPInfo (struct _Unwind_Context
*context
, int *ip_before_insn
)
1715 *ip_before_insn
= 0;
1719 /* Overwrite the return address for CONTEXT with VAL. */
1722 _Unwind_SetIP (struct _Unwind_Context
*context
, _Unwind_Ptr val
)
1728 _Unwind_GetLanguageSpecificData (struct _Unwind_Context
*context
)
1730 return context
->lsda
;
1734 _Unwind_GetRegionStart (struct _Unwind_Context
*context
)
1736 return context
->region_start
;
1740 _Unwind_FindEnclosingFunction (void *pc
)
1742 struct unw_table_entry
*entp
, ent
;
1743 unsigned long segment_base
, gp
;
1745 entp
= _Unwind_FindTableEntry (pc
, &segment_base
, &gp
, &ent
);
1749 return (void *)(segment_base
+ entp
->start_offset
);
1752 /* Get the value of the CFA as saved in CONTEXT. In GCC/Dwarf2 parlance,
1753 the CFA is the value of the stack pointer on entry; In IA-64 unwind
1754 parlance, this is the PSP. */
1757 _Unwind_GetCFA (struct _Unwind_Context
*context
)
1759 return (_Unwind_Ptr
) context
->psp
;
1762 /* Get the value of the Backing Store Pointer as saved in CONTEXT. */
1765 _Unwind_GetBSP (struct _Unwind_Context
*context
)
1767 return (_Unwind_Ptr
) context
->bsp
;
1770 #include "md-unwind-support.h"
1772 static _Unwind_Reason_Code
1773 uw_frame_state_for (struct _Unwind_Context
*context
, _Unwind_FrameState
*fs
)
1775 struct unw_table_entry
*entp
, ent
;
1776 unsigned long *unw
, header
, length
;
1777 unsigned char *insn
, *insn_end
;
1778 unsigned long segment_base
;
1779 struct unw_reg_info
*r
;
1781 memset (fs
, 0, sizeof (*fs
));
1782 for (r
= fs
->curr
.reg
; r
< fs
->curr
.reg
+ UNW_NUM_REGS
; ++r
)
1783 r
->when
= UNW_WHEN_NEVER
;
1786 entp
= _Unwind_FindTableEntry ((void *) context
->rp
,
1787 &segment_base
, &context
->gp
, &ent
);
1790 /* Couldn't find unwind info for this function. Try an
1791 os-specific fallback mechanism. This will necessarily
1792 not provide a personality routine or LSDA. */
1793 #ifdef MD_FALLBACK_FRAME_STATE_FOR
1794 if (MD_FALLBACK_FRAME_STATE_FOR (context
, fs
) == _URC_NO_REASON
)
1795 return _URC_NO_REASON
;
1798 /* [SCRA 11.4.1] A leaf function with no memory stack, no exception
1799 handlers, and which keeps the return value in B0 does not need
1800 an unwind table entry.
1802 This can only happen in the frame after unwinding through a signal
1803 handler. Avoid infinite looping by requiring that B0 != RP.
1804 RP == 0 terminates the chain. */
1805 if (context
->br_loc
[0]
1806 && *context
->br_loc
[0] != context
->rp
1807 && context
->rp
!= 0)
1808 goto skip_unwind_info
;
1810 return _URC_END_OF_STACK
;
1813 context
->region_start
= entp
->start_offset
+ segment_base
;
1814 fs
->when_target
= ((context
->rp
& -16) - context
->region_start
) / 16 * 3
1815 + (context
->rp
& 15);
1817 unw
= (unsigned long *) (entp
->info_offset
+ segment_base
);
1819 length
= UNW_LENGTH (header
);
1821 /* Some operating systems use the personality routine slot in way not
1822 compatible with what we expect. For instance, OpenVMS uses this slot to
1823 designate "condition handlers" with very different arguments than what we
1824 would be providing. Such cases are typically identified from OS specific
1825 bits in the unwind information block header, and checked by the target
1826 MD_UNW_COMPATIBLE_PERSONALITY_P macro.
1828 We just pretend there is no personality from our standpoint in such
1829 situations, and expect GCC not to set the identifying bits itself so that
1830 compatible personalities for GCC compiled code are called.
1832 Of course, this raises the question of what combinations of native/GCC
1833 calls can be expected to behave properly exception handling-wise. We are
1834 not to provide a magic answer here, merely to prevent crashes assuming
1835 users know what they are doing.
1837 ??? Perhaps check UNW_VER / UNW_FLAG_OSMASK as well. */
1839 if (MD_UNW_COMPATIBLE_PERSONALITY_P (header
)
1840 && (UNW_FLAG_EHANDLER (header
) | UNW_FLAG_UHANDLER (header
)))
1843 *(_Unwind_Personality_Fn
*) (unw
[length
+ 1] + context
->gp
);
1844 context
->lsda
= unw
+ length
+ 2;
1847 insn
= (unsigned char *) (unw
+ 1);
1848 insn_end
= (unsigned char *) (unw
+ 1 + length
);
1849 while (!fs
->done
&& insn
< insn_end
)
1850 insn
= unw_decode (insn
, fs
->in_body
, fs
);
1852 free_label_states (fs
->labeled_states
);
1853 free_state_stack (&fs
->curr
);
1855 #ifdef ENABLE_MALLOC_CHECKING
1856 if (reg_state_alloced
|| labeled_state_alloced
)
1860 /* If we're in the epilogue, sp has been restored and all values
1861 on the memory stack below psp also have been restored. */
1862 if (fs
->when_target
> fs
->epilogue_start
)
1864 struct unw_reg_info
*r
;
1866 fs
->curr
.reg
[UNW_REG_PSP
].where
= UNW_WHERE_NONE
;
1867 fs
->curr
.reg
[UNW_REG_PSP
].val
= 0;
1868 for (r
= fs
->curr
.reg
; r
< fs
->curr
.reg
+ UNW_NUM_REGS
; ++r
)
1869 if ((r
->where
== UNW_WHERE_PSPREL
&& r
->val
<= 0x10)
1870 || r
->where
== UNW_WHERE_SPREL
)
1871 r
->where
= UNW_WHERE_NONE
;
1875 /* If RP didn't get saved, generate entry for the return link register. */
1876 if (fs
->curr
.reg
[UNW_REG_RP
].when
>= fs
->when_target
)
1878 fs
->curr
.reg
[UNW_REG_RP
].where
= UNW_WHERE_BR
;
1879 fs
->curr
.reg
[UNW_REG_RP
].when
= -1;
1880 fs
->curr
.reg
[UNW_REG_RP
].val
= fs
->return_link_reg
;
1883 /* There is a subtlety for the frame after unwinding through a signal
1884 handler: should we restore the cfm as usual or the pfs? We can't
1885 restore both because we use br.ret to resume execution of user code.
1886 For other frames the procedure is by definition non-leaf so the pfs
1887 is saved and restored and thus effectively dead in the body; only
1888 the cfm need therefore be restored.
1890 Here we have 2 cases:
1891 - either the pfs is saved and restored and thus effectively dead
1892 like in regular frames; then we do nothing special and restore
1894 - or the pfs is not saved and thus live; but in that case the
1895 procedure is necessarily leaf so the cfm is effectively dead
1896 and we restore the pfs. */
1897 if (context
->signal_pfs_loc
)
1899 if (fs
->curr
.reg
[UNW_REG_PFS
].when
>= fs
->when_target
)
1900 context
->pfs_loc
= context
->signal_pfs_loc
;
1901 context
->signal_pfs_loc
= NULL
;
1904 return _URC_NO_REASON
;
1908 uw_update_reg_address (struct _Unwind_Context
*context
,
1909 _Unwind_FrameState
*fs
,
1910 enum unw_register_index regno
)
1912 struct unw_reg_info
*r
= fs
->curr
.reg
+ regno
;
1916 if (r
->where
== UNW_WHERE_NONE
|| r
->when
>= fs
->when_target
)
1924 addr
= ia64_rse_skip_regs ((unsigned long *) context
->bsp
, rval
- 32);
1926 addr
= context
->ireg
[rval
- 2].loc
;
1929 static const unsigned long dummy
;
1930 addr
= (void *) &dummy
;
1937 if (rval
>= 2 && rval
< 32)
1938 addr
= context
->fr_loc
[rval
- 2];
1944 /* Note that while RVAL can only be 1-5 from normal descriptors,
1945 we can want to look at B0, B6 and B7 due to having manually unwound a
1948 addr
= context
->br_loc
[rval
];
1953 case UNW_WHERE_SPREL
:
1954 addr
= (void *)(context
->sp
+ rval
);
1957 case UNW_WHERE_PSPREL
:
1958 addr
= (void *)(context
->psp
+ rval
);
1967 case UNW_REG_R2
... UNW_REG_R31
:
1968 context
->ireg
[regno
- UNW_REG_R2
].loc
= addr
;
1974 context
->ireg
[regno
- UNW_REG_R2
].nat
.type
= UNW_NAT_MEMSTK
;
1975 context
->ireg
[regno
- UNW_REG_R2
].nat
.off
1976 = context
->pri_unat_loc
- (unsigned long *) addr
;
1980 context
->ireg
[regno
- UNW_REG_R2
].nat
1981 = context
->ireg
[rval
- 2].nat
;
1985 context
->ireg
[regno
- UNW_REG_R2
].nat
.type
= UNW_NAT_NONE
;
1986 context
->ireg
[regno
- UNW_REG_R2
].nat
.off
= 0;
1993 context
->ireg
[regno
- UNW_REG_R2
].nat
.type
= UNW_NAT_VAL
;
1994 context
->ireg
[regno
- UNW_REG_R2
].nat
.off
= 0;
1998 context
->ireg
[regno
- UNW_REG_R2
].nat
.type
= UNW_NAT_NONE
;
1999 context
->ireg
[regno
- UNW_REG_R2
].nat
.off
= 0;
2002 case UNW_WHERE_PSPREL
:
2003 case UNW_WHERE_SPREL
:
2004 context
->ireg
[regno
- UNW_REG_R2
].nat
.type
= UNW_NAT_MEMSTK
;
2005 context
->ireg
[regno
- UNW_REG_R2
].nat
.off
2006 = context
->pri_unat_loc
- (unsigned long *) addr
;
2014 case UNW_REG_F2
... UNW_REG_F31
:
2015 context
->fr_loc
[regno
- UNW_REG_F2
] = addr
;
2018 case UNW_REG_B1
... UNW_REG_B5
:
2019 context
->br_loc
[regno
- UNW_REG_B0
] = addr
;
2023 context
->bsp_loc
= addr
;
2025 case UNW_REG_BSPSTORE
:
2026 context
->bspstore_loc
= addr
;
2029 context
->pfs_loc
= addr
;
2032 context
->rp
= *(unsigned long *)addr
;
2035 context
->unat_loc
= addr
;
2038 context
->pr
= *(unsigned long *) addr
;
2041 context
->lc_loc
= addr
;
2044 context
->fpsr_loc
= addr
;
2048 context
->psp
= *(unsigned long *)addr
;
2057 uw_update_context (struct _Unwind_Context
*context
, _Unwind_FrameState
*fs
)
2061 #ifdef MD_HANDLE_UNWABI
2062 MD_HANDLE_UNWABI (context
, fs
);
2065 context
->sp
= context
->psp
;
2067 /* First, set PSP. Subsequent instructions may depend on this value. */
2068 if (fs
->when_target
> fs
->curr
.reg
[UNW_REG_PSP
].when
)
2070 if (fs
->curr
.reg
[UNW_REG_PSP
].where
== UNW_WHERE_NONE
)
2071 context
->psp
= context
->psp
+ fs
->curr
.reg
[UNW_REG_PSP
].val
;
2073 uw_update_reg_address (context
, fs
, UNW_REG_PSP
);
2076 /* Determine the location of the primary UNaT. */
2079 if (fs
->when_target
< fs
->curr
.reg
[UNW_REG_PRI_UNAT_GR
].when
)
2080 i
= UNW_REG_PRI_UNAT_MEM
;
2081 else if (fs
->when_target
< fs
->curr
.reg
[UNW_REG_PRI_UNAT_MEM
].when
)
2082 i
= UNW_REG_PRI_UNAT_GR
;
2083 else if (fs
->curr
.reg
[UNW_REG_PRI_UNAT_MEM
].when
2084 > fs
->curr
.reg
[UNW_REG_PRI_UNAT_GR
].when
)
2085 i
= UNW_REG_PRI_UNAT_MEM
;
2087 i
= UNW_REG_PRI_UNAT_GR
;
2088 uw_update_reg_address (context
, fs
, i
);
2091 /* Compute the addresses of all registers saved in this frame. */
2092 for (i
= UNW_REG_BSP
; i
< UNW_NUM_REGS
; ++i
)
2093 uw_update_reg_address (context
, fs
, i
);
2095 /* Unwind BSP for the local registers allocated this frame. */
2096 /* ??? What to do with stored BSP or BSPSTORE registers. */
2097 /* We assert that we are either at a call site, or we have
2098 just unwound through a signal frame. In either case
2099 pfs_loc is valid. */
2100 if (!(fs
-> no_reg_stack_frame
))
2102 unsigned long pfs
= *context
->pfs_loc
;
2103 unsigned long sol
= (pfs
>> 7) & 0x7f;
2104 context
->bsp
= (unsigned long)
2105 ia64_rse_skip_regs ((unsigned long *) context
->bsp
, -sol
);
2110 uw_advance_context (struct _Unwind_Context
*context
, _Unwind_FrameState
*fs
)
2112 uw_update_context (context
, fs
);
2115 /* Fill in CONTEXT for top-of-stack. The only valid registers at this
2116 level will be the return address and the CFA. Note that CFA = SP+16. */
2118 #define uw_init_context(CONTEXT) \
2120 /* ??? There is a whole lot o code in uw_install_context that \
2121 tries to avoid spilling the entire machine state here. We \
2122 should try to make that work again. */ \
2123 __builtin_unwind_init(); \
2124 uw_init_context_1 (CONTEXT, __builtin_ia64_bsp ()); \
2127 static void __attribute__((noinline
))
2128 uw_init_context_1 (struct _Unwind_Context
*context
, void *bsp
)
2130 void *rp
= __builtin_extract_return_addr (__builtin_return_address (0));
2131 /* Set psp to the caller's stack pointer. */
2132 void *psp
= __builtin_dwarf_cfa () - 16;
2133 _Unwind_FrameState fs
;
2134 unsigned long rnat
, tmp1
, tmp2
;
2136 /* Flush the register stack to memory so that we can access it.
2137 Get rse nat collection for the last incomplete rbs chunk of
2138 registers at the same time. For this RSE needs to be turned
2139 into the mandatory only mode. */
2140 asm ("mov.m %1 = ar.rsc;;\n\t"
2141 "and %2 = 0x1c, %1;;\n\t"
2142 "mov.m ar.rsc = %2;;\n\t"
2144 "mov.m %0 = ar.rnat;;\n\t"
2145 "mov.m ar.rsc = %1\n\t"
2146 : "=r" (rnat
), "=r" (tmp1
), "=r" (tmp2
));
2148 memset (context
, 0, sizeof (struct _Unwind_Context
));
2149 context
->bsp
= (unsigned long) bsp
;
2150 /* Set context->regstk_top to lowest rbs address which will use
2151 context->rnat collection. */
2152 context
->regstk_top
= context
->bsp
& ~0x1ffULL
;
2153 context
->rnat
= rnat
;
2154 context
->psp
= (unsigned long) psp
;
2155 context
->rp
= (unsigned long) rp
;
2156 asm ("mov %0 = sp" : "=r" (context
->sp
));
2157 asm ("mov %0 = pr" : "=r" (context
->pr
));
2158 context
->pri_unat_loc
= &context
->initial_unat
; /* ??? */
2160 if (uw_frame_state_for (context
, &fs
) != _URC_NO_REASON
)
2163 uw_update_context (context
, &fs
);
2166 /* Install (i.e. longjmp to) the contents of TARGET. */
2168 static void __attribute__((noreturn
))
2169 uw_install_context (struct _Unwind_Context
*current
__attribute__((unused
)),
2170 struct _Unwind_Context
*target
)
2172 unsigned long ireg_buf
[4], ireg_nat
= 0, ireg_pr
= 0;
2175 /* Copy integer register data from the target context to a
2176 temporary buffer. Do this so that we can frob AR.UNAT
2177 to get the NaT bits for these registers set properly. */
2178 for (i
= 4; i
<= 7; ++i
)
2181 void *t
= target
->ireg
[i
- 2].loc
;
2184 unw_access_gr (target
, i
, &ireg_buf
[i
- 4], &nat
, 0);
2185 ireg_nat
|= (long)nat
<< (((size_t)&ireg_buf
[i
- 4] >> 3) & 0x3f);
2191 /* The value in uc_bsp that we've computed is that for the
2192 target function. The value that we install below will be
2193 adjusted by the BR.RET instruction based on the contents
2194 of AR.PFS. So we must unadjust that here. */
2195 target
->bsp
= (unsigned long)
2196 ia64_rse_skip_regs ((unsigned long *)target
->bsp
,
2197 (*target
->pfs_loc
>> 7) & 0x7f);
2199 if (target
->bsp
< target
->regstk_top
)
2200 target
->rnat
= *ia64_rse_rnat_addr ((unsigned long *) target
->bsp
);
2202 /* Provide assembly with the offsets into the _Unwind_Context. */
2203 asm volatile ("uc_rnat = %0"
2204 : : "i"(offsetof (struct _Unwind_Context
, rnat
)));
2205 asm volatile ("uc_bsp = %0"
2206 : : "i"(offsetof (struct _Unwind_Context
, bsp
)));
2207 asm volatile ("uc_psp = %0"
2208 : : "i"(offsetof (struct _Unwind_Context
, psp
)));
2209 asm volatile ("uc_rp = %0"
2210 : : "i"(offsetof (struct _Unwind_Context
, rp
)));
2211 asm volatile ("uc_pr = %0"
2212 : : "i"(offsetof (struct _Unwind_Context
, pr
)));
2213 asm volatile ("uc_gp = %0"
2214 : : "i"(offsetof (struct _Unwind_Context
, gp
)));
2215 asm volatile ("uc_pfs_loc = %0"
2216 : : "i"(offsetof (struct _Unwind_Context
, pfs_loc
)));
2217 asm volatile ("uc_unat_loc = %0"
2218 : : "i"(offsetof (struct _Unwind_Context
, unat_loc
)));
2219 asm volatile ("uc_lc_loc = %0"
2220 : : "i"(offsetof (struct _Unwind_Context
, lc_loc
)));
2221 asm volatile ("uc_fpsr_loc = %0"
2222 : : "i"(offsetof (struct _Unwind_Context
, fpsr_loc
)));
2223 asm volatile ("uc_eh_data = %0"
2224 : : "i"(offsetof (struct _Unwind_Context
, eh_data
)));
2225 asm volatile ("uc_br_loc = %0"
2226 : : "i"(offsetof (struct _Unwind_Context
, br_loc
)));
2227 asm volatile ("uc_fr_loc = %0"
2228 : : "i"(offsetof (struct _Unwind_Context
, fr_loc
)));
2231 /* Load up call-saved non-window integer registers from ireg_buf. */
2232 "add r20 = 8, %1 \n\t"
2233 "mov ar.unat = %2 \n\t"
2234 "mov pr = %3, 0x3c0 \n\t"
2236 "(p6) ld8.fill r4 = [%1] \n\t"
2237 "(p7) ld8.fill r5 = [r20] \n\t"
2238 "add r21 = uc_br_loc + 16, %0 \n\t"
2239 "adds %1 = 16, %1 \n\t"
2240 "adds r20 = 16, r20 \n\t"
2242 "(p8) ld8.fill r6 = [%1] \n\t"
2243 "(p9) ld8.fill r7 = [r20] \n\t"
2244 "add r20 = uc_br_loc + 8, %0 \n\t"
2246 /* Load up call-saved branch registers. */
2247 "ld8 r22 = [r20], 16 \n\t"
2248 "ld8 r23 = [r21], 16 \n\t"
2250 "ld8 r24 = [r20], 16 \n\t"
2251 "ld8 r25 = [r21], uc_fr_loc - (uc_br_loc + 32)\n\t"
2253 "ld8 r26 = [r20], uc_fr_loc + 8 - (uc_br_loc + 40)\n\t"
2254 "ld8 r27 = [r21], 24 \n\t"
2255 "cmp.ne p6, p0 = r0, r22 \n\t"
2257 "ld8 r28 = [r20], 8 \n\t"
2258 "(p6) ld8 r22 = [r22] \n\t"
2259 "cmp.ne p7, p0 = r0, r23 \n\t"
2261 "(p7) ld8 r23 = [r23] \n\t"
2262 "cmp.ne p8, p0 = r0, r24 \n\t"
2264 "(p8) ld8 r24 = [r24] \n\t"
2265 "(p6) mov b1 = r22 \n\t"
2266 "cmp.ne p9, p0 = r0, r25 \n\t"
2268 "(p9) ld8 r25 = [r25] \n\t"
2269 "(p7) mov b2 = r23 \n\t"
2270 "cmp.ne p6, p0 = r0, r26 \n\t"
2272 "(p6) ld8 r26 = [r26] \n\t"
2273 "(p8) mov b3 = r24 \n\t"
2274 "cmp.ne p7, p0 = r0, r27 \n\t"
2276 /* Load up call-saved fp registers. */
2277 "(p7) ldf.fill f2 = [r27] \n\t"
2278 "(p9) mov b4 = r25 \n\t"
2279 "cmp.ne p8, p0 = r0, r28 \n\t"
2281 "(p8) ldf.fill f3 = [r28] \n\t"
2282 "(p6) mov b5 = r26 \n\t"
2284 "ld8 r29 = [r20], 16*8 - 4*8 \n\t"
2285 "ld8 r30 = [r21], 17*8 - 5*8 \n\t"
2287 "ld8 r22 = [r20], 16 \n\t"
2288 "ld8 r23 = [r21], 16 \n\t"
2290 "ld8 r24 = [r20], 16 \n\t"
2291 "ld8 r25 = [r21] \n\t"
2292 "cmp.ne p6, p0 = r0, r29 \n\t"
2294 "ld8 r26 = [r20], 8 \n\t"
2295 "(p6) ldf.fill f4 = [r29] \n\t"
2296 "cmp.ne p7, p0 = r0, r30 \n\t"
2298 "ld8 r27 = [r20], 8 \n\t"
2299 "(p7) ldf.fill f5 = [r30] \n\t"
2300 "cmp.ne p6, p0 = r0, r22 \n\t"
2302 "ld8 r28 = [r20], 8 \n\t"
2303 "(p6) ldf.fill f16 = [r22] \n\t"
2304 "cmp.ne p7, p0 = r0, r23 \n\t"
2306 "ld8 r29 = [r20], 8 \n\t"
2307 "(p7) ldf.fill f17 = [r23] \n\t"
2308 "cmp.ne p6, p0 = r0, r24 \n\t"
2310 "ld8 r22 = [r20], 8 \n\t"
2311 "(p6) ldf.fill f18 = [r24] \n\t"
2312 "cmp.ne p7, p0 = r0, r25 \n\t"
2314 "ld8 r23 = [r20], 8 \n\t"
2315 "(p7) ldf.fill f19 = [r25] \n\t"
2316 "cmp.ne p6, p0 = r0, r26 \n\t"
2318 "ld8 r24 = [r20], 8 \n\t"
2319 "(p6) ldf.fill f20 = [r26] \n\t"
2320 "cmp.ne p7, p0 = r0, r27 \n\t"
2322 "ld8 r25 = [r20], 8 \n\t"
2323 "(p7) ldf.fill f21 = [r27] \n\t"
2324 "cmp.ne p6, p0 = r0, r28 \n\t"
2326 "ld8 r26 = [r20], 8 \n\t"
2327 "(p6) ldf.fill f22 = [r28] \n\t"
2328 "cmp.ne p7, p0 = r0, r29 \n\t"
2330 "ld8 r27 = [r20], 8 \n\t"
2332 "ld8 r28 = [r20], 8 \n\t"
2333 "(p7) ldf.fill f23 = [r29] \n\t"
2334 "cmp.ne p6, p0 = r0, r22 \n\t"
2336 "ld8 r29 = [r20], 8 \n\t"
2337 "(p6) ldf.fill f24 = [r22] \n\t"
2338 "cmp.ne p7, p0 = r0, r23 \n\t"
2340 "(p7) ldf.fill f25 = [r23] \n\t"
2341 "cmp.ne p6, p0 = r0, r24 \n\t"
2342 "cmp.ne p7, p0 = r0, r25 \n\t"
2344 "(p6) ldf.fill f26 = [r24] \n\t"
2345 "(p7) ldf.fill f27 = [r25] \n\t"
2346 "cmp.ne p6, p0 = r0, r26 \n\t"
2348 "(p6) ldf.fill f28 = [r26] \n\t"
2349 "cmp.ne p7, p0 = r0, r27 \n\t"
2350 "cmp.ne p6, p0 = r0, r28 \n\t"
2352 "(p7) ldf.fill f29 = [r27] \n\t"
2353 "(p6) ldf.fill f30 = [r28] \n\t"
2354 "cmp.ne p7, p0 = r0, r29 \n\t"
2356 "(p7) ldf.fill f31 = [r29] \n\t"
2357 "add r20 = uc_rnat, %0 \n\t"
2358 "add r21 = uc_bsp, %0 \n\t"
2360 /* Load the balance of the thread state from the context. */
2361 "ld8 r22 = [r20], uc_psp - uc_rnat \n\t"
2362 "ld8 r23 = [r21], uc_gp - uc_bsp \n\t"
2364 "ld8 r24 = [r20], uc_pfs_loc - uc_psp \n\t"
2365 "ld8 r1 = [r21], uc_rp - uc_gp \n\t"
2367 "ld8 r25 = [r20], uc_unat_loc - uc_pfs_loc\n\t"
2368 "ld8 r26 = [r21], uc_pr - uc_rp \n\t"
2370 "ld8 r27 = [r20], uc_lc_loc - uc_unat_loc\n\t"
2371 "ld8 r28 = [r21], uc_fpsr_loc - uc_pr \n\t"
2373 "ld8 r29 = [r20], uc_eh_data - uc_lc_loc\n\t"
2374 "ld8 r30 = [r21], uc_eh_data + 8 - uc_fpsr_loc\n\t"
2376 /* Load data for the exception handler. */
2377 "ld8 r15 = [r20], 16 \n\t"
2378 "ld8 r16 = [r21], 16 \n\t"
2380 "ld8 r17 = [r20] \n\t"
2381 "ld8 r18 = [r21] \n\t"
2383 /* Install the balance of the thread state loaded above. */
2384 "cmp.ne p6, p0 = r0, r25 \n\t"
2385 "cmp.ne p7, p0 = r0, r27 \n\t"
2387 "(p6) ld8 r25 = [r25] \n\t"
2388 "(p7) ld8 r27 = [r27] \n\t"
2390 "(p7) mov.m ar.unat = r27 \n\t"
2391 "(p6) mov.i ar.pfs = r25 \n\t"
2392 "cmp.ne p9, p0 = r0, r29 \n\t"
2394 "(p9) ld8 r29 = [r29] \n\t"
2395 "cmp.ne p6, p0 = r0, r30 \n\t"
2397 "(p6) ld8 r30 = [r30] \n\t"
2398 /* Don't clobber p6-p9, which are in use at present. */
2399 "mov pr = r28, ~0x3c0 \n\t"
2400 "(p9) mov.i ar.lc = r29 \n\t"
2402 "mov.m r25 = ar.rsc \n\t"
2403 "(p6) mov.m ar.fpsr = r30 \n\t"
2405 "and r29 = 0x1c, r25 \n\t"
2408 "mov.m ar.rsc = r29 \n\t"
2410 /* This must be done before setting AR.BSPSTORE, otherwise
2411 AR.BSP will be initialized with a random displacement
2412 below the value we want, based on the current number of
2413 dirty stacked registers. */
2417 "mov.m ar.bspstore = r23 \n\t"
2419 "mov.m ar.rnat = r22 \n\t"
2421 "mov.m ar.rsc = r25 \n\t"
2423 "br.ret.sptk.few b0"
2424 : : "r"(target
), "r"(ireg_buf
), "r"(ireg_nat
), "r"(ireg_pr
)
2425 : "r15", "r16", "r17", "r18", "r20", "r21", "r22",
2426 "r23", "r24", "r25", "r26", "r27", "r28", "r29",
2432 static inline _Unwind_Ptr
2433 uw_identify_context (struct _Unwind_Context
*context
)
2435 return _Unwind_GetIP (context
);
2438 #include "unwind.inc"
2440 #if defined (USE_GAS_SYMVER) && defined (SHARED) && defined (USE_LIBUNWIND_EXCEPTIONS)
2441 alias (_Unwind_Backtrace
);
2442 alias (_Unwind_DeleteException
);
2443 alias (_Unwind_FindEnclosingFunction
);
2444 alias (_Unwind_ForcedUnwind
);
2445 alias (_Unwind_GetBSP
);
2446 alias (_Unwind_GetCFA
);
2447 alias (_Unwind_GetGR
);
2448 alias (_Unwind_GetIP
);
2449 alias (_Unwind_GetLanguageSpecificData
);
2450 alias (_Unwind_GetRegionStart
);
2451 alias (_Unwind_RaiseException
);
2452 alias (_Unwind_Resume
);
2453 alias (_Unwind_Resume_or_Rethrow
);
2454 alias (_Unwind_SetGR
);
2455 alias (_Unwind_SetIP
);