1 |
/* PCSX2 - PS2 Emulator for PCs |
2 |
* Copyright (C) 2002-2010 PCSX2 Dev Team |
3 |
* |
4 |
* PCSX2 is free software: you can redistribute it and/or modify it under the terms |
5 |
* of the GNU Lesser General Public License as published by the Free Software Found- |
6 |
* ation, either version 3 of the License, or (at your option) any later version. |
7 |
* |
8 |
* PCSX2 is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; |
9 |
* without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR |
10 |
* PURPOSE. See the GNU General Public License for more details. |
11 |
* |
12 |
* You should have received a copy of the GNU General Public License along with PCSX2. |
13 |
* If not, see <http://www.gnu.org/licenses/>. |
14 |
*/ |
15 |
|
16 |
#pragma once |
17 |
|
18 |
template< typename T> |
19 |
static __ri const char* _eelog_GetHwName( u32 addr, T val ) |
20 |
{ |
21 |
#define EasyCase(label) case label: return #label |
22 |
|
23 |
switch( addr ) |
24 |
{ |
25 |
// Counters! |
26 |
EasyCase(RCNT0_COUNT); |
27 |
EasyCase(RCNT0_MODE); |
28 |
EasyCase(RCNT0_TARGET); |
29 |
EasyCase(RCNT0_HOLD); |
30 |
|
31 |
EasyCase(RCNT1_COUNT); |
32 |
EasyCase(RCNT1_MODE); |
33 |
EasyCase(RCNT1_TARGET); |
34 |
EasyCase(RCNT1_HOLD); |
35 |
|
36 |
EasyCase(RCNT2_COUNT); |
37 |
EasyCase(RCNT2_MODE); |
38 |
EasyCase(RCNT2_TARGET); |
39 |
|
40 |
EasyCase(RCNT3_COUNT); |
41 |
EasyCase(RCNT3_MODE); |
42 |
EasyCase(RCNT3_TARGET); |
43 |
|
44 |
// IPU! |
45 |
EasyCase(IPU_CMD); |
46 |
EasyCase(IPU_CTRL); |
47 |
EasyCase(IPU_BP); |
48 |
EasyCase(IPU_TOP); |
49 |
|
50 |
// GIF! |
51 |
EasyCase(GIF_CTRL); |
52 |
EasyCase(GIF_MODE); |
53 |
EasyCase(GIF_STAT); |
54 |
EasyCase(GIF_TAG0); |
55 |
EasyCase(GIF_TAG1); |
56 |
EasyCase(GIF_TAG2); |
57 |
EasyCase(GIF_TAG3); |
58 |
EasyCase(GIF_CNT); |
59 |
EasyCase(GIF_P3CNT); |
60 |
EasyCase(GIF_P3TAG); |
61 |
|
62 |
// VIF! |
63 |
EasyCase(VIF0_STAT); |
64 |
EasyCase(VIF0_FBRST); |
65 |
EasyCase(VIF0_ERR); |
66 |
EasyCase(VIF0_MARK); |
67 |
EasyCase(VIF0_CYCLE); |
68 |
EasyCase(VIF0_MODE); |
69 |
EasyCase(VIF0_NUM); |
70 |
EasyCase(VIF0_MASK); |
71 |
EasyCase(VIF0_CODE); |
72 |
EasyCase(VIF0_ITOPS); |
73 |
EasyCase(VIF0_ITOP); |
74 |
EasyCase(VIF0_TOP); |
75 |
EasyCase(VIF0_ROW0); |
76 |
EasyCase(VIF0_ROW1); |
77 |
EasyCase(VIF0_ROW2); |
78 |
EasyCase(VIF0_ROW3); |
79 |
EasyCase(VIF0_COL0); |
80 |
EasyCase(VIF0_COL1); |
81 |
EasyCase(VIF0_COL2); |
82 |
EasyCase(VIF0_COL3); |
83 |
|
84 |
EasyCase(VIF1_STAT); |
85 |
EasyCase(VIF1_FBRST); |
86 |
EasyCase(VIF1_ERR); |
87 |
EasyCase(VIF1_MARK); |
88 |
EasyCase(VIF1_CYCLE); |
89 |
EasyCase(VIF1_MODE); |
90 |
EasyCase(VIF1_NUM); |
91 |
EasyCase(VIF1_MASK); |
92 |
EasyCase(VIF1_CODE); |
93 |
EasyCase(VIF1_ITOPS); |
94 |
EasyCase(VIF1_BASE); |
95 |
EasyCase(VIF1_OFST); |
96 |
EasyCase(VIF1_TOPS); |
97 |
EasyCase(VIF1_ITOP); |
98 |
EasyCase(VIF1_TOP); |
99 |
EasyCase(VIF1_ROW0); |
100 |
EasyCase(VIF1_ROW1); |
101 |
EasyCase(VIF1_ROW2); |
102 |
EasyCase(VIF1_ROW3); |
103 |
EasyCase(VIF1_COL0); |
104 |
EasyCase(VIF1_COL1); |
105 |
EasyCase(VIF1_COL2); |
106 |
EasyCase(VIF1_COL3); |
107 |
|
108 |
// VIF DMA! |
109 |
EasyCase(VIF0_CHCR); |
110 |
EasyCase(VIF0_MADR); |
111 |
EasyCase(VIF0_QWC); |
112 |
EasyCase(VIF0_TADR); |
113 |
EasyCase(VIF0_ASR0); |
114 |
EasyCase(VIF0_ASR1); |
115 |
|
116 |
EasyCase(VIF1_CHCR); |
117 |
EasyCase(VIF1_QWC); |
118 |
EasyCase(VIF1_TADR); |
119 |
EasyCase(VIF1_ASR0); |
120 |
EasyCase(VIF1_ASR1); |
121 |
|
122 |
// GIF DMA! |
123 |
EasyCase(GIF_CHCR); |
124 |
EasyCase(GIF_MADR); |
125 |
EasyCase(GIF_QWC); |
126 |
EasyCase(GIF_TADR); |
127 |
EasyCase(GIF_ASR0); |
128 |
EasyCase(GIF_ASR1); |
129 |
|
130 |
// IPU DMA! |
131 |
EasyCase(fromIPU_CHCR); |
132 |
EasyCase(fromIPU_MADR); |
133 |
EasyCase(fromIPU_QWC); |
134 |
EasyCase(fromIPU_TADR); |
135 |
|
136 |
EasyCase(toIPU_CHCR); |
137 |
EasyCase(toIPU_MADR); |
138 |
EasyCase(toIPU_QWC); |
139 |
EasyCase(toIPU_TADR); |
140 |
|
141 |
// SIF DMA! |
142 |
EasyCase(SIF0_CHCR); |
143 |
EasyCase(SIF0_MADR); |
144 |
EasyCase(SIF0_QWC); |
145 |
|
146 |
EasyCase(SIF1_CHCR); |
147 |
EasyCase(SIF1_MADR); |
148 |
EasyCase(SIF1_QWC); |
149 |
|
150 |
EasyCase(SIF2_CHCR); |
151 |
EasyCase(SIF2_MADR); |
152 |
EasyCase(SIF2_QWC); |
153 |
|
154 |
// Scratchpad DMA! (SPRdma) |
155 |
|
156 |
EasyCase(fromSPR_CHCR); |
157 |
EasyCase(fromSPR_MADR); |
158 |
EasyCase(fromSPR_QWC); |
159 |
|
160 |
EasyCase(toSPR_CHCR); |
161 |
EasyCase(toSPR_MADR); |
162 |
EasyCase(toSPR_QWC); |
163 |
|
164 |
// DMAC! |
165 |
EasyCase(DMAC_CTRL); |
166 |
EasyCase(DMAC_STAT); |
167 |
EasyCase(DMAC_PCR); |
168 |
EasyCase(DMAC_SQWC); |
169 |
EasyCase(DMAC_RBSR); |
170 |
EasyCase(DMAC_RBOR); |
171 |
EasyCase(DMAC_STADR); |
172 |
EasyCase(DMAC_ENABLER); |
173 |
EasyCase(DMAC_ENABLEW); |
174 |
|
175 |
// INTC! |
176 |
EasyCase(INTC_STAT); |
177 |
EasyCase(INTC_MASK); |
178 |
|
179 |
// SIO |
180 |
EasyCase(SIO_LCR); |
181 |
EasyCase(SIO_LSR); |
182 |
EasyCase(SIO_IER); |
183 |
EasyCase(SIO_ISR); |
184 |
EasyCase(SIO_FCR); |
185 |
EasyCase(SIO_BGR); |
186 |
EasyCase(SIO_TXFIFO); |
187 |
EasyCase(SIO_RXFIFO); |
188 |
|
189 |
// SBUS (terribly mysterious!) |
190 |
EasyCase(SBUS_F200); |
191 |
EasyCase(SBUS_F210); |
192 |
EasyCase(SBUS_F220); |
193 |
EasyCase(SBUS_F230); |
194 |
EasyCase(SBUS_F240); |
195 |
EasyCase(SBUS_F250); |
196 |
EasyCase(SBUS_F260); |
197 |
|
198 |
// MCH (vaguely mysterious!) |
199 |
EasyCase(MCH_RICM); |
200 |
EasyCase(MCH_DRD); |
201 |
} |
202 |
|
203 |
#define EasyZone(zone) \ |
204 |
if ((addr >= EEMemoryMap::zone##_Start) && (addr < EEMemoryMap::zone##_End)) return #zone |
205 |
|
206 |
#define EasyZoneR(zone) \ |
207 |
EasyZone(zone) "_reserved" |
208 |
|
209 |
// Nothing discovered/handled : Check for "zoned" registers -- registers mirrored |
210 |
// across large sections of memory (FIFOs mainly). |
211 |
|
212 |
EasyZone(VIF0_FIFO); EasyZone(VIF1_FIFO); EasyZone(GIF_FIFO); |
213 |
|
214 |
if( (addr >= EEMemoryMap::IPU_FIFO_Start) && (addr < EEMemoryMap::IPU_FIFO_End) ) |
215 |
{ |
216 |
return (addr & 0x10) ? "IPUin_FIFO" : "IPUout_FIFO"; |
217 |
} |
218 |
|
219 |
// Check for "reserved" regions -- registers that most likely discard writes and |
220 |
// return 0 when read. To assist in having useful logs, we determine the general |
221 |
// "zone" of the register address and return the zone name in the unknown string. |
222 |
|
223 |
EasyZoneR(RCNT0); EasyZoneR(RCNT1); |
224 |
EasyZoneR(RCNT2); EasyZoneR(RCNT3); |
225 |
|
226 |
EasyZoneR(IPU); EasyZoneR(GIF); |
227 |
EasyZoneR(VIF0); EasyZoneR(VIF1); |
228 |
EasyZoneR(VIF0dma); EasyZoneR(VIF1dma); |
229 |
EasyZoneR(GIFdma); EasyZoneR(fromIPU); EasyZoneR(toIPU); |
230 |
EasyZoneR(SIF0dma); EasyZoneR(SIF1dma); EasyZoneR(SIF2dma); |
231 |
EasyZoneR(fromSPR); EasyZoneR(toSPR); |
232 |
|
233 |
EasyZoneR(DMAC); EasyZoneR(INTC); |
234 |
EasyZoneR(SIO); EasyZoneR(SBUS); |
235 |
EasyZoneR(MCH); EasyZoneR(DMACext); |
236 |
|
237 |
// If we get this far it's an *unknown* register; plain and simple. |
238 |
|
239 |
return NULL; //"Unknown"; |
240 |
} |
241 |
|
242 |
template< typename T> |
243 |
static __ri void eeHwTraceLog( u32 addr, T val, bool mode ) |
244 |
{ |
245 |
if (!IsDevBuild) return; |
246 |
if (!EmuConfig.Trace.EE.m_EnableRegisters) return; |
247 |
|
248 |
FastFormatAscii valStr; |
249 |
FastFormatAscii labelStr; |
250 |
labelStr.Write("Hw%s%u", mode ? "Read" : "Write", sizeof (T) * 8); |
251 |
|
252 |
switch( sizeof(T) ) |
253 |
{ |
254 |
case 1: valStr.Write("0x%02x", val); break; |
255 |
case 2: valStr.Write("0x%04x", val); break; |
256 |
case 4: valStr.Write("0x%08x", val); break; |
257 |
|
258 |
case 8: valStr.Write("0x%08x.%08x", ((u32*)&val)[1], ((u32*)&val)[0]); break; |
259 |
case 16: ((u128&)val).WriteTo(valStr); |
260 |
} |
261 |
|
262 |
static const char* temp = "%-12s @ 0x%08X/%-16s %s %s"; |
263 |
|
264 |
if( const char* regname = _eelog_GetHwName<T>( addr, val ) ) |
265 |
HW_LOG( temp, labelStr.c_str(), addr, regname, mode ? "->" : "<-", valStr.c_str() ); |
266 |
else |
267 |
UnknownHW_LOG( temp, labelStr.c_str(), addr, "Unknown", mode ? "->" : "<-", valStr.c_str() ); |
268 |
} |