PS2SDK
PS2 Homebrew Libraries
Loading...
Searching...
No Matches
iop_debug.c
Go to the documentation of this file.
1/*
2# _____ ___ ____ ___ ____
3# ____| | ____| | | |____|
4# | ___| |____ ___| ____| | \ PS2DEV Open Source Project.
5#-----------------------------------------------------------------------
6# Copyright 2001-2009, ps2dev - http://www.ps2dev.org
7# Licenced under Academic Free License version 2.0
8# Review ps2sdk README & LICENSE files for further details.
9*/
10
17#include <tamtypes.h>
18#include <excepman.h>
19#include <iop_cop0_defs.h>
20#include <ps2_debug.h>
21
22#include "iopdebug.h"
23#include "iopdebug_priv.h"
24#include "iopdebug_defs.h"
25
26u32 _iop_ex_def_stack[_EX_DEF_STACK_SIZE / 4];
27u32 _iop_ex_dbg_stack[_EX_DBG_STACK_SIZE / 4];
28
29IOP_RegFrame _iop_ex_def_frame;
30IOP_RegFrame _iop_ex_dbg_frame;
31
32static int _is_iop_dbg_installed = 0;
33
34static void *orig_iop_def_ex_handler = NULL;
35static void *orig_iop_break_ex_handler = NULL;
36static void *orig_iop_dbg_ex_handler = NULL;
37
38static IOP_ExceptionHandler *iop_exception_handlers[16];
39
40IOP_ExceptionHandler *iop_dbg_get_handler(int cause)
41{
42 if((cause < 0) || (cause > 15)) { return(NULL); }
43
44 return(iop_exception_handlers[cause]);
45}
46
47IOP_ExceptionHandler *iop_dbg_set_handler(int cause, IOP_ExceptionHandler *handler)
48{
49 IOP_ExceptionHandler *old_handler;
50 u32 old_state;
51
52 if((cause < 0) || (cause > 15)) { return(NULL); }
53
54 EnterCritical(&old_state);
55
56 old_handler = iop_exception_handlers[cause];
57 iop_exception_handlers[cause] = handler;
58
59 ExitCritical(old_state);
60
61 return(old_handler);
62}
63
64// this is called by the IOP debug/exception handlers
65void iop_exception_dispatcher(IOP_RegFrame *frame)
66{
67 int excode = M_IOP_GET_CAUSE_EXCODE(frame->cause);
68 IOP_ExceptionHandler *handler = iop_exception_handlers[excode];
69
70 if(handler)
71 {
72 handler(frame);
73 }
74}
75
76extern void _iop_dbg_set_bpda(u32 addr, u32 mask, u32 user_mask);
77extern void _iop_dbg_set_bpx(u32 addr, u32 mask, u32 user_mask);
78
79// ex: iop_dbg_set_bpr(&var, 0xFFFFFFFF, (IOP_DCIC_UD | IOP_DCIC_KD));
80void iop_dbg_set_bpr(u32 addr, u32 mask, u32 user_mask) { _iop_dbg_set_bpda(addr, mask, IOP_DCIC_DR | user_mask); }
81
82// ex: iop_dbg_set_bpw(&var, 0xFFFFFFFF, (IOP_DCIC_UD | IOP_DCIC_KD));
83void iop_dbg_set_bpw(u32 addr, u32 mask, u32 user_mask) { _iop_dbg_set_bpda(addr, mask, IOP_DCIC_DW | user_mask); }
84
85// ex: iop_dbg_set_bpx(&func, 0xFFFFFFFF, (IOP_DCIC_UD | IOP_DCIC_KD));
86void iop_dbg_set_bpx(u32 addr, u32 mask, u32 user_mask) { _iop_dbg_set_bpx(addr, mask, user_mask); }
87
88void iop_dbg_clr_bpda(void)
89{
90 u32 dcic = iop_dbg_get_dcic();
92 if(!(dcic & IOP_DCIC_PCE)) { dcic = 0; }
93 iop_dbg_set_dcic(dcic);
94}
95
96void iop_dbg_clr_bpx(void)
97{
98 u32 dcic = iop_dbg_get_dcic();
99 dcic &= ~(IOP_DCIC_PCE);
100 if(!(dcic & IOP_DCIC_DAE)) { dcic = 0; }
101 iop_dbg_set_dcic(dcic);
102}
103
104void iop_dbg_clr_bps(void)
105{
106 iop_dbg_set_dcic(0);
107 iop_dbg_set_bda(0);
108 iop_dbg_set_bdam(0);
109 iop_dbg_set_bpc(0);
110 iop_dbg_set_bpcm(0);
111}
112
113extern void _iop_ex_def_handler(void);
114extern void _iop_ex_dbg_handler(void);
115extern void _iop_ex_break_handler(void);
116
117int iop_dbg_install(void)
118{
119 int i;
120
121 // if already installed, return with an error.
122 if(_is_iop_dbg_installed) { return(-1); }
123
124 // initialize our exception handler pointers.
125 for(i = 0; i < 16; i++)
126 {
127 iop_exception_handlers[i] = NULL;
128 }
129
130 // todo: preserve original exception handlers here!
131 // This will require using "EXCEPMAN" export 3..
132
133 // register our "default" exception handler.
134 if(RegisterDefaultExceptionHandler((exception_handler_t) _iop_ex_def_handler) < 0)
135 {
136 orig_iop_def_ex_handler = NULL;
137 return(-2);
138 }
139
140 // register our "BREAK" instruction exception handler.
141 if(RegisterPriorityExceptionHandler(IOP_EXCEPTION_BP, 0, (exception_handler_t) _iop_ex_break_handler) < 0)
142 {
143 RegisterDefaultExceptionHandler((exception_handler_t) orig_iop_def_ex_handler);
144 orig_iop_def_ex_handler = NULL;
145 orig_iop_break_ex_handler = NULL;
146 return(-3);
147 }
148
149 // register our "Hardware DeBug"(aka "Hardware BreakPoint") exception handler.
150 if(RegisterPriorityExceptionHandler(IOP_EXCEPTION_HDB, 0, (exception_handler_t) _iop_ex_dbg_handler) < 0)
151 {
152 RegisterDefaultExceptionHandler((exception_handler_t) orig_iop_def_ex_handler);
153 orig_iop_def_ex_handler = NULL;
154
155 RegisterPriorityExceptionHandler(IOP_EXCEPTION_BP, 0, (exception_handler_t) orig_iop_break_ex_handler);
156 orig_iop_break_ex_handler = NULL;
157
158 orig_iop_dbg_ex_handler = NULL;
159 return(-4);
160 }
161
162 _is_iop_dbg_installed = 1;
163 return(0);
164}
165
166int iop_dbg_remove(void)
167{
168 // if not installed, return with an error.
169 if(!_is_iop_dbg_installed) { return(-1); }
170
171 if(orig_iop_def_ex_handler)
172 {
173 RegisterDefaultExceptionHandler((exception_handler_t) orig_iop_def_ex_handler);
174 orig_iop_def_ex_handler = NULL;
175 }
176
177 if(orig_iop_break_ex_handler)
178 {
179 RegisterPriorityExceptionHandler(IOP_EXCEPTION_BP, 0, (exception_handler_t) orig_iop_break_ex_handler);
180 orig_iop_break_ex_handler = NULL;
181 }
182
183 if(orig_iop_dbg_ex_handler)
184 {
185 RegisterPriorityExceptionHandler(IOP_EXCEPTION_HDB, 0, (exception_handler_t) orig_iop_dbg_ex_handler);
186 orig_iop_dbg_ex_handler = NULL;
187 }
188
189 _is_iop_dbg_installed = 0;
190 return(0);
191}
192
193void iop_dbg_get_reg_frames(IOP_RegFrame **def_frame_ptr, IOP_RegFrame **dbg_frame_ptr)
194{
195 if(def_frame_ptr) { *def_frame_ptr = &_iop_ex_def_frame; }
196 if(dbg_frame_ptr) { *dbg_frame_ptr = &_iop_ex_dbg_frame; }
197}
198
#define IOP_EXCEPTION_BP
Definition excepman.h:46
#define IOP_EXCEPTION_HDB
Definition excepman.h:58
#define IOP_DCIC_DAE
#define IOP_DCIC_PCE
#define IOP_DCIC_DW
#define IOP_DCIC_DR
#define _EX_DEF_STACK_SIZE
#define _EX_DBG_STACK_SIZE
static void EnterCritical(u32 *old_state)
static void ExitCritical(u32 old_state)