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.
 
 
 
 
 
 

455 lines
16 KiB

  1. /***************************************************************************
  2. * Copyright (C) 2008 by Kevin McGuire *
  3. * Copyright (C) 2008 by Marcel Wijlaars *
  4. * Copyright (C) 2009 by Michael Ashton *
  5. * *
  6. * This program is free software; you can redistribute it and/or modify *
  7. * it under the terms of the GNU General Public License as published by *
  8. * the Free Software Foundation; either version 2 of the License, or *
  9. * (at your option) any later version. *
  10. * *
  11. * This program is distributed in the hope that it will be useful, *
  12. * but WITHOUT ANY WARRANTY; without even the implied warranty of *
  13. * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the *
  14. * GNU General Public License for more details. *
  15. * *
  16. * You should have received a copy of the GNU General Public License *
  17. * along with this program; if not, write to the *
  18. * Free Software Foundation, Inc., *
  19. * 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. *
  20. ***************************************************************************/
  21. #ifdef HAVE_CONFIG_H
  22. #include "config.h"
  23. #endif
  24. #include "flash.h"
  25. #include "armv4_5.h"
  26. #include "binarybuffer.h"
  27. #include "time_support.h"
  28. static int aduc702x_flash_bank_command(struct command_context_s *cmd_ctx, char *cmd, char **args, int argc, struct flash_bank_s *bank);
  29. static int aduc702x_register_commands(struct command_context_s *cmd_ctx);
  30. static int aduc702x_erase(struct flash_bank_s *bank, int first, int last);
  31. static int aduc702x_protect(struct flash_bank_s *bank, int set, int first, int last);
  32. static int aduc702x_write(struct flash_bank_s *bank, uint8_t *buffer, uint32_t offset, uint32_t count);
  33. static int aduc702x_write_single(struct flash_bank_s *bank, uint8_t *buffer, uint32_t offset, uint32_t count);
  34. static int aduc702x_write_block(struct flash_bank_s *bank, uint8_t *buffer, uint32_t offset, uint32_t count);
  35. static int aduc702x_probe(struct flash_bank_s *bank);
  36. static int aduc702x_info(struct flash_bank_s *bank, char *buf, int buf_size);
  37. static int aduc702x_protect_check(struct flash_bank_s *bank);
  38. static int aduc702x_build_sector_list(struct flash_bank_s *bank);
  39. static int aduc702x_check_flash_completion(target_t* target, unsigned int timeout_ms);
  40. static int aduc702x_set_write_enable(target_t *target, int enable);
  41. #define ADUC702x_FLASH 0xfffff800
  42. #define ADUC702x_FLASH_FEESTA (0*4)
  43. #define ADUC702x_FLASH_FEEMOD (1*4)
  44. #define ADUC702x_FLASH_FEECON (2*4)
  45. #define ADUC702x_FLASH_FEEDAT (3*4)
  46. #define ADUC702x_FLASH_FEEADR (4*4)
  47. #define ADUC702x_FLASH_FEESIGN (5*4)
  48. #define ADUC702x_FLASH_FEEPRO (6*4)
  49. #define ADUC702x_FLASH_FEEHIDE (7*4)
  50. typedef struct {
  51. uint32_t feesta;
  52. uint32_t feemod;
  53. uint32_t feecon;
  54. uint32_t feedat;
  55. uint32_t feeadr;
  56. uint32_t feesign;
  57. uint32_t feepro;
  58. uint32_t feehide;
  59. } ADUC702x_FLASH_MMIO;
  60. typedef struct
  61. {
  62. working_area_t *write_algorithm;
  63. } aduc702x_flash_bank_t;
  64. flash_driver_t aduc702x_flash =
  65. {
  66. .name = "aduc702x",
  67. .register_commands = aduc702x_register_commands,
  68. .flash_bank_command = aduc702x_flash_bank_command,
  69. .erase = aduc702x_erase,
  70. .protect = aduc702x_protect,
  71. .write = aduc702x_write,
  72. .probe = aduc702x_probe,
  73. .auto_probe = aduc702x_probe,
  74. .erase_check = default_flash_blank_check,
  75. .protect_check = aduc702x_protect_check,
  76. .info = aduc702x_info
  77. };
  78. static int aduc702x_register_commands(struct command_context_s *cmd_ctx)
  79. {
  80. return ERROR_OK;
  81. }
  82. /* flash bank aduc702x 0 0 0 0 <target#>
  83. * The ADC7019-28 devices all have the same flash layout */
  84. static int aduc702x_flash_bank_command(struct command_context_s *cmd_ctx, char *cmd, char **args, int argc, struct flash_bank_s *bank)
  85. {
  86. aduc702x_flash_bank_t *nbank;
  87. nbank = malloc(sizeof(aduc702x_flash_bank_t));
  88. bank->base = 0x80000;
  89. bank->size = 0xF800; // top 4k not accessible
  90. bank->driver_priv = nbank;
  91. aduc702x_build_sector_list(bank);
  92. return ERROR_OK;
  93. }
  94. static int aduc702x_build_sector_list(struct flash_bank_s *bank)
  95. {
  96. //aduc7026_flash_bank_t *aduc7026_info = bank->driver_priv;
  97. int i = 0;
  98. uint32_t offset = 0;
  99. // sector size is 512
  100. bank->num_sectors = bank->size / 512;
  101. bank->sectors = malloc(sizeof(flash_sector_t) * bank->num_sectors);
  102. for (i = 0; i < bank->num_sectors; ++i)
  103. {
  104. bank->sectors[i].offset = offset;
  105. bank->sectors[i].size = 512;
  106. offset += bank->sectors[i].size;
  107. bank->sectors[i].is_erased = -1;
  108. bank->sectors[i].is_protected = 0;
  109. }
  110. return ERROR_OK;
  111. }
  112. static int aduc702x_protect_check(struct flash_bank_s *bank)
  113. {
  114. printf("aduc702x_protect_check not implemented yet.\n");
  115. return ERROR_OK;
  116. }
  117. static int aduc702x_erase(struct flash_bank_s *bank, int first, int last)
  118. {
  119. //int res;
  120. int x;
  121. int count;
  122. //uint32_t v;
  123. target_t *target = bank->target;
  124. aduc702x_set_write_enable(target, 1);
  125. /* mass erase */
  126. if (((first | last) == 0) || ((first == 0) && (last >= bank->num_sectors))) {
  127. LOG_DEBUG("performing mass erase.\n");
  128. target_write_u16(target, ADUC702x_FLASH + ADUC702x_FLASH_FEEDAT, 0x3cff);
  129. target_write_u16(target, ADUC702x_FLASH + ADUC702x_FLASH_FEEADR, 0xffc3);
  130. target_write_u8(target, ADUC702x_FLASH + ADUC702x_FLASH_FEECON, 0x06);
  131. if (aduc702x_check_flash_completion(target, 3500) != ERROR_OK)
  132. {
  133. LOG_ERROR("mass erase failed\n");
  134. aduc702x_set_write_enable(target, 0);
  135. return ERROR_FLASH_OPERATION_FAILED;
  136. }
  137. LOG_DEBUG("mass erase successful.\n");
  138. return ERROR_OK;
  139. } else {
  140. unsigned long adr;
  141. count = last - first + 1;
  142. for (x = 0; x < count; ++x)
  143. {
  144. adr = bank->base + ((first + x) * 512);
  145. target_write_u16(target, ADUC702x_FLASH + ADUC702x_FLASH_FEEADR, adr);
  146. target_write_u8(target, ADUC702x_FLASH + ADUC702x_FLASH_FEECON, 0x05);
  147. if (aduc702x_check_flash_completion(target, 50) != ERROR_OK)
  148. {
  149. LOG_ERROR("failed to erase sector at address 0x%08lX\n", adr);
  150. aduc702x_set_write_enable(target, 0);
  151. return ERROR_FLASH_SECTOR_NOT_ERASED;
  152. }
  153. LOG_DEBUG("erased sector at address 0x%08lX\n", adr);
  154. }
  155. }
  156. aduc702x_set_write_enable(target, 0);
  157. return ERROR_OK;
  158. }
  159. static int aduc702x_protect(struct flash_bank_s *bank, int set, int first, int last)
  160. {
  161. printf("aduc702x_protect not implemented yet.\n");
  162. return ERROR_FLASH_OPERATION_FAILED;
  163. }
  164. /* If this fn returns ERROR_TARGET_RESOURCE_NOT_AVAILABLE, then the caller can fall
  165. * back to another mechanism that does not require onboard RAM
  166. *
  167. * Caller should not check for other return values specifically
  168. */
  169. static int aduc702x_write_block(struct flash_bank_s *bank, uint8_t *buffer, uint32_t offset, uint32_t count)
  170. {
  171. aduc702x_flash_bank_t *aduc702x_info = bank->driver_priv;
  172. target_t *target = bank->target;
  173. uint32_t buffer_size = 7000;
  174. working_area_t *source;
  175. uint32_t address = bank->base + offset;
  176. reg_param_t reg_params[6];
  177. armv4_5_algorithm_t armv4_5_info;
  178. int retval = ERROR_OK;
  179. if (((count%2)!=0)||((offset%2)!=0))
  180. {
  181. LOG_ERROR("write block must be multiple of two bytes in offset & length");
  182. return ERROR_FAIL;
  183. }
  184. /* parameters:
  185. r0 - address of source data (absolute)
  186. r1 - number of halfwords to be copied
  187. r2 - start address in flash (offset from beginning of flash memory)
  188. r3 - exit code
  189. r4 - base address of flash controller (0xFFFFF800)
  190. registers:
  191. r5 - scratch
  192. r6 - set to 2, used to write flash command
  193. */
  194. uint32_t aduc702x_flash_write_code[] = {
  195. //<_start>:
  196. 0xe3a05008, // mov r5, #8 ; 0x8
  197. 0xe5845004, // str r5, [r4, #4]
  198. 0xe3a06002, // mov r6, #2 ; 0x2
  199. //<next>:
  200. 0xe1c421b0, // strh r2, [r4, #16]
  201. 0xe0d050b2, // ldrh r5, [r0], #2
  202. 0xe1c450bc, // strh r5, [r4, #12]
  203. 0xe5c46008, // strb r6, [r4, #8]
  204. //<wait_complete>:
  205. 0xe1d430b0, // ldrh r3, [r4]
  206. 0xe3130004, // tst r3, #4 ; 0x4
  207. 0x1afffffc, // bne 1001c <wait_complete>
  208. 0xe2822002, // add r2, r2, #2 ; 0x2
  209. 0xe2511001, // subs r1, r1, #1 ; 0x1
  210. 0x0a000001, // beq 1003c <done>
  211. 0xe3130001, // tst r3, #1 ; 0x1
  212. 0x1afffff3, // bne 1000c <next>
  213. //<done>:
  214. 0xeafffffe // b 1003c <done>
  215. };
  216. /* flash write code */
  217. if (target_alloc_working_area(target, sizeof(aduc702x_flash_write_code),
  218. &aduc702x_info->write_algorithm) != ERROR_OK)
  219. {
  220. LOG_WARNING("no working area available, can't do block memory writes");
  221. return ERROR_TARGET_RESOURCE_NOT_AVAILABLE;
  222. };
  223. retval=target_write_buffer(target, aduc702x_info->write_algorithm->address,
  224. sizeof(aduc702x_flash_write_code), (uint8_t*)aduc702x_flash_write_code);
  225. if (retval!=ERROR_OK)
  226. {
  227. return retval;
  228. }
  229. /* memory buffer */
  230. while (target_alloc_working_area(target, buffer_size, &source) != ERROR_OK)
  231. {
  232. buffer_size /= 2;
  233. if (buffer_size <= 256)
  234. {
  235. /* if we already allocated the writing code, but failed to get a buffer, free the algorithm */
  236. if (aduc702x_info->write_algorithm)
  237. target_free_working_area(target, aduc702x_info->write_algorithm);
  238. LOG_WARNING("no large enough working area available, can't do block memory writes");
  239. return ERROR_TARGET_RESOURCE_NOT_AVAILABLE;
  240. }
  241. }
  242. armv4_5_info.common_magic = ARMV4_5_COMMON_MAGIC;
  243. armv4_5_info.core_mode = ARMV4_5_MODE_SVC;
  244. armv4_5_info.core_state = ARMV4_5_STATE_ARM;
  245. init_reg_param(&reg_params[0], "r0", 32, PARAM_OUT);
  246. init_reg_param(&reg_params[1], "r1", 32, PARAM_OUT);
  247. init_reg_param(&reg_params[2], "r2", 32, PARAM_OUT);
  248. init_reg_param(&reg_params[3], "r3", 32, PARAM_IN);
  249. init_reg_param(&reg_params[4], "r4", 32, PARAM_OUT);
  250. while (count > 0)
  251. {
  252. uint32_t thisrun_count = (count > buffer_size) ? buffer_size : count;
  253. retval=target_write_buffer(target, source->address, thisrun_count, buffer);
  254. if (retval!=ERROR_OK)
  255. {
  256. break;
  257. }
  258. buf_set_u32(reg_params[0].value, 0, 32, source->address);
  259. buf_set_u32(reg_params[1].value, 0, 32, thisrun_count/2);
  260. buf_set_u32(reg_params[2].value, 0, 32, address);
  261. buf_set_u32(reg_params[4].value, 0, 32, 0xFFFFF800);
  262. if ((retval = target_run_algorithm(target, 0, NULL, 5,
  263. reg_params, aduc702x_info->write_algorithm->address,
  264. aduc702x_info->write_algorithm->address + sizeof(aduc702x_flash_write_code) - 4,
  265. 10000, &armv4_5_info)) != ERROR_OK)
  266. {
  267. LOG_ERROR("error executing aduc702x flash write algorithm");
  268. break;
  269. }
  270. if ((buf_get_u32(reg_params[3].value, 0, 32) & 1) != 1)
  271. {
  272. /* FIX!!!! what does this mean??? replace w/sensible error message */
  273. LOG_ERROR("aduc702x detected error writing flash");
  274. retval = ERROR_FAIL;
  275. break;
  276. }
  277. buffer += thisrun_count;
  278. address += thisrun_count;
  279. count -= thisrun_count;
  280. }
  281. target_free_working_area(target, source);
  282. target_free_working_area(target, aduc702x_info->write_algorithm);
  283. destroy_reg_param(&reg_params[0]);
  284. destroy_reg_param(&reg_params[1]);
  285. destroy_reg_param(&reg_params[2]);
  286. destroy_reg_param(&reg_params[3]);
  287. destroy_reg_param(&reg_params[4]);
  288. return retval;
  289. }
  290. /* All-JTAG, single-access method. Very slow. Used only if there is no
  291. * working area available. */
  292. static int aduc702x_write_single(struct flash_bank_s *bank, uint8_t *buffer, uint32_t offset, uint32_t count)
  293. {
  294. uint32_t x;
  295. uint8_t b;
  296. target_t *target = bank->target;
  297. aduc702x_set_write_enable(target, 1);
  298. for (x = 0; x < count; x += 2) {
  299. // FEEADR = address
  300. target_write_u16(target, ADUC702x_FLASH + ADUC702x_FLASH_FEEADR, offset + x);
  301. // set up data
  302. if ((x + 1) == count)
  303. {
  304. // last byte
  305. target_read_u8(target, offset + x + 1, &b);
  306. }
  307. else
  308. b = buffer[x + 1];
  309. target_write_u16(target, ADUC702x_FLASH + ADUC702x_FLASH_FEEDAT, buffer[x] | (b << 8));
  310. // do single-write command
  311. target_write_u8(target, ADUC702x_FLASH + ADUC702x_FLASH_FEECON, 0x02);
  312. if (aduc702x_check_flash_completion(target, 1) != ERROR_OK)
  313. {
  314. LOG_ERROR("single write failed for address 0x%08lX\n", (unsigned long)(offset + x));
  315. aduc702x_set_write_enable(target, 0);
  316. return ERROR_FLASH_OPERATION_FAILED;
  317. }
  318. }
  319. LOG_DEBUG("wrote %d bytes at address 0x%08lX\n", (int)count, (unsigned long)(offset + x));
  320. aduc702x_set_write_enable(target, 0);
  321. return ERROR_OK;
  322. }
  323. int aduc702x_write(struct flash_bank_s *bank, uint8_t *buffer, uint32_t offset, uint32_t count)
  324. {
  325. int retval;
  326. /* try using a block write */
  327. if ((retval = aduc702x_write_block(bank, buffer, offset, count)) != ERROR_OK)
  328. {
  329. if (retval == ERROR_TARGET_RESOURCE_NOT_AVAILABLE)
  330. {
  331. /* if block write failed (no sufficient working area),
  332. * use normal (slow) JTAG method */
  333. LOG_WARNING("couldn't use block writes, falling back to single memory accesses");
  334. if ((retval = aduc702x_write_single(bank, buffer, offset, count)) != ERROR_OK)
  335. {
  336. LOG_ERROR("slow write failed");
  337. return ERROR_FLASH_OPERATION_FAILED;
  338. }
  339. }
  340. }
  341. return retval;
  342. }
  343. static int aduc702x_probe(struct flash_bank_s *bank)
  344. {
  345. return ERROR_OK;
  346. }
  347. static int aduc702x_info(struct flash_bank_s *bank, char *buf, int buf_size)
  348. {
  349. snprintf(buf, buf_size, "aduc702x flash driver info");
  350. return ERROR_OK;
  351. }
  352. /* sets FEEMOD bit 3
  353. * enable = 1 enables writes & erases, 0 disables them */
  354. static int aduc702x_set_write_enable(target_t *target, int enable)
  355. {
  356. // don't bother to preserve int enable bit here
  357. target_write_u16(target, ADUC702x_FLASH + ADUC702x_FLASH_FEEMOD, enable ? 8 : 0);
  358. return ERROR_OK;
  359. }
  360. /* wait up to timeout_ms for controller to not be busy,
  361. * then check whether the command passed or failed.
  362. *
  363. * this function sleeps 1ms between checks (after the first one),
  364. * so in some cases may slow things down without a usleep after the first read */
  365. static int aduc702x_check_flash_completion(target_t* target, unsigned int timeout_ms)
  366. {
  367. uint8_t v = 4;
  368. long long endtime = timeval_ms() + timeout_ms;
  369. while (1) {
  370. target_read_u8(target, ADUC702x_FLASH + ADUC702x_FLASH_FEESTA, &v);
  371. if ((v & 4) == 0) break;
  372. alive_sleep(1);
  373. if (timeval_ms() >= endtime) break;
  374. }
  375. if (v & 2) return ERROR_FAIL;
  376. // if a command is ignored, both the success and fail bits may be 0
  377. else if ((v & 3) == 0) return ERROR_FAIL;
  378. else return ERROR_OK;
  379. }