MIPS: whitespace cleanup
[fw/openocd] / src / target / mips_ejtag.c
1 /***************************************************************************
2  *   Copyright (C) 2008 by Spencer Oliver                                  *
3  *   spen@spen-soft.co.uk                                                  *
4  *                                                                         *
5  *   Copyright (C) 2008 by David T.L. Wong                                 *
6  *                                                                         *
7  *   Copyright (C) 2009 by David N. Claffey <dnclaffey@gmail.com>          *
8  *                                                                         *
9  *   This program is free software; you can redistribute it and/or modify  *
10  *   it under the terms of the GNU General Public License as published by  *
11  *   the Free Software Foundation; either version 2 of the License, or     *
12  *   (at your option) any later version.                                   *
13  *                                                                         *
14  *   This program is distributed in the hope that it will be useful,       *
15  *   but WITHOUT ANY WARRANTY; without even the implied warranty of        *
16  *   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the         *
17  *   GNU General Public License for more details.                          *
18  *                                                                         *
19  *   You should have received a copy of the GNU General Public License     *
20  *   along with this program; if not, write to the                         *
21  *   Free Software Foundation, Inc.,                                       *
22  *   59 Temple Place - Suite 330, Boston, MA  02111-1307, USA.             *
23  ***************************************************************************/
24 #ifdef HAVE_CONFIG_H
25 #include "config.h"
26 #endif
27
28 #include "mips32.h"
29 #include "mips_ejtag.h"
30
31 int mips_ejtag_set_instr(struct mips_ejtag *ejtag_info, int new_instr, void *delete_me_and_submit_patch)
32 {
33         struct jtag_tap *tap;
34
35         tap = ejtag_info->tap;
36         if (tap == NULL)
37                 return ERROR_FAIL;
38
39         if (buf_get_u32(tap->cur_instr, 0, tap->ir_length) != (uint32_t)new_instr)
40         {
41                 struct scan_field field;
42                 uint8_t t[4];
43
44                 field.tap = tap;
45                 field.num_bits = tap->ir_length;
46                 field.out_value = t;
47                 buf_set_u32(field.out_value, 0, field.num_bits, new_instr);
48                 field.in_value = NULL;
49
50                 jtag_add_ir_scan(1, &field, jtag_get_end_state());
51         }
52
53         return ERROR_OK;
54 }
55
56 int mips_ejtag_get_idcode(struct mips_ejtag *ejtag_info, uint32_t *idcode)
57 {
58         struct scan_field field;
59
60         jtag_set_end_state(TAP_IDLE);
61
62         mips_ejtag_set_instr(ejtag_info, EJTAG_INST_IDCODE, NULL);
63
64         field.tap = ejtag_info->tap;
65         field.num_bits = 32;
66         field.out_value = NULL;
67         field.in_value = (void*)idcode;
68
69         jtag_add_dr_scan(1, &field, jtag_get_end_state());
70
71         if (jtag_execute_queue() != ERROR_OK)
72         {
73                 LOG_ERROR("register read failed");
74         }
75
76         return ERROR_OK;
77 }
78
79 int mips_ejtag_get_impcode(struct mips_ejtag *ejtag_info, uint32_t *impcode)
80 {
81         struct scan_field field;
82
83         jtag_set_end_state(TAP_IDLE);
84
85         mips_ejtag_set_instr(ejtag_info, EJTAG_INST_IMPCODE, NULL);
86
87         field.tap = ejtag_info->tap;
88         field.num_bits = 32;
89         field.out_value = NULL;
90         field.in_value = (void*)impcode;
91
92         jtag_add_dr_scan(1, &field, jtag_get_end_state());
93
94         if (jtag_execute_queue() != ERROR_OK)
95         {
96                 LOG_ERROR("register read failed");
97         }
98
99         return ERROR_OK;
100 }
101
102 int mips_ejtag_drscan_32(struct mips_ejtag *ejtag_info, uint32_t *data)
103 {
104         struct jtag_tap *tap;
105         tap  = ejtag_info->tap;
106
107         if (tap == NULL)
108                 return ERROR_FAIL;
109         struct scan_field field;
110         uint8_t t[4], r[4];
111         int retval;
112
113         field.tap = tap;
114         field.num_bits = 32;
115         field.out_value = t;
116         buf_set_u32(field.out_value, 0, field.num_bits, *data);
117         field.in_value = r;
118
119         jtag_add_dr_scan(1, &field, jtag_get_end_state());
120
121         if ((retval = jtag_execute_queue()) != ERROR_OK)
122         {
123                 LOG_ERROR("register read failed");
124                 return retval;
125         }
126
127         *data = buf_get_u32(field.in_value, 0, 32);
128
129         keep_alive();
130
131         return ERROR_OK;
132 }
133
134 int mips_ejtag_step_enable(struct mips_ejtag *ejtag_info)
135 {
136         uint32_t code[] = {
137                         MIPS32_MTC0(1,31,0),                    /* move $1 to COP0 DeSave */
138                         MIPS32_MFC0(1,23,0),                    /* move COP0 Debug to $1 */
139                         MIPS32_ORI(1,1,0x0100),                 /* set SSt bit in debug reg */
140                         MIPS32_MTC0(1,23,0),                    /* move $1 to COP0 Debug */
141                         MIPS32_B(NEG16(5)),
142                         MIPS32_MFC0(1,31,0),                    /* move COP0 DeSave to $1 */
143         };
144
145         mips32_pracc_exec(ejtag_info, ARRAY_SIZE(code), code, \
146                 0, NULL, 0, NULL, 1);
147
148         return ERROR_OK;
149 }
150 int mips_ejtag_step_disable(struct mips_ejtag *ejtag_info)
151 {
152         uint32_t code[] = {
153                         MIPS32_MTC0(15,31,0),                                                   /* move $15 to COP0 DeSave */
154                         MIPS32_LUI(15,UPPER16(MIPS32_PRACC_STACK)),             /* $15 = MIPS32_PRACC_STACK */
155                         MIPS32_ORI(15,15,LOWER16(MIPS32_PRACC_STACK)),
156                         MIPS32_SW(1,0,15),                                                              /* sw $1,($15) */
157                         MIPS32_SW(2,0,15),                                                              /* sw $2,($15) */
158                         MIPS32_MFC0(1,23,0),                                                    /* move COP0 Debug to $1 */
159                         MIPS32_LUI(2,0xFFFF),                                                   /* $2 = 0xfffffeff */
160                         MIPS32_ORI(2,2,0xFEFF),
161                         MIPS32_AND(1,1,2),
162                         MIPS32_MTC0(1,23,0),                                                    /* move $1 to COP0 Debug */
163                         MIPS32_LW(2,0,15),
164                         MIPS32_LW(1,0,15),
165                         MIPS32_B(NEG16(13)),
166                         MIPS32_MFC0(15,31,0),                                                   /* move COP0 DeSave to $15 */
167         };
168
169         mips32_pracc_exec(ejtag_info, ARRAY_SIZE(code), code, \
170                 0, NULL, 0, NULL, 1);
171
172         return ERROR_OK;
173 }
174
175 int mips_ejtag_config_step(struct mips_ejtag *ejtag_info, int enable_step)
176 {
177         if (enable_step)
178                 return mips_ejtag_step_enable(ejtag_info);
179         return mips_ejtag_step_disable(ejtag_info);
180 }
181
182 int mips_ejtag_enter_debug(struct mips_ejtag *ejtag_info)
183 {
184         uint32_t ejtag_ctrl;
185         jtag_set_end_state(TAP_IDLE);
186         mips_ejtag_set_instr(ejtag_info, EJTAG_INST_CONTROL, NULL);
187
188         /* set debug break bit */
189         ejtag_ctrl = ejtag_info->ejtag_ctrl | EJTAG_CTRL_JTAGBRK;
190         mips_ejtag_drscan_32(ejtag_info, &ejtag_ctrl);
191
192         /* break bit will be cleared by hardware */
193         ejtag_ctrl = ejtag_info->ejtag_ctrl;
194         mips_ejtag_drscan_32(ejtag_info, &ejtag_ctrl);
195         LOG_DEBUG("ejtag_ctrl: 0x%8.8" PRIx32 "", ejtag_ctrl);
196         if ((ejtag_ctrl & EJTAG_CTRL_BRKST) == 0)
197                 LOG_DEBUG("Failed to enter Debug Mode!");
198
199         return ERROR_OK;
200 }
201
202 int mips_ejtag_exit_debug(struct mips_ejtag *ejtag_info)
203 {
204         uint32_t inst;
205         inst = MIPS32_DRET;
206
207         /* execute our dret instruction */
208         mips32_pracc_exec(ejtag_info, 1, &inst, 0, NULL, 0, NULL, 0);
209
210         return ERROR_OK;
211 }
212
213 int mips_ejtag_read_debug(struct mips_ejtag *ejtag_info, uint32_t* debug_reg)
214 {
215         /* read ejtag ECR */
216         uint32_t code[] = {
217                         MIPS32_MTC0(15,31,0),                                                   /* move $15 to COP0 DeSave */
218                         MIPS32_LUI(15,UPPER16(MIPS32_PRACC_STACK)),             /* $15 = MIPS32_PRACC_STACK */
219                         MIPS32_ORI(15,15,LOWER16(MIPS32_PRACC_STACK)),
220                         MIPS32_SW(1,0,15),                                                              /* sw $1,($15) */
221                         MIPS32_SW(2,0,15),                                                              /* sw $2,($15) */
222                         MIPS32_LUI(1,UPPER16(MIPS32_PRACC_PARAM_OUT)),  /* $1 = MIPS32_PRACC_PARAM_OUT */
223                         MIPS32_ORI(1,1,LOWER16(MIPS32_PRACC_PARAM_OUT)),
224                         MIPS32_MFC0(2,23,0),                                                    /* move COP0 Debug to $2 */
225                         MIPS32_SW(2,0,1),
226                         MIPS32_LW(2,0,15),
227                         MIPS32_LW(1,0,15),
228                         MIPS32_B(NEG16(12)),
229                         MIPS32_MFC0(15,31,0),                                                   /* move COP0 DeSave to $15 */
230         };
231
232         mips32_pracc_exec(ejtag_info, ARRAY_SIZE(code), code, \
233                 0, NULL, 1, debug_reg, 1);
234
235         return ERROR_OK;
236 }
237
238 int mips_ejtag_init(struct mips_ejtag *ejtag_info)
239 {
240         uint32_t ejtag_version;
241
242         mips_ejtag_get_impcode(ejtag_info, &ejtag_info->impcode);
243         LOG_DEBUG("impcode: 0x%8.8" PRIx32 "", ejtag_info->impcode);
244
245         /* get ejtag version */
246         ejtag_version = ((ejtag_info->impcode >> 29) & 0x07);
247
248         switch (ejtag_version)
249         {
250                 case 0:
251                         LOG_DEBUG("EJTAG: Version 1 or 2.0 Detected");
252                         break;
253                 case 1:
254                         LOG_DEBUG("EJTAG: Version 2.5 Detected");
255                         break;
256                 case 2:
257                         LOG_DEBUG("EJTAG: Version 2.6 Detected");
258                         break;
259                 case 3:
260                         LOG_DEBUG("EJTAG: Version 3.1 Detected");
261                         break;
262                 default:
263                         LOG_DEBUG("EJTAG: Unknown Version Detected");
264                         break;
265         }
266         LOG_DEBUG("EJTAG: features:%s%s%s%s%s%s%s",
267                 ejtag_info->impcode & (1 << 28) ? " R3k":    " R4k",
268                 ejtag_info->impcode & (1 << 24) ? " DINT":   "",
269                 ejtag_info->impcode & (1 << 22) ? " ASID_8": "",
270                 ejtag_info->impcode & (1 << 21) ? " ASID_6": "",
271                 ejtag_info->impcode & (1 << 16) ? " MIPS16": "",
272                 ejtag_info->impcode & (1 << 14) ? " noDMA":  " DMA",
273                 ejtag_info->impcode & (1 << 0)  ? " MIPS64": " MIPS32"
274 );
275
276         if ((ejtag_info->impcode & (1 << 14)) == 0)
277                 LOG_DEBUG("EJTAG: DMA Access Mode Support Enabled");
278
279         /* set initial state for ejtag control reg */
280         ejtag_info->ejtag_ctrl = EJTAG_CTRL_ROCC | EJTAG_CTRL_PRACC | EJTAG_CTRL_PROBEN | EJTAG_CTRL_SETDEV;
281
282         return ERROR_OK;
283 }
284
285 int mips_ejtag_fastdata_scan(struct mips_ejtag *ejtag_info, int write, uint32_t *data)
286 {
287         struct jtag_tap *tap;
288         tap = ejtag_info->tap;
289
290         if (tap == NULL)
291                 return ERROR_FAIL;
292
293         struct scan_field fields[2];
294         uint8_t spracc = 0;
295         uint8_t t[4] = {0, 0, 0, 0};
296
297         /* fastdata 1-bit register */
298         fields[0].tap = tap;
299         fields[0].num_bits = 1;
300         fields[0].out_value = &spracc;
301         fields[0].in_value = NULL;
302
303         /* processor access data register 32 bit */
304         fields[1].tap = tap;
305         fields[1].num_bits = 32;
306         fields[1].out_value = t;
307
308         if (write)
309         {
310                 fields[1].in_value = NULL;
311                 buf_set_u32(t, 0, 32, *data);
312         }
313         else
314         {
315                 fields[1].in_value = (uint8_t *) data;
316         }
317
318         jtag_add_dr_scan(2, fields, jtag_get_end_state());
319         keep_alive();
320
321         return ERROR_OK;
322 }