[IA64] unwind.c uses wrong unat from switch_stack
authorKeith Owens <kaos@sgi.com>
Fri, 22 Jul 2005 06:41:00 +0000 (23:41 -0700)
committerTony Luck <tony.luck@intel.com>
Wed, 27 Jul 2005 21:18:08 +0000 (14:18 -0700)
commitb833961bd30eec201b9a94eec36aa7ac96f9c9c0
tree2ae8efad5995f7f23564304fd5027bea026ac65e
parentd108919b2b5c064946c9bd30cbd4761d491cddb0
[IA64] unwind.c uses wrong unat from switch_stack

unwind.c can read the wrong unat bits from switch_stack.
sw->caller_unat is the value of ar.unat when the task was blocked.
sw->ar_unat is the value of ar.unat after doing st8.spill for r4-7.
IOW, ar_unat is caller_unat with 4 bits changed.

unw_access_gr() uses sw->ar_unat for r4-7 (correct), but it also uses
sw->ar_unat for other scratch registers (incorrect).  sw->ar_unat
should only be used for r4-7, everything else should use
sw->caller_unat, unless modified by unwind info.  Using sw->ar_unat
risks picking up the 4 bits that were overwritten when r4-7 were saved.

Also this line is wrong
unw.sw_off[unw.preg_index[UNW_REG_PFS]] = SW(AR_UNAT);
and should be
unw.sw_off[unw.preg_index[UNW_REG_PFS]] = SW(AR_PFS);

Signed-off-by: Keith Owens <kaos@sgi.com>
Signed-off-by: Tony Luck <tony.luck@intel.com>
arch/ia64/kernel/unwind.c