jtag: linuxgpiod: drop extra parenthesis
[openocd.git] / src / flash / nor / efm32.c
1 /***************************************************************************
2 * Copyright (C) 2005 by Dominic Rath *
3 * Dominic.Rath@gmx.de *
4 * *
5 * Copyright (C) 2008 by Spencer Oliver *
6 * spen@spen-soft.co.uk *
7 * *
8 * Copyright (C) 2011 by Andreas Fritiofson *
9 * andreas.fritiofson@gmail.com *
10 * *
11 * Copyright (C) 2013 by Roman Dmitrienko *
12 * me@iamroman.org *
13 * *
14 * Copyright (C) 2014 Nemui Trinomius *
15 * nemuisan_kawausogasuki@live.jp *
16 * *
17 * Copyright (C) 2021 Doug Brunner *
18 * doug.a.brunner@gmail.com *
19 * *
20 * This program is free software; you can redistribute it and/or modify *
21 * it under the terms of the GNU General Public License as published by *
22 * the Free Software Foundation; either version 2 of the License, or *
23 * (at your option) any later version. *
24 * *
25 * This program is distributed in the hope that it will be useful, *
26 * but WITHOUT ANY WARRANTY; without even the implied warranty of *
27 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the *
28 * GNU General Public License for more details. *
29 * *
30 * You should have received a copy of the GNU General Public License *
31 * along with this program. If not, see <http://www.gnu.org/licenses/>. *
32 ***************************************************************************/
33
34 #ifdef HAVE_CONFIG_H
35 #include "config.h"
36 #endif
37
38 #include "imp.h"
39 #include <helper/binarybuffer.h>
40 #include <target/algorithm.h>
41 #include <target/armv7m.h>
42 #include <target/cortex_m.h>
43
44 #define EFM_FAMILY_ID_GIANT_GECKO 72
45 #define EFM_FAMILY_ID_LEOPARD_GECKO 74
46
47 #define EFM32_FLASH_ERASE_TMO 100
48 #define EFM32_FLASH_WDATAREADY_TMO 100
49 #define EFM32_FLASH_WRITE_TMO 100
50
51 #define EFM32_FLASH_BASE 0
52
53 /* size in bytes, not words; must fit all Gecko devices */
54 #define LOCKWORDS_SZ 512
55
56 #define EFM32_MSC_INFO_BASE 0x0fe00000
57
58 #define EFM32_MSC_USER_DATA EFM32_MSC_INFO_BASE
59 #define EFM32_MSC_LOCK_BITS (EFM32_MSC_INFO_BASE+0x4000)
60 #define EFM32_MSC_LOCK_BITS_EXTRA (EFM32_MSC_LOCK_BITS+LOCKWORDS_SZ)
61 #define EFM32_MSC_DEV_INFO (EFM32_MSC_INFO_BASE+0x8000)
62
63 /* PAGE_SIZE is not present in Zero, Happy and the original Gecko MCU */
64 #define EFM32_MSC_DI_PAGE_SIZE (EFM32_MSC_DEV_INFO+0x1e7)
65 #define EFM32_MSC_DI_FLASH_SZ (EFM32_MSC_DEV_INFO+0x1f8)
66 #define EFM32_MSC_DI_RAM_SZ (EFM32_MSC_DEV_INFO+0x1fa)
67 #define EFM32_MSC_DI_PART_NUM (EFM32_MSC_DEV_INFO+0x1fc)
68 #define EFM32_MSC_DI_PART_FAMILY (EFM32_MSC_DEV_INFO+0x1fe)
69 #define EFM32_MSC_DI_PROD_REV (EFM32_MSC_DEV_INFO+0x1ff)
70
71 #define EFM32_MSC_REGBASE 0x400c0000
72 #define EFM32_MSC_REGBASE_SERIES1 0x400e0000
73 #define EFM32_MSC_REG_WRITECTRL 0x008
74 #define EFM32_MSC_WRITECTRL_WREN_MASK 0x1
75 #define EFM32_MSC_REG_WRITECMD 0x00c
76 #define EFM32_MSC_WRITECMD_LADDRIM_MASK 0x1
77 #define EFM32_MSC_WRITECMD_ERASEPAGE_MASK 0x2
78 #define EFM32_MSC_WRITECMD_WRITEONCE_MASK 0x8
79 #define EFM32_MSC_REG_ADDRB 0x010
80 #define EFM32_MSC_REG_WDATA 0x018
81 #define EFM32_MSC_REG_STATUS 0x01c
82 #define EFM32_MSC_STATUS_BUSY_MASK 0x1
83 #define EFM32_MSC_STATUS_LOCKED_MASK 0x2
84 #define EFM32_MSC_STATUS_INVADDR_MASK 0x4
85 #define EFM32_MSC_STATUS_WDATAREADY_MASK 0x8
86 #define EFM32_MSC_STATUS_WORDTIMEOUT_MASK 0x10
87 #define EFM32_MSC_STATUS_ERASEABORTED_MASK 0x20
88 #define EFM32_MSC_REG_LOCK 0x03c
89 #define EFM32_MSC_REG_LOCK_SERIES1 0x040
90 #define EFM32_MSC_LOCK_LOCKKEY 0x1b71
91
92 enum efm32_bank_index {
93 EFM32_BANK_INDEX_MAIN,
94 EFM32_BANK_INDEX_USER_DATA,
95 EFM32_BANK_INDEX_LOCK_BITS,
96 EFM32_N_BANKS
97 };
98
99 static int efm32x_get_bank_index(target_addr_t base)
100 {
101 switch (base) {
102 case EFM32_FLASH_BASE:
103 return EFM32_BANK_INDEX_MAIN;
104 case EFM32_MSC_USER_DATA:
105 return EFM32_BANK_INDEX_USER_DATA;
106 case EFM32_MSC_LOCK_BITS:
107 return EFM32_BANK_INDEX_LOCK_BITS;
108 default:
109 return ERROR_FAIL;
110 }
111 }
112
113 struct efm32_family_data {
114 int family_id;
115 const char *name;
116
117 /* EFM32 series (EFM32LG995F is the "old" series 0, while EFR32MG12P132
118 is the "new" series 1). Determines location of MSC registers. */
119 int series;
120
121 /* Page size in bytes, or 0 to read from EFM32_MSC_DI_PAGE_SIZE */
122 int page_size;
123
124 /* MSC register base address, or 0 to use default */
125 uint32_t msc_regbase;
126 };
127
128 struct efm32_info {
129 const struct efm32_family_data *family_data;
130 uint16_t flash_sz_kib;
131 uint16_t ram_sz_kib;
132 uint16_t part_num;
133 uint8_t part_family;
134 uint8_t prod_rev;
135 uint16_t page_size;
136 };
137
138 struct efm32x_flash_chip {
139 struct efm32_info info;
140 bool probed[EFM32_N_BANKS];
141 uint32_t lb_page[LOCKWORDS_SZ/4];
142 uint32_t reg_base;
143 uint32_t reg_lock;
144 uint32_t refcount;
145 };
146
147 static const struct efm32_family_data efm32_families[] = {
148 { 16, "EFR32MG1P Mighty", .series = 1 },
149 { 17, "EFR32MG1B Mighty", .series = 1 },
150 { 18, "EFR32MG1V Mighty", .series = 1 },
151 { 19, "EFR32BG1P Blue", .series = 1 },
152 { 20, "EFR32BG1B Blue", .series = 1 },
153 { 21, "EFR32BG1V Blue", .series = 1 },
154 { 25, "EFR32FG1P Flex", .series = 1 },
155 { 26, "EFR32FG1B Flex", .series = 1 },
156 { 27, "EFR32FG1V Flex", .series = 1 },
157 { 28, "EFR32MG2P Mighty", .series = 1 },
158 { 29, "EFR32MG2B Mighty", .series = 1 },
159 { 30, "EFR32MG2V Mighty", .series = 1 },
160 { 31, "EFR32BG12P Blue", .series = 1 },
161 { 32, "EFR32BG12B Blue", .series = 1 },
162 { 33, "EFR32BG12V Blue", .series = 1 },
163 { 37, "EFR32FG12P Flex", .series = 1 },
164 { 38, "EFR32FG12B Flex", .series = 1 },
165 { 39, "EFR32FG12V Flex", .series = 1 },
166 { 40, "EFR32MG13P Mighty", .series = 1 },
167 { 41, "EFR32MG13B Mighty", .series = 1 },
168 { 42, "EFR32MG13V Mighty", .series = 1 },
169 { 43, "EFR32BG13P Blue", .series = 1 },
170 { 44, "EFR32BG13B Blue", .series = 1 },
171 { 45, "EFR32BG13V Blue", .series = 1 },
172 { 46, "EFR32ZG13P Zen", .series = 1 },
173 { 49, "EFR32FG13P Flex", .series = 1 },
174 { 50, "EFR32FG13B Flex", .series = 1 },
175 { 51, "EFR32FG13V Flex", .series = 1 },
176 { 52, "EFR32MG14P Mighty", .series = 1 },
177 { 53, "EFR32MG14B Mighty", .series = 1 },
178 { 54, "EFR32MG14V Mighty", .series = 1 },
179 { 55, "EFR32BG14P Blue", .series = 1 },
180 { 56, "EFR32BG14B Blue", .series = 1 },
181 { 57, "EFR32BG14V Blue", .series = 1 },
182 { 58, "EFR32ZG14P Zen", .series = 1 },
183 { 61, "EFR32FG14P Flex", .series = 1 },
184 { 62, "EFR32FG14B Flex", .series = 1 },
185 { 63, "EFR32FG14V Flex", .series = 1 },
186 { 71, "EFM32G", .series = 0, .page_size = 512 },
187 { 72, "EFM32GG Giant", .series = 0 },
188 { 73, "EFM32TG Tiny", .series = 0, .page_size = 512 },
189 { 74, "EFM32LG Leopard", .series = 0 },
190 { 75, "EFM32WG Wonder", .series = 0 },
191 { 76, "EFM32ZG Zero", .series = 0, .page_size = 1024 },
192 { 77, "EFM32HG Happy", .series = 0, .page_size = 1024 },
193 { 81, "EFM32PG1B Pearl", .series = 1 },
194 { 83, "EFM32JG1B Jade", .series = 1 },
195 { 85, "EFM32PG12B Pearl", .series = 1 },
196 { 87, "EFM32JG12B Jade", .series = 1 },
197 { 89, "EFM32PG13B Pearl", .series = 1 },
198 { 91, "EFM32JG13B Jade", .series = 1 },
199 { 100, "EFM32GG11B Giant", .series = 1, .msc_regbase = 0x40000000 },
200 { 103, "EFM32TG11B Tiny", .series = 1, .msc_regbase = 0x40000000 },
201 { 106, "EFM32GG12B Giant", .series = 1, .msc_regbase = 0x40000000 },
202 { 120, "EZR32WG Wonder", .series = 0 },
203 { 121, "EZR32LG Leopard", .series = 0 },
204 { 122, "EZR32HG Happy", .series = 0, .page_size = 1024 },
205 };
206
207 const struct flash_driver efm32_flash;
208
209 static int efm32x_priv_write(struct flash_bank *bank, const uint8_t *buffer,
210 uint32_t addr, uint32_t count);
211
212 static int efm32x_write_only_lockbits(struct flash_bank *bank);
213
214 static int efm32x_get_flash_size(struct flash_bank *bank, uint16_t *flash_sz)
215 {
216 return target_read_u16(bank->target, EFM32_MSC_DI_FLASH_SZ, flash_sz);
217 }
218
219 static int efm32x_get_ram_size(struct flash_bank *bank, uint16_t *ram_sz)
220 {
221 return target_read_u16(bank->target, EFM32_MSC_DI_RAM_SZ, ram_sz);
222 }
223
224 static int efm32x_get_part_num(struct flash_bank *bank, uint16_t *pnum)
225 {
226 return target_read_u16(bank->target, EFM32_MSC_DI_PART_NUM, pnum);
227 }
228
229 static int efm32x_get_part_family(struct flash_bank *bank, uint8_t *pfamily)
230 {
231 return target_read_u8(bank->target, EFM32_MSC_DI_PART_FAMILY, pfamily);
232 }
233
234 static int efm32x_get_prod_rev(struct flash_bank *bank, uint8_t *prev)
235 {
236 return target_read_u8(bank->target, EFM32_MSC_DI_PROD_REV, prev);
237 }
238
239 static int efm32x_read_reg_u32(struct flash_bank *bank, target_addr_t offset,
240 uint32_t *value)
241 {
242 struct efm32x_flash_chip *efm32x_info = bank->driver_priv;
243 uint32_t base = efm32x_info->reg_base;
244
245 return target_read_u32(bank->target, base + offset, value);
246 }
247
248 static int efm32x_write_reg_u32(struct flash_bank *bank, target_addr_t offset,
249 uint32_t value)
250 {
251 struct efm32x_flash_chip *efm32x_info = bank->driver_priv;
252 uint32_t base = efm32x_info->reg_base;
253
254 return target_write_u32(bank->target, base + offset, value);
255 }
256
257 static int efm32x_read_info(struct flash_bank *bank)
258 {
259 int ret;
260 struct efm32x_flash_chip *efm32x_info = bank->driver_priv;
261 struct efm32_info *efm32_info = &(efm32x_info->info);
262
263 memset(efm32_info, 0, sizeof(struct efm32_info));
264
265 const struct cortex_m_common *cortex_m = target_to_cm(bank->target);
266
267 switch (cortex_m->core_info->partno) {
268 case CORTEX_M3_PARTNO:
269 case CORTEX_M4_PARTNO:
270 case CORTEX_M0P_PARTNO:
271 break;
272 default:
273 LOG_ERROR("Target is not Cortex-Mx Device");
274 return ERROR_FAIL;
275 }
276
277 ret = efm32x_get_flash_size(bank, &(efm32_info->flash_sz_kib));
278 if (ret != ERROR_OK)
279 return ret;
280
281 ret = efm32x_get_ram_size(bank, &(efm32_info->ram_sz_kib));
282 if (ret != ERROR_OK)
283 return ret;
284
285 ret = efm32x_get_part_num(bank, &(efm32_info->part_num));
286 if (ret != ERROR_OK)
287 return ret;
288
289 ret = efm32x_get_part_family(bank, &(efm32_info->part_family));
290 if (ret != ERROR_OK)
291 return ret;
292
293 ret = efm32x_get_prod_rev(bank, &(efm32_info->prod_rev));
294 if (ret != ERROR_OK)
295 return ret;
296
297 for (size_t i = 0; i < ARRAY_SIZE(efm32_families); i++) {
298 if (efm32_families[i].family_id == efm32_info->part_family)
299 efm32_info->family_data = &efm32_families[i];
300 }
301
302 if (!efm32_info->family_data) {
303 LOG_ERROR("Unknown MCU family %d", efm32_info->part_family);
304 return ERROR_FAIL;
305 }
306
307 switch (efm32_info->family_data->series) {
308 case 0:
309 efm32x_info->reg_base = EFM32_MSC_REGBASE;
310 efm32x_info->reg_lock = EFM32_MSC_REG_LOCK;
311 break;
312 case 1:
313 efm32x_info->reg_base = EFM32_MSC_REGBASE_SERIES1;
314 efm32x_info->reg_lock = EFM32_MSC_REG_LOCK_SERIES1;
315 break;
316 }
317
318 if (efm32_info->family_data->msc_regbase != 0)
319 efm32x_info->reg_base = efm32_info->family_data->msc_regbase;
320
321 if (efm32_info->family_data->page_size != 0) {
322 efm32_info->page_size = efm32_info->family_data->page_size;
323 } else {
324 uint8_t pg_size = 0;
325 ret = target_read_u8(bank->target, EFM32_MSC_DI_PAGE_SIZE,
326 &pg_size);
327 if (ret != ERROR_OK)
328 return ret;
329
330 efm32_info->page_size = (1 << ((pg_size+10) & 0xff));
331
332 if (efm32_info->part_family == EFM_FAMILY_ID_GIANT_GECKO ||
333 efm32_info->part_family == EFM_FAMILY_ID_LEOPARD_GECKO) {
334 /* Giant or Leopard Gecko */
335 if (efm32_info->prod_rev < 18) {
336 /* EFM32 GG/LG errata: MEM_INFO_PAGE_SIZE is invalid
337 for MCUs with PROD_REV < 18 */
338 if (efm32_info->flash_sz_kib < 512)
339 efm32_info->page_size = 2048;
340 else
341 efm32_info->page_size = 4096;
342 }
343 }
344
345 if ((efm32_info->page_size != 2048) &&
346 (efm32_info->page_size != 4096)) {
347 LOG_ERROR("Invalid page size %u", efm32_info->page_size);
348 return ERROR_FAIL;
349 }
350 }
351
352 return ERROR_OK;
353 }
354
355 /* flash bank efm32 <base> <size> 0 0 <target#> */
356 FLASH_BANK_COMMAND_HANDLER(efm32x_flash_bank_command)
357 {
358 struct efm32x_flash_chip *efm32x_info = NULL;
359
360 if (CMD_ARGC < 6)
361 return ERROR_COMMAND_SYNTAX_ERROR;
362
363 int bank_index = efm32x_get_bank_index(bank->base);
364 if (bank_index < 0) {
365 LOG_ERROR("Flash bank with base address %" PRIx32 " is not supported",
366 (uint32_t) bank->base);
367 return ERROR_FAIL;
368 }
369
370 /* look for an existing flash structure matching target */
371 for (struct flash_bank *bank_iter = flash_bank_list(); bank_iter; bank_iter = bank_iter->next) {
372 if (bank_iter->driver == &efm32_flash
373 && bank_iter->target == bank->target
374 && bank->driver_priv) {
375 efm32x_info = bank->driver_priv;
376 break;
377 }
378 }
379
380 if (!efm32x_info) {
381 /* target not matched, make a new one */
382 efm32x_info = calloc(1, sizeof(struct efm32x_flash_chip));
383
384 memset(efm32x_info->lb_page, 0xff, LOCKWORDS_SZ);
385 }
386
387 ++efm32x_info->refcount;
388 bank->driver_priv = efm32x_info;
389
390 return ERROR_OK;
391 }
392
393 /**
394 * Remove flash structure corresponding to this bank,
395 * if and only if it's not used by any others
396 */
397 static void efm32x_free_driver_priv(struct flash_bank *bank)
398 {
399 struct efm32x_flash_chip *efm32x_info = bank->driver_priv;
400
401 if (efm32x_info) {
402 /* Use ref count to determine if it can be freed; scanning bank list doesn't work,
403 * because this function can be called after some banks in the list have been
404 * already destroyed */
405 --efm32x_info->refcount;
406 if (efm32x_info->refcount == 0) {
407 free(efm32x_info);
408 bank->driver_priv = NULL;
409 }
410 }
411 }
412
413 /* set or reset given bits in a register */
414 static int efm32x_set_reg_bits(struct flash_bank *bank, uint32_t reg,
415 uint32_t bitmask, int set)
416 {
417 int ret = 0;
418 uint32_t reg_val = 0;
419
420 ret = efm32x_read_reg_u32(bank, reg, &reg_val);
421 if (ret != ERROR_OK)
422 return ret;
423
424 if (set)
425 reg_val |= bitmask;
426 else
427 reg_val &= ~bitmask;
428
429 return efm32x_write_reg_u32(bank, reg, reg_val);
430 }
431
432 static int efm32x_set_wren(struct flash_bank *bank, int write_enable)
433 {
434 return efm32x_set_reg_bits(bank, EFM32_MSC_REG_WRITECTRL,
435 EFM32_MSC_WRITECTRL_WREN_MASK, write_enable);
436 }
437
438 static int efm32x_msc_lock(struct flash_bank *bank, int lock)
439 {
440 struct efm32x_flash_chip *efm32x_info = bank->driver_priv;
441 return efm32x_write_reg_u32(bank, efm32x_info->reg_lock,
442 (lock ? 0 : EFM32_MSC_LOCK_LOCKKEY));
443 }
444
445 static int efm32x_wait_status(struct flash_bank *bank, int timeout,
446 uint32_t wait_mask, int wait_for_set)
447 {
448 int ret = 0;
449 uint32_t status = 0;
450
451 while (1) {
452 ret = efm32x_read_reg_u32(bank, EFM32_MSC_REG_STATUS, &status);
453 if (ret != ERROR_OK)
454 break;
455
456 LOG_DEBUG("status: 0x%" PRIx32 "", status);
457
458 if (((status & wait_mask) == 0) && (wait_for_set == 0))
459 break;
460 else if (((status & wait_mask) != 0) && wait_for_set)
461 break;
462
463 if (timeout-- <= 0) {
464 LOG_ERROR("timed out waiting for MSC status");
465 return ERROR_FAIL;
466 }
467
468 alive_sleep(1);
469 }
470
471 if (status & EFM32_MSC_STATUS_ERASEABORTED_MASK)
472 LOG_WARNING("page erase was aborted");
473
474 return ret;
475 }
476
477 static int efm32x_erase_page(struct flash_bank *bank, uint32_t addr)
478 {
479 /* this function DOES NOT set WREN; must be set already */
480 /* 1. write address to ADDRB
481 2. write LADDRIM
482 3. check status (INVADDR, LOCKED)
483 4. write ERASEPAGE
484 5. wait until !STATUS_BUSY
485 */
486 int ret = 0;
487 uint32_t status = 0;
488 LOG_DEBUG("erasing flash page at 0x%08" PRIx32, addr);
489
490 ret = efm32x_write_reg_u32(bank, EFM32_MSC_REG_ADDRB, addr);
491 if (ret != ERROR_OK)
492 return ret;
493
494 ret = efm32x_set_reg_bits(bank, EFM32_MSC_REG_WRITECMD,
495 EFM32_MSC_WRITECMD_LADDRIM_MASK, 1);
496 if (ret != ERROR_OK)
497 return ret;
498
499 ret = efm32x_read_reg_u32(bank, EFM32_MSC_REG_STATUS, &status);
500 if (ret != ERROR_OK)
501 return ret;
502
503 LOG_DEBUG("status 0x%" PRIx32, status);
504
505 if (status & EFM32_MSC_STATUS_LOCKED_MASK) {
506 LOG_ERROR("Page is locked");
507 return ERROR_FAIL;
508 } else if (status & EFM32_MSC_STATUS_INVADDR_MASK) {
509 LOG_ERROR("Invalid address 0x%" PRIx32, addr);
510 return ERROR_FAIL;
511 }
512
513 ret = efm32x_set_reg_bits(bank, EFM32_MSC_REG_WRITECMD,
514 EFM32_MSC_WRITECMD_ERASEPAGE_MASK, 1);
515 if (ret != ERROR_OK)
516 return ret;
517
518 return efm32x_wait_status(bank, EFM32_FLASH_ERASE_TMO,
519 EFM32_MSC_STATUS_BUSY_MASK, 0);
520 }
521
522 static int efm32x_erase(struct flash_bank *bank, unsigned int first,
523 unsigned int last)
524 {
525 struct target *target = bank->target;
526 int ret = 0;
527
528 if (target->state != TARGET_HALTED) {
529 LOG_ERROR("Target not halted");
530 return ERROR_TARGET_NOT_HALTED;
531 }
532
533 efm32x_msc_lock(bank, 0);
534 ret = efm32x_set_wren(bank, 1);
535 if (ret != ERROR_OK) {
536 LOG_ERROR("Failed to enable MSC write");
537 return ret;
538 }
539
540 for (unsigned int i = first; i <= last; i++) {
541 ret = efm32x_erase_page(bank, bank->base + bank->sectors[i].offset);
542 if (ret != ERROR_OK)
543 LOG_ERROR("Failed to erase page %d", i);
544 }
545
546 ret = efm32x_set_wren(bank, 0);
547 efm32x_msc_lock(bank, 1);
548 if (ret != ERROR_OK)
549 return ret;
550
551 if (bank->base == EFM32_MSC_LOCK_BITS) {
552 ret = efm32x_write_only_lockbits(bank);
553 if (ret != ERROR_OK)
554 LOG_ERROR("Failed to restore lockbits after erase");
555 }
556
557 return ret;
558 }
559
560 static int efm32x_read_lock_data(struct flash_bank *bank)
561 {
562 struct efm32x_flash_chip *efm32x_info = bank->driver_priv;
563 struct target *target = bank->target;
564 int data_size = 0;
565 uint32_t *ptr = NULL;
566 int ret = 0;
567
568 assert(bank->num_sectors > 0);
569
570 /* calculate the number of 32-bit words to read (one lock bit per sector) */
571 data_size = (bank->num_sectors + 31) / 32;
572
573 ptr = efm32x_info->lb_page;
574
575 for (int i = 0; i < data_size; i++, ptr++) {
576 ret = target_read_u32(target, EFM32_MSC_LOCK_BITS+i*4, ptr);
577 if (ret != ERROR_OK) {
578 LOG_ERROR("Failed to read PLW %d", i);
579 return ret;
580 }
581 }
582
583 /* also, read ULW, DLW, MLW, ALW and CLW words */
584
585 /* ULW, word 126 */
586 ptr = efm32x_info->lb_page + 126;
587 ret = target_read_u32(target, EFM32_MSC_LOCK_BITS+126*4, ptr);
588 if (ret != ERROR_OK) {
589 LOG_ERROR("Failed to read ULW");
590 return ret;
591 }
592
593 /* DLW, word 127 */
594 ptr = efm32x_info->lb_page + 127;
595 ret = target_read_u32(target, EFM32_MSC_LOCK_BITS+127*4, ptr);
596 if (ret != ERROR_OK) {
597 LOG_ERROR("Failed to read DLW");
598 return ret;
599 }
600
601 /* MLW, word 125, present in GG, LG, PG, JG, EFR32 */
602 ptr = efm32x_info->lb_page + 125;
603 ret = target_read_u32(target, EFM32_MSC_LOCK_BITS+125*4, ptr);
604 if (ret != ERROR_OK) {
605 LOG_ERROR("Failed to read MLW");
606 return ret;
607 }
608
609 /* ALW, word 124, present in GG, LG, PG, JG, EFR32 */
610 ptr = efm32x_info->lb_page + 124;
611 ret = target_read_u32(target, EFM32_MSC_LOCK_BITS+124*4, ptr);
612 if (ret != ERROR_OK) {
613 LOG_ERROR("Failed to read ALW");
614 return ret;
615 }
616
617 /* CLW1, word 123, present in EFR32 */
618 ptr = efm32x_info->lb_page + 123;
619 ret = target_read_u32(target, EFM32_MSC_LOCK_BITS+123*4, ptr);
620 if (ret != ERROR_OK) {
621 LOG_ERROR("Failed to read CLW1");
622 return ret;
623 }
624
625 /* CLW0, word 122, present in GG, LG, PG, JG, EFR32 */
626 ptr = efm32x_info->lb_page + 122;
627 ret = target_read_u32(target, EFM32_MSC_LOCK_BITS+122*4, ptr);
628 if (ret != ERROR_OK) {
629 LOG_ERROR("Failed to read CLW0");
630 return ret;
631 }
632
633 return ERROR_OK;
634 }
635
636 static int efm32x_write_only_lockbits(struct flash_bank *bank)
637 {
638 struct efm32x_flash_chip *efm32x_info = bank->driver_priv;
639 return efm32x_priv_write(bank, (uint8_t *)efm32x_info->lb_page, EFM32_MSC_LOCK_BITS, LOCKWORDS_SZ);
640 }
641
642 static int efm32x_write_lock_data(struct flash_bank *bank)
643 {
644 struct efm32x_flash_chip *efm32x_info = bank->driver_priv;
645 int ret = 0;
646
647 /* Preserve any data written to the high portion of the lockbits page */
648 assert(efm32x_info->info.page_size >= LOCKWORDS_SZ);
649 uint32_t extra_bytes = efm32x_info->info.page_size - LOCKWORDS_SZ;
650 uint8_t *extra_data = NULL;
651 if (extra_bytes) {
652 extra_data = malloc(extra_bytes);
653 ret = target_read_buffer(bank->target, EFM32_MSC_LOCK_BITS_EXTRA, extra_bytes, extra_data);
654 if (ret != ERROR_OK) {
655 LOG_ERROR("Failed to read extra contents of LB page");
656 free(extra_data);
657 return ret;
658 }
659 }
660
661 ret = efm32x_erase_page(bank, EFM32_MSC_LOCK_BITS);
662 if (ret != ERROR_OK) {
663 LOG_ERROR("Failed to erase LB page");
664 if (extra_data)
665 free(extra_data);
666 return ret;
667 }
668
669 if (extra_data) {
670 ret = efm32x_priv_write(bank, extra_data, EFM32_MSC_LOCK_BITS_EXTRA, extra_bytes);
671 free(extra_data);
672 if (ret != ERROR_OK) {
673 LOG_ERROR("Failed to restore extra contents of LB page");
674 return ret;
675 }
676 }
677
678 return efm32x_write_only_lockbits(bank);
679 }
680
681 static int efm32x_get_page_lock(struct flash_bank *bank, size_t page)
682 {
683 struct efm32x_flash_chip *efm32x_info = bank->driver_priv;
684 uint32_t dw = 0;
685 uint32_t mask = 0;
686
687 switch (bank->base) {
688 case EFM32_FLASH_BASE:
689 dw = efm32x_info->lb_page[page >> 5];
690 mask = 1 << (page & 0x1f);
691 break;
692 case EFM32_MSC_USER_DATA:
693 dw = efm32x_info->lb_page[126];
694 mask = 0x1;
695 break;
696 case EFM32_MSC_LOCK_BITS:
697 dw = efm32x_info->lb_page[126];
698 mask = 0x2;
699 break;
700 }
701
702 return (dw & mask) ? 0 : 1;
703 }
704
705 static int efm32x_set_page_lock(struct flash_bank *bank, size_t page, int set)
706 {
707 struct efm32x_flash_chip *efm32x_info = bank->driver_priv;
708
709 if (bank->base != EFM32_FLASH_BASE) {
710 LOG_ERROR("Locking user and lockbits pages is not supported yet");
711 return ERROR_FAIL;
712 }
713
714 uint32_t *dw = &efm32x_info->lb_page[page >> 5];
715 uint32_t mask = 0;
716
717 mask = 1 << (page & 0x1f);
718
719 if (!set)
720 *dw |= mask;
721 else
722 *dw &= ~mask;
723
724 return ERROR_OK;
725 }
726
727 static int efm32x_protect(struct flash_bank *bank, int set, unsigned int first,
728 unsigned int last)
729 {
730 struct target *target = bank->target;
731 int ret = 0;
732
733 if (target->state != TARGET_HALTED) {
734 LOG_ERROR("Target not halted");
735 return ERROR_TARGET_NOT_HALTED;
736 }
737
738 for (unsigned int i = first; i <= last; i++) {
739 ret = efm32x_set_page_lock(bank, i, set);
740 if (ret != ERROR_OK) {
741 LOG_ERROR("Failed to set lock on page %d", i);
742 return ret;
743 }
744 }
745
746 ret = efm32x_write_lock_data(bank);
747 if (ret != ERROR_OK) {
748 LOG_ERROR("Failed to write LB page");
749 return ret;
750 }
751
752 return ERROR_OK;
753 }
754
755 static int efm32x_write_block(struct flash_bank *bank, const uint8_t *buf,
756 uint32_t address, uint32_t count)
757 {
758 struct target *target = bank->target;
759 uint32_t buffer_size = 16384;
760 struct working_area *write_algorithm;
761 struct working_area *source;
762 struct reg_param reg_params[5];
763 struct armv7m_algorithm armv7m_info;
764 struct efm32x_flash_chip *efm32x_info = bank->driver_priv;
765 int ret = ERROR_OK;
766
767 /* see contrib/loaders/flash/efm32.S for src */
768 static const uint8_t efm32x_flash_write_code[] = {
769 /* #define EFM32_MSC_WRITECTRL_OFFSET 0x008 */
770 /* #define EFM32_MSC_WRITECMD_OFFSET 0x00c */
771 /* #define EFM32_MSC_ADDRB_OFFSET 0x010 */
772 /* #define EFM32_MSC_WDATA_OFFSET 0x018 */
773 /* #define EFM32_MSC_STATUS_OFFSET 0x01c */
774
775 0x01, 0x26, /* movs r6, #1 */
776 0x86, 0x60, /* str r6, [r0, #EFM32_MSC_WRITECTRL_OFFSET] */
777
778 /* wait_fifo: */
779 0x16, 0x68, /* ldr r6, [r2, #0] */
780 0x00, 0x2e, /* cmp r6, #0 */
781 0x22, 0xd0, /* beq exit */
782 0x55, 0x68, /* ldr r5, [r2, #4] */
783 0xb5, 0x42, /* cmp r5, r6 */
784 0xf9, 0xd0, /* beq wait_fifo */
785
786 0x04, 0x61, /* str r4, [r0, #EFM32_MSC_ADDRB_OFFSET] */
787 0x01, 0x26, /* movs r6, #1 */
788 0xc6, 0x60, /* str r6, [r0, #EFM32_MSC_WRITECMD_OFFSET] */
789 0xc6, 0x69, /* ldr r6, [r0, #EFM32_MSC_STATUS_OFFSET] */
790 0x06, 0x27, /* movs r7, #6 */
791 0x3e, 0x42, /* tst r6, r7 */
792 0x16, 0xd1, /* bne error */
793
794 /* wait_wdataready: */
795 0xc6, 0x69, /* ldr r6, [r0, #EFM32_MSC_STATUS_OFFSET] */
796 0x08, 0x27, /* movs r7, #8 */
797 0x3e, 0x42, /* tst r6, r7 */
798 0xfb, 0xd0, /* beq wait_wdataready */
799
800 0x2e, 0x68, /* ldr r6, [r5] */
801 0x86, 0x61, /* str r6, [r0, #EFM32_MSC_WDATA_OFFSET] */
802 0x08, 0x26, /* movs r6, #8 */
803 0xc6, 0x60, /* str r6, [r0, #EFM32_MSC_WRITECMD_OFFSET] */
804
805 0x04, 0x35, /* adds r5, #4 */
806 0x04, 0x34, /* adds r4, #4 */
807
808 /* busy: */
809 0xc6, 0x69, /* ldr r6, [r0, #EFM32_MSC_STATUS_OFFSET] */
810 0x01, 0x27, /* movs r7, #1 */
811 0x3e, 0x42, /* tst r6, r7 */
812 0xfb, 0xd1, /* bne busy */
813
814 0x9d, 0x42, /* cmp r5, r3 */
815 0x01, 0xd3, /* bcc no_wrap */
816 0x15, 0x46, /* mov r5, r2 */
817 0x08, 0x35, /* adds r5, #8 */
818
819 /* no_wrap: */
820 0x55, 0x60, /* str r5, [r2, #4] */
821 0x01, 0x39, /* subs r1, r1, #1 */
822 0x00, 0x29, /* cmp r1, #0 */
823 0x02, 0xd0, /* beq exit */
824 0xdb, 0xe7, /* b wait_fifo */
825
826 /* error: */
827 0x00, 0x20, /* movs r0, #0 */
828 0x50, 0x60, /* str r0, [r2, #4] */
829
830 /* exit: */
831 0x30, 0x46, /* mov r0, r6 */
832 0x00, 0xbe, /* bkpt #0 */
833 };
834
835
836 /* flash write code */
837 if (target_alloc_working_area(target, sizeof(efm32x_flash_write_code),
838 &write_algorithm) != ERROR_OK) {
839 LOG_WARNING("no working area available, can't do block memory writes");
840 return ERROR_TARGET_RESOURCE_NOT_AVAILABLE;
841 }
842
843 ret = target_write_buffer(target, write_algorithm->address,
844 sizeof(efm32x_flash_write_code), efm32x_flash_write_code);
845 if (ret != ERROR_OK)
846 return ret;
847
848 /* memory buffer */
849 while (target_alloc_working_area_try(target, buffer_size, &source) != ERROR_OK) {
850 buffer_size /= 2;
851 buffer_size &= ~3UL; /* Make sure it's 4 byte aligned */
852 if (buffer_size <= 256) {
853 /* we already allocated the writing code, but failed to get a
854 * buffer, free the algorithm */
855 target_free_working_area(target, write_algorithm);
856
857 LOG_WARNING("no large enough working area available, can't do block memory writes");
858 return ERROR_TARGET_RESOURCE_NOT_AVAILABLE;
859 }
860 }
861
862 init_reg_param(&reg_params[0], "r0", 32, PARAM_IN_OUT); /* flash base (in), status (out) */
863 init_reg_param(&reg_params[1], "r1", 32, PARAM_OUT); /* count (word-32bit) */
864 init_reg_param(&reg_params[2], "r2", 32, PARAM_OUT); /* buffer start */
865 init_reg_param(&reg_params[3], "r3", 32, PARAM_OUT); /* buffer end */
866 init_reg_param(&reg_params[4], "r4", 32, PARAM_IN_OUT); /* target address */
867
868 buf_set_u32(reg_params[0].value, 0, 32, efm32x_info->reg_base);
869 buf_set_u32(reg_params[1].value, 0, 32, count);
870 buf_set_u32(reg_params[2].value, 0, 32, source->address);
871 buf_set_u32(reg_params[3].value, 0, 32, source->address + source->size);
872 buf_set_u32(reg_params[4].value, 0, 32, address);
873
874 armv7m_info.common_magic = ARMV7M_COMMON_MAGIC;
875 armv7m_info.core_mode = ARM_MODE_THREAD;
876
877 ret = target_run_flash_async_algorithm(target, buf, count, 4,
878 0, NULL,
879 5, reg_params,
880 source->address, source->size,
881 write_algorithm->address, 0,
882 &armv7m_info);
883
884 if (ret == ERROR_FLASH_OPERATION_FAILED) {
885 LOG_ERROR("flash write failed at address 0x%"PRIx32,
886 buf_get_u32(reg_params[4].value, 0, 32));
887
888 if (buf_get_u32(reg_params[0].value, 0, 32) &
889 EFM32_MSC_STATUS_LOCKED_MASK) {
890 LOG_ERROR("flash memory write protected");
891 }
892
893 if (buf_get_u32(reg_params[0].value, 0, 32) &
894 EFM32_MSC_STATUS_INVADDR_MASK) {
895 LOG_ERROR("invalid flash memory write address");
896 }
897 }
898
899 target_free_working_area(target, source);
900 target_free_working_area(target, write_algorithm);
901
902 destroy_reg_param(&reg_params[0]);
903 destroy_reg_param(&reg_params[1]);
904 destroy_reg_param(&reg_params[2]);
905 destroy_reg_param(&reg_params[3]);
906 destroy_reg_param(&reg_params[4]);
907
908 return ret;
909 }
910
911 static int efm32x_write_word(struct flash_bank *bank, uint32_t addr,
912 uint32_t val)
913 {
914 /* this function DOES NOT set WREN; must be set already */
915 /* 1. write address to ADDRB
916 2. write LADDRIM
917 3. check status (INVADDR, LOCKED)
918 4. wait for WDATAREADY
919 5. write data to WDATA
920 6. write WRITECMD_WRITEONCE to WRITECMD
921 7. wait until !STATUS_BUSY
922 */
923
924 /* FIXME: EFM32G ref states (7.3.2) that writes should be
925 * performed twice per dword */
926
927 int ret = 0;
928 uint32_t status = 0;
929
930 /* if not called, GDB errors will be reported during large writes */
931 keep_alive();
932
933 ret = efm32x_write_reg_u32(bank, EFM32_MSC_REG_ADDRB, addr);
934 if (ret != ERROR_OK)
935 return ret;
936
937 ret = efm32x_set_reg_bits(bank, EFM32_MSC_REG_WRITECMD,
938 EFM32_MSC_WRITECMD_LADDRIM_MASK, 1);
939 if (ret != ERROR_OK)
940 return ret;
941
942 ret = efm32x_read_reg_u32(bank, EFM32_MSC_REG_STATUS, &status);
943 if (ret != ERROR_OK)
944 return ret;
945
946 LOG_DEBUG("status 0x%" PRIx32, status);
947
948 if (status & EFM32_MSC_STATUS_LOCKED_MASK) {
949 LOG_ERROR("Page is locked");
950 return ERROR_FAIL;
951 } else if (status & EFM32_MSC_STATUS_INVADDR_MASK) {
952 LOG_ERROR("Invalid address 0x%" PRIx32, addr);
953 return ERROR_FAIL;
954 }
955
956 ret = efm32x_wait_status(bank, EFM32_FLASH_WDATAREADY_TMO,
957 EFM32_MSC_STATUS_WDATAREADY_MASK, 1);
958 if (ret != ERROR_OK) {
959 LOG_ERROR("Wait for WDATAREADY failed");
960 return ret;
961 }
962
963 ret = efm32x_write_reg_u32(bank, EFM32_MSC_REG_WDATA, val);
964 if (ret != ERROR_OK) {
965 LOG_ERROR("WDATA write failed");
966 return ret;
967 }
968
969 ret = efm32x_write_reg_u32(bank, EFM32_MSC_REG_WRITECMD,
970 EFM32_MSC_WRITECMD_WRITEONCE_MASK);
971 if (ret != ERROR_OK) {
972 LOG_ERROR("WRITECMD write failed");
973 return ret;
974 }
975
976 ret = efm32x_wait_status(bank, EFM32_FLASH_WRITE_TMO,
977 EFM32_MSC_STATUS_BUSY_MASK, 0);
978 if (ret != ERROR_OK) {
979 LOG_ERROR("Wait for BUSY failed");
980 return ret;
981 }
982
983 return ERROR_OK;
984 }
985
986 static int efm32x_priv_write(struct flash_bank *bank, const uint8_t *buffer,
987 uint32_t addr, uint32_t count)
988 {
989 struct target *target = bank->target;
990 uint8_t *new_buffer = NULL;
991
992 if (target->state != TARGET_HALTED) {
993 LOG_ERROR("Target not halted");
994 return ERROR_TARGET_NOT_HALTED;
995 }
996
997 if (addr & 0x3) {
998 LOG_ERROR("addr 0x%" PRIx32 " breaks required 4-byte "
999 "alignment", addr);
1000 return ERROR_FLASH_DST_BREAKS_ALIGNMENT;
1001 }
1002
1003 if (count & 0x3) {
1004 uint32_t old_count = count;
1005 count = (old_count | 3) + 1;
1006 new_buffer = malloc(count);
1007 if (!new_buffer) {
1008 LOG_ERROR("odd number of bytes to write and no memory "
1009 "for padding buffer");
1010 return ERROR_FAIL;
1011 }
1012 LOG_INFO("odd number of bytes to write (%" PRIu32 "), extending to %" PRIu32 " "
1013 "and padding with 0xff", old_count, count);
1014 memset(new_buffer, 0xff, count);
1015 buffer = memcpy(new_buffer, buffer, old_count);
1016 }
1017
1018 uint32_t words_remaining = count / 4;
1019 int retval, retval2;
1020
1021 /* unlock flash registers */
1022 efm32x_msc_lock(bank, 0);
1023 retval = efm32x_set_wren(bank, 1);
1024 if (retval != ERROR_OK)
1025 goto cleanup;
1026
1027 /* try using a block write */
1028 retval = efm32x_write_block(bank, buffer, addr, words_remaining);
1029
1030 if (retval == ERROR_TARGET_RESOURCE_NOT_AVAILABLE) {
1031 /* if block write failed (no sufficient working area),
1032 * we use normal (slow) single word accesses */
1033 LOG_WARNING("couldn't use block writes, falling back to single "
1034 "memory accesses");
1035
1036 while (words_remaining > 0) {
1037 uint32_t value;
1038 memcpy(&value, buffer, sizeof(uint32_t));
1039
1040 retval = efm32x_write_word(bank, addr, value);
1041 if (retval != ERROR_OK)
1042 goto reset_pg_and_lock;
1043
1044 words_remaining--;
1045 buffer += 4;
1046 addr += 4;
1047 }
1048 }
1049
1050 reset_pg_and_lock:
1051 retval2 = efm32x_set_wren(bank, 0);
1052 efm32x_msc_lock(bank, 1);
1053 if (retval == ERROR_OK)
1054 retval = retval2;
1055
1056 cleanup:
1057 free(new_buffer);
1058 return retval;
1059 }
1060
1061 static int efm32x_write(struct flash_bank *bank, const uint8_t *buffer,
1062 uint32_t offset, uint32_t count)
1063 {
1064 if (bank->base == EFM32_MSC_LOCK_BITS && offset < LOCKWORDS_SZ) {
1065 LOG_ERROR("Cannot write to lock words");
1066 return ERROR_FAIL;
1067 }
1068 return efm32x_priv_write(bank, buffer, bank->base + offset, count);
1069 }
1070
1071 static int efm32x_probe(struct flash_bank *bank)
1072 {
1073 struct efm32x_flash_chip *efm32x_info = bank->driver_priv;
1074 struct efm32_info *efm32_mcu_info = &(efm32x_info->info);
1075 int ret;
1076
1077 int bank_index = efm32x_get_bank_index(bank->base);
1078 assert(bank_index >= 0);
1079
1080 efm32x_info->probed[bank_index] = false;
1081 memset(efm32x_info->lb_page, 0xff, LOCKWORDS_SZ);
1082
1083 ret = efm32x_read_info(bank);
1084 if (ret != ERROR_OK)
1085 return ret;
1086
1087 LOG_INFO("detected part: %s Gecko, rev %d",
1088 efm32_mcu_info->family_data->name, efm32_mcu_info->prod_rev);
1089 LOG_INFO("flash size = %dkbytes", efm32_mcu_info->flash_sz_kib);
1090 LOG_INFO("flash page size = %dbytes", efm32_mcu_info->page_size);
1091
1092 assert(efm32_mcu_info->page_size != 0);
1093
1094 free(bank->sectors);
1095 bank->sectors = NULL;
1096
1097 if (bank->base == EFM32_FLASH_BASE) {
1098 bank->num_sectors = efm32_mcu_info->flash_sz_kib * 1024 /
1099 efm32_mcu_info->page_size;
1100 assert(bank->num_sectors > 0);
1101
1102 ret = efm32x_read_lock_data(bank);
1103 if (ret != ERROR_OK) {
1104 LOG_ERROR("Failed to read LB data");
1105 return ret;
1106 }
1107 } else
1108 bank->num_sectors = 1;
1109 bank->size = bank->num_sectors * efm32_mcu_info->page_size;
1110 bank->sectors = malloc(sizeof(struct flash_sector) * bank->num_sectors);
1111
1112 for (uint32_t i = 0; i < bank->num_sectors; i++) {
1113 bank->sectors[i].offset = i * efm32_mcu_info->page_size;
1114 bank->sectors[i].size = efm32_mcu_info->page_size;
1115 bank->sectors[i].is_erased = -1;
1116 bank->sectors[i].is_protected = 1;
1117 }
1118
1119 efm32x_info->probed[bank_index] = true;
1120
1121 return ERROR_OK;
1122 }
1123
1124 static int efm32x_auto_probe(struct flash_bank *bank)
1125 {
1126 struct efm32x_flash_chip *efm32x_info = bank->driver_priv;
1127
1128 int bank_index = efm32x_get_bank_index(bank->base);
1129 assert(bank_index >= 0);
1130
1131 if (efm32x_info->probed[bank_index])
1132 return ERROR_OK;
1133 return efm32x_probe(bank);
1134 }
1135
1136 static int efm32x_protect_check(struct flash_bank *bank)
1137 {
1138 struct target *target = bank->target;
1139 int ret = 0;
1140
1141 if (target->state != TARGET_HALTED) {
1142 LOG_ERROR("Target not halted");
1143 return ERROR_TARGET_NOT_HALTED;
1144 }
1145
1146 ret = efm32x_read_lock_data(bank);
1147 if (ret != ERROR_OK) {
1148 LOG_ERROR("Failed to read LB data");
1149 return ret;
1150 }
1151
1152 assert(bank->sectors);
1153
1154 for (unsigned int i = 0; i < bank->num_sectors; i++)
1155 bank->sectors[i].is_protected = efm32x_get_page_lock(bank, i);
1156
1157 return ERROR_OK;
1158 }
1159
1160 static int get_efm32x_info(struct flash_bank *bank, struct command_invocation *cmd)
1161 {
1162 struct efm32x_flash_chip *efm32x_info = bank->driver_priv;
1163 int ret;
1164
1165 ret = efm32x_read_info(bank);
1166 if (ret != ERROR_OK) {
1167 LOG_ERROR("Failed to read EFM32 info");
1168 return ret;
1169 }
1170
1171 command_print_sameline(cmd, "%s Gecko, rev %d", efm32x_info->info.family_data->name,
1172 efm32x_info->info.prod_rev);
1173 return ERROR_OK;
1174 }
1175
1176 COMMAND_HANDLER(efm32x_handle_debuglock_command)
1177 {
1178 struct target *target = NULL;
1179
1180 if (CMD_ARGC < 1)
1181 return ERROR_COMMAND_SYNTAX_ERROR;
1182
1183 struct flash_bank *bank;
1184 int retval = CALL_COMMAND_HANDLER(flash_command_get_bank, 0, &bank);
1185 if (retval != ERROR_OK)
1186 return retval;
1187
1188 struct efm32x_flash_chip *efm32x_info = bank->driver_priv;
1189
1190 target = bank->target;
1191
1192 if (target->state != TARGET_HALTED) {
1193 LOG_ERROR("Target not halted");
1194 return ERROR_TARGET_NOT_HALTED;
1195 }
1196
1197 uint32_t *ptr;
1198 ptr = efm32x_info->lb_page + 127;
1199 *ptr = 0;
1200
1201 retval = efm32x_write_lock_data(bank);
1202 if (retval != ERROR_OK) {
1203 LOG_ERROR("Failed to write LB page");
1204 return retval;
1205 }
1206
1207 command_print(CMD, "efm32x debug interface locked, reset the device to apply");
1208
1209 return ERROR_OK;
1210 }
1211
1212 static const struct command_registration efm32x_exec_command_handlers[] = {
1213 {
1214 .name = "debuglock",
1215 .handler = efm32x_handle_debuglock_command,
1216 .mode = COMMAND_EXEC,
1217 .usage = "bank_id",
1218 .help = "Lock the debug interface of the device.",
1219 },
1220 COMMAND_REGISTRATION_DONE
1221 };
1222
1223 static const struct command_registration efm32x_command_handlers[] = {
1224 {
1225 .name = "efm32",
1226 .mode = COMMAND_ANY,
1227 .help = "efm32 flash command group",
1228 .usage = "",
1229 .chain = efm32x_exec_command_handlers,
1230 },
1231 COMMAND_REGISTRATION_DONE
1232 };
1233
1234 const struct flash_driver efm32_flash = {
1235 .name = "efm32",
1236 .commands = efm32x_command_handlers,
1237 .flash_bank_command = efm32x_flash_bank_command,
1238 .erase = efm32x_erase,
1239 .protect = efm32x_protect,
1240 .write = efm32x_write,
1241 .read = default_flash_read,
1242 .probe = efm32x_probe,
1243 .auto_probe = efm32x_auto_probe,
1244 .erase_check = default_flash_blank_check,
1245 .protect_check = efm32x_protect_check,
1246 .info = get_efm32x_info,
1247 .free_driver_priv = efm32x_free_driver_priv,
1248 };

