40#define RESTORE_RETURNVAL 0x8fbf0000
41#define RESTORE_RETURNVAL_MASK 0xffff0000
46#define RESTORE_RETURNVAL2 0xdfbf0000
51#define RESTORE_RETURNVAL3 0x7bbf0000
56#define ADJUST_STACKP_C 0x27bd0000
57#define ADJUST_STACKP_C_MASK 0xffff0000
62#define ADJUST_STACKP_V 0x03a1e821
63#define ADJUST_STACKP_V_MASK 0xffffffff
68#define SET_UPPER_C 0x3c010000
69#define SET_UPPER_C_MASK 0xffff0000
74#define OR_LOWER_C 0x34210000
75#define OR_LOWER_C_MASK 0xffff0000
80#define SET_LOWER_C 0x34010000
81#define SET_LOWER_C_MASK 0xffff0000
84#define RETURN 0x03e00008
86#define CALL(f) (0x0c000000 | (((int) (f)) >> 2))
97 unsigned int *returnAddress;
104#define HASH(ra) ((((int) (ra)) >> 2) & (HASH_SIZE - 1))
115extern unsigned int* ps2GetReturnAddress();
116extern unsigned int* ps2GetStackPointer();
119void ps2GetStackTrace(
unsigned int* results,
int max)
122 unsigned int* ra_limit;
125 unsigned int mainCall;
126 unsigned short const_upper;
127 unsigned short const_lower;
130 Bool found_ra_offset, found_sp_adjust;
131 Bool found_const_upper, found_const_lower;
133 ra = ps2GetReturnAddress();
134 sp = ps2GetStackPointer();
135 mainCall = CALL(main);
140 rc = &returnCache[HASH(ra)];
141 if (rc->returnAddress != ra)
143 found_ra_offset = FALSE;
144 found_sp_adjust = FALSE;
145 found_const_upper = FALSE;
146 found_const_lower = FALSE;
149 rc->returnAddress = ra;
150 ra_limit = (
unsigned int *) 0x200000;
154 while ((!found_ra_offset || !found_sp_adjust) && ra < ra_limit)
158 if ((inst & RESTORE_RETURNVAL_MASK) == RESTORE_RETURNVAL)
160 ra_offset = inst & ~RESTORE_RETURNVAL_MASK;
161 found_ra_offset = TRUE;
163 else if ((inst & RESTORE_RETURNVAL_MASK) == RESTORE_RETURNVAL2)
165 ra_offset = inst & ~RESTORE_RETURNVAL_MASK;
166 found_ra_offset = TRUE;
168 else if ((inst & RESTORE_RETURNVAL_MASK) == RESTORE_RETURNVAL3)
170 ra_offset = inst & ~RESTORE_RETURNVAL_MASK;
171 found_ra_offset = TRUE;
173 else if ((inst & ADJUST_STACKP_C_MASK) == ADJUST_STACKP_C)
175 sp_adjust = inst & ~ADJUST_STACKP_C_MASK;
176 found_sp_adjust = TRUE;
178 else if ((inst & ADJUST_STACKP_V_MASK) == ADJUST_STACKP_V)
181 found_sp_adjust = TRUE;
183 else if ((inst & SET_UPPER_C_MASK) == SET_UPPER_C)
185 const_upper = inst & ~SET_UPPER_C_MASK;
187 found_const_upper = TRUE;
189 else if ((inst & OR_LOWER_C_MASK) == OR_LOWER_C)
191 const_lower = inst & ~OR_LOWER_C_MASK;
192 found_const_lower = TRUE;
194 else if ((inst & SET_LOWER_C_MASK) == SET_LOWER_C)
196 const_lower = inst & ~SET_LOWER_C_MASK;
198 found_const_lower = TRUE;
200 else if (inst == RETURN)
205 if (sp_adjust == 0 && (found_const_upper || found_const_lower))
206 sp_adjust = (const_upper << 16) | const_lower;
207 rc->raOffset = ra_offset;
208 rc->spAdjust = sp_adjust;
211 if (rc->spAdjust <= 0)
217 ra = (
unsigned int *) sp[rc->raOffset>>2];
218 sp += rc->spAdjust >> 2;
226 *results++ = ((
unsigned int) ra) - 8;
227 if (ra[-2] == mainCall)