You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
 
 
 
 
 
 

650 lines
17 KiB

  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. * This program is free software; you can redistribute it and/or modify *
  9. * it under the terms of the GNU General Public License as published by *
  10. * the Free Software Foundation; either version 2 of the License, or *
  11. * (at your option) any later version. *
  12. * *
  13. * This program is distributed in the hope that it will be useful, *
  14. * but WITHOUT ANY WARRANTY; without even the implied warranty of *
  15. * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the *
  16. * GNU General Public License for more details. *
  17. * *
  18. * You should have received a copy of the GNU General Public License *
  19. * along with this program; if not, write to the *
  20. * Free Software Foundation, Inc., *
  21. * 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. *
  22. ***************************************************************************/
  23. #ifdef HAVE_CONFIG_H
  24. #include "config.h"
  25. #endif
  26. #include "replacements.h"
  27. #include "str9x.h"
  28. #include "flash.h"
  29. #include "target.h"
  30. #include "log.h"
  31. #include "armv4_5.h"
  32. #include "arm966e.h"
  33. #include "algorithm.h"
  34. #include "binarybuffer.h"
  35. #include <stdlib.h>
  36. #include <string.h>
  37. #include <unistd.h>
  38. static u32 bank1start = 0x00080000;
  39. int str9x_register_commands(struct command_context_s *cmd_ctx);
  40. int str9x_flash_bank_command(struct command_context_s *cmd_ctx, char *cmd, char **args, int argc, struct flash_bank_s *bank);
  41. int str9x_erase(struct flash_bank_s *bank, int first, int last);
  42. int str9x_protect(struct flash_bank_s *bank, int set, int first, int last);
  43. int str9x_write(struct flash_bank_s *bank, u8 *buffer, u32 offset, u32 count);
  44. int str9x_probe(struct flash_bank_s *bank);
  45. int str9x_handle_part_id_command(struct command_context_s *cmd_ctx, char *cmd, char **args, int argc);
  46. int str9x_protect_check(struct flash_bank_s *bank);
  47. int str9x_info(struct flash_bank_s *bank, char *buf, int buf_size);
  48. int str9x_handle_flash_config_command(struct command_context_s *cmd_ctx, char *cmd, char **args, int argc);
  49. flash_driver_t str9x_flash =
  50. {
  51. .name = "str9x",
  52. .register_commands = str9x_register_commands,
  53. .flash_bank_command = str9x_flash_bank_command,
  54. .erase = str9x_erase,
  55. .protect = str9x_protect,
  56. .write = str9x_write,
  57. .probe = str9x_probe,
  58. .auto_probe = str9x_probe,
  59. .erase_check = default_flash_blank_check,
  60. .protect_check = str9x_protect_check,
  61. .info = str9x_info
  62. };
  63. int str9x_register_commands(struct command_context_s *cmd_ctx)
  64. {
  65. command_t *str9x_cmd = register_command(cmd_ctx, NULL, "str9x", NULL, COMMAND_ANY, NULL);
  66. register_command(cmd_ctx, str9x_cmd, "flash_config", str9x_handle_flash_config_command, COMMAND_EXEC,
  67. "configure str9 flash controller");
  68. return ERROR_OK;
  69. }
  70. int str9x_build_block_list(struct flash_bank_s *bank)
  71. {
  72. str9x_flash_bank_t *str9x_info = bank->driver_priv;
  73. int i;
  74. int num_sectors;
  75. int b0_sectors = 0, b1_sectors = 0;
  76. u32 offset = 0;
  77. /* set if we have large flash str9 */
  78. str9x_info->variant = 0;
  79. str9x_info->bank1 = 0;
  80. switch (bank->size)
  81. {
  82. case (256 * 1024):
  83. b0_sectors = 4;
  84. break;
  85. case (512 * 1024):
  86. b0_sectors = 8;
  87. break;
  88. case (1024 * 1024):
  89. bank1start = 0x00100000;
  90. str9x_info->variant = 1;
  91. b0_sectors = 16;
  92. break;
  93. case (2048 * 1024):
  94. bank1start = 0x00200000;
  95. str9x_info->variant = 1;
  96. b0_sectors = 32;
  97. break;
  98. case (128 * 1024):
  99. str9x_info->variant = 1;
  100. str9x_info->bank1 = 1;
  101. b1_sectors = 8;
  102. bank1start = bank->base;
  103. break;
  104. case (32 * 1024):
  105. str9x_info->bank1 = 1;
  106. b1_sectors = 4;
  107. bank1start = bank->base;
  108. break;
  109. default:
  110. LOG_ERROR("BUG: unknown bank->size encountered");
  111. exit(-1);
  112. }
  113. num_sectors = b0_sectors + b1_sectors;
  114. bank->num_sectors = num_sectors;
  115. bank->sectors = malloc(sizeof(flash_sector_t) * num_sectors);
  116. str9x_info->sector_bits = malloc(sizeof(u32) * num_sectors);
  117. num_sectors = 0;
  118. for (i = 0; i < b0_sectors; i++)
  119. {
  120. bank->sectors[num_sectors].offset = offset;
  121. bank->sectors[num_sectors].size = 0x10000;
  122. offset += bank->sectors[i].size;
  123. bank->sectors[num_sectors].is_erased = -1;
  124. bank->sectors[num_sectors].is_protected = 1;
  125. str9x_info->sector_bits[num_sectors++] = (1<<i);
  126. }
  127. for (i = 0; i < b1_sectors; i++)
  128. {
  129. bank->sectors[num_sectors].offset = offset;
  130. bank->sectors[num_sectors].size = str9x_info->variant == 0 ? 0x2000 : 0x4000;
  131. offset += bank->sectors[i].size;
  132. bank->sectors[num_sectors].is_erased = -1;
  133. bank->sectors[num_sectors].is_protected = 1;
  134. if (str9x_info->variant)
  135. str9x_info->sector_bits[num_sectors++] = (1<<i);
  136. else
  137. str9x_info->sector_bits[num_sectors++] = (1<<(i+8));
  138. }
  139. return ERROR_OK;
  140. }
  141. /* flash bank str9x <base> <size> 0 0 <target#>
  142. */
  143. int str9x_flash_bank_command(struct command_context_s *cmd_ctx, char *cmd, char **args, int argc, struct flash_bank_s *bank)
  144. {
  145. str9x_flash_bank_t *str9x_info;
  146. if (argc < 6)
  147. {
  148. LOG_WARNING("incomplete flash_bank str9x configuration");
  149. return ERROR_FLASH_BANK_INVALID;
  150. }
  151. str9x_info = malloc(sizeof(str9x_flash_bank_t));
  152. bank->driver_priv = str9x_info;
  153. str9x_build_block_list(bank);
  154. str9x_info->write_algorithm = NULL;
  155. return ERROR_OK;
  156. }
  157. int str9x_protect_check(struct flash_bank_s *bank)
  158. {
  159. str9x_flash_bank_t *str9x_info = bank->driver_priv;
  160. target_t *target = bank->target;
  161. int i;
  162. u32 adr;
  163. u32 status = 0;
  164. if (bank->target->state != TARGET_HALTED)
  165. {
  166. LOG_ERROR("Target not halted");
  167. return ERROR_TARGET_NOT_HALTED;
  168. }
  169. /* read level one protection */
  170. if (str9x_info->variant)
  171. {
  172. if (str9x_info->bank1)
  173. {
  174. adr = bank1start + 0x18;
  175. target_write_u16(target, adr, 0x90);
  176. target_read_u16(target, adr, (u16*)&status);
  177. }
  178. else
  179. {
  180. adr = bank1start + 0x14;
  181. target_write_u16(target, adr, 0x90);
  182. target_read_u32(target, adr, &status);
  183. }
  184. }
  185. else
  186. {
  187. adr = bank1start + 0x10;
  188. target_write_u16(target, adr, 0x90);
  189. target_read_u16(target, adr, (u16*)&status);
  190. }
  191. /* read array command */
  192. target_write_u16(target, adr, 0xFF);
  193. for (i = 0; i < bank->num_sectors; i++)
  194. {
  195. if (status & str9x_info->sector_bits[i])
  196. bank->sectors[i].is_protected = 1;
  197. else
  198. bank->sectors[i].is_protected = 0;
  199. }
  200. return ERROR_OK;
  201. }
  202. int str9x_erase(struct flash_bank_s *bank, int first, int last)
  203. {
  204. target_t *target = bank->target;
  205. int i;
  206. u32 adr;
  207. u8 status;
  208. u8 erase_cmd;
  209. if (bank->target->state != TARGET_HALTED)
  210. {
  211. LOG_ERROR("Target not halted");
  212. return ERROR_TARGET_NOT_HALTED;
  213. }
  214. /* Check if we erase whole bank */
  215. if ((first == 0) && (last == (bank->num_sectors - 1)))
  216. {
  217. /* Optimize to run erase bank command instead of sector */
  218. erase_cmd = 0x80;
  219. }
  220. else
  221. {
  222. /* Erase sector command */
  223. erase_cmd = 0x20;
  224. }
  225. for (i = first; i <= last; i++)
  226. {
  227. adr = bank->base + bank->sectors[i].offset;
  228. /* erase sectors */
  229. target_write_u16(target, adr, erase_cmd);
  230. target_write_u16(target, adr, 0xD0);
  231. /* get status */
  232. target_write_u16(target, adr, 0x70);
  233. while (1) {
  234. target_read_u8(target, adr, &status);
  235. if( status & 0x80 )
  236. break;
  237. usleep(1000);
  238. }
  239. /* clear status, also clear read array */
  240. target_write_u16(target, adr, 0x50);
  241. /* read array command */
  242. target_write_u16(target, adr, 0xFF);
  243. if( status & 0x22 )
  244. {
  245. LOG_ERROR("error erasing flash bank, status: 0x%x", status);
  246. return ERROR_FLASH_OPERATION_FAILED;
  247. }
  248. /* If we ran erase bank command, we are finished */
  249. if (erase_cmd == 0x80)
  250. break;
  251. }
  252. for (i = first; i <= last; i++)
  253. bank->sectors[i].is_erased = 1;
  254. return ERROR_OK;
  255. }
  256. int str9x_protect(struct flash_bank_s *bank, int set, int first, int last)
  257. {
  258. target_t *target = bank->target;
  259. int i;
  260. u32 adr;
  261. u8 status;
  262. if (bank->target->state != TARGET_HALTED)
  263. {
  264. LOG_ERROR("Target not halted");
  265. return ERROR_TARGET_NOT_HALTED;
  266. }
  267. for (i = first; i <= last; i++)
  268. {
  269. /* Level One Protection */
  270. adr = bank->base + bank->sectors[i].offset;
  271. target_write_u16(target, adr, 0x60);
  272. if( set )
  273. target_write_u16(target, adr, 0x01);
  274. else
  275. target_write_u16(target, adr, 0xD0);
  276. /* query status */
  277. target_read_u8(target, adr, &status);
  278. /* clear status, also clear read array */
  279. target_write_u16(target, adr, 0x50);
  280. /* read array command */
  281. target_write_u16(target, adr, 0xFF);
  282. }
  283. return ERROR_OK;
  284. }
  285. int str9x_write_block(struct flash_bank_s *bank, u8 *buffer, u32 offset, u32 count)
  286. {
  287. str9x_flash_bank_t *str9x_info = bank->driver_priv;
  288. target_t *target = bank->target;
  289. u32 buffer_size = 8192;
  290. working_area_t *source;
  291. u32 address = bank->base + offset;
  292. reg_param_t reg_params[4];
  293. armv4_5_algorithm_t armv4_5_info;
  294. int retval = ERROR_OK;
  295. u32 str9x_flash_write_code[] = {
  296. /* write: */
  297. 0xe3c14003, /* bic r4, r1, #3 */
  298. 0xe3a03040, /* mov r3, #0x40 */
  299. 0xe1c430b0, /* strh r3, [r4, #0] */
  300. 0xe0d030b2, /* ldrh r3, [r0], #2 */
  301. 0xe0c130b2, /* strh r3, [r1], #2 */
  302. 0xe3a03070, /* mov r3, #0x70 */
  303. 0xe1c430b0, /* strh r3, [r4, #0] */
  304. /* busy: */
  305. 0xe5d43000, /* ldrb r3, [r4, #0] */
  306. 0xe3130080, /* tst r3, #0x80 */
  307. 0x0afffffc, /* beq busy */
  308. 0xe3a05050, /* mov r5, #0x50 */
  309. 0xe1c450b0, /* strh r5, [r4, #0] */
  310. 0xe3a050ff, /* mov r5, #0xFF */
  311. 0xe1c450b0, /* strh r5, [r4, #0] */
  312. 0xe3130012, /* tst r3, #0x12 */
  313. 0x1a000001, /* bne exit */
  314. 0xe2522001, /* subs r2, r2, #1 */
  315. 0x1affffed, /* bne write */
  316. /* exit: */
  317. 0xeafffffe, /* b exit */
  318. };
  319. /* flash write code */
  320. if (target_alloc_working_area(target, 4 * 19, &str9x_info->write_algorithm) != ERROR_OK)
  321. {
  322. LOG_WARNING("no working area available, can't do block memory writes");
  323. return ERROR_TARGET_RESOURCE_NOT_AVAILABLE;
  324. };
  325. target_write_buffer(target, str9x_info->write_algorithm->address, 19 * 4, (u8*)str9x_flash_write_code);
  326. /* memory buffer */
  327. while (target_alloc_working_area(target, buffer_size, &source) != ERROR_OK)
  328. {
  329. buffer_size /= 2;
  330. if (buffer_size <= 256)
  331. {
  332. /* if we already allocated the writing code, but failed to get a buffer, free the algorithm */
  333. if (str9x_info->write_algorithm)
  334. target_free_working_area(target, str9x_info->write_algorithm);
  335. LOG_WARNING("no large enough working area available, can't do block memory writes");
  336. return ERROR_TARGET_RESOURCE_NOT_AVAILABLE;
  337. }
  338. }
  339. armv4_5_info.common_magic = ARMV4_5_COMMON_MAGIC;
  340. armv4_5_info.core_mode = ARMV4_5_MODE_SVC;
  341. armv4_5_info.core_state = ARMV4_5_STATE_ARM;
  342. init_reg_param(&reg_params[0], "r0", 32, PARAM_OUT);
  343. init_reg_param(&reg_params[1], "r1", 32, PARAM_OUT);
  344. init_reg_param(&reg_params[2], "r2", 32, PARAM_OUT);
  345. init_reg_param(&reg_params[3], "r3", 32, PARAM_IN);
  346. while (count > 0)
  347. {
  348. u32 thisrun_count = (count > (buffer_size / 2)) ? (buffer_size / 2) : count;
  349. target_write_buffer(target, source->address, thisrun_count * 2, buffer);
  350. buf_set_u32(reg_params[0].value, 0, 32, source->address);
  351. buf_set_u32(reg_params[1].value, 0, 32, address);
  352. buf_set_u32(reg_params[2].value, 0, 32, thisrun_count);
  353. if ((retval = target->type->run_algorithm(target, 0, NULL, 4, reg_params, str9x_info->write_algorithm->address, str9x_info->write_algorithm->address + (18 * 4), 10000, &armv4_5_info)) != ERROR_OK)
  354. {
  355. LOG_ERROR("error executing str9x flash write algorithm");
  356. retval = ERROR_FLASH_OPERATION_FAILED;
  357. break;
  358. }
  359. if (buf_get_u32(reg_params[3].value, 0, 32) != 0x80)
  360. {
  361. retval = ERROR_FLASH_OPERATION_FAILED;
  362. break;
  363. }
  364. buffer += thisrun_count * 2;
  365. address += thisrun_count * 2;
  366. count -= thisrun_count;
  367. }
  368. target_free_working_area(target, source);
  369. target_free_working_area(target, str9x_info->write_algorithm);
  370. destroy_reg_param(&reg_params[0]);
  371. destroy_reg_param(&reg_params[1]);
  372. destroy_reg_param(&reg_params[2]);
  373. destroy_reg_param(&reg_params[3]);
  374. return retval;
  375. }
  376. int str9x_write(struct flash_bank_s *bank, u8 *buffer, u32 offset, u32 count)
  377. {
  378. target_t *target = bank->target;
  379. u32 words_remaining = (count / 2);
  380. u32 bytes_remaining = (count & 0x00000001);
  381. u32 address = bank->base + offset;
  382. u32 bytes_written = 0;
  383. u8 status;
  384. u32 retval;
  385. u32 check_address = offset;
  386. u32 bank_adr;
  387. int i;
  388. if (bank->target->state != TARGET_HALTED)
  389. {
  390. LOG_ERROR("Target not halted");
  391. return ERROR_TARGET_NOT_HALTED;
  392. }
  393. if (offset & 0x1)
  394. {
  395. LOG_WARNING("offset 0x%x breaks required 2-byte alignment", offset);
  396. return ERROR_FLASH_DST_BREAKS_ALIGNMENT;
  397. }
  398. for (i = 0; i < bank->num_sectors; i++)
  399. {
  400. u32 sec_start = bank->sectors[i].offset;
  401. u32 sec_end = sec_start + bank->sectors[i].size;
  402. /* check if destination falls within the current sector */
  403. if ((check_address >= sec_start) && (check_address < sec_end))
  404. {
  405. /* check if destination ends in the current sector */
  406. if (offset + count < sec_end)
  407. check_address = offset + count;
  408. else
  409. check_address = sec_end;
  410. }
  411. }
  412. if (check_address != offset + count)
  413. return ERROR_FLASH_DST_OUT_OF_BANK;
  414. /* multiple half words (2-byte) to be programmed? */
  415. if (words_remaining > 0)
  416. {
  417. /* try using a block write */
  418. if ((retval = str9x_write_block(bank, buffer, offset, words_remaining)) != ERROR_OK)
  419. {
  420. if (retval == ERROR_TARGET_RESOURCE_NOT_AVAILABLE)
  421. {
  422. /* if block write failed (no sufficient working area),
  423. * we use normal (slow) single dword accesses */
  424. LOG_WARNING("couldn't use block writes, falling back to single memory accesses");
  425. }
  426. else if (retval == ERROR_FLASH_OPERATION_FAILED)
  427. {
  428. LOG_ERROR("flash writing failed with error code: 0x%x", retval);
  429. return ERROR_FLASH_OPERATION_FAILED;
  430. }
  431. }
  432. else
  433. {
  434. buffer += words_remaining * 2;
  435. address += words_remaining * 2;
  436. words_remaining = 0;
  437. }
  438. }
  439. while (words_remaining > 0)
  440. {
  441. bank_adr = address & ~0x03;
  442. /* write data command */
  443. target_write_u16(target, bank_adr, 0x40);
  444. target->type->write_memory(target, address, 2, 1, buffer + bytes_written);
  445. /* get status command */
  446. target_write_u16(target, bank_adr, 0x70);
  447. while (1) {
  448. target_read_u8(target, bank_adr, &status);
  449. if( status & 0x80 )
  450. break;
  451. usleep(1000);
  452. }
  453. /* clear status reg and read array */
  454. target_write_u16(target, bank_adr, 0x50);
  455. target_write_u16(target, bank_adr, 0xFF);
  456. if (status & 0x10)
  457. return ERROR_FLASH_OPERATION_FAILED;
  458. else if (status & 0x02)
  459. return ERROR_FLASH_OPERATION_FAILED;
  460. bytes_written += 2;
  461. words_remaining--;
  462. address += 2;
  463. }
  464. if (bytes_remaining)
  465. {
  466. u8 last_halfword[2] = {0xff, 0xff};
  467. int i = 0;
  468. while(bytes_remaining > 0)
  469. {
  470. last_halfword[i++] = *(buffer + bytes_written);
  471. bytes_remaining--;
  472. bytes_written++;
  473. }
  474. bank_adr = address & ~0x03;
  475. /* write data comamnd */
  476. target_write_u16(target, bank_adr, 0x40);
  477. target->type->write_memory(target, address, 2, 1, last_halfword);
  478. /* query status command */
  479. target_write_u16(target, bank_adr, 0x70);
  480. while (1) {
  481. target_read_u8(target, bank_adr, &status);
  482. if( status & 0x80 )
  483. break;
  484. usleep(1000);
  485. }
  486. /* clear status reg and read array */
  487. target_write_u16(target, bank_adr, 0x50);
  488. target_write_u16(target, bank_adr, 0xFF);
  489. if (status & 0x10)
  490. return ERROR_FLASH_OPERATION_FAILED;
  491. else if (status & 0x02)
  492. return ERROR_FLASH_OPERATION_FAILED;
  493. }
  494. return ERROR_OK;
  495. }
  496. int str9x_probe(struct flash_bank_s *bank)
  497. {
  498. return ERROR_OK;
  499. }
  500. int str9x_handle_part_id_command(struct command_context_s *cmd_ctx, char *cmd, char **args, int argc)
  501. {
  502. return ERROR_OK;
  503. }
  504. int str9x_info(struct flash_bank_s *bank, char *buf, int buf_size)
  505. {
  506. snprintf(buf, buf_size, "str9x flash driver info" );
  507. return ERROR_OK;
  508. }
  509. int str9x_handle_flash_config_command(struct command_context_s *cmd_ctx, char *cmd, char **args, int argc)
  510. {
  511. str9x_flash_bank_t *str9x_info;
  512. flash_bank_t *bank;
  513. target_t *target = NULL;
  514. if (argc < 5)
  515. {
  516. return ERROR_COMMAND_SYNTAX_ERROR;
  517. }
  518. bank = get_flash_bank_by_num(strtoul(args[0], NULL, 0));
  519. if (!bank)
  520. {
  521. command_print(cmd_ctx, "flash bank '#%s' is out of bounds", args[0]);
  522. return ERROR_OK;
  523. }
  524. str9x_info = bank->driver_priv;
  525. target = bank->target;
  526. if (bank->target->state != TARGET_HALTED)
  527. {
  528. LOG_ERROR("Target not halted");
  529. return ERROR_TARGET_NOT_HALTED;
  530. }
  531. /* config flash controller */
  532. target_write_u32(target, FLASH_BBSR, strtoul(args[1], NULL, 0));
  533. target_write_u32(target, FLASH_NBBSR, strtoul(args[2], NULL, 0));
  534. target_write_u32(target, FLASH_BBADR, (strtoul(args[3], NULL, 0) >> 2));
  535. target_write_u32(target, FLASH_NBBADR, (strtoul(args[4], NULL, 0) >> 2));
  536. /* set bit 18 instruction TCM order as per flash programming manual */
  537. arm966e_write_cp15(target, 62, 0x40000);
  538. /* enable flash bank 1 */
  539. target_write_u32(target, FLASH_CR, 0x18);
  540. return ERROR_OK;
  541. }