Linking to existing account procedure

If you already have an account and want to add another login method you MUST first sign in with your existing account and then change URL to read https://review.openocd.org/login/?link to get to this page again but this time it'll work for linking. Thank you.

SSH host keys fingerprints

1024 SHA256:YKx8b7u5ZWdcbp7/4AeXNaqElP49m6QrwfXaqQGJAOk gerrit-code-review@openocd.zylin.com (DSA)
384 SHA256:jHIbSQa4REvwCFG4cq5LBlBLxmxSqelQPem/EXIrxjk gerrit-code-review@openocd.org (ECDSA)
521 SHA256:UAOPYkU9Fjtcao0Ul/Rrlnj/OsQvt+pgdYSZ4jOYdgs gerrit-code-review@openocd.org (ECDSA)
256 SHA256:A13M5QlnozFOvTllybRZH6vm7iSt0XLxbA48yfc2yfY gerrit-code-review@openocd.org (ECDSA)
256 SHA256:spYMBqEYoAOtK7yZBrcwE8ZpYt6b68Cfh9yEVetvbXg gerrit-code-review@openocd.org (ED25519)
+--[ED25519 256]--+
|=..              |
|+o..   .         |
|*.o   . .        |
|+B . . .         |
|Bo. = o S        |
|Oo.+ + =         |
|oB=.* = . o      |
| =+=.+   + E     |
|. .=o   . o      |
+----[SHA256]-----+
2048 SHA256:0Onrb7/PHjpo6iVZ7xQX2riKN83FJ3KGU0TvI0TaFG4 gerrit-code-review@openocd.zylin.com (RSA)