blockops.S
上传用户:jlfgdled
上传日期:2013-04-10
资源大小:33168k
文件大小:12k
源码类别:

Linux/Unix编程

开发平台:

Unix_Linux

  1. /* $Id: blockops.S,v 1.41 2001/12/05 06:05:35 davem Exp $
  2.  * blockops.S: UltraSparc block zero optimized routines.
  3.  *
  4.  * Copyright (C) 1996, 1998, 1999, 2000 David S. Miller (davem@redhat.com)
  5.  * Copyright (C) 1997 Jakub Jelinek (jakub@redhat.com)
  6.  */
  7. #include "VIS.h"
  8. #include <asm/visasm.h>
  9. #include <asm/page.h>
  10. #include <asm/dcu.h>
  11. #include <asm/spitfire.h>
  12. #include <asm/pgtable.h>
  13. #include <asm/asm_offsets.h>
  14. #define TOUCH(reg0, reg1, reg2, reg3, reg4, reg5, reg6, reg7)
  15. fmovd %reg0, %f48;  fmovd %reg1, %f50;
  16. fmovd %reg2, %f52;  fmovd %reg3, %f54;
  17. fmovd %reg4, %f56;  fmovd %reg5, %f58;
  18. fmovd %reg6, %f60;  fmovd %reg7, %f62;
  19. #define DCACHE_SIZE (PAGE_SIZE * 2)
  20. #define TLBTEMP_ENT1 (60 << 3)
  21. #define TLBTEMP_ENT2 (61 << 3)
  22. #define TLBTEMP_ENTSZ (1 << 3)
  23. #if (PAGE_SHIFT == 13) || (PAGE_SHIFT == 19)
  24. #define PAGE_SIZE_REM 0x80
  25. #elif (PAGE_SHIFT == 16) || (PAGE_SHIFT == 22)
  26. #define PAGE_SIZE_REM 0x100
  27. #else
  28. #error Wrong PAGE_SHIFT specified
  29. #endif
  30. .text
  31. .align 32
  32. .globl copy_user_page
  33. .type copy_user_page,@function
  34. copy_user_page: /* %o0=dest, %o1=src, %o2=vaddr */
  35. VISEntry
  36. sethi %hi(PAGE_SIZE), %g3
  37. sub %o0, %g4, %g1
  38. and %o2, %g3, %o0
  39. sethi %hi(TLBTEMP_BASE), %o3
  40. sethi %uhi(_PAGE_VALID | _PAGE_SZBITS), %g3
  41. sub %o1, %g4, %g2
  42. sllx %g3, 32, %g3
  43. mov TLB_TAG_ACCESS, %o2
  44. or %g3, (_PAGE_CP | _PAGE_CV | _PAGE_P | _PAGE_L | _PAGE_W), %g3
  45. sethi %hi(DCACHE_SIZE), %o1
  46. or %g1, %g3, %g1
  47. or %g2, %g3, %g2
  48. add %o0, %o3, %o0
  49. add %o0, %o1, %o1
  50. #define FIX_INSN_1 0x96102060 /* mov (12 << 3), %o3 */
  51. cheetah_patch_1:
  52. mov TLBTEMP_ENT1, %o3
  53. rdpr %pstate, %g3
  54. wrpr %g3, PSTATE_IE, %pstate
  55. /* Do this now, before loading the fixed TLB entries for copying,
  56.  * so we do not risk a multiple TLB match condition later when
  57.  * restoring those entries.
  58.  */
  59. ldub [%g6 + AOFF_task_thread + AOFF_thread_use_blkcommit], %g3
  60. /* Spitfire Errata #32 workaround */
  61. mov PRIMARY_CONTEXT, %o4
  62. stxa %g0, [%o4] ASI_DMMU
  63. membar #Sync
  64. ldxa [%o3] ASI_DTLB_TAG_READ, %o4
  65. /* Spitfire Errata #32 workaround */
  66. mov PRIMARY_CONTEXT, %o5
  67. stxa %g0, [%o5] ASI_DMMU
  68. membar #Sync
  69. ldxa [%o3] ASI_DTLB_DATA_ACCESS, %g0
  70. ldxa [%o3] ASI_DTLB_DATA_ACCESS, %o5
  71. stxa %o0, [%o2] ASI_DMMU
  72. stxa %g1, [%o3] ASI_DTLB_DATA_ACCESS
  73. membar #Sync
  74. add %o3, (TLBTEMP_ENTSZ), %o3
  75. /* Spitfire Errata #32 workaround */
  76. mov PRIMARY_CONTEXT, %g5
  77. stxa %g0, [%g5] ASI_DMMU
  78. membar #Sync
  79. ldxa [%o3] ASI_DTLB_TAG_READ, %g5
  80. /* Spitfire Errata #32 workaround */
  81. mov PRIMARY_CONTEXT, %g7
  82. stxa %g0, [%g7] ASI_DMMU
  83. membar #Sync
  84. ldxa [%o3] ASI_DTLB_DATA_ACCESS, %g0
  85. ldxa [%o3] ASI_DTLB_DATA_ACCESS, %g7
  86. stxa %o1, [%o2] ASI_DMMU
  87. stxa %g2, [%o3] ASI_DTLB_DATA_ACCESS
  88. membar #Sync
  89. cmp %g3, 0
  90. bne,pn %xcc, copy_page_using_blkcommit
  91.  nop
  92. BRANCH_IF_ANY_CHEETAH(g3,o2,cheetah_copy_user_page)
  93. ba,pt %xcc, spitfire_copy_user_page
  94.  nop
  95. cheetah_copy_user_page:
  96. .globl cheetah_copy_user_page_nop_1_6
  97. cheetah_copy_user_page_nop_1_6:
  98. ldxa [%g0] ASI_DCU_CONTROL_REG, %g3
  99. sethi %uhi(DCU_PE), %o2
  100. sllx %o2, 32, %o2
  101. or %g3, %o2, %o2
  102. stxa %o2, [%g0] ASI_DCU_CONTROL_REG ! Enable P-cache
  103. membar #Sync
  104. sethi %hi((PAGE_SIZE/64)-7), %o2 ! A0 Group
  105. prefetch [%o1 + 0x000], #one_read ! MS
  106. or %o2, %lo((PAGE_SIZE/64)-7), %o2 ! A1 Group
  107. prefetch [%o1 + 0x040], #one_read ! MS
  108. prefetch [%o1 + 0x080], #one_read ! MS Group
  109. prefetch [%o1 + 0x0c0], #one_read ! MS Group
  110. ldd [%o1 + 0x000], %f0 ! MS Group
  111. prefetch [%o1 + 0x100], #one_read ! MS Group
  112. ldd [%o1 + 0x008], %f2 ! AX
  113. prefetch [%o1 + 0x140], #one_read ! MS Group
  114. ldd [%o1 + 0x010], %f4 ! AX
  115. prefetch [%o1 + 0x180], #one_read ! MS Group
  116. fmovd %f0, %f32 ! FGA Group
  117. ldd [%o1 + 0x018], %f6 ! AX
  118. fmovd %f2, %f34 ! FGA Group
  119. ldd [%o1 + 0x020], %f8 ! MS
  120. fmovd %f4, %f36 ! FGA Group
  121. ldd [%o1 + 0x028], %f10 ! AX
  122. membar #StoreStore ! MS
  123. fmovd %f6, %f38 ! FGA Group
  124. ldd [%o1 + 0x030], %f12 ! MS
  125. fmovd %f8, %f40 ! FGA Group
  126. ldd [%o1 + 0x038], %f14 ! AX
  127. fmovd %f10, %f42 ! FGA Group
  128. ldd [%o1 + 0x040], %f16 ! MS
  129. 1: ldd [%o1 + 0x048], %f2 ! AX (Group)
  130. fmovd %f12, %f44 ! FGA
  131. ldd [%o1 + 0x050], %f4 ! MS
  132. fmovd %f14, %f46 ! FGA Group
  133. stda %f32, [%o0] ASI_BLK_P ! MS
  134. ldd [%o1 + 0x058], %f6 ! AX
  135. fmovd %f16, %f32 ! FGA Group (8-cycle stall)
  136. ldd [%o1 + 0x060], %f8 ! MS
  137. fmovd %f2, %f34 ! FGA Group
  138. ldd [%o1 + 0x068], %f10 ! AX
  139. fmovd %f4, %f36 ! FGA Group
  140. ldd [%o1 + 0x070], %f12 ! MS
  141. fmovd %f6, %f38 ! FGA Group
  142. ldd [%o1 + 0x078], %f14 ! AX
  143. fmovd %f8, %f40 ! FGA Group
  144. ldd [%o1 + 0x080], %f16 ! AX
  145. prefetch [%o1 + 0x180], #one_read ! MS
  146. fmovd %f10, %f42 ! FGA Group
  147. subcc %o2, 1, %o2 ! A0
  148. add %o0, 0x40, %o0 ! A1
  149. bne,pt %xcc, 1b ! BR
  150.  add %o1, 0x40, %o1 ! A0 Group
  151. mov 5, %o2 ! A0 Group
  152. 1: ldd [%o1 + 0x048], %f2 ! AX
  153. fmovd %f12, %f44 ! FGA
  154. ldd [%o1 + 0x050], %f4 ! MS
  155. fmovd %f14, %f46 ! FGA Group
  156. stda %f32, [%o0] ASI_BLK_P ! MS
  157. ldd [%o1 + 0x058], %f6 ! AX
  158. fmovd %f16, %f32 ! FGA Group (8-cycle stall)
  159. ldd [%o1 + 0x060], %f8 ! MS
  160. fmovd %f2, %f34 ! FGA Group
  161. ldd [%o1 + 0x068], %f10 ! AX
  162. fmovd %f4, %f36 ! FGA Group
  163. ldd [%o1 + 0x070], %f12 ! MS
  164. fmovd %f6, %f38 ! FGA Group
  165. ldd [%o1 + 0x078], %f14 ! AX
  166. fmovd %f8, %f40 ! FGA Group
  167. ldd [%o1 + 0x080], %f16 ! MS
  168. fmovd %f10, %f42 ! FGA Group
  169. subcc %o2, 1, %o2 ! A0
  170. add %o0, 0x40, %o0 ! A1
  171. bne,pt %xcc, 1b ! BR
  172.  add %o1, 0x40, %o1 ! A0 Group
  173. ldd [%o1 + 0x048], %f2 ! AX
  174. fmovd %f12, %f44 ! FGA
  175. ldd [%o1 + 0x050], %f4 ! MS
  176. fmovd %f14, %f46 ! FGA Group
  177. stda %f32, [%o0] ASI_BLK_P ! MS
  178. ldd [%o1 + 0x058], %f6 ! AX
  179. fmovd %f16, %f32 ! FGA Group (8-cycle stall)
  180. ldd [%o1 + 0x060], %f8 ! MS
  181. fmovd %f2, %f34 ! FGA Group
  182. ldd [%o1 + 0x068], %f10 ! AX
  183. fmovd %f4, %f36 ! FGA Group
  184. ldd [%o1 + 0x070], %f12 ! MS
  185. fmovd %f6, %f38 ! FGA Group
  186. add %o0, 0x40, %o0 ! A0
  187. ldd [%o1 + 0x078], %f14 ! AX
  188. fmovd %f8, %f40 ! FGA Group
  189. fmovd %f10, %f42 ! FGA Group
  190. fmovd %f12, %f44 ! FGA Group
  191. fmovd %f14, %f46 ! FGA Group
  192. stda %f32, [%o0] ASI_BLK_P ! MS
  193. .globl cheetah_copy_user_page_nop_2_3
  194. cheetah_copy_user_page_nop_2_3:
  195. mov PRIMARY_CONTEXT, %o2
  196. stxa %g0, [%o2] ASI_DMMU ! Flush P-cache
  197. stxa %g3, [%g0] ASI_DCU_CONTROL_REG ! Disable P-cache
  198. ba,a,pt %xcc, copy_user_page_continue
  199. spitfire_copy_user_page:
  200. ldda [%o1] ASI_BLK_P, %f0
  201. add %o1, 0x40, %o1
  202. ldda [%o1] ASI_BLK_P, %f16
  203. add %o1, 0x40, %o1
  204. sethi %hi(PAGE_SIZE), %o2
  205. 1: TOUCH(f0, f2, f4, f6, f8, f10, f12, f14)
  206. ldda [%o1] ASI_BLK_P, %f32
  207. stda %f48, [%o0] ASI_BLK_P
  208. add %o1, 0x40, %o1
  209. sub %o2, 0x40, %o2
  210. add %o0, 0x40, %o0
  211. TOUCH(f16, f18, f20, f22, f24, f26, f28, f30)
  212. ldda [%o1] ASI_BLK_P, %f0
  213. stda %f48, [%o0] ASI_BLK_P
  214. add %o1, 0x40, %o1
  215. sub %o2, 0x40, %o2
  216. add %o0, 0x40, %o0
  217. TOUCH(f32, f34, f36, f38, f40, f42, f44, f46)
  218. ldda [%o1] ASI_BLK_P, %f16
  219. stda %f48, [%o0] ASI_BLK_P
  220. sub %o2, 0x40, %o2
  221. add %o1, 0x40, %o1
  222. cmp %o2, PAGE_SIZE_REM
  223. bne,pt %xcc, 1b
  224.  add %o0, 0x40, %o0
  225. #if (PAGE_SHIFT == 16) || (PAGE_SHIFT == 22)
  226. TOUCH(f0, f2, f4, f6, f8, f10, f12, f14)
  227. ldda [%o1] ASI_BLK_P, %f32
  228. stda %f48, [%o0] ASI_BLK_P
  229. add %o1, 0x40, %o1
  230. sub %o2, 0x40, %o2
  231. add %o0, 0x40, %o0
  232. TOUCH(f16, f18, f20, f22, f24, f26, f28, f30)
  233. ldda [%o1] ASI_BLK_P, %f0
  234. stda %f48, [%o0] ASI_BLK_P
  235. add %o1, 0x40, %o1
  236. sub %o2, 0x40, %o2
  237. add %o0, 0x40, %o0
  238. membar #Sync
  239. stda %f32, [%o0] ASI_BLK_P
  240. add %o0, 0x40, %o0
  241. stda %f0, [%o0] ASI_BLK_P
  242. #else
  243. membar #Sync
  244. stda %f0, [%o0] ASI_BLK_P
  245. add %o0, 0x40, %o0
  246. stda %f16, [%o0] ASI_BLK_P
  247. #endif
  248. copy_user_page_continue:
  249. membar #Sync
  250. VISExit
  251. mov TLB_TAG_ACCESS, %o2
  252. stxa %g5, [%o2] ASI_DMMU
  253. stxa %g7, [%o3] ASI_DTLB_DATA_ACCESS
  254. membar #Sync
  255. sub %o3, (TLBTEMP_ENTSZ), %o3
  256. stxa %o4, [%o2] ASI_DMMU
  257. stxa %o5, [%o3] ASI_DTLB_DATA_ACCESS
  258. membar #Sync
  259. rdpr %pstate, %g3
  260. jmpl %o7 + 0x8, %g0
  261.  wrpr %g3, PSTATE_IE, %pstate
  262. copy_page_using_blkcommit:
  263. membar #LoadStore | #StoreStore | #StoreLoad
  264. ldda [%o1] ASI_BLK_P, %f0
  265. add %o1, 0x40, %o1
  266. ldda [%o1] ASI_BLK_P, %f16
  267. add %o1, 0x40, %o1
  268. sethi %hi(PAGE_SIZE), %o2
  269. 1: TOUCH(f0, f2, f4, f6, f8, f10, f12, f14)
  270. ldda [%o1] ASI_BLK_P, %f32
  271. stda %f48, [%o0] ASI_BLK_COMMIT_P
  272. add %o1, 0x40, %o1
  273. sub %o2, 0x40, %o2
  274. add %o0, 0x40, %o0
  275. TOUCH(f16, f18, f20, f22, f24, f26, f28, f30)
  276. ldda [%o1] ASI_BLK_P, %f0
  277. stda %f48, [%o0] ASI_BLK_COMMIT_P
  278. add %o1, 0x40, %o1
  279. sub %o2, 0x40, %o2
  280. add %o0, 0x40, %o0
  281. TOUCH(f32, f34, f36, f38, f40, f42, f44, f46)
  282. ldda [%o1] ASI_BLK_P, %f16
  283. stda %f48, [%o0] ASI_BLK_COMMIT_P
  284. sub %o2, 0x40, %o2
  285. add %o1, 0x40, %o1
  286. cmp %o2, PAGE_SIZE_REM
  287. bne,pt %xcc, 1b
  288.  add %o0, 0x40, %o0
  289. #if (PAGE_SHIFT == 16) || (PAGE_SHIFT == 22)
  290. TOUCH(f0, f2, f4, f6, f8, f10, f12, f14)
  291. ldda [%o1] ASI_BLK_P, %f32
  292. stda %f48, [%o0] ASI_BLK_COMMIT_P
  293. add %o1, 0x40, %o1
  294. sub %o2, 0x40, %o2
  295. add %o0, 0x40, %o0
  296. TOUCH(f16, f18, f20, f22, f24, f26, f28, f30)
  297. ldda [%o1] ASI_BLK_P, %f0
  298. stda %f48, [%o0] ASI_BLK_COMMIT_P
  299. add %o1, 0x40, %o1
  300. sub %o2, 0x40, %o2
  301. add %o0, 0x40, %o0
  302. membar #Sync
  303. stda %f32, [%o0] ASI_BLK_COMMIT_P
  304. add %o0, 0x40, %o0
  305. ba,pt %xcc, copy_user_page_continue
  306.  stda %f0, [%o0] ASI_BLK_COMMIT_P
  307. #else
  308. membar #Sync
  309. stda %f0, [%o0] ASI_BLK_COMMIT_P
  310. add %o0, 0x40, %o0
  311. ba,pt %xcc, copy_user_page_continue
  312.  stda %f16, [%o0] ASI_BLK_COMMIT_P
  313. #endif
  314. .align 32
  315. .globl _clear_page
  316. .type _clear_page,@function
  317. _clear_page: /* %o0=dest */
  318. VISEntryHalf
  319. ba,pt %xcc, clear_page_common
  320.  clr %o4
  321. .align 32
  322. .globl clear_user_page
  323. .type clear_user_page,@function
  324. clear_user_page: /* %o0=dest, %o1=vaddr */
  325. VISEntryHalf
  326. sethi %hi(PAGE_SIZE), %g3
  327. sub %o0, %g4, %g1
  328. and %o1, %g3, %o0
  329. mov TLB_TAG_ACCESS, %o2
  330. sethi %uhi(_PAGE_VALID | _PAGE_SZBITS), %g3
  331. sethi %hi(TLBTEMP_BASE), %o3
  332. sllx %g3, 32, %g3
  333. or %g3, (_PAGE_CP | _PAGE_CV | _PAGE_P | _PAGE_L | _PAGE_W), %g3
  334. or %g1, %g3, %g1
  335. add %o0, %o3, %o0
  336. #define FIX_INSN_2 0x96102068 /* mov (13 << 3), %o3 */
  337. cheetah_patch_2:
  338. mov TLBTEMP_ENT2, %o3
  339. rdpr %pstate, %g3
  340. wrpr %g3, PSTATE_IE, %pstate
  341. /* Spitfire Errata #32 workaround */
  342. mov PRIMARY_CONTEXT, %g5
  343. stxa %g0, [%g5] ASI_DMMU
  344. membar #Sync
  345. ldxa [%o3] ASI_DTLB_TAG_READ, %g5
  346. /* Spitfire Errata #32 workaround */
  347. mov PRIMARY_CONTEXT, %g7
  348. stxa %g0, [%g7] ASI_DMMU
  349. membar #Sync
  350. ldxa [%o3] ASI_DTLB_DATA_ACCESS, %g0
  351. ldxa [%o3] ASI_DTLB_DATA_ACCESS, %g7
  352. stxa %o0, [%o2] ASI_DMMU
  353. stxa %g1, [%o3] ASI_DTLB_DATA_ACCESS
  354. membar #Sync
  355. mov 1, %o4
  356. clear_page_common:
  357. membar #StoreLoad | #StoreStore | #LoadStore ! LSU Group
  358. fzero %f0 ! FPA Group
  359. sethi %hi(PAGE_SIZE/256), %o1 ! IEU0
  360. fzero %f2 ! FPA Group
  361. or %o1, %lo(PAGE_SIZE/256), %o1 ! IEU0
  362. faddd %f0, %f2, %f4 ! FPA Group
  363. fmuld %f0, %f2, %f6 ! FPM
  364. faddd %f0, %f2, %f8 ! FPA Group
  365. fmuld %f0, %f2, %f10 ! FPM
  366. faddd %f0, %f2, %f12 ! FPA Group
  367. fmuld %f0, %f2, %f14 ! FPM
  368. 1: stda %f0, [%o0 + %g0] ASI_BLK_P ! Store Group
  369. add %o0, 0x40, %o0 ! IEU0
  370. stda %f0, [%o0 + %g0] ASI_BLK_P ! Store Group
  371. add %o0, 0x40, %o0 ! IEU0
  372. stda %f0, [%o0 + %g0] ASI_BLK_P ! Store Group
  373. add %o0, 0x40, %o0 ! IEU0 Group
  374. stda %f0, [%o0 + %g0] ASI_BLK_P ! Store Group
  375. subcc %o1, 1, %o1 ! IEU1
  376. bne,pt %icc, 1b ! CTI
  377.  add %o0, 0x40, %o0 ! IEU0 Group
  378. membar #Sync ! LSU Group
  379. VISExitHalf
  380. brnz,pt %o4, 1f
  381.  nop
  382. retl
  383.  nop
  384. 1:
  385. stxa %g5, [%o2] ASI_DMMU
  386. stxa %g7, [%o3] ASI_DTLB_DATA_ACCESS
  387. membar #Sync
  388. jmpl %o7 + 0x8, %g0
  389.  wrpr %g3, 0x0, %pstate
  390. .globl cheetah_patch_pgcopyops
  391. cheetah_patch_pgcopyops:
  392. sethi %hi(FIX_INSN_1), %g1
  393. or %g1, %lo(FIX_INSN_1), %g1
  394. sethi %hi(cheetah_patch_1), %g2
  395. or %g2, %lo(cheetah_patch_1), %g2
  396. stw %g1, [%g2]
  397. flush %g2
  398. sethi %hi(FIX_INSN_2), %g1
  399. or %g1, %lo(FIX_INSN_2), %g1
  400. sethi %hi(cheetah_patch_2), %g2
  401. or %g2, %lo(cheetah_patch_2), %g2
  402. stw %g1, [%g2]
  403. flush %g2
  404. retl
  405.  nop
  406. #undef FIX_INSN1
  407. #undef FIX_INSN2
  408. #undef PAGE_SIZE_REM