Kinetis: FlexNVM handling
[openocd.git] / src / flash / nor / kinetis.c
1 /***************************************************************************
2 * Copyright (C) 2011 by Mathias Kuester *
3 * kesmtp@freenet.de *
4 * *
5 * Copyright (C) 2011 sleep(5) ltd *
6 * tomas@sleepfive.com *
7 * *
8 * Copyright (C) 2012 by Christopher D. Kilgour *
9 * techie at whiterocker.com *
10 * *
11 * Copyright (C) 2013 Nemui Trinomius *
12 * nemuisan_kawausogasuki@live.jp *
13 * *
14 * This program is free software; you can redistribute it and/or modify *
15 * it under the terms of the GNU General Public License as published by *
16 * the Free Software Foundation; either version 2 of the License, or *
17 * (at your option) any later version. *
18 * *
19 * This program is distributed in the hope that it will be useful, *
20 * but WITHOUT ANY WARRANTY; without even the implied warranty of *
21 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the *
22 * GNU General Public License for more details. *
23 * *
24 * You should have received a copy of the GNU General Public License *
25 * along with this program; if not, write to the *
26 * Free Software Foundation, Inc., *
27 * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA. *
28 ***************************************************************************/
29
30 #ifdef HAVE_CONFIG_H
31 #include "config.h"
32 #endif
33
34 #include "jtag/interface.h"
35 #include "imp.h"
36 #include <helper/binarybuffer.h>
37 #include <target/target_type.h>
38 #include <target/algorithm.h>
39 #include <target/armv7m.h>
40 #include <target/cortex_m.h>
41
42 /*
43 * Implementation Notes
44 *
45 * The persistent memories in the Kinetis chip families K10 through
46 * K70 are all manipulated with the Flash Memory Module. Some
47 * variants call this module the FTFE, others call it the FTFL. To
48 * indicate that both are considered here, we use FTFX.
49 *
50 * Within the module, according to the chip variant, the persistent
51 * memory is divided into what Freescale terms Program Flash, FlexNVM,
52 * and FlexRAM. All chip variants have Program Flash. Some chip
53 * variants also have FlexNVM and FlexRAM, which always appear
54 * together.
55 *
56 * A given Kinetis chip may have 1, 2 or 4 blocks of flash. Here we map
57 * each block to a separate bank. Each block size varies by chip and
58 * may be determined by the read-only SIM_FCFG1 register. The sector
59 * size within each bank/block varies by chip, and may be 1, 2 or 4k.
60 * The sector size may be different for flash and FlexNVM.
61 *
62 * The first half of the flash (1 or 2 blocks) is always Program Flash
63 * and always starts at address 0x00000000. The "PFLSH" flag, bit 23
64 * of the read-only SIM_FCFG2 register, determines whether the second
65 * half of the flash is also Program Flash or FlexNVM+FlexRAM. When
66 * PFLSH is set, the second from the first half. When PFLSH is clear,
67 * the second half of flash is FlexNVM and always starts at address
68 * 0x10000000. FlexRAM, which is also present when PFLSH is clear,
69 * always starts at address 0x14000000.
70 *
71 * The Flash Memory Module provides a register set where flash
72 * commands are loaded to perform flash operations like erase and
73 * program. Different commands are available depending on whether
74 * Program Flash or FlexNVM/FlexRAM is being manipulated. Although
75 * the commands used are quite consistent between flash blocks, the
76 * parameters they accept differ according to the flash sector size.
77 *
78 */
79
80 /* Addressess */
81 #define FLEXRAM 0x14000000
82 #define FTFx_FSTAT 0x40020000
83 #define FTFx_FCNFG 0x40020001
84 #define FTFx_FCCOB3 0x40020004
85 #define FTFx_FPROT3 0x40020010
86 #define FTFx_FDPROT 0x40020017
87 #define SIM_SDID 0x40048024
88 #define SIM_SOPT1 0x40047000
89 #define SIM_FCFG1 0x4004804c
90 #define SIM_FCFG2 0x40048050
91 #define WDOG_STCTRH 0x40052000
92
93 /* Commands */
94 #define FTFx_CMD_BLOCKSTAT 0x00
95 #define FTFx_CMD_SECTSTAT 0x01
96 #define FTFx_CMD_LWORDPROG 0x06
97 #define FTFx_CMD_SECTERASE 0x09
98 #define FTFx_CMD_SECTWRITE 0x0b
99 #define FTFx_CMD_SETFLEXRAM 0x81
100 #define FTFx_CMD_MASSERASE 0x44
101
102 /* The older Kinetis K series uses the following SDID layout :
103 * Bit 31-16 : 0
104 * Bit 15-12 : REVID
105 * Bit 11-7 : DIEID
106 * Bit 6-4 : FAMID
107 * Bit 3-0 : PINID
108 *
109 * The newer Kinetis series uses the following SDID layout :
110 * Bit 31-28 : FAMID
111 * Bit 27-24 : SUBFAMID
112 * Bit 23-20 : SERIESID
113 * Bit 19-16 : SRAMSIZE
114 * Bit 15-12 : REVID
115 * Bit 6-4 : Reserved (0)
116 * Bit 3-0 : PINID
117 *
118 * We assume that if bits 31-16 are 0 then it's an older
119 * K-series MCU.
120 */
121
122 #define KINETIS_SOPT1_RAMSIZE_MASK 0x0000F000
123 #define KINETIS_SOPT1_RAMSIZE_K24FN1M 0x0000B000
124
125 #define KINETIS_SDID_K_SERIES_MASK 0x0000FFFF
126
127 #define KINETIS_SDID_DIEID_MASK 0x00000F80
128
129 #define KINETIS_SDID_DIEID_K22FN128 0x00000680 /* smaller pflash with FTFA */
130 #define KINETIS_SDID_DIEID_K22FN256 0x00000A80
131 #define KINETIS_SDID_DIEID_K22FN512 0x00000E80
132 #define KINETIS_SDID_DIEID_K24FN256 0x00000700
133
134 #define KINETIS_SDID_DIEID_K24FN1M 0x00000300 /* Detect Errata 7534 */
135
136 /* We can't rely solely on the FAMID field to determine the MCU
137 * type since some FAMID values identify multiple MCUs with
138 * different flash sector sizes (K20 and K22 for instance).
139 * Therefore we combine it with the DIEID bits which may possibly
140 * break if Freescale bumps the DIEID for a particular MCU. */
141 #define KINETIS_K_SDID_TYPE_MASK 0x00000FF0
142 #define KINETIS_K_SDID_K10_M50 0x00000000
143 #define KINETIS_K_SDID_K10_M72 0x00000080
144 #define KINETIS_K_SDID_K10_M100 0x00000100
145 #define KINETIS_K_SDID_K10_M120 0x00000180
146 #define KINETIS_K_SDID_K11 0x00000220
147 #define KINETIS_K_SDID_K12 0x00000200
148 #define KINETIS_K_SDID_K20_M50 0x00000010
149 #define KINETIS_K_SDID_K20_M72 0x00000090
150 #define KINETIS_K_SDID_K20_M100 0x00000110
151 #define KINETIS_K_SDID_K20_M120 0x00000190
152 #define KINETIS_K_SDID_K21_M50 0x00000230
153 #define KINETIS_K_SDID_K21_M120 0x00000330
154 #define KINETIS_K_SDID_K22_M50 0x00000210
155 #define KINETIS_K_SDID_K22_M120 0x00000310
156 #define KINETIS_K_SDID_K30_M72 0x000000A0
157 #define KINETIS_K_SDID_K30_M100 0x00000120
158 #define KINETIS_K_SDID_K40_M72 0x000000B0
159 #define KINETIS_K_SDID_K40_M100 0x00000130
160 #define KINETIS_K_SDID_K50_M72 0x000000E0
161 #define KINETIS_K_SDID_K51_M72 0x000000F0
162 #define KINETIS_K_SDID_K53 0x00000170
163 #define KINETIS_K_SDID_K60_M100 0x00000140
164 #define KINETIS_K_SDID_K60_M150 0x000001C0
165 #define KINETIS_K_SDID_K70_M150 0x000001D0
166
167 #define KINETIS_SDID_SERIESID_MASK 0x00F00000
168 #define KINETIS_SDID_SERIESID_K 0x00000000
169 #define KINETIS_SDID_SERIESID_KL 0x00100000
170 #define KINETIS_SDID_SERIESID_KW 0x00500000
171 #define KINETIS_SDID_SERIESID_KV 0x00600000
172
173 #define KINETIS_SDID_SUBFAMID_MASK 0x0F000000
174 #define KINETIS_SDID_SUBFAMID_KX0 0x00000000
175 #define KINETIS_SDID_SUBFAMID_KX1 0x01000000
176 #define KINETIS_SDID_SUBFAMID_KX2 0x02000000
177 #define KINETIS_SDID_SUBFAMID_KX3 0x03000000
178 #define KINETIS_SDID_SUBFAMID_KX4 0x04000000
179 #define KINETIS_SDID_SUBFAMID_KX5 0x05000000
180 #define KINETIS_SDID_SUBFAMID_KX6 0x06000000
181
182 #define KINETIS_SDID_FAMILYID_MASK 0xF0000000
183 #define KINETIS_SDID_FAMILYID_K0X 0x00000000
184 #define KINETIS_SDID_FAMILYID_K1X 0x10000000
185 #define KINETIS_SDID_FAMILYID_K2X 0x20000000
186 #define KINETIS_SDID_FAMILYID_K3X 0x30000000
187 #define KINETIS_SDID_FAMILYID_K4X 0x40000000
188 #define KINETIS_SDID_FAMILYID_K6X 0x60000000
189 #define KINETIS_SDID_FAMILYID_K7X 0x70000000
190
191 struct kinetis_flash_bank {
192 bool probed;
193 uint32_t sector_size;
194 uint32_t max_flash_prog_size;
195 uint32_t protection_size;
196 uint32_t prog_base; /* base address for FTFx operations */
197 /* same as bank->base for pflash, differs for FlexNVM */
198 uint32_t protection_block; /* number of first protection block in this bank */
199
200 uint32_t sim_sdid;
201 uint32_t sim_fcfg1;
202 uint32_t sim_fcfg2;
203
204 enum {
205 FC_AUTO = 0,
206 FC_PFLASH,
207 FC_FLEX_NVM,
208 FC_FLEX_RAM,
209 } flash_class;
210
211 enum {
212 FS_PROGRAM_SECTOR = 1,
213 FS_PROGRAM_LONGWORD = 2,
214 FS_PROGRAM_PHRASE = 4, /* Unsupported */
215 } flash_support;
216 };
217
218 #define MDM_REG_STAT 0x00
219 #define MDM_REG_CTRL 0x04
220 #define MDM_REG_ID 0xfc
221
222 #define MDM_STAT_FMEACK (1<<0)
223 #define MDM_STAT_FREADY (1<<1)
224 #define MDM_STAT_SYSSEC (1<<2)
225 #define MDM_STAT_SYSRES (1<<3)
226 #define MDM_STAT_FMEEN (1<<5)
227 #define MDM_STAT_BACKDOOREN (1<<6)
228 #define MDM_STAT_LPEN (1<<7)
229 #define MDM_STAT_VLPEN (1<<8)
230 #define MDM_STAT_LLSMODEXIT (1<<9)
231 #define MDM_STAT_VLLSXMODEXIT (1<<10)
232 #define MDM_STAT_CORE_HALTED (1<<16)
233 #define MDM_STAT_CORE_SLEEPDEEP (1<<17)
234 #define MDM_STAT_CORESLEEPING (1<<18)
235
236 #define MEM_CTRL_FMEIP (1<<0)
237 #define MEM_CTRL_DBG_DIS (1<<1)
238 #define MEM_CTRL_DBG_REQ (1<<2)
239 #define MEM_CTRL_SYS_RES_REQ (1<<3)
240 #define MEM_CTRL_CORE_HOLD_RES (1<<4)
241 #define MEM_CTRL_VLLSX_DBG_REQ (1<<5)
242 #define MEM_CTRL_VLLSX_DBG_ACK (1<<6)
243 #define MEM_CTRL_VLLSX_STAT_ACK (1<<7)
244
245 #define MDM_ACCESS_TIMEOUT 3000 /* iterations */
246
247 static int kinetis_mdm_write_register(struct adiv5_dap *dap, unsigned reg, uint32_t value)
248 {
249 int retval;
250 LOG_DEBUG("MDM_REG[0x%02x] <- %08" PRIX32, reg, value);
251
252 retval = dap_queue_ap_write(dap_ap(dap, 1), reg, value);
253 if (retval != ERROR_OK) {
254 LOG_DEBUG("MDM: failed to queue a write request");
255 return retval;
256 }
257
258 retval = dap_run(dap);
259 if (retval != ERROR_OK) {
260 LOG_DEBUG("MDM: dap_run failed");
261 return retval;
262 }
263
264
265 return ERROR_OK;
266 }
267
268 static int kinetis_mdm_read_register(struct adiv5_dap *dap, unsigned reg, uint32_t *result)
269 {
270 int retval;
271
272 retval = dap_queue_ap_read(dap_ap(dap, 1), reg, result);
273 if (retval != ERROR_OK) {
274 LOG_DEBUG("MDM: failed to queue a read request");
275 return retval;
276 }
277
278 retval = dap_run(dap);
279 if (retval != ERROR_OK) {
280 LOG_DEBUG("MDM: dap_run failed");
281 return retval;
282 }
283
284 LOG_DEBUG("MDM_REG[0x%02x]: %08" PRIX32, reg, *result);
285 return ERROR_OK;
286 }
287
288 static int kinetis_mdm_poll_register(struct adiv5_dap *dap, unsigned reg, uint32_t mask, uint32_t value)
289 {
290 uint32_t val;
291 int retval;
292 int timeout = MDM_ACCESS_TIMEOUT;
293
294 do {
295 retval = kinetis_mdm_read_register(dap, reg, &val);
296 if (retval != ERROR_OK || (val & mask) == value)
297 return retval;
298
299 alive_sleep(1);
300 } while (timeout--);
301
302 LOG_DEBUG("MDM: polling timed out");
303 return ERROR_FAIL;
304 }
305
306 /*
307 * This function implements the procedure to mass erase the flash via
308 * SWD/JTAG on Kinetis K and L series of devices as it is described in
309 * AN4835 "Production Flash Programming Best Practices for Kinetis K-
310 * and L-series MCUs" Section 4.2.1
311 */
312 COMMAND_HANDLER(kinetis_mdm_mass_erase)
313 {
314 struct target *target = get_current_target(CMD_CTX);
315 struct cortex_m_common *cortex_m = target_to_cm(target);
316 struct adiv5_dap *dap = cortex_m->armv7m.arm.dap;
317
318 if (!dap) {
319 LOG_ERROR("Cannot perform mass erase with a high-level adapter");
320 return ERROR_FAIL;
321 }
322
323 int retval;
324
325 /*
326 * ... Power on the processor, or if power has already been
327 * applied, assert the RESET pin to reset the processor. For
328 * devices that do not have a RESET pin, write the System
329 * Reset Request bit in the MDM-AP control register after
330 * establishing communication...
331 */
332
333 /* assert SRST */
334 if (jtag_get_reset_config() & RESET_HAS_SRST)
335 adapter_assert_reset();
336 else
337 LOG_WARNING("Attempting mass erase without hardware reset. This is not reliable; "
338 "it's recommended you connect SRST and use ``reset_config srst_only''.");
339
340 retval = kinetis_mdm_write_register(dap, MDM_REG_CTRL, MEM_CTRL_SYS_RES_REQ);
341 if (retval != ERROR_OK)
342 return retval;
343
344 /*
345 * ... Read the MDM-AP status register until the Flash Ready bit sets...
346 */
347 retval = kinetis_mdm_poll_register(dap, MDM_REG_STAT,
348 MDM_STAT_FREADY | MDM_STAT_SYSRES,
349 MDM_STAT_FREADY);
350 if (retval != ERROR_OK) {
351 LOG_ERROR("MDM : flash ready timeout");
352 return retval;
353 }
354
355 /*
356 * ... Write the MDM-AP control register to set the Flash Mass
357 * Erase in Progress bit. This will start the mass erase
358 * process...
359 */
360 retval = kinetis_mdm_write_register(dap, MDM_REG_CTRL,
361 MEM_CTRL_SYS_RES_REQ | MEM_CTRL_FMEIP);
362 if (retval != ERROR_OK)
363 return retval;
364
365 /* As a sanity check make sure that device started mass erase procedure */
366 retval = kinetis_mdm_poll_register(dap, MDM_REG_STAT,
367 MDM_STAT_FMEACK, MDM_STAT_FMEACK);
368 if (retval != ERROR_OK)
369 return retval;
370
371 /*
372 * ... Read the MDM-AP control register until the Flash Mass
373 * Erase in Progress bit clears...
374 */
375 retval = kinetis_mdm_poll_register(dap, MDM_REG_CTRL,
376 MEM_CTRL_FMEIP,
377 0);
378 if (retval != ERROR_OK)
379 return retval;
380
381 /*
382 * ... Negate the RESET signal or clear the System Reset Request
383 * bit in the MDM-AP control register...
384 */
385 retval = kinetis_mdm_write_register(dap, MDM_REG_CTRL, 0);
386 if (retval != ERROR_OK)
387 return retval;
388
389 if (jtag_get_reset_config() & RESET_HAS_SRST) {
390 /* halt MCU otherwise it loops in hard fault - WDOG reset cycle */
391 target->reset_halt = true;
392 target->type->assert_reset(target);
393 target->type->deassert_reset(target);
394 }
395
396 return ERROR_OK;
397 }
398
399 static const uint32_t kinetis_known_mdm_ids[] = {
400 0x001C0000, /* Kinetis-K Series */
401 0x001C0020, /* Kinetis-L/M/V/E Series */
402 };
403
404 /*
405 * This function implements the procedure to connect to
406 * SWD/JTAG on Kinetis K and L series of devices as it is described in
407 * AN4835 "Production Flash Programming Best Practices for Kinetis K-
408 * and L-series MCUs" Section 4.1.1
409 */
410 COMMAND_HANDLER(kinetis_check_flash_security_status)
411 {
412 struct target *target = get_current_target(CMD_CTX);
413 struct cortex_m_common *cortex_m = target_to_cm(target);
414 struct adiv5_dap *dap = cortex_m->armv7m.arm.dap;
415
416 if (!dap) {
417 LOG_WARNING("Cannot check flash security status with a high-level adapter");
418 return ERROR_OK;
419 }
420
421 uint32_t val;
422 int retval;
423
424 /*
425 * ... The MDM-AP ID register can be read to verify that the
426 * connection is working correctly...
427 */
428 retval = kinetis_mdm_read_register(dap, MDM_REG_ID, &val);
429 if (retval != ERROR_OK) {
430 LOG_ERROR("MDM: failed to read ID register");
431 goto fail;
432 }
433
434 bool found = false;
435 for (size_t i = 0; i < ARRAY_SIZE(kinetis_known_mdm_ids); i++) {
436 if (val == kinetis_known_mdm_ids[i]) {
437 found = true;
438 break;
439 }
440 }
441
442 if (!found)
443 LOG_WARNING("MDM: unknown ID %08" PRIX32, val);
444
445 /*
446 * ... Read the MDM-AP status register until the Flash Ready bit sets...
447 */
448 retval = kinetis_mdm_poll_register(dap, MDM_REG_STAT,
449 MDM_STAT_FREADY,
450 MDM_STAT_FREADY);
451 if (retval != ERROR_OK) {
452 LOG_ERROR("MDM: flash ready timeout");
453 goto fail;
454 }
455
456 /*
457 * ... Read the System Security bit to determine if security is enabled.
458 * If System Security = 0, then proceed. If System Security = 1, then
459 * communication with the internals of the processor, including the
460 * flash, will not be possible without issuing a mass erase command or
461 * unsecuring the part through other means (backdoor key unlock)...
462 */
463 retval = kinetis_mdm_read_register(dap, MDM_REG_STAT, &val);
464 if (retval != ERROR_OK) {
465 LOG_ERROR("MDM: failed to read MDM_REG_STAT");
466 goto fail;
467 }
468
469 if ((val & (MDM_STAT_SYSSEC | MDM_STAT_CORE_HALTED)) == MDM_STAT_SYSSEC) {
470 LOG_WARNING("MDM: Secured MCU state detected however it may be a false alarm");
471 LOG_WARNING("MDM: Halting target to detect secured state reliably");
472
473 retval = target_halt(target);
474 if (retval == ERROR_OK)
475 retval = target_wait_state(target, TARGET_HALTED, 100);
476
477 if (retval != ERROR_OK) {
478 LOG_WARNING("MDM: Target not halted, trying reset halt");
479 target->reset_halt = true;
480 target->type->assert_reset(target);
481 target->type->deassert_reset(target);
482 }
483
484 /* re-read status */
485 retval = kinetis_mdm_read_register(dap, MDM_REG_STAT, &val);
486 if (retval != ERROR_OK) {
487 LOG_ERROR("MDM: failed to read MDM_REG_STAT");
488 goto fail;
489 }
490 }
491
492 if (val & MDM_STAT_SYSSEC) {
493 jtag_poll_set_enabled(false);
494
495 LOG_WARNING("*********** ATTENTION! ATTENTION! ATTENTION! ATTENTION! **********");
496 LOG_WARNING("**** ****");
497 LOG_WARNING("**** Your Kinetis MCU is in secured state, which means that, ****");
498 LOG_WARNING("**** with exception for very basic communication, JTAG/SWD ****");
499 LOG_WARNING("**** interface will NOT work. In order to restore its ****");
500 LOG_WARNING("**** functionality please issue 'kinetis mdm mass_erase' ****");
501 LOG_WARNING("**** command, power cycle the MCU and restart OpenOCD. ****");
502 LOG_WARNING("**** ****");
503 LOG_WARNING("*********** ATTENTION! ATTENTION! ATTENTION! ATTENTION! **********");
504 } else {
505 LOG_INFO("MDM: Chip is unsecured. Continuing.");
506 jtag_poll_set_enabled(true);
507 }
508
509 return ERROR_OK;
510
511 fail:
512 LOG_ERROR("MDM: Failed to check security status of the MCU. Cannot proceed further");
513 jtag_poll_set_enabled(false);
514 return retval;
515 }
516
517 FLASH_BANK_COMMAND_HANDLER(kinetis_flash_bank_command)
518 {
519 struct kinetis_flash_bank *bank_info;
520
521 if (CMD_ARGC < 6)
522 return ERROR_COMMAND_SYNTAX_ERROR;
523
524 LOG_INFO("add flash_bank kinetis %s", bank->name);
525
526 bank_info = malloc(sizeof(struct kinetis_flash_bank));
527
528 memset(bank_info, 0, sizeof(struct kinetis_flash_bank));
529
530 bank->driver_priv = bank_info;
531
532 return ERROR_OK;
533 }
534
535 /* Disable the watchdog on Kinetis devices */
536 int kinetis_disable_wdog(struct target *target, uint32_t sim_sdid)
537 {
538 struct working_area *wdog_algorithm;
539 struct armv7m_algorithm armv7m_info;
540 uint16_t wdog;
541 int retval;
542
543 static const uint8_t kinetis_unlock_wdog_code[] = {
544 /* WDOG_UNLOCK = 0xC520 */
545 0x4f, 0xf4, 0x00, 0x53, /* mov.w r3, #8192 ; 0x2000 */
546 0xc4, 0xf2, 0x05, 0x03, /* movt r3, #16389 ; 0x4005 */
547 0x4c, 0xf2, 0x20, 0x52, /* movw r2, #50464 ; 0xc520 */
548 0xda, 0x81, /* strh r2, [r3, #14] */
549
550 /* WDOG_UNLOCK = 0xD928 */
551 0x4f, 0xf4, 0x00, 0x53, /* mov.w r3, #8192 ; 0x2000 */
552 0xc4, 0xf2, 0x05, 0x03, /* movt r3, #16389 ; 0x4005 */
553 0x4d, 0xf6, 0x28, 0x12, /* movw r2, #55592 ; 0xd928 */
554 0xda, 0x81, /* strh r2, [r3, #14] */
555
556 /* WDOG_SCR = 0x1d2 */
557 0x4f, 0xf4, 0x00, 0x53, /* mov.w r3, #8192 ; 0x2000 */
558 0xc4, 0xf2, 0x05, 0x03, /* movt r3, #16389 ; 0x4005 */
559 0x4f, 0xf4, 0xe9, 0x72, /* mov.w r2, #466 ; 0x1d2 */
560 0x1a, 0x80, /* strh r2, [r3, #0] */
561
562 /* END */
563 0x00, 0xBE, /* bkpt #0 */
564 };
565
566 /* Decide whether the connected device needs watchdog disabling.
567 * Disable for all Kx devices, i.e., return if it is a KLx */
568
569 if ((sim_sdid & KINETIS_SDID_SERIESID_MASK) == KINETIS_SDID_SERIESID_KL)
570 return ERROR_OK;
571
572 /* The connected device requires watchdog disabling. */
573 retval = target_read_u16(target, WDOG_STCTRH, &wdog);
574 if (retval != ERROR_OK)
575 return retval;
576
577 if ((wdog & 0x1) == 0) {
578 /* watchdog already disabled */
579 return ERROR_OK;
580 }
581 LOG_INFO("Disabling Kinetis watchdog (initial WDOG_STCTRLH = 0x%x)", wdog);
582
583 if (target->state != TARGET_HALTED) {
584 LOG_ERROR("Target not halted");
585 return ERROR_TARGET_NOT_HALTED;
586 }
587
588 retval = target_alloc_working_area(target, sizeof(kinetis_unlock_wdog_code), &wdog_algorithm);
589 if (retval != ERROR_OK)
590 return retval;
591
592 retval = target_write_buffer(target, wdog_algorithm->address,
593 sizeof(kinetis_unlock_wdog_code), (uint8_t *)kinetis_unlock_wdog_code);
594 if (retval != ERROR_OK) {
595 target_free_working_area(target, wdog_algorithm);
596 return retval;
597 }
598
599 armv7m_info.common_magic = ARMV7M_COMMON_MAGIC;
600 armv7m_info.core_mode = ARM_MODE_THREAD;
601
602 retval = target_run_algorithm(target, 0, NULL, 0, NULL, wdog_algorithm->address,
603 wdog_algorithm->address + (sizeof(kinetis_unlock_wdog_code) - 2),
604 10000, &armv7m_info);
605
606 if (retval != ERROR_OK)
607 LOG_ERROR("error executing kinetis wdog unlock algorithm");
608
609 retval = target_read_u16(target, WDOG_STCTRH, &wdog);
610 if (retval != ERROR_OK)
611 return retval;
612 LOG_INFO("WDOG_STCTRLH = 0x%x", wdog);
613
614 target_free_working_area(target, wdog_algorithm);
615
616 return retval;
617 }
618
619 COMMAND_HANDLER(kinetis_disable_wdog_handler)
620 {
621 int result;
622 uint32_t sim_sdid;
623 struct target *target = get_current_target(CMD_CTX);
624
625 if (CMD_ARGC > 0)
626 return ERROR_COMMAND_SYNTAX_ERROR;
627
628 result = target_read_u32(target, SIM_SDID, &sim_sdid);
629 if (result != ERROR_OK) {
630 LOG_ERROR("Failed to read SIMSDID");
631 return result;
632 }
633
634 result = kinetis_disable_wdog(target, sim_sdid);
635 return result;
636 }
637
638
639 /* Kinetis Program-LongWord Microcodes */
640 static const uint8_t kinetis_flash_write_code[] = {
641 /* Params:
642 * r0 - workarea buffer
643 * r1 - target address
644 * r2 - wordcount
645 * Clobbered:
646 * r4 - tmp
647 * r5 - tmp
648 * r6 - tmp
649 * r7 - tmp
650 */
651
652 /* .L1: */
653 /* for(register uint32_t i=0;i<wcount;i++){ */
654 0x04, 0x1C, /* mov r4, r0 */
655 0x00, 0x23, /* mov r3, #0 */
656 /* .L2: */
657 0x0E, 0x1A, /* sub r6, r1, r0 */
658 0xA6, 0x19, /* add r6, r4, r6 */
659 0x93, 0x42, /* cmp r3, r2 */
660 0x16, 0xD0, /* beq .L9 */
661 /* .L5: */
662 /* while((FTFx_FSTAT&FTFA_FSTAT_CCIF_MASK) != FTFA_FSTAT_CCIF_MASK){}; */
663 0x0B, 0x4D, /* ldr r5, .L10 */
664 0x2F, 0x78, /* ldrb r7, [r5] */
665 0x7F, 0xB2, /* sxtb r7, r7 */
666 0x00, 0x2F, /* cmp r7, #0 */
667 0xFA, 0xDA, /* bge .L5 */
668 /* FTFx_FSTAT = FTFA_FSTAT_ACCERR_MASK|FTFA_FSTAT_FPVIOL_MASK|FTFA_FSTAT_RDCO */
669 0x70, 0x27, /* mov r7, #112 */
670 0x2F, 0x70, /* strb r7, [r5] */
671 /* FTFx_FCCOB3 = faddr; */
672 0x09, 0x4F, /* ldr r7, .L10+4 */
673 0x3E, 0x60, /* str r6, [r7] */
674 0x06, 0x27, /* mov r7, #6 */
675 /* FTFx_FCCOB0 = 0x06; */
676 0x08, 0x4E, /* ldr r6, .L10+8 */
677 0x37, 0x70, /* strb r7, [r6] */
678 /* FTFx_FCCOB7 = *pLW; */
679 0x80, 0xCC, /* ldmia r4!, {r7} */
680 0x08, 0x4E, /* ldr r6, .L10+12 */
681 0x37, 0x60, /* str r7, [r6] */
682 /* FTFx_FSTAT = FTFA_FSTAT_CCIF_MASK; */
683 0x80, 0x27, /* mov r7, #128 */
684 0x2F, 0x70, /* strb r7, [r5] */
685 /* .L4: */
686 /* while((FTFx_FSTAT&FTFA_FSTAT_CCIF_MASK) != FTFA_FSTAT_CCIF_MASK){}; */
687 0x2E, 0x78, /* ldrb r6, [r5] */
688 0x77, 0xB2, /* sxtb r7, r6 */
689 0x00, 0x2F, /* cmp r7, #0 */
690 0xFB, 0xDA, /* bge .L4 */
691 0x01, 0x33, /* add r3, r3, #1 */
692 0xE4, 0xE7, /* b .L2 */
693 /* .L9: */
694 0x00, 0xBE, /* bkpt #0 */
695 /* .L10: */
696 0x00, 0x00, 0x02, 0x40, /* .word 1073872896 */
697 0x04, 0x00, 0x02, 0x40, /* .word 1073872900 */
698 0x07, 0x00, 0x02, 0x40, /* .word 1073872903 */
699 0x08, 0x00, 0x02, 0x40, /* .word 1073872904 */
700 };
701
702 /* Program LongWord Block Write */
703 static int kinetis_write_block(struct flash_bank *bank, const uint8_t *buffer,
704 uint32_t offset, uint32_t wcount)
705 {
706 struct target *target = bank->target;
707 uint32_t buffer_size = 2048; /* Default minimum value */
708 struct working_area *write_algorithm;
709 struct working_area *source;
710 struct kinetis_flash_bank *kinfo = bank->driver_priv;
711 uint32_t address = kinfo->prog_base + offset;
712 struct reg_param reg_params[3];
713 struct armv7m_algorithm armv7m_info;
714 int retval = ERROR_OK;
715
716 /* Params:
717 * r0 - workarea buffer
718 * r1 - target address
719 * r2 - wordcount
720 * Clobbered:
721 * r4 - tmp
722 * r5 - tmp
723 * r6 - tmp
724 * r7 - tmp
725 */
726
727 /* Increase buffer_size if needed */
728 if (buffer_size < (target->working_area_size/2))
729 buffer_size = (target->working_area_size/2);
730
731 LOG_INFO("Kinetis: FLASH Write ...");
732
733 /* check code alignment */
734 if (offset & 0x1) {
735 LOG_WARNING("offset 0x%" PRIx32 " breaks required 2-byte alignment", offset);
736 return ERROR_FLASH_DST_BREAKS_ALIGNMENT;
737 }
738
739 /* allocate working area with flash programming code */
740 if (target_alloc_working_area(target, sizeof(kinetis_flash_write_code),
741 &write_algorithm) != ERROR_OK) {
742 LOG_WARNING("no working area available, can't do block memory writes");
743 return ERROR_TARGET_RESOURCE_NOT_AVAILABLE;
744 }
745
746 retval = target_write_buffer(target, write_algorithm->address,
747 sizeof(kinetis_flash_write_code), kinetis_flash_write_code);
748 if (retval != ERROR_OK)
749 return retval;
750
751 /* memory buffer */
752 while (target_alloc_working_area(target, buffer_size, &source) != ERROR_OK) {
753 buffer_size /= 4;
754 if (buffer_size <= 256) {
755 /* free working area, write algorithm already allocated */
756 target_free_working_area(target, write_algorithm);
757
758 LOG_WARNING("No large enough working area available, can't do block memory writes");
759 return ERROR_TARGET_RESOURCE_NOT_AVAILABLE;
760 }
761 }
762
763 armv7m_info.common_magic = ARMV7M_COMMON_MAGIC;
764 armv7m_info.core_mode = ARM_MODE_THREAD;
765
766 init_reg_param(&reg_params[0], "r0", 32, PARAM_OUT); /* *pLW (*buffer) */
767 init_reg_param(&reg_params[1], "r1", 32, PARAM_OUT); /* faddr */
768 init_reg_param(&reg_params[2], "r2", 32, PARAM_OUT); /* number of words to program */
769
770 /* write code buffer and use Flash programming code within kinetis */
771 /* Set breakpoint to 0 with time-out of 1000 ms */
772 while (wcount > 0) {
773 uint32_t thisrun_count = (wcount > (buffer_size / 4)) ? (buffer_size / 4) : wcount;
774
775 retval = target_write_buffer(target, source->address, thisrun_count * 4, buffer);
776 if (retval != ERROR_OK)
777 break;
778
779 buf_set_u32(reg_params[0].value, 0, 32, source->address);
780 buf_set_u32(reg_params[1].value, 0, 32, address);
781 buf_set_u32(reg_params[2].value, 0, 32, thisrun_count);
782
783 retval = target_run_algorithm(target, 0, NULL, 3, reg_params,
784 write_algorithm->address, 0, 100000, &armv7m_info);
785 if (retval != ERROR_OK) {
786 LOG_ERROR("Error executing kinetis Flash programming algorithm");
787 retval = ERROR_FLASH_OPERATION_FAILED;
788 break;
789 }
790
791 buffer += thisrun_count * 4;
792 address += thisrun_count * 4;
793 wcount -= thisrun_count;
794 }
795
796 target_free_working_area(target, source);
797 target_free_working_area(target, write_algorithm);
798
799 destroy_reg_param(&reg_params[0]);
800 destroy_reg_param(&reg_params[1]);
801 destroy_reg_param(&reg_params[2]);
802
803 return retval;
804 }
805
806 static int kinetis_protect(struct flash_bank *bank, int set, int first, int last)
807 {
808 LOG_WARNING("kinetis_protect not supported yet");
809 /* FIXME: TODO */
810
811 if (bank->target->state != TARGET_HALTED) {
812 LOG_ERROR("Target not halted");
813 return ERROR_TARGET_NOT_HALTED;
814 }
815
816 return ERROR_FLASH_BANK_INVALID;
817 }
818
819 static int kinetis_protect_check(struct flash_bank *bank)
820 {
821 struct kinetis_flash_bank *kinfo = bank->driver_priv;
822 int result;
823 int i, b;
824 uint32_t fprot, psec;
825
826 if (bank->target->state != TARGET_HALTED) {
827 LOG_ERROR("Target not halted");
828 return ERROR_TARGET_NOT_HALTED;
829 }
830
831 if (kinfo->flash_class == FC_PFLASH) {
832 uint8_t buffer[4];
833
834 /* read protection register */
835 result = target_read_memory(bank->target, FTFx_FPROT3, 1, 4, buffer);
836
837 if (result != ERROR_OK)
838 return result;
839
840 fprot = target_buffer_get_u32(bank->target, buffer);
841 /* Every bit protects 1/32 of the full flash (not necessarily just this bank) */
842
843 } else if (kinfo->flash_class == FC_FLEX_NVM) {
844 uint8_t fdprot;
845
846 /* read protection register */
847 result = target_read_memory(bank->target, FTFx_FDPROT, 1, 1, &fdprot);
848
849 if (result != ERROR_OK)
850 return result;
851
852 fprot = fdprot;
853
854 } else {
855 LOG_ERROR("Protection checks for FlexRAM not supported");
856 return ERROR_FLASH_BANK_INVALID;
857 }
858
859 b = kinfo->protection_block;
860 for (psec = 0, i = 0; i < bank->num_sectors; i++) {
861 if ((fprot >> b) & 1)
862 bank->sectors[i].is_protected = 0;
863 else
864 bank->sectors[i].is_protected = 1;
865
866 psec += bank->sectors[i].size;
867
868 if (psec >= kinfo->protection_size) {
869 psec = 0;
870 b++;
871 }
872 }
873
874 return ERROR_OK;
875 }
876
877 static int kinetis_ftfx_command(struct flash_bank *bank, uint8_t fcmd, uint32_t faddr,
878 uint8_t fccob4, uint8_t fccob5, uint8_t fccob6, uint8_t fccob7,
879 uint8_t fccob8, uint8_t fccob9, uint8_t fccoba, uint8_t fccobb,
880 uint8_t *ftfx_fstat)
881 {
882 uint8_t command[12] = {faddr & 0xff, (faddr >> 8) & 0xff, (faddr >> 16) & 0xff, fcmd,
883 fccob7, fccob6, fccob5, fccob4,
884 fccobb, fccoba, fccob9, fccob8};
885 int result, i;
886 uint8_t buffer;
887
888 /* wait for done */
889 for (i = 0; i < 50; i++) {
890 result =
891 target_read_memory(bank->target, FTFx_FSTAT, 1, 1, &buffer);
892
893 if (result != ERROR_OK)
894 return result;
895
896 if (buffer & 0x80)
897 break;
898
899 buffer = 0x00;
900 }
901
902 if (buffer != 0x80) {
903 /* reset error flags */
904 buffer = 0x30;
905 result =
906 target_write_memory(bank->target, FTFx_FSTAT, 1, 1, &buffer);
907 if (result != ERROR_OK)
908 return result;
909 }
910
911 result = target_write_memory(bank->target, FTFx_FCCOB3, 4, 3, command);
912
913 if (result != ERROR_OK)
914 return result;
915
916 /* start command */
917 buffer = 0x80;
918 result = target_write_memory(bank->target, FTFx_FSTAT, 1, 1, &buffer);
919 if (result != ERROR_OK)
920 return result;
921
922 /* wait for done */
923 for (i = 0; i < 240; i++) { /* Need longtime for "Mass Erase" Command Nemui Changed */
924 result =
925 target_read_memory(bank->target, FTFx_FSTAT, 1, 1, ftfx_fstat);
926
927 if (result != ERROR_OK)
928 return result;
929
930 if (*ftfx_fstat & 0x80)
931 break;
932 }
933
934 if ((*ftfx_fstat & 0xf0) != 0x80) {
935 LOG_ERROR
936 ("ftfx command failed FSTAT: %02X FCCOB: %02X%02X%02X%02X %02X%02X%02X%02X %02X%02X%02X%02X",
937 *ftfx_fstat, command[3], command[2], command[1], command[0],
938 command[7], command[6], command[5], command[4],
939 command[11], command[10], command[9], command[8]);
940 return ERROR_FLASH_OPERATION_FAILED;
941 }
942
943 return ERROR_OK;
944 }
945
946 COMMAND_HANDLER(kinetis_securing_test)
947 {
948 int result;
949 uint8_t ftfx_fstat;
950 struct target *target = get_current_target(CMD_CTX);
951 struct flash_bank *bank = NULL;
952
953 result = get_flash_bank_by_addr(target, 0x00000000, true, &bank);
954 if (result != ERROR_OK)
955 return result;
956
957 assert(bank != NULL);
958
959 if (target->state != TARGET_HALTED) {
960 LOG_ERROR("Target not halted");
961 return ERROR_TARGET_NOT_HALTED;
962 }
963
964 return kinetis_ftfx_command(bank, FTFx_CMD_SECTERASE, bank->base + 0x00000400,
965 0, 0, 0, 0, 0, 0, 0, 0, &ftfx_fstat);
966 }
967
968 static int kinetis_erase(struct flash_bank *bank, int first, int last)
969 {
970 int result, i;
971 struct kinetis_flash_bank *kinfo = bank->driver_priv;
972
973 if (bank->target->state != TARGET_HALTED) {
974 LOG_ERROR("Target not halted");
975 return ERROR_TARGET_NOT_HALTED;
976 }
977
978 if ((first > bank->num_sectors) || (last > bank->num_sectors))
979 return ERROR_FLASH_OPERATION_FAILED;
980
981 /*
982 * FIXME: TODO: use the 'Erase Flash Block' command if the
983 * requested erase is PFlash or NVM and encompasses the entire
984 * block. Should be quicker.
985 */
986 for (i = first; i <= last; i++) {
987 uint8_t ftfx_fstat;
988 /* set command and sector address */
989 result = kinetis_ftfx_command(bank, FTFx_CMD_SECTERASE, kinfo->prog_base + bank->sectors[i].offset,
990 0, 0, 0, 0, 0, 0, 0, 0, &ftfx_fstat);
991
992 if (result != ERROR_OK) {
993 LOG_WARNING("erase sector %d failed", i);
994 return ERROR_FLASH_OPERATION_FAILED;
995 }
996
997 bank->sectors[i].is_erased = 1;
998 }
999
1000 if (first == 0) {
1001 LOG_WARNING
1002 ("flash configuration field erased, please reset the device");
1003 }
1004
1005 return ERROR_OK;
1006 }
1007
1008 static int kinetis_write(struct flash_bank *bank, const uint8_t *buffer,
1009 uint32_t offset, uint32_t count)
1010 {
1011 unsigned int i, result, fallback = 0;
1012 uint8_t buf[8];
1013 uint32_t wc;
1014 struct kinetis_flash_bank *kinfo = bank->driver_priv;
1015 uint8_t *new_buffer = NULL;
1016
1017 if (bank->target->state != TARGET_HALTED) {
1018 LOG_ERROR("Target not halted");
1019 return ERROR_TARGET_NOT_HALTED;
1020 }
1021
1022 if (!(kinfo->flash_support & FS_PROGRAM_SECTOR)) {
1023 /* fallback to longword write */
1024 fallback = 1;
1025 LOG_WARNING("This device supports Program Longword execution only.");
1026 LOG_DEBUG("flash write into PFLASH @08%" PRIX32, offset);
1027
1028 } else if (kinfo->flash_class == FC_FLEX_NVM) {
1029 uint8_t ftfx_fstat;
1030
1031 LOG_DEBUG("flash write into FlexNVM @%08" PRIX32, offset);
1032
1033 /* make flex ram available */
1034 result = kinetis_ftfx_command(bank, FTFx_CMD_SETFLEXRAM, 0x00ff0000, 0, 0, 0, 0, 0, 0, 0, 0, &ftfx_fstat);
1035
1036 if (result != ERROR_OK)
1037 return ERROR_FLASH_OPERATION_FAILED;
1038
1039 /* check if ram ready */
1040 result = target_read_memory(bank->target, FTFx_FCNFG, 1, 1, buf);
1041
1042 if (result != ERROR_OK)
1043 return result;
1044
1045 if (!(buf[0] & (1 << 1))) {
1046 /* fallback to longword write */
1047 fallback = 1;
1048
1049 LOG_WARNING("ram not ready, fallback to slow longword write (FCNFG: %02X)", buf[0]);
1050 }
1051 } else {
1052 LOG_DEBUG("flash write into PFLASH @08%" PRIX32, offset);
1053 }
1054
1055
1056 /* program section command */
1057 if (fallback == 0) {
1058 /*
1059 * Kinetis uses different terms for the granularity of
1060 * sector writes, e.g. "phrase" or "128 bits". We use
1061 * the generic term "chunk". The largest possible
1062 * Kinetis "chunk" is 16 bytes (128 bits).
1063 */
1064 unsigned prog_section_chunk_bytes = kinfo->sector_size >> 8;
1065 unsigned prog_size_bytes = kinfo->max_flash_prog_size;
1066 for (i = 0; i < count; i += prog_size_bytes) {
1067 uint8_t residual_buffer[16];
1068 uint8_t ftfx_fstat;
1069 uint32_t section_count = prog_size_bytes / prog_section_chunk_bytes;
1070 uint32_t residual_wc = 0;
1071
1072 /*
1073 * Assume the word count covers an entire
1074 * sector.
1075 */
1076 wc = prog_size_bytes / 4;
1077
1078 /*
1079 * If bytes to be programmed are less than the
1080 * full sector, then determine the number of
1081 * full-words to program, and put together the
1082 * residual buffer so that a full "section"
1083 * may always be programmed.
1084 */
1085 if ((count - i) < prog_size_bytes) {
1086 /* number of bytes to program beyond full section */
1087 unsigned residual_bc = (count-i) % prog_section_chunk_bytes;
1088
1089 /* number of complete words to copy directly from buffer */
1090 wc = (count - i - residual_bc) / 4;
1091
1092 /* number of total sections to write, including residual */
1093 section_count = DIV_ROUND_UP((count-i), prog_section_chunk_bytes);
1094
1095 /* any residual bytes delivers a whole residual section */
1096 residual_wc = (residual_bc ? prog_section_chunk_bytes : 0)/4;
1097
1098 /* clear residual buffer then populate residual bytes */
1099 (void) memset(residual_buffer, 0xff, prog_section_chunk_bytes);
1100 (void) memcpy(residual_buffer, &buffer[i+4*wc], residual_bc);
1101 }
1102
1103 LOG_DEBUG("write section @ %08" PRIX32 " with length %" PRIu32 " bytes",
1104 offset + i, (uint32_t)wc*4);
1105
1106 /* write data to flexram as whole-words */
1107 result = target_write_memory(bank->target, FLEXRAM, 4, wc,
1108 buffer + i);
1109
1110 if (result != ERROR_OK) {
1111 LOG_ERROR("target_write_memory failed");
1112 return result;
1113 }
1114
1115 /* write the residual words to the flexram */
1116 if (residual_wc) {
1117 result = target_write_memory(bank->target,
1118 FLEXRAM+4*wc,
1119 4, residual_wc,
1120 residual_buffer);
1121
1122 if (result != ERROR_OK) {
1123 LOG_ERROR("target_write_memory failed");
1124 return result;
1125 }
1126 }
1127
1128 /* execute section-write command */
1129 result = kinetis_ftfx_command(bank, FTFx_CMD_SECTWRITE, kinfo->prog_base + offset + i,
1130 section_count>>8, section_count, 0, 0,
1131 0, 0, 0, 0, &ftfx_fstat);
1132
1133 if (result != ERROR_OK)
1134 return ERROR_FLASH_OPERATION_FAILED;
1135 }
1136 }
1137 /* program longword command, not supported in "SF3" devices */
1138 else if (kinfo->flash_support & FS_PROGRAM_LONGWORD) {
1139 if (count & 0x3) {
1140 uint32_t old_count = count;
1141 count = (old_count | 3) + 1;
1142 new_buffer = malloc(count);
1143 if (new_buffer == NULL) {
1144 LOG_ERROR("odd number of bytes to write and no memory "
1145 "for padding buffer");
1146 return ERROR_FAIL;
1147 }
1148 LOG_INFO("odd number of bytes to write (%" PRIu32 "), extending to %" PRIu32 " "
1149 "and padding with 0xff", old_count, count);
1150 memset(new_buffer, 0xff, count);
1151 buffer = memcpy(new_buffer, buffer, old_count);
1152 }
1153
1154 uint32_t words_remaining = count / 4;
1155
1156 kinetis_disable_wdog(bank->target, kinfo->sim_sdid);
1157
1158 /* try using a block write */
1159 int retval = kinetis_write_block(bank, buffer, offset, words_remaining);
1160
1161 if (retval == ERROR_TARGET_RESOURCE_NOT_AVAILABLE) {
1162 /* if block write failed (no sufficient working area),
1163 * we use normal (slow) single word accesses */
1164 LOG_WARNING("couldn't use block writes, falling back to single "
1165 "memory accesses");
1166
1167 for (i = 0; i < count; i += 4) {
1168 uint8_t ftfx_fstat;
1169
1170 LOG_DEBUG("write longword @ %08" PRIX32, (uint32_t)(offset + i));
1171
1172 uint8_t padding[4] = {0xff, 0xff, 0xff, 0xff};
1173 memcpy(padding, buffer + i, MIN(4, count-i));
1174
1175 result = kinetis_ftfx_command(bank, FTFx_CMD_LWORDPROG, kinfo->prog_base + offset + i,
1176 padding[3], padding[2], padding[1], padding[0],
1177 0, 0, 0, 0, &ftfx_fstat);
1178
1179 if (result != ERROR_OK)
1180 return ERROR_FLASH_OPERATION_FAILED;
1181 }
1182 }
1183 } else {
1184 LOG_ERROR("Flash write strategy not implemented");
1185 return ERROR_FLASH_OPERATION_FAILED;
1186 }
1187
1188 return ERROR_OK;
1189 }
1190
1191 static int kinetis_read_part_info(struct flash_bank *bank)
1192 {
1193 int result, i;
1194 uint32_t offset = 0;
1195 uint8_t fcfg1_nvmsize, fcfg1_pfsize, fcfg1_eesize, fcfg1_depart;
1196 uint8_t fcfg2_pflsh;
1197 uint32_t nvm_size = 0, pf_size = 0, df_size = 0, ee_size = 0;
1198 unsigned num_blocks = 0, num_pflash_blocks = 0, num_nvm_blocks = 0, first_nvm_bank = 0,
1199 pflash_sector_size_bytes = 0, nvm_sector_size_bytes = 0;
1200 struct target *target = bank->target;
1201 struct kinetis_flash_bank *kinfo = bank->driver_priv;
1202
1203 kinfo->probed = false;
1204
1205 result = target_read_u32(target, SIM_SDID, &kinfo->sim_sdid);
1206 if (result != ERROR_OK)
1207 return result;
1208
1209 if ((kinfo->sim_sdid & (~KINETIS_SDID_K_SERIES_MASK)) == 0) {
1210 /* older K-series MCU */
1211 uint32_t mcu_type = kinfo->sim_sdid & KINETIS_K_SDID_TYPE_MASK;
1212
1213 switch (mcu_type) {
1214 case KINETIS_K_SDID_K10_M50:
1215 case KINETIS_K_SDID_K20_M50:
1216 /* 1kB sectors */
1217 pflash_sector_size_bytes = 1<<10;
1218 nvm_sector_size_bytes = 1<<10;
1219 num_blocks = 2;
1220 kinfo->flash_support = FS_PROGRAM_LONGWORD | FS_PROGRAM_SECTOR;
1221 break;
1222 case KINETIS_K_SDID_K10_M72:
1223 case KINETIS_K_SDID_K20_M72:
1224 case KINETIS_K_SDID_K30_M72:
1225 case KINETIS_K_SDID_K30_M100:
1226 case KINETIS_K_SDID_K40_M72:
1227 case KINETIS_K_SDID_K40_M100:
1228 case KINETIS_K_SDID_K50_M72:
1229 /* 2kB sectors, 1kB FlexNVM sectors */
1230 pflash_sector_size_bytes = 2<<10;
1231 nvm_sector_size_bytes = 1<<10;
1232 num_blocks = 2;
1233 kinfo->flash_support = FS_PROGRAM_LONGWORD | FS_PROGRAM_SECTOR;
1234 kinfo->max_flash_prog_size = 1<<10;
1235 break;
1236 case KINETIS_K_SDID_K10_M100:
1237 case KINETIS_K_SDID_K20_M100:
1238 case KINETIS_K_SDID_K11:
1239 case KINETIS_K_SDID_K12:
1240 case KINETIS_K_SDID_K21_M50:
1241 case KINETIS_K_SDID_K22_M50:
1242 case KINETIS_K_SDID_K51_M72:
1243 case KINETIS_K_SDID_K53:
1244 case KINETIS_K_SDID_K60_M100:
1245 /* 2kB sectors */
1246 pflash_sector_size_bytes = 2<<10;
1247 nvm_sector_size_bytes = 2<<10;
1248 num_blocks = 2;
1249 kinfo->flash_support = FS_PROGRAM_LONGWORD | FS_PROGRAM_SECTOR;
1250 break;
1251 case KINETIS_K_SDID_K21_M120:
1252 case KINETIS_K_SDID_K22_M120:
1253 /* 4kB sectors (MK21FN1M0, MK21FX512, MK22FN1M0, MK22FX512) */
1254 pflash_sector_size_bytes = 4<<10;
1255 kinfo->max_flash_prog_size = 1<<10;
1256 nvm_sector_size_bytes = 4<<10;
1257 num_blocks = 2;
1258 kinfo->flash_support = FS_PROGRAM_PHRASE | FS_PROGRAM_SECTOR;
1259 break;
1260 case KINETIS_K_SDID_K10_M120:
1261 case KINETIS_K_SDID_K20_M120:
1262 case KINETIS_K_SDID_K60_M150:
1263 case KINETIS_K_SDID_K70_M150:
1264 /* 4kB sectors */
1265 pflash_sector_size_bytes = 4<<10;
1266 nvm_sector_size_bytes = 4<<10;
1267 num_blocks = 4;
1268 kinfo->flash_support = FS_PROGRAM_PHRASE | FS_PROGRAM_SECTOR;
1269 break;
1270 default:
1271 LOG_ERROR("Unsupported K-family FAMID");
1272 }
1273 } else {
1274 /* Newer K-series or KL series MCU */
1275 switch (kinfo->sim_sdid & KINETIS_SDID_SERIESID_MASK) {
1276 case KINETIS_SDID_SERIESID_K:
1277 switch (kinfo->sim_sdid & (KINETIS_SDID_FAMILYID_MASK | KINETIS_SDID_SUBFAMID_MASK)) {
1278 case KINETIS_SDID_FAMILYID_K0X | KINETIS_SDID_SUBFAMID_KX2:
1279 /* K02FN64, K02FN128: FTFA, 2kB sectors */
1280 pflash_sector_size_bytes = 2<<10;
1281 num_blocks = 1;
1282 kinfo->flash_support = FS_PROGRAM_LONGWORD;
1283 break;
1284
1285 case KINETIS_SDID_FAMILYID_K2X | KINETIS_SDID_SUBFAMID_KX2: {
1286 /* MK24FN1M reports as K22, this should detect it (according to errata note 1N83J) */
1287 uint32_t sopt1;
1288 result = target_read_u32(target, SIM_SOPT1, &sopt1);
1289 if (result != ERROR_OK)
1290 return result;
1291
1292 if (((kinfo->sim_sdid & (KINETIS_SDID_DIEID_MASK)) == KINETIS_SDID_DIEID_K24FN1M) &&
1293 ((sopt1 & KINETIS_SOPT1_RAMSIZE_MASK) == KINETIS_SOPT1_RAMSIZE_K24FN1M)) {
1294 /* MK24FN1M */
1295 pflash_sector_size_bytes = 4<<10;
1296 num_blocks = 2;
1297 kinfo->flash_support = FS_PROGRAM_PHRASE | FS_PROGRAM_SECTOR;
1298 kinfo->max_flash_prog_size = 1<<10;
1299 break;
1300 }
1301 if ((kinfo->sim_sdid & (KINETIS_SDID_DIEID_MASK)) == KINETIS_SDID_DIEID_K22FN128
1302 || (kinfo->sim_sdid & (KINETIS_SDID_DIEID_MASK)) == KINETIS_SDID_DIEID_K22FN256
1303 || (kinfo->sim_sdid & (KINETIS_SDID_DIEID_MASK)) == KINETIS_SDID_DIEID_K22FN512) {
1304 /* K22 with new-style SDID - smaller pflash with FTFA, 2kB sectors */
1305 pflash_sector_size_bytes = 2<<10;
1306 num_blocks = 2; /* 1 or 2 blocks */
1307 kinfo->flash_support = FS_PROGRAM_LONGWORD;
1308 break;
1309 }
1310 LOG_ERROR("Unsupported Kinetis K22 DIEID");
1311 break;
1312 }
1313 case KINETIS_SDID_FAMILYID_K2X | KINETIS_SDID_SUBFAMID_KX4:
1314 pflash_sector_size_bytes = 4<<10;
1315 if ((kinfo->sim_sdid & (KINETIS_SDID_DIEID_MASK)) == KINETIS_SDID_DIEID_K24FN256) {
1316 /* K24FN256 - smaller pflash with FTFA */
1317 num_blocks = 1;
1318 kinfo->flash_support = FS_PROGRAM_LONGWORD;
1319 break;
1320 }
1321 /* K24FN1M without errata 7534 */
1322 num_blocks = 2;
1323 kinfo->flash_support = FS_PROGRAM_PHRASE | FS_PROGRAM_SECTOR;
1324 kinfo->max_flash_prog_size = 1<<10;
1325 break;
1326
1327 case KINETIS_SDID_FAMILYID_K6X | KINETIS_SDID_SUBFAMID_KX3:
1328 case KINETIS_SDID_FAMILYID_K6X | KINETIS_SDID_SUBFAMID_KX1: /* errata 7534 - should be K63 */
1329 /* K63FN1M0 */
1330 case KINETIS_SDID_FAMILYID_K6X | KINETIS_SDID_SUBFAMID_KX4:
1331 case KINETIS_SDID_FAMILYID_K6X | KINETIS_SDID_SUBFAMID_KX2: /* errata 7534 - should be K64 */
1332 /* K64FN1M0, K64FX512 */
1333 pflash_sector_size_bytes = 4<<10;
1334 nvm_sector_size_bytes = 4<<10;
1335 kinfo->max_flash_prog_size = 1<<10;
1336 num_blocks = 2;
1337 kinfo->flash_support = FS_PROGRAM_PHRASE | FS_PROGRAM_SECTOR;
1338 break;
1339
1340 case KINETIS_SDID_FAMILYID_K2X | KINETIS_SDID_SUBFAMID_KX6:
1341 /* K26FN2M0 */
1342 case KINETIS_SDID_FAMILYID_K6X | KINETIS_SDID_SUBFAMID_KX6:
1343 /* K66FN2M0, K66FX1M0 */
1344 pflash_sector_size_bytes = 4<<10;
1345 nvm_sector_size_bytes = 4<<10;
1346 kinfo->max_flash_prog_size = 1<<10;
1347 num_blocks = 4;
1348 kinfo->flash_support = FS_PROGRAM_PHRASE | FS_PROGRAM_SECTOR;
1349 break;
1350 default:
1351 LOG_ERROR("Unsupported Kinetis FAMILYID SUBFAMID");
1352 }
1353 break;
1354 case KINETIS_SDID_SERIESID_KL:
1355 /* KL-series */
1356 pflash_sector_size_bytes = 1<<10;
1357 nvm_sector_size_bytes = 1<<10;
1358 num_blocks = 1;
1359 kinfo->flash_support = FS_PROGRAM_LONGWORD;
1360 break;
1361 default:
1362 LOG_ERROR("Unsupported K-series");
1363 }
1364 }
1365
1366 if (pflash_sector_size_bytes == 0) {
1367 LOG_ERROR("MCU is unsupported, SDID 0x%08" PRIx32, kinfo->sim_sdid);
1368 return ERROR_FLASH_OPER_UNSUPPORTED;
1369 }
1370
1371 result = target_read_u32(target, SIM_FCFG1, &kinfo->sim_fcfg1);
1372 if (result != ERROR_OK)
1373 return result;
1374
1375 result = target_read_u32(target, SIM_FCFG2, &kinfo->sim_fcfg2);
1376 if (result != ERROR_OK)
1377 return result;
1378
1379 LOG_DEBUG("SDID: 0x%08" PRIX32 " FCFG1: 0x%08" PRIX32 " FCFG2: 0x%08" PRIX32, kinfo->sim_sdid,
1380 kinfo->sim_fcfg1, kinfo->sim_fcfg2);
1381
1382 fcfg1_nvmsize = (uint8_t)((kinfo->sim_fcfg1 >> 28) & 0x0f);
1383 fcfg1_pfsize = (uint8_t)((kinfo->sim_fcfg1 >> 24) & 0x0f);
1384 fcfg1_eesize = (uint8_t)((kinfo->sim_fcfg1 >> 16) & 0x0f);
1385 fcfg1_depart = (uint8_t)((kinfo->sim_fcfg1 >> 8) & 0x0f);
1386
1387 fcfg2_pflsh = (uint8_t)((kinfo->sim_fcfg2 >> 23) & 0x01);
1388
1389 /* when the PFLSH bit is set, there is no FlexNVM/FlexRAM */
1390 if (!fcfg2_pflsh) {
1391 switch (fcfg1_nvmsize) {
1392 case 0x03:
1393 case 0x05:
1394 case 0x07:
1395 case 0x09:
1396 case 0x0b:
1397 nvm_size = 1 << (14 + (fcfg1_nvmsize >> 1));
1398 break;
1399 case 0x0f:
1400 if (pflash_sector_size_bytes >= 4<<10)
1401 nvm_size = 512<<10;
1402 else
1403 /* K20_100 */
1404 nvm_size = 256<<10;
1405 break;
1406 default:
1407 nvm_size = 0;
1408 break;
1409 }
1410
1411 switch (fcfg1_eesize) {
1412 case 0x00:
1413 case 0x01:
1414 case 0x02:
1415 case 0x03:
1416 case 0x04:
1417 case 0x05:
1418 case 0x06:
1419 case 0x07:
1420 case 0x08:
1421 case 0x09:
1422 ee_size = (16 << (10 - fcfg1_eesize));
1423 break;
1424 default:
1425 ee_size = 0;
1426 break;
1427 }
1428
1429 switch (fcfg1_depart) {
1430 case 0x01:
1431 case 0x02:
1432 case 0x03:
1433 case 0x04:
1434 case 0x05:
1435 case 0x06:
1436 df_size = nvm_size - (4096 << fcfg1_depart);
1437 break;
1438 case 0x08:
1439 df_size = 0;
1440 break;
1441 case 0x09:
1442 case 0x0a:
1443 case 0x0b:
1444 case 0x0c:
1445 case 0x0d:
1446 df_size = 4096 << (fcfg1_depart & 0x7);
1447 break;
1448 default:
1449 df_size = nvm_size;
1450 break;
1451 }
1452 }
1453
1454 switch (fcfg1_pfsize) {
1455 case 0x03:
1456 case 0x05:
1457 case 0x07:
1458 case 0x09:
1459 case 0x0b:
1460 case 0x0d:
1461 pf_size = 1 << (14 + (fcfg1_pfsize >> 1));
1462 break;
1463 case 0x0f:
1464 if (pflash_sector_size_bytes >= 4<<10)
1465 pf_size = 1024<<10;
1466 else if (fcfg2_pflsh)
1467 pf_size = 512<<10;
1468 else
1469 pf_size = 256<<10;
1470 break;
1471 default:
1472 pf_size = 0;
1473 break;
1474 }
1475
1476 LOG_DEBUG("FlexNVM: %" PRIu32 " PFlash: %" PRIu32 " FlexRAM: %" PRIu32 " PFLSH: %d",
1477 nvm_size, pf_size, ee_size, fcfg2_pflsh);
1478
1479 num_pflash_blocks = num_blocks / (2 - fcfg2_pflsh);
1480 first_nvm_bank = num_pflash_blocks;
1481 num_nvm_blocks = num_blocks - num_pflash_blocks;
1482
1483 LOG_DEBUG("%d blocks total: %d PFlash, %d FlexNVM",
1484 num_blocks, num_pflash_blocks, num_nvm_blocks);
1485
1486 LOG_INFO("Probing flash info for bank %d", bank->bank_number);
1487
1488 if ((unsigned)bank->bank_number < num_pflash_blocks) {
1489 /* pflash, banks start at address zero */
1490 kinfo->flash_class = FC_PFLASH;
1491 bank->size = (pf_size / num_pflash_blocks);
1492 bank->base = 0x00000000 + bank->size * bank->bank_number;
1493 kinfo->prog_base = bank->base;
1494 kinfo->sector_size = pflash_sector_size_bytes;
1495 kinfo->protection_size = pf_size / 32;
1496 kinfo->protection_block = (32 / num_pflash_blocks) * bank->bank_number;
1497
1498 } else if ((unsigned)bank->bank_number < num_blocks) {
1499 /* nvm, banks start at address 0x10000000 */
1500 unsigned nvm_ord = bank->bank_number - first_nvm_bank;
1501 uint32_t limit;
1502
1503 kinfo->flash_class = FC_FLEX_NVM;
1504 bank->size = (nvm_size / num_nvm_blocks);
1505 bank->base = 0x10000000 + bank->size * nvm_ord;
1506 kinfo->prog_base = 0x00800000 + bank->size * nvm_ord;
1507 kinfo->sector_size = nvm_sector_size_bytes;
1508 if (df_size == 0) {
1509 kinfo->protection_size = 0;
1510 } else {
1511 for (i = df_size; ~i & 1; i >>= 1)
1512 ;
1513 if (i == 1)
1514 kinfo->protection_size = df_size / 8; /* data flash size = 2^^n */
1515 else
1516 kinfo->protection_size = nvm_size / 8; /* TODO: verify on SF1, not documented in RM */
1517 }
1518 kinfo->protection_block = (8 / num_nvm_blocks) * nvm_ord;
1519
1520 /* EEPROM backup part of FlexNVM is not accessible, use df_size as a limit */
1521 if (df_size > bank->size * nvm_ord)
1522 limit = df_size - bank->size * nvm_ord;
1523 else
1524 limit = 0;
1525
1526 if (bank->size > limit) {
1527 bank->size = limit;
1528 LOG_DEBUG("FlexNVM bank %d limited to 0x%08" PRIx32 " due to active EEPROM backup",
1529 bank->bank_number, limit);
1530 }
1531
1532 } else if ((unsigned)bank->bank_number == num_blocks) {
1533 LOG_ERROR("FlexRAM support not yet implemented");
1534 return ERROR_FLASH_OPER_UNSUPPORTED;
1535 } else {
1536 LOG_ERROR("Cannot determine parameters for bank %d, only %d banks on device",
1537 bank->bank_number, num_blocks);
1538 return ERROR_FLASH_BANK_INVALID;
1539 }
1540
1541 if (bank->sectors) {
1542 free(bank->sectors);
1543 bank->sectors = NULL;
1544 }
1545
1546 if (kinfo->sector_size == 0) {
1547 LOG_ERROR("Unknown sector size for bank %d", bank->bank_number);
1548 return ERROR_FLASH_BANK_INVALID;
1549 }
1550
1551 if (kinfo->flash_support & FS_PROGRAM_SECTOR
1552 && kinfo->max_flash_prog_size == 0) {
1553 kinfo->max_flash_prog_size = kinfo->sector_size;
1554 /* Program section size is equal to sector size by default */
1555 }
1556
1557 bank->num_sectors = bank->size / kinfo->sector_size;
1558
1559 if (bank->num_sectors > 0) {
1560 /* FlexNVM bank can be used for EEPROM backup therefore zero sized */
1561 bank->sectors = malloc(sizeof(struct flash_sector) * bank->num_sectors);
1562
1563 for (i = 0; i < bank->num_sectors; i++) {
1564 bank->sectors[i].offset = offset;
1565 bank->sectors[i].size = kinfo->sector_size;
1566 offset += kinfo->sector_size;
1567 bank->sectors[i].is_erased = -1;
1568 bank->sectors[i].is_protected = 1;
1569 }
1570 }
1571
1572 kinfo->probed = true;
1573
1574 return ERROR_OK;
1575 }
1576
1577 static int kinetis_probe(struct flash_bank *bank)
1578 {
1579 if (bank->target->state != TARGET_HALTED) {
1580 LOG_WARNING("Cannot communicate... target not halted.");
1581 return ERROR_TARGET_NOT_HALTED;
1582 }
1583
1584 return kinetis_read_part_info(bank);
1585 }
1586
1587 static int kinetis_auto_probe(struct flash_bank *bank)
1588 {
1589 struct kinetis_flash_bank *kinfo = bank->driver_priv;
1590
1591 if (kinfo && kinfo->probed)
1592 return ERROR_OK;
1593
1594 return kinetis_probe(bank);
1595 }
1596
1597 static int kinetis_info(struct flash_bank *bank, char *buf, int buf_size)
1598 {
1599 const char *bank_class_names[] = {
1600 "(ANY)", "PFlash", "FlexNVM", "FlexRAM"
1601 };
1602
1603 struct kinetis_flash_bank *kinfo = bank->driver_priv;
1604
1605 (void) snprintf(buf, buf_size,
1606 "%s driver for %s flash bank %s at 0x%8.8" PRIx32 "",
1607 bank->driver->name, bank_class_names[kinfo->flash_class],
1608 bank->name, bank->base);
1609
1610 return ERROR_OK;
1611 }
1612
1613 static int kinetis_blank_check(struct flash_bank *bank)
1614 {
1615 struct kinetis_flash_bank *kinfo = bank->driver_priv;
1616
1617 if (bank->target->state != TARGET_HALTED) {
1618 LOG_ERROR("Target not halted");
1619 return ERROR_TARGET_NOT_HALTED;
1620 }
1621
1622 if (kinfo->flash_class == FC_PFLASH || kinfo->flash_class == FC_FLEX_NVM) {
1623 int result;
1624 bool block_dirty = false;
1625 uint8_t ftfx_fstat;
1626
1627 if (kinfo->flash_class == FC_FLEX_NVM) {
1628 uint8_t fcfg1_depart = (uint8_t)((kinfo->sim_fcfg1 >> 8) & 0x0f);
1629 /* block operation cannot be used on FlexNVM when EEPROM backup partition is set */
1630 if (fcfg1_depart != 0xf && fcfg1_depart != 0)
1631 block_dirty = true;
1632 }
1633
1634 if (!block_dirty) {
1635 /* check if whole bank is blank */
1636 result = kinetis_ftfx_command(bank, FTFx_CMD_BLOCKSTAT, kinfo->prog_base,
1637 0, 0, 0, 0, 0, 0, 0, 0, &ftfx_fstat);
1638
1639 if (result != ERROR_OK || (ftfx_fstat & 0x01))
1640 block_dirty = true;
1641 }
1642
1643 if (block_dirty) {
1644 /* the whole bank is not erased, check sector-by-sector */
1645 int i;
1646 for (i = 0; i < bank->num_sectors; i++) {
1647 /* normal margin */
1648 result = kinetis_ftfx_command(bank, FTFx_CMD_SECTSTAT, kinfo->prog_base + bank->sectors[i].offset,
1649 1, 0, 0, 0, 0, 0, 0, 0, &ftfx_fstat);
1650
1651 if (result == ERROR_OK) {
1652 bank->sectors[i].is_erased = !(ftfx_fstat & 0x01);
1653 } else {
1654 LOG_DEBUG("Ignoring errored PFlash sector blank-check");
1655 bank->sectors[i].is_erased = -1;
1656 }
1657 }
1658 } else {
1659 /* the whole bank is erased, update all sectors */
1660 int i;
1661 for (i = 0; i < bank->num_sectors; i++)
1662 bank->sectors[i].is_erased = 1;
1663 }
1664 } else {
1665 LOG_WARNING("kinetis_blank_check not supported yet for FlexRAM");
1666 return ERROR_FLASH_OPERATION_FAILED;
1667 }
1668
1669 return ERROR_OK;
1670 }
1671
1672 static const struct command_registration kinetis_securtiy_command_handlers[] = {
1673 {
1674 .name = "check_security",
1675 .mode = COMMAND_EXEC,
1676 .help = "",
1677 .usage = "",
1678 .handler = kinetis_check_flash_security_status,
1679 },
1680 {
1681 .name = "mass_erase",
1682 .mode = COMMAND_EXEC,
1683 .help = "",
1684 .usage = "",
1685 .handler = kinetis_mdm_mass_erase,
1686 },
1687 {
1688 .name = "test_securing",
1689 .mode = COMMAND_EXEC,
1690 .help = "",
1691 .usage = "",
1692 .handler = kinetis_securing_test,
1693 },
1694 COMMAND_REGISTRATION_DONE
1695 };
1696
1697 static const struct command_registration kinetis_exec_command_handlers[] = {
1698 {
1699 .name = "mdm",
1700 .mode = COMMAND_ANY,
1701 .help = "",
1702 .usage = "",
1703 .chain = kinetis_securtiy_command_handlers,
1704 },
1705 {
1706 .name = "disable_wdog",
1707 .mode = COMMAND_EXEC,
1708 .help = "Disable the watchdog timer",
1709 .usage = "",
1710 .handler = kinetis_disable_wdog_handler,
1711 },
1712 COMMAND_REGISTRATION_DONE
1713 };
1714
1715 static const struct command_registration kinetis_command_handler[] = {
1716 {
1717 .name = "kinetis",
1718 .mode = COMMAND_ANY,
1719 .help = "kinetis NAND flash controller commands",
1720 .usage = "",
1721 .chain = kinetis_exec_command_handlers,
1722 },
1723 COMMAND_REGISTRATION_DONE
1724 };
1725
1726
1727
1728 struct flash_driver kinetis_flash = {
1729 .name = "kinetis",
1730 .commands = kinetis_command_handler,
1731 .flash_bank_command = kinetis_flash_bank_command,
1732 .erase = kinetis_erase,
1733 .protect = kinetis_protect,
1734 .write = kinetis_write,
1735 .read = default_flash_read,
1736 .probe = kinetis_probe,
1737 .auto_probe = kinetis_auto_probe,
1738 .erase_check = kinetis_blank_check,
1739 .protect_check = kinetis_protect_check,
1740 .info = kinetis_info,
1741 };

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)