rdc.c 18 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725726727728729730731732733734735736737738739740741742743744745746747748749
  1. #include "chip.h"
  2. #include "rdc.h"
  3. #define DDR_RDC_MEM_RANGE (512*1024*1024)
  4. #define SRAM_RDC_MEM_RANGE (4*1024*1024)
  5. // CRTL
  6. #define SEC_CFG_LOCK (1<<31)
  7. #define INC_BLK_IDX (1<<8)
  8. typedef struct {
  9. rdc_master_e master;
  10. uint32_t seg_start;
  11. uint32_t seg_end;
  12. uint8_t access; // 0: not allow access 1: allow access
  13. }rdc_init_item_t;
  14. // seg size = 1MB
  15. static const rdc_init_item_t rdc_ddr_init_tab[] = {
  16. {RDC_M_CPU, 0, 512, 1},
  17. {RDC_M_MCU, 0, 512, 1},
  18. {RDC_M_LCD, 0, 512, 1},
  19. {RDC_M_ITU, 0, 512, 1},
  20. {RDC_M_MFC, 0, 512, 1},
  21. {RDC_M_GPU, 0, 512, 1},
  22. {RDC_M_QOI, 0, 512, 1},
  23. {RDC_M_BLEND, 0, 512, 1},
  24. {RDC_M_PXP, 0, 512, 1},
  25. {RDC_M_WRAP, 0, 512, 1},
  26. {RDC_M_DMA, 0, 512, 1},
  27. {RDC_M_USB, 0, 512, 1},
  28. {RDC_M_SD0, 0, 512, 1},
  29. {RDC_M_SD1, 0, 512, 1},
  30. {RDC_M_ETH, 0, 512, 1},
  31. };
  32. // seg size = 128KB
  33. static const rdc_init_item_t rdc_sram_init_tab[] = {
  34. {RDC_M_CPU, 0, 32, 1},
  35. {RDC_M_MCU, 0, 32, 1},
  36. {RDC_M_LCD, 0, 32, 1},
  37. {RDC_M_ITU, 0, 32, 1},
  38. {RDC_M_MFC, 0, 32, 1},
  39. {RDC_M_GPU, 0, 32, 1},
  40. {RDC_M_QOI, 0, 32, 1},
  41. {RDC_M_BLEND, 0, 32, 1},
  42. {RDC_M_PXP, 0, 32, 1},
  43. {RDC_M_WRAP, 0, 32, 1},
  44. {RDC_M_DMA, 0, 32, 1},
  45. {RDC_M_USB, 0, 32, 1},
  46. {RDC_M_SD0, 0, 32, 1},
  47. {RDC_M_SD1, 0, 32, 1},
  48. {RDC_M_ETH, 0, 32, 1},
  49. };
  50. /*
  51. * When set to 1, CTRL, BLK_LUT, IRQ_ENABLE and IRQ_SET become read-only registers.
  52. * To set this bit to 0, the RDC must be reset.
  53. */
  54. static void rdc_ddr_security_cfg_lock(rdc_ddr_t *rdc, int lock)
  55. {
  56. if (lock)
  57. rdc->CTRL |= SEC_CFG_LOCK;
  58. else
  59. rdc->CTRL &= ~SEC_CFG_LOCK;
  60. }
  61. static void rdc_ddr_blk_idx_auto_inc_enable(rdc_ddr_t *rdc, int enable)
  62. {
  63. if (enable)
  64. rdc->CTRL |= INC_BLK_IDX;
  65. else
  66. rdc->CTRL &= ~INC_BLK_IDX;
  67. }
  68. static uint32_t rdc_ddr_get_blk_max(rdc_ddr_t *rdc)
  69. {
  70. if (rdc->BLK_MAX == 0)
  71. return 1;
  72. else
  73. return rdc->BLK_MAX;
  74. }
  75. static uint32_t rdc_ddr_get_blk_size_in_bytes(rdc_ddr_t *rdc)
  76. {
  77. return DDR_RDC_MEM_RANGE / rdc_ddr_get_blk_max(rdc);
  78. }
  79. static int rdc_ddr_set_blk_idx(rdc_ddr_t *rdc, uint32_t blk)
  80. {
  81. if (blk >= rdc_ddr_get_blk_max(rdc))
  82. return -1;
  83. rdc->BLK_IDX_ADDR = blk;
  84. return 0;
  85. }
  86. static uint32_t rdc_ddr_get_seg_max_of_blk(rdc_ddr_t *rdc)
  87. {
  88. return 32;
  89. }
  90. static uint32_t rdc_ddr_get_seg_sum(rdc_ddr_t *rdc)
  91. {
  92. return rdc_ddr_get_seg_max_of_blk(rdc) * rdc_ddr_get_blk_max(rdc);
  93. }
  94. static uint32_t rdc_ddr_get_seg_size_in_bytes(rdc_ddr_t *rdc)
  95. {
  96. return DDR_RDC_MEM_RANGE / rdc_ddr_get_seg_sum(rdc);
  97. }
  98. /*
  99. *@param
  100. * access:
  101. * 0: not allow access 1: allow access
  102. */
  103. static int rdc_ddr_set_seg_range_of_blk(rdc_ddr_t *rdc, uint32_t blk,
  104. uint32_t seg_start, uint32_t seg_end, uint8_t access)
  105. {
  106. if (seg_start >= rdc_ddr_get_seg_max_of_blk(rdc))
  107. return -1;
  108. if (seg_end > rdc_ddr_get_seg_max_of_blk(rdc))
  109. return -1;
  110. if (seg_start >= seg_end)
  111. return -1;
  112. if (rdc_ddr_set_blk_idx(rdc, blk) != 0)
  113. return -1;
  114. if (access) {
  115. rdc->BLK_LUT &= ~((~(0xffffffff << (seg_end - seg_start))) << seg_start);
  116. } else {
  117. rdc->BLK_LUT |= ((~(0xffffffff << (seg_end - seg_start))) << seg_start);
  118. }
  119. return 0;
  120. }
  121. static uint32_t rdc_ddr_get_irq_status(rdc_ddr_t *rdc)
  122. {
  123. return rdc->IRQ_STAT;
  124. }
  125. static void rdc_ddr_irq_enable(rdc_ddr_t *rdc, uint32_t irqs, int enable)
  126. {
  127. if (enable)
  128. rdc->IRQ_ENABLE |= irqs;
  129. else
  130. rdc->IRQ_ENABLE &= ~irqs;
  131. }
  132. static void rdc_ddr_irq_clear(rdc_ddr_t *rdc, uint32_t irqs)
  133. {
  134. rdc->IRQ_CLEAR |= irqs;
  135. }
  136. /*
  137. * used for debug.
  138. */
  139. static void rdc_ddr_irq_set(rdc_ddr_t *rdc, uint32_t irqs, int set)
  140. {
  141. if (set)
  142. rdc->IRQ_SET |= irqs;
  143. else
  144. rdc->IRQ_SET &= ~irqs;
  145. }
  146. /*
  147. *@param
  148. * access:
  149. * 0: not allow access 1: allow access
  150. *@note:
  151. * seg size = 1 MB.
  152. * seg max = 512.
  153. */
  154. int rdc_ddr_set_master_mem_range(rdc_ddr_t *rdc, rdc_master_e rdc_master,
  155. uint32_t seg_start, uint32_t seg_end, uint8_t access)
  156. {
  157. int blk_start;
  158. int blk_end;
  159. int i;
  160. int seg_start_of_blk;
  161. int seg_end_of_blk;
  162. if (seg_start >= rdc_ddr_get_seg_sum(rdc))
  163. return -1;
  164. if (seg_end > rdc_ddr_get_seg_sum(rdc))
  165. return -1;
  166. if (seg_start >= seg_end)
  167. return -1;
  168. rdc_ddr_blk_idx_auto_inc_enable(rdc, 0);
  169. blk_start = seg_start / rdc_ddr_get_seg_max_of_blk(rdc);
  170. blk_end = (seg_end + rdc_ddr_get_seg_max_of_blk(rdc) - 1) / rdc_ddr_get_seg_max_of_blk(rdc);
  171. for (i=blk_start; i<blk_end; i++) {
  172. seg_start_of_blk = seg_start % rdc_ddr_get_seg_max_of_blk(rdc);
  173. if ((rdc_ddr_get_seg_max_of_blk(rdc) - seg_start_of_blk) > (seg_end - seg_start)) {
  174. seg_end_of_blk = seg_start_of_blk + seg_end - seg_start;
  175. } else {
  176. seg_end_of_blk = rdc_ddr_get_seg_max_of_blk(rdc);
  177. }
  178. seg_start += seg_end_of_blk - seg_start_of_blk;
  179. rdc->LUT_MASTER_SEL = rdc_master;
  180. rdc_ddr_set_seg_range_of_blk(rdc, i, seg_start_of_blk, seg_end_of_blk, access);
  181. }
  182. return 0;
  183. }
  184. /*
  185. *@brief:
  186. * 获取从seg_offset开始的第一段符合access条件的段区域。
  187. */
  188. int rdc_ddr_get_master_mem_range(rdc_ddr_t *rdc, rdc_master_e rdc_master,
  189. uint32_t seg_offset,
  190. uint32_t *seg_start, uint32_t *seg_end, uint8_t access)
  191. {
  192. int ret = -1;
  193. int blk;
  194. int seg;
  195. int flag = 0;
  196. if (seg_offset >= rdc_ddr_get_seg_sum(rdc)) {
  197. goto exit;
  198. }
  199. rdc_ddr_blk_idx_auto_inc_enable(rdc, 0);
  200. rdc->LUT_MASTER_SEL = rdc_master;
  201. blk = seg_offset / rdc_ddr_get_seg_max_of_blk(rdc);
  202. seg = seg_offset % rdc_ddr_get_seg_max_of_blk(rdc);
  203. for (; blk<rdc_ddr_get_blk_max(rdc); blk++) {
  204. rdc_ddr_set_blk_idx(rdc, blk);
  205. for (; seg < rdc_ddr_get_seg_max_of_blk(rdc); seg++) {
  206. if (access) {
  207. if (!(rdc->BLK_LUT & (1 << seg))) {
  208. if (!flag) {
  209. flag = 1;
  210. *seg_end = rdc_ddr_get_seg_sum(rdc);
  211. *seg_start = blk*rdc_ddr_get_seg_max_of_blk(rdc) + seg;
  212. }
  213. } else {
  214. if (flag) {
  215. *seg_end = blk*rdc_ddr_get_seg_max_of_blk(rdc) + seg;
  216. ret = 0;
  217. goto exit;
  218. }
  219. }
  220. } else {
  221. if (rdc->BLK_LUT & (1 << seg)) {
  222. if (!flag) {
  223. flag = 1;
  224. *seg_end = rdc_ddr_get_seg_sum(rdc);
  225. *seg_start = blk*rdc_ddr_get_seg_max_of_blk(rdc) + seg;
  226. }
  227. } else {
  228. if (flag) {
  229. *seg_end = blk*rdc_ddr_get_seg_max_of_blk(rdc) + seg;
  230. ret = 0;
  231. goto exit;
  232. }
  233. }
  234. }
  235. }
  236. seg = 0;
  237. }
  238. exit:
  239. return ret;
  240. }
  241. /*
  242. *@brief:
  243. * 获取master在某段上的访问权限。
  244. *@return:
  245. * 0: 不允许访问 1: 允许访问
  246. */
  247. int rdc_ddr_get_master_mem_seg_access_sta(rdc_ddr_t *rdc,
  248. rdc_master_e rdc_master, uint32_t seg)
  249. {
  250. int blk;
  251. if (seg >= rdc_ddr_get_seg_sum(rdc)) {
  252. return 0;
  253. }
  254. rdc_ddr_blk_idx_auto_inc_enable(rdc, 0);
  255. rdc->LUT_MASTER_SEL = rdc_master;
  256. blk = seg / rdc_ddr_get_seg_max_of_blk(rdc);
  257. rdc_ddr_set_blk_idx(rdc, blk);
  258. seg = seg % rdc_ddr_get_seg_max_of_blk(rdc);
  259. return (rdc->BLK_LUT & (1 << seg))? 0:1;
  260. }
  261. static rdc_irq_info_t rdc_ddr_get_irq_info_vbus(rdc_ddr_t *rdc)
  262. {
  263. rdc_irq_info_t bus_irq_info = {0};
  264. bus_irq_info.violation_addr = rdc->IRQ_INFO1_VBUS;
  265. bus_irq_info.AxPROT = (rdc->IRQ_INFO2_VBUS & (1<<31))? 1:0;
  266. bus_irq_info.ERR_MULTI = (rdc->IRQ_INFO2_VBUS & (1<<24))? 1:0;
  267. bus_irq_info.ERR_BOTH = (rdc->IRQ_INFO2_VBUS & (1<<20))? 1:0;
  268. bus_irq_info.WnR = (rdc->IRQ_INFO2_VBUS & (1<<16))? 1:0;
  269. bus_irq_info.AxID = rdc->IRQ_INFO2_VBUS & 0xffff;
  270. return bus_irq_info;
  271. }
  272. static rdc_irq_info_t rdc_ddr_get_irq_info_gbus(rdc_ddr_t *rdc)
  273. {
  274. rdc_irq_info_t bus_irq_info = {0};
  275. bus_irq_info.violation_addr = rdc->IRQ_INFO1_GBUS;
  276. bus_irq_info.AxPROT = (rdc->IRQ_INFO2_GBUS & (1<<31))? 1:0;
  277. bus_irq_info.ERR_MULTI = (rdc->IRQ_INFO2_GBUS & (1<<24))? 1:0;
  278. bus_irq_info.ERR_BOTH = (rdc->IRQ_INFO2_GBUS & (1<<20))? 1:0;
  279. bus_irq_info.WnR = (rdc->IRQ_INFO2_GBUS & (1<<16))? 1:0;
  280. bus_irq_info.AxID = rdc->IRQ_INFO2_GBUS & 0xffff;
  281. return bus_irq_info;
  282. }
  283. static rdc_irq_info_t rdc_ddr_get_irq_info_chbus(rdc_ddr_t *rdc)
  284. {
  285. rdc_irq_info_t bus_irq_info = {0};
  286. bus_irq_info.violation_addr = rdc->IRQ_INFO1_CHBUS;
  287. bus_irq_info.AxPROT = (rdc->IRQ_INFO2_CHBUS & (1<<31))? 1:0;
  288. bus_irq_info.ERR_MULTI = (rdc->IRQ_INFO2_CHBUS & (1<<24))? 1:0;
  289. bus_irq_info.ERR_BOTH = (rdc->IRQ_INFO2_CHBUS & (1<<20))? 1:0;
  290. bus_irq_info.WnR = (rdc->IRQ_INFO2_CHBUS & (1<<16))? 1:0;
  291. bus_irq_info.AxID = rdc->IRQ_INFO2_CHBUS & 0xffff;
  292. return bus_irq_info;
  293. }
  294. static rdc_irq_info_t rdc_ddr_get_irq_info_mcu(rdc_ddr_t *rdc)
  295. {
  296. rdc_irq_info_t bus_irq_info = {0};
  297. bus_irq_info.violation_addr = rdc->IRQ_INFO1_MCU;
  298. bus_irq_info.AxPROT = (rdc->IRQ_INFO2_MCU & (1<<31))? 1:0;
  299. bus_irq_info.ERR_MULTI = (rdc->IRQ_INFO2_MCU & (1<<24))? 1:0;
  300. bus_irq_info.ERR_BOTH = (rdc->IRQ_INFO2_MCU & (1<<20))? 1:0;
  301. bus_irq_info.WnR = (rdc->IRQ_INFO2_MCU & (1<<16))? 1:0;
  302. bus_irq_info.AxID = rdc->IRQ_INFO2_MCU & 0xffff;
  303. return bus_irq_info;
  304. }
  305. static rdc_irq_info_t rdc_ddr_get_irq_info_cpu(rdc_ddr_t *rdc)
  306. {
  307. rdc_irq_info_t bus_irq_info = {0};
  308. bus_irq_info.violation_addr = rdc->IRQ_INFO1_CPU;
  309. bus_irq_info.AxPROT = (rdc->IRQ_INFO2_CPU & (1<<31))? 1:0;
  310. bus_irq_info.ERR_MULTI = (rdc->IRQ_INFO2_CPU & (1<<24))? 1:0;
  311. bus_irq_info.ERR_BOTH = (rdc->IRQ_INFO2_CPU & (1<<20))? 1:0;
  312. bus_irq_info.WnR = (rdc->IRQ_INFO2_CPU & (1<<16))? 1:0;
  313. bus_irq_info.AxID = rdc->IRQ_INFO2_CPU & 0xffff;
  314. return bus_irq_info;
  315. }
  316. static void rdc_sram_security_cfg_lock(rdc_sram_t *rdc, int lock)
  317. {
  318. if (lock)
  319. rdc->CTRL |= SEC_CFG_LOCK;
  320. else
  321. rdc->CTRL &= ~SEC_CFG_LOCK;
  322. }
  323. static void rdc_sram_blk_idx_auto_inc_enable(rdc_sram_t *rdc, int enable)
  324. {
  325. if (enable)
  326. rdc->CTRL |= INC_BLK_IDX;
  327. else
  328. rdc->CTRL &= ~INC_BLK_IDX;
  329. }
  330. static uint32_t rdc_sram_get_blk_max(rdc_sram_t *rdc)
  331. {
  332. return 1;
  333. }
  334. static uint32_t rdc_sram_get_blk_size_in_bytes(rdc_sram_t *rdc)
  335. {
  336. return SRAM_RDC_MEM_RANGE / rdc_sram_get_blk_max(rdc);
  337. }
  338. static int rdc_sram_set_blk_idx(rdc_sram_t *rdc, uint32_t blk)
  339. {
  340. return 0;
  341. }
  342. static uint32_t rdc_sram_get_seg_max_of_blk(rdc_sram_t *rdc)
  343. {
  344. return 32;
  345. }
  346. static uint32_t rdc_sram_get_seg_sum(rdc_sram_t *rdc)
  347. {
  348. return rdc_sram_get_seg_max_of_blk(rdc) * rdc_sram_get_blk_max(rdc);
  349. }
  350. static uint32_t rdc_sram_get_seg_size_in_bytes(rdc_sram_t *rdc)
  351. {
  352. return SRAM_RDC_MEM_RANGE / rdc_sram_get_seg_sum(rdc);
  353. }
  354. /*
  355. *@param
  356. * access:
  357. * 0: not allow access 1: allow access
  358. */
  359. static int rdc_sram_set_seg_range_of_blk(rdc_sram_t *rdc, uint32_t blk, uint32_t seg_start,
  360. uint32_t seg_end, uint8_t access)
  361. {
  362. if (seg_start >= rdc_sram_get_seg_max_of_blk(rdc))
  363. return -1;
  364. if (seg_end > rdc_sram_get_seg_max_of_blk(rdc))
  365. return -1;
  366. if (seg_start >= seg_end)
  367. return -1;
  368. if (rdc_sram_set_blk_idx(rdc, blk) != 0)
  369. return -1;
  370. if (access) {
  371. rdc->BLK_LUT &= ~((~(0xffffffff << (seg_end - seg_start))) << seg_start);
  372. } else {
  373. rdc->BLK_LUT |= ((~(0xffffffff << (seg_end - seg_start))) << seg_start);
  374. }
  375. return 0;
  376. }
  377. static uint32_t rdc_sram_get_irq_status(rdc_sram_t *rdc)
  378. {
  379. return rdc->IRQ_STAT;
  380. }
  381. static void rdc_sram_irq_enable(rdc_sram_t *rdc, uint32_t irqs, int enable)
  382. {
  383. if (enable)
  384. rdc->IRQ_ENABLE |= irqs;
  385. else
  386. rdc->IRQ_ENABLE &= ~irqs;
  387. }
  388. static void rdc_sram_irq_clear(rdc_sram_t *rdc, uint32_t irqs)
  389. {
  390. rdc->IRQ_CLEAR |= irqs;
  391. }
  392. static void rdc_sram_irq_set(rdc_sram_t *rdc, uint32_t irqs, int set)
  393. {
  394. if (set)
  395. rdc->IRQ_SET |= irqs;
  396. else
  397. rdc->IRQ_SET &= ~irqs;
  398. }
  399. /*
  400. *@brief:
  401. * 获取从seg_offset开始的第一段符合access条件的段区域。
  402. */
  403. int rdc_sram_get_master_mem_range(rdc_sram_t *rdc, rdc_master_e rdc_master,
  404. uint32_t seg_offset,
  405. uint32_t *seg_start, uint32_t *seg_end, uint8_t access)
  406. {
  407. int ret = -1;
  408. int blk;
  409. int seg;
  410. int flag = 0;
  411. if (seg_offset >= rdc_sram_get_seg_sum(rdc)) {
  412. goto exit;
  413. }
  414. rdc_sram_blk_idx_auto_inc_enable(rdc, 0);
  415. rdc->LUT_MASTER_SEL = rdc_master;
  416. blk = seg_offset / rdc_sram_get_seg_max_of_blk(rdc);
  417. seg = seg_offset % rdc_sram_get_seg_max_of_blk(rdc);
  418. for (; blk<rdc_sram_get_blk_max(rdc); blk++) {
  419. rdc_sram_set_blk_idx(rdc, blk);
  420. for (; seg < rdc_sram_get_seg_max_of_blk(rdc); seg++) {
  421. if (access) {
  422. if (!(rdc->BLK_LUT & (1 << seg))) {
  423. if (!flag) {
  424. flag = 1;
  425. *seg_end = rdc_sram_get_seg_sum(rdc);
  426. *seg_start = blk*rdc_sram_get_seg_max_of_blk(rdc) + seg;
  427. }
  428. } else {
  429. if (flag) {
  430. *seg_end = blk*rdc_sram_get_seg_max_of_blk(rdc) + seg;
  431. ret = 0;
  432. goto exit;
  433. }
  434. }
  435. } else {
  436. if (rdc->BLK_LUT & (1 << seg)) {
  437. if (!flag) {
  438. flag = 1;
  439. *seg_end = rdc_sram_get_seg_sum(rdc);
  440. *seg_start = blk*rdc_sram_get_seg_max_of_blk(rdc) + seg;
  441. }
  442. } else {
  443. if (flag) {
  444. *seg_end = blk*rdc_sram_get_seg_max_of_blk(rdc) + seg;
  445. ret = 0;
  446. goto exit;
  447. }
  448. }
  449. }
  450. }
  451. seg = 0;
  452. }
  453. exit:
  454. return ret;
  455. }
  456. /*
  457. *@brief:
  458. * 获取master在某段上的访问权限。
  459. *@return:
  460. * 0: 不允许访问 1: 允许访问
  461. */
  462. int rdc_sram_get_master_mem_seg_access_sta(rdc_sram_t *rdc,
  463. rdc_master_e rdc_master, uint32_t seg)
  464. {
  465. int blk;
  466. if (seg >= rdc_sram_get_seg_sum(rdc)) {
  467. return 0;
  468. }
  469. rdc_sram_blk_idx_auto_inc_enable(rdc, 0);
  470. rdc->LUT_MASTER_SEL = rdc_master;
  471. blk = seg / rdc_sram_get_seg_max_of_blk(rdc);
  472. rdc_sram_set_blk_idx(rdc, blk);
  473. seg = seg % rdc_sram_get_seg_max_of_blk(rdc);
  474. return (rdc->BLK_LUT & (1 << seg))? 0:1;
  475. }
  476. /*
  477. *@param
  478. * access:
  479. * 0: not allow access 1: allow access
  480. *@note:
  481. * seg size = 128 KB.
  482. * seg max = 32.
  483. */
  484. int rdc_sram_set_master_mem_range(rdc_sram_t *rdc, rdc_master_e rdc_master,
  485. uint32_t seg_start, uint32_t seg_end, uint8_t access)
  486. {
  487. int blk_start;
  488. int blk_end;
  489. int i;
  490. int seg_start_of_blk;
  491. int seg_end_of_blk;
  492. if (seg_start >= rdc_sram_get_seg_sum(rdc))
  493. return -1;
  494. if (seg_end > rdc_sram_get_seg_sum(rdc))
  495. return -1;
  496. if (seg_start >= seg_end)
  497. return -1;
  498. rdc_sram_blk_idx_auto_inc_enable(rdc, 0);
  499. blk_start = seg_start / rdc_sram_get_seg_max_of_blk(rdc);
  500. blk_end = (seg_end + rdc_sram_get_seg_max_of_blk(rdc) - 1) / rdc_sram_get_seg_max_of_blk(rdc);
  501. for (i=blk_start; i<blk_end; i++) {
  502. seg_start_of_blk = seg_start % rdc_sram_get_seg_max_of_blk(rdc);
  503. if ((rdc_sram_get_seg_max_of_blk(rdc) - seg_start_of_blk) > (seg_end - seg_start)) {
  504. seg_end_of_blk = seg_start_of_blk + seg_end - seg_start;
  505. } else {
  506. seg_end_of_blk = rdc_sram_get_seg_max_of_blk(rdc);
  507. }
  508. seg_start += seg_end_of_blk - seg_start_of_blk;
  509. rdc->LUT_MASTER_SEL = rdc_master;
  510. rdc_sram_set_seg_range_of_blk(rdc, i, seg_start_of_blk, seg_end_of_blk, access);
  511. }
  512. return 0;
  513. }
  514. static rdc_irq_info_t rdc_sram_get_irq_info_others(rdc_sram_t *rdc)
  515. {
  516. rdc_irq_info_t bus_irq_info = {0};
  517. bus_irq_info.violation_addr = rdc->IRQ_INFO1_OTHERS;
  518. bus_irq_info.AxPROT = (rdc->IRQ_INFO2_OTHERS & (1<<31))? 1:0;
  519. bus_irq_info.ERR_MULTI = (rdc->IRQ_INFO2_OTHERS & (1<<24))? 1:0;
  520. bus_irq_info.ERR_BOTH = (rdc->IRQ_INFO2_OTHERS & (1<<20))? 1:0;
  521. bus_irq_info.WnR = (rdc->IRQ_INFO2_OTHERS & (1<<16))? 1:0;
  522. bus_irq_info.AxID = rdc->IRQ_INFO2_OTHERS & 0xffff;
  523. return bus_irq_info;
  524. }
  525. static rdc_irq_info_t rdc_sram_get_irq_info_mcu(rdc_sram_t *rdc)
  526. {
  527. rdc_irq_info_t bus_irq_info = {0};
  528. bus_irq_info.violation_addr = rdc->IRQ_INFO1_MCU;
  529. bus_irq_info.AxPROT = (rdc->IRQ_INFO2_MCU & (1<<31))? 1:0;
  530. bus_irq_info.ERR_MULTI = (rdc->IRQ_INFO2_MCU & (1<<24))? 1:0;
  531. bus_irq_info.ERR_BOTH = (rdc->IRQ_INFO2_MCU & (1<<20))? 1:0;
  532. bus_irq_info.WnR = (rdc->IRQ_INFO2_MCU & (1<<16))? 1:0;
  533. bus_irq_info.AxID = rdc->IRQ_INFO2_MCU & 0xffff;
  534. return bus_irq_info;
  535. }
  536. static void print_irq_info(rdc_irq_info_t irq_info)
  537. {
  538. #if 1
  539. printf("ADDR:0x%x\r\n \
  540. AxPROT:%d\r\n \
  541. ERR_MULTI:%d\r\n \
  542. ERR_BOTH:%d\r\n \
  543. WnR:%d\r\n \
  544. AxID:0x%x\r\n",
  545. irq_info.violation_addr,
  546. irq_info.AxPROT,
  547. irq_info.ERR_MULTI,
  548. irq_info.ERR_BOTH,
  549. irq_info.WnR,
  550. irq_info.AxID);
  551. #endif
  552. }
  553. static void rdc_ddr_IrqHandler(void *param)
  554. {
  555. uint32_t irq_sta;
  556. rdc_irq_info_t irq_info;
  557. rdc_ddr_t *rdc = (rdc_ddr_t *)param;
  558. irq_sta = rdc_ddr_get_irq_status(rdc);
  559. if (irq_sta & RDC_DDR_IRQ_CPU) {
  560. rdc_ddr_irq_set(rdc, RDC_DDR_IRQ_CPU, 0);
  561. irq_info = rdc_ddr_get_irq_info_cpu(rdc);
  562. printf("[rdc] ddr error int from CPU!\r\n");
  563. print_irq_info(irq_info);
  564. }
  565. if (irq_sta & RDC_DDR_IRQ_MCU) {
  566. rdc_ddr_irq_set(rdc, RDC_DDR_IRQ_MCU, 0);
  567. irq_info = rdc_ddr_get_irq_info_mcu(rdc);
  568. printf("[rdc] ddr error int from MCU!\r\n");
  569. print_irq_info(irq_info);
  570. }
  571. if (irq_sta & RDC_DDR_IRQ_CHBUS) {
  572. rdc_ddr_irq_set(rdc, RDC_DDR_IRQ_CHBUS, 0);
  573. irq_info = rdc_ddr_get_irq_info_chbus(rdc);
  574. printf("[rdc] ddr error int from CHBUS!\r\n");
  575. print_irq_info(irq_info);
  576. }
  577. if (irq_sta & RDC_DDR_IRQ_GBUS) {
  578. rdc_ddr_irq_set(rdc, RDC_DDR_IRQ_GBUS, 0);
  579. irq_info = rdc_ddr_get_irq_info_gbus(rdc);
  580. printf("[rdc] ddr error int from GBUS!\r\n");
  581. print_irq_info(irq_info);
  582. }
  583. if (irq_sta & RDC_DDR_IRQ_VBUS) {
  584. rdc_ddr_irq_set(rdc, RDC_DDR_IRQ_VBUS, 0);
  585. irq_info = rdc_ddr_get_irq_info_vbus(rdc);
  586. printf("[rdc] ddr error int from VBUS!\r\n");
  587. print_irq_info(irq_info);
  588. }
  589. rdc_ddr_irq_clear(rdc ,irq_sta);
  590. }
  591. static void rdc_sram_IrqHandler(void *param)
  592. {
  593. uint32_t irq_sta;
  594. rdc_irq_info_t irq_info;
  595. rdc_sram_t *rdc = (rdc_sram_t *)param;
  596. irq_sta = rdc_sram_get_irq_status(rdc);
  597. if (irq_sta & RDC_SRAM_IRQ_MCU) {
  598. rdc_sram_irq_set(rdc, RDC_SRAM_IRQ_MCU, 0);
  599. irq_info = rdc_sram_get_irq_info_mcu(rdc);
  600. printf("[rdc] sram error int from MCU!\r\n");
  601. print_irq_info(irq_info);
  602. }
  603. if (irq_sta & RDC_SRAM_IRQ_OTHER) {
  604. rdc_sram_irq_set(rdc, RDC_SRAM_IRQ_OTHER, 0);
  605. irq_info = rdc_sram_get_irq_info_others(rdc);
  606. printf("[rdc] sram error int from others!\r\n");
  607. print_irq_info(irq_info);
  608. }
  609. rdc_sram_irq_clear(rdc ,irq_sta);
  610. }
  611. static void rdc_ddr_init(rdc_ddr_t *rdc)
  612. {
  613. int i;
  614. for (i=0; i< sizeof(rdc_ddr_init_tab)/sizeof(rdc_ddr_init_tab[0]); i++) {
  615. rdc_ddr_set_master_mem_range(rdc,
  616. rdc_ddr_init_tab[i].master,
  617. rdc_ddr_init_tab[i].seg_start,
  618. rdc_ddr_init_tab[i].seg_end,
  619. rdc_ddr_init_tab[i].access);
  620. }
  621. request_irq(RDC_DDR_IRQn, 0, rdc_ddr_IrqHandler, (void *)rdc);
  622. rdc_ddr_irq_enable(rdc, RDC_DDR_IRQ_CPU | RDC_DDR_IRQ_MCU | \
  623. RDC_DDR_IRQ_CHBUS | RDC_DDR_IRQ_GBUS | \
  624. RDC_DDR_IRQ_VBUS, 1);
  625. }
  626. static void rdc_sram_init(rdc_sram_t *rdc)
  627. {
  628. int i;
  629. for (i=0; i< sizeof(rdc_sram_init_tab)/sizeof(rdc_sram_init_tab[0]); i++) {
  630. rdc_sram_set_master_mem_range(rdc,
  631. rdc_sram_init_tab[i].master,
  632. rdc_sram_init_tab[i].seg_start,
  633. rdc_sram_init_tab[i].seg_end,
  634. rdc_sram_init_tab[i].access);
  635. }
  636. request_irq(RDC_SRAM_IRQn, 0, rdc_sram_IrqHandler, (void *)rdc);
  637. rdc_sram_irq_enable(rdc, RDC_SRAM_IRQ_MCU | RDC_SRAM_IRQ_OTHER, 1);
  638. }
  639. void rdc_init(void)
  640. {
  641. rdc_ddr_init(RDC_DDR);
  642. rdc_sram_init(RDC_SRAM);
  643. }