cortex_m: Fix single stepping will not return to debug mode sometimes
[fw/openocd] / src / target / avr32_mem.c
1 /***************************************************************************
2  *   Copyright (C) 2010 by Oleksandr Tymoshenko <gonzo@bluezbox.com>       *
3  *                                                                         *
4  *   This program is free software; you can redistribute it and/or modify  *
5  *   it under the terms of the GNU General Public License as published by  *
6  *   the Free Software Foundation; either version 2 of the License, or     *
7  *   (at your option) any later version.                                   *
8  *                                                                         *
9  *   This program is distributed in the hope that it will be useful,       *
10  *   but WITHOUT ANY WARRANTY; without even the implied warranty of        *
11  *   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the         *
12  *   GNU General Public License for more details.                          *
13  *                                                                         *
14  *   You should have received a copy of the GNU General Public License     *
15  *   along with this program; if not, write to the                         *
16  *   Free Software Foundation, Inc.,                                       *
17  *   59 Temple Place - Suite 330, Boston, MA  02111-1307, USA.             *
18  ***************************************************************************/
19
20 #ifdef HAVE_CONFIG_H
21 #include "config.h"
22 #endif
23
24 #include "target.h"
25 #include "jtag/jtag.h"
26 #include "avr32_jtag.h"
27 #include "avr32_mem.h"
28
29 int avr32_jtag_read_memory32(struct avr32_jtag *jtag_info,
30         uint32_t addr, int count, uint32_t *buffer)
31 {
32         int i, retval;
33         uint32_t data;
34
35         for (i = 0; i < count; i++) {
36                 retval = avr32_jtag_mwa_read(jtag_info, SLAVE_HSB_UNCACHED,
37                                 addr + i*4, &data);
38
39                 if (retval != ERROR_OK)
40                         return retval;
41
42                 /* XXX: Assume AVR32 is BE */
43                 buffer[i] = be_to_h_u32((uint8_t *)&data);
44         }
45
46         return ERROR_OK;
47 }
48
49 int avr32_jtag_read_memory16(struct avr32_jtag *jtag_info,
50         uint32_t addr, int count, uint16_t *buffer)
51 {
52         int i, retval;
53         uint32_t data;
54
55         i = 0;
56
57         /* any unaligned half-words? */
58         if (addr & 3) {
59                 retval = avr32_jtag_mwa_read(jtag_info, SLAVE_HSB_UNCACHED,
60                                 addr + i*2, &data);
61
62                 if (retval != ERROR_OK)
63                         return retval;
64
65                 /* XXX: Assume AVR32 is BE */
66                 data = be_to_h_u32((uint8_t *)&data);
67                 buffer[i] = (data >> 16) & 0xffff;
68                 i++;
69         }
70
71         /* read all complete words */
72         for (; i < (count & ~1); i += 2) {
73                 retval = avr32_jtag_mwa_read(jtag_info, SLAVE_HSB_UNCACHED,
74                                 addr + i*2, &data);
75
76                 if (retval != ERROR_OK)
77                         return retval;
78
79                 /* XXX: Assume AVR32 is BE */
80                 data = be_to_h_u32((uint8_t *)&data);
81                 buffer[i] = data & 0xffff;
82                 buffer[i+1] = (data >> 16) & 0xffff;
83         }
84
85         /* last halfword */
86         if (i < count) {
87                 retval = avr32_jtag_mwa_read(jtag_info, SLAVE_HSB_UNCACHED,
88                                 addr + i*2, &data);
89
90                 if (retval != ERROR_OK)
91                         return retval;
92
93                 /* XXX: Assume AVR32 is BE */
94                 data = be_to_h_u32((uint8_t *)&data);
95                 buffer[i] = data & 0xffff;
96         }
97
98         return ERROR_OK;
99 }
100
101 int avr32_jtag_read_memory8(struct avr32_jtag *jtag_info,
102         uint32_t addr, int count, uint8_t *buffer)
103 {
104         int i, j, retval;
105         uint8_t data[4];
106         i = 0;
107
108         /* Do we have non-aligned bytes? */
109         if (addr & 3) {
110                 retval = avr32_jtag_mwa_read(jtag_info, SLAVE_HSB_UNCACHED,
111                                 addr + i, (uint32_t *)(void *)data);
112
113                 if (retval != ERROR_OK)
114                         return retval;
115
116                 for (j = addr & 3; (j < 4) && (i < count); j++, i++)
117                         buffer[i] = data[3-j];
118         }
119
120         /* read all complete words */
121         for (; i < (count & ~3); i += 4) {
122                 retval = avr32_jtag_mwa_read(jtag_info, SLAVE_HSB_UNCACHED,
123                                 addr + i, (uint32_t *)(void *)data);
124
125                 if (retval != ERROR_OK)
126                         return retval;
127
128                 for (j = 0; j < 4; j++)
129                         buffer[i+j] = data[3-j];
130         }
131
132         /* remaining bytes */
133         if (i < count) {
134                 retval = avr32_jtag_mwa_read(jtag_info, SLAVE_HSB_UNCACHED,
135                                 addr + i, (uint32_t *)(void *)data);
136
137                 if (retval != ERROR_OK)
138                         return retval;
139
140                 for (j = 0; i + j < count; j++)
141                         buffer[i+j] = data[3-j];
142         }
143
144         return ERROR_OK;
145 }
146
147 int avr32_jtag_write_memory32(struct avr32_jtag *jtag_info,
148         uint32_t addr, int count, const uint32_t *buffer)
149 {
150         int i, retval;
151         uint32_t data;
152
153         for (i = 0; i < count; i++) {
154                 /* XXX: Assume AVR32 is BE */
155                 h_u32_to_be((uint8_t *)&data, buffer[i]);
156                 retval = avr32_jtag_mwa_write(jtag_info, SLAVE_HSB_UNCACHED,
157                                 addr + i*4, data);
158
159                 if (retval != ERROR_OK)
160                         return retval;
161
162         }
163
164         return ERROR_OK;
165 }
166
167 int avr32_jtag_write_memory16(struct avr32_jtag *jtag_info,
168         uint32_t addr, int count, const uint16_t *buffer)
169 {
170         int i, retval;
171         uint32_t data;
172         uint32_t data_out;
173
174         i = 0;
175
176         /*
177          * Do we have any non-aligned half-words?
178          */
179         if (addr & 3) {
180                 /*
181                  * mwa_read will read whole world, no nead to fiddle
182                  * with address. It will be truncated in set_addr
183                  */
184                 retval = avr32_jtag_mwa_read(jtag_info, SLAVE_HSB_UNCACHED,
185                                 addr, &data);
186
187                 if (retval != ERROR_OK)
188                         return retval;
189
190                 data = be_to_h_u32((uint8_t *)&data);
191                 data = (buffer[i] << 16) | (data & 0xffff);
192                 h_u32_to_be((uint8_t *)&data_out, data);
193
194                 retval = avr32_jtag_mwa_write(jtag_info, SLAVE_HSB_UNCACHED,
195                                 addr, data_out);
196
197                 if (retval != ERROR_OK)
198                         return retval;
199
200                 i++;
201         }
202
203         /* write all complete words */
204         for (; i < (count & ~1); i += 2) {
205                 /* XXX: Assume AVR32 is BE */
206                 data = (buffer[i+1] << 16) | buffer[i];
207                 h_u32_to_be((uint8_t *)&data_out, data);
208
209                 retval = avr32_jtag_mwa_write(jtag_info, SLAVE_HSB_UNCACHED,
210                                 addr + i*2, data_out);
211
212                 if (retval != ERROR_OK)
213                         return retval;
214         }
215
216         /* last halfword */
217         if (i < count) {
218                 retval = avr32_jtag_mwa_read(jtag_info, SLAVE_HSB_UNCACHED,
219                                 addr + i*2, &data);
220
221                 if (retval != ERROR_OK)
222                         return retval;
223
224                 data = be_to_h_u32((uint8_t *)&data);
225                 data &= ~0xffff;
226                 data |= buffer[i];
227                 h_u32_to_be((uint8_t *)&data_out, data);
228
229                 retval = avr32_jtag_mwa_write(jtag_info, SLAVE_HSB_UNCACHED,
230                                 addr + i*2, data_out);
231
232                 if (retval != ERROR_OK)
233                         return retval;
234         }
235
236         return ERROR_OK;
237 }
238
239 int avr32_jtag_write_memory8(struct avr32_jtag *jtag_info,
240         uint32_t addr, int count, const uint8_t *buffer)
241 {
242         int i, j, retval;
243         uint32_t data;
244         uint32_t data_out;
245
246         i = 0;
247
248         /*
249          * Do we have any non-aligned bytes?
250          */
251         if (addr & 3) {
252                 /*
253                  * mwa_read will read whole world, no nead to fiddle
254                  * with address. It will be truncated in set_addr
255                  */
256                 retval = avr32_jtag_mwa_read(jtag_info, SLAVE_HSB_UNCACHED,
257                                 addr, &data);
258
259                 if (retval != ERROR_OK)
260                         return retval;
261
262                 data = be_to_h_u32((uint8_t *)&data);
263                 for (j = addr & 3; (j < 4) && (i < count); j++, i++) {
264                         data &= ~(0xff << j*8);
265                         data |= (buffer[i] << j*8);
266                 }
267
268                 h_u32_to_be((uint8_t *)&data_out, data);
269                 retval = avr32_jtag_mwa_write(jtag_info, SLAVE_HSB_UNCACHED,
270                                 addr, data_out);
271
272                 if (retval != ERROR_OK)
273                         return retval;
274         }
275
276
277         /* write all complete words */
278         for (; i < (count & ~3); i += 4) {
279                 data = 0;
280
281                 for (j = 0; j < 4; j++)
282                         data |= (buffer[j+i] << j*8);
283
284                 h_u32_to_be((uint8_t *)&data_out, data);
285
286                 retval = avr32_jtag_mwa_write(jtag_info, SLAVE_HSB_UNCACHED,
287                                 addr + i, data_out);
288
289                 if (retval != ERROR_OK)
290                         return retval;
291         }
292
293         /*
294          * Write trailing bytes
295          */
296         if (i < count) {
297                 retval = avr32_jtag_mwa_read(jtag_info, SLAVE_HSB_UNCACHED,
298                                 addr + i, &data);
299
300                 if (retval != ERROR_OK)
301                         return retval;
302
303                 data = be_to_h_u32((uint8_t *)&data);
304                 for (j = 0; i < count; j++, i++) {
305                         data &= ~(0xff << j*8);
306                         data |= (buffer[j+i] << j*8);
307                 }
308
309                 h_u32_to_be((uint8_t *)&data_out, data);
310
311                 retval = avr32_jtag_mwa_write(jtag_info, SLAVE_HSB_UNCACHED,
312                                 addr+i, data_out);
313
314                 if (retval != ERROR_OK)
315                         return retval;
316         }
317
318         return ERROR_OK;
319 }