field_5x52_asm_impl.h 13 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503
  1. /**********************************************************************
  2. * Copyright (c) 2013-2014 Diederik Huys, Pieter Wuille *
  3. * Distributed under the MIT software license, see the accompanying *
  4. * file COPYING or http://www.opensource.org/licenses/mit-license.php.*
  5. **********************************************************************/
  6. /**
  7. * Changelog:
  8. * - March 2013, Diederik Huys: original version
  9. * - November 2014, Pieter Wuille: updated to use Peter Dettman's parallel multiplication algorithm
  10. * - December 2014, Pieter Wuille: converted from YASM to GCC inline assembly
  11. */
  12. #ifndef _SECP256K1_FIELD_INNER5X52_IMPL_H_
  13. #define _SECP256K1_FIELD_INNER5X52_IMPL_H_
  14. SECP256K1_INLINE static void secp256k1_fe_mul_inner(uint64_t *r, const uint64_t *a, const uint64_t * SECP256K1_RESTRICT b) {
  15. /**
  16. * Registers: rdx:rax = multiplication accumulator
  17. * r9:r8 = c
  18. * r15:rcx = d
  19. * r10-r14 = a0-a4
  20. * rbx = b
  21. * rdi = r
  22. * rsi = a / t?
  23. */
  24. uint64_t tmp1, tmp2, tmp3;
  25. __asm__ __volatile__(
  26. "movq 0(%%rsi),%%r10\n"
  27. "movq 8(%%rsi),%%r11\n"
  28. "movq 16(%%rsi),%%r12\n"
  29. "movq 24(%%rsi),%%r13\n"
  30. "movq 32(%%rsi),%%r14\n"
  31. /* d += a3 * b0 */
  32. "movq 0(%%rbx),%%rax\n"
  33. "mulq %%r13\n"
  34. "movq %%rax,%%rcx\n"
  35. "movq %%rdx,%%r15\n"
  36. /* d += a2 * b1 */
  37. "movq 8(%%rbx),%%rax\n"
  38. "mulq %%r12\n"
  39. "addq %%rax,%%rcx\n"
  40. "adcq %%rdx,%%r15\n"
  41. /* d += a1 * b2 */
  42. "movq 16(%%rbx),%%rax\n"
  43. "mulq %%r11\n"
  44. "addq %%rax,%%rcx\n"
  45. "adcq %%rdx,%%r15\n"
  46. /* d = a0 * b3 */
  47. "movq 24(%%rbx),%%rax\n"
  48. "mulq %%r10\n"
  49. "addq %%rax,%%rcx\n"
  50. "adcq %%rdx,%%r15\n"
  51. /* c = a4 * b4 */
  52. "movq 32(%%rbx),%%rax\n"
  53. "mulq %%r14\n"
  54. "movq %%rax,%%r8\n"
  55. "movq %%rdx,%%r9\n"
  56. /* d += (c & M) * R */
  57. "movq $0xfffffffffffff,%%rdx\n"
  58. "andq %%rdx,%%rax\n"
  59. "movq $0x1000003d10,%%rdx\n"
  60. "mulq %%rdx\n"
  61. "addq %%rax,%%rcx\n"
  62. "adcq %%rdx,%%r15\n"
  63. /* c >>= 52 (%%r8 only) */
  64. "shrdq $52,%%r9,%%r8\n"
  65. /* t3 (tmp1) = d & M */
  66. "movq %%rcx,%%rsi\n"
  67. "movq $0xfffffffffffff,%%rdx\n"
  68. "andq %%rdx,%%rsi\n"
  69. "movq %%rsi,%q1\n"
  70. /* d >>= 52 */
  71. "shrdq $52,%%r15,%%rcx\n"
  72. "xorq %%r15,%%r15\n"
  73. /* d += a4 * b0 */
  74. "movq 0(%%rbx),%%rax\n"
  75. "mulq %%r14\n"
  76. "addq %%rax,%%rcx\n"
  77. "adcq %%rdx,%%r15\n"
  78. /* d += a3 * b1 */
  79. "movq 8(%%rbx),%%rax\n"
  80. "mulq %%r13\n"
  81. "addq %%rax,%%rcx\n"
  82. "adcq %%rdx,%%r15\n"
  83. /* d += a2 * b2 */
  84. "movq 16(%%rbx),%%rax\n"
  85. "mulq %%r12\n"
  86. "addq %%rax,%%rcx\n"
  87. "adcq %%rdx,%%r15\n"
  88. /* d += a1 * b3 */
  89. "movq 24(%%rbx),%%rax\n"
  90. "mulq %%r11\n"
  91. "addq %%rax,%%rcx\n"
  92. "adcq %%rdx,%%r15\n"
  93. /* d += a0 * b4 */
  94. "movq 32(%%rbx),%%rax\n"
  95. "mulq %%r10\n"
  96. "addq %%rax,%%rcx\n"
  97. "adcq %%rdx,%%r15\n"
  98. /* d += c * R */
  99. "movq %%r8,%%rax\n"
  100. "movq $0x1000003d10,%%rdx\n"
  101. "mulq %%rdx\n"
  102. "addq %%rax,%%rcx\n"
  103. "adcq %%rdx,%%r15\n"
  104. /* t4 = d & M (%%rsi) */
  105. "movq %%rcx,%%rsi\n"
  106. "movq $0xfffffffffffff,%%rdx\n"
  107. "andq %%rdx,%%rsi\n"
  108. /* d >>= 52 */
  109. "shrdq $52,%%r15,%%rcx\n"
  110. "xorq %%r15,%%r15\n"
  111. /* tx = t4 >> 48 (tmp3) */
  112. "movq %%rsi,%%rax\n"
  113. "shrq $48,%%rax\n"
  114. "movq %%rax,%q3\n"
  115. /* t4 &= (M >> 4) (tmp2) */
  116. "movq $0xffffffffffff,%%rax\n"
  117. "andq %%rax,%%rsi\n"
  118. "movq %%rsi,%q2\n"
  119. /* c = a0 * b0 */
  120. "movq 0(%%rbx),%%rax\n"
  121. "mulq %%r10\n"
  122. "movq %%rax,%%r8\n"
  123. "movq %%rdx,%%r9\n"
  124. /* d += a4 * b1 */
  125. "movq 8(%%rbx),%%rax\n"
  126. "mulq %%r14\n"
  127. "addq %%rax,%%rcx\n"
  128. "adcq %%rdx,%%r15\n"
  129. /* d += a3 * b2 */
  130. "movq 16(%%rbx),%%rax\n"
  131. "mulq %%r13\n"
  132. "addq %%rax,%%rcx\n"
  133. "adcq %%rdx,%%r15\n"
  134. /* d += a2 * b3 */
  135. "movq 24(%%rbx),%%rax\n"
  136. "mulq %%r12\n"
  137. "addq %%rax,%%rcx\n"
  138. "adcq %%rdx,%%r15\n"
  139. /* d += a1 * b4 */
  140. "movq 32(%%rbx),%%rax\n"
  141. "mulq %%r11\n"
  142. "addq %%rax,%%rcx\n"
  143. "adcq %%rdx,%%r15\n"
  144. /* u0 = d & M (%%rsi) */
  145. "movq %%rcx,%%rsi\n"
  146. "movq $0xfffffffffffff,%%rdx\n"
  147. "andq %%rdx,%%rsi\n"
  148. /* d >>= 52 */
  149. "shrdq $52,%%r15,%%rcx\n"
  150. "xorq %%r15,%%r15\n"
  151. /* u0 = (u0 << 4) | tx (%%rsi) */
  152. "shlq $4,%%rsi\n"
  153. "movq %q3,%%rax\n"
  154. "orq %%rax,%%rsi\n"
  155. /* c += u0 * (R >> 4) */
  156. "movq $0x1000003d1,%%rax\n"
  157. "mulq %%rsi\n"
  158. "addq %%rax,%%r8\n"
  159. "adcq %%rdx,%%r9\n"
  160. /* r[0] = c & M */
  161. "movq %%r8,%%rax\n"
  162. "movq $0xfffffffffffff,%%rdx\n"
  163. "andq %%rdx,%%rax\n"
  164. "movq %%rax,0(%%rdi)\n"
  165. /* c >>= 52 */
  166. "shrdq $52,%%r9,%%r8\n"
  167. "xorq %%r9,%%r9\n"
  168. /* c += a1 * b0 */
  169. "movq 0(%%rbx),%%rax\n"
  170. "mulq %%r11\n"
  171. "addq %%rax,%%r8\n"
  172. "adcq %%rdx,%%r9\n"
  173. /* c += a0 * b1 */
  174. "movq 8(%%rbx),%%rax\n"
  175. "mulq %%r10\n"
  176. "addq %%rax,%%r8\n"
  177. "adcq %%rdx,%%r9\n"
  178. /* d += a4 * b2 */
  179. "movq 16(%%rbx),%%rax\n"
  180. "mulq %%r14\n"
  181. "addq %%rax,%%rcx\n"
  182. "adcq %%rdx,%%r15\n"
  183. /* d += a3 * b3 */
  184. "movq 24(%%rbx),%%rax\n"
  185. "mulq %%r13\n"
  186. "addq %%rax,%%rcx\n"
  187. "adcq %%rdx,%%r15\n"
  188. /* d += a2 * b4 */
  189. "movq 32(%%rbx),%%rax\n"
  190. "mulq %%r12\n"
  191. "addq %%rax,%%rcx\n"
  192. "adcq %%rdx,%%r15\n"
  193. /* c += (d & M) * R */
  194. "movq %%rcx,%%rax\n"
  195. "movq $0xfffffffffffff,%%rdx\n"
  196. "andq %%rdx,%%rax\n"
  197. "movq $0x1000003d10,%%rdx\n"
  198. "mulq %%rdx\n"
  199. "addq %%rax,%%r8\n"
  200. "adcq %%rdx,%%r9\n"
  201. /* d >>= 52 */
  202. "shrdq $52,%%r15,%%rcx\n"
  203. "xorq %%r15,%%r15\n"
  204. /* r[1] = c & M */
  205. "movq %%r8,%%rax\n"
  206. "movq $0xfffffffffffff,%%rdx\n"
  207. "andq %%rdx,%%rax\n"
  208. "movq %%rax,8(%%rdi)\n"
  209. /* c >>= 52 */
  210. "shrdq $52,%%r9,%%r8\n"
  211. "xorq %%r9,%%r9\n"
  212. /* c += a2 * b0 */
  213. "movq 0(%%rbx),%%rax\n"
  214. "mulq %%r12\n"
  215. "addq %%rax,%%r8\n"
  216. "adcq %%rdx,%%r9\n"
  217. /* c += a1 * b1 */
  218. "movq 8(%%rbx),%%rax\n"
  219. "mulq %%r11\n"
  220. "addq %%rax,%%r8\n"
  221. "adcq %%rdx,%%r9\n"
  222. /* c += a0 * b2 (last use of %%r10 = a0) */
  223. "movq 16(%%rbx),%%rax\n"
  224. "mulq %%r10\n"
  225. "addq %%rax,%%r8\n"
  226. "adcq %%rdx,%%r9\n"
  227. /* fetch t3 (%%r10, overwrites a0), t4 (%%rsi) */
  228. "movq %q2,%%rsi\n"
  229. "movq %q1,%%r10\n"
  230. /* d += a4 * b3 */
  231. "movq 24(%%rbx),%%rax\n"
  232. "mulq %%r14\n"
  233. "addq %%rax,%%rcx\n"
  234. "adcq %%rdx,%%r15\n"
  235. /* d += a3 * b4 */
  236. "movq 32(%%rbx),%%rax\n"
  237. "mulq %%r13\n"
  238. "addq %%rax,%%rcx\n"
  239. "adcq %%rdx,%%r15\n"
  240. /* c += (d & M) * R */
  241. "movq %%rcx,%%rax\n"
  242. "movq $0xfffffffffffff,%%rdx\n"
  243. "andq %%rdx,%%rax\n"
  244. "movq $0x1000003d10,%%rdx\n"
  245. "mulq %%rdx\n"
  246. "addq %%rax,%%r8\n"
  247. "adcq %%rdx,%%r9\n"
  248. /* d >>= 52 (%%rcx only) */
  249. "shrdq $52,%%r15,%%rcx\n"
  250. /* r[2] = c & M */
  251. "movq %%r8,%%rax\n"
  252. "movq $0xfffffffffffff,%%rdx\n"
  253. "andq %%rdx,%%rax\n"
  254. "movq %%rax,16(%%rdi)\n"
  255. /* c >>= 52 */
  256. "shrdq $52,%%r9,%%r8\n"
  257. "xorq %%r9,%%r9\n"
  258. /* c += t3 */
  259. "addq %%r10,%%r8\n"
  260. /* c += d * R */
  261. "movq %%rcx,%%rax\n"
  262. "movq $0x1000003d10,%%rdx\n"
  263. "mulq %%rdx\n"
  264. "addq %%rax,%%r8\n"
  265. "adcq %%rdx,%%r9\n"
  266. /* r[3] = c & M */
  267. "movq %%r8,%%rax\n"
  268. "movq $0xfffffffffffff,%%rdx\n"
  269. "andq %%rdx,%%rax\n"
  270. "movq %%rax,24(%%rdi)\n"
  271. /* c >>= 52 (%%r8 only) */
  272. "shrdq $52,%%r9,%%r8\n"
  273. /* c += t4 (%%r8 only) */
  274. "addq %%rsi,%%r8\n"
  275. /* r[4] = c */
  276. "movq %%r8,32(%%rdi)\n"
  277. : "+S"(a), "=m"(tmp1), "=m"(tmp2), "=m"(tmp3)
  278. : "b"(b), "D"(r)
  279. : "%rax", "%rcx", "%rdx", "%r8", "%r9", "%r10", "%r11", "%r12", "%r13", "%r14", "%r15", "cc", "memory"
  280. );
  281. }
  282. SECP256K1_INLINE static void secp256k1_fe_sqr_inner(uint64_t *r, const uint64_t *a) {
  283. /**
  284. * Registers: rdx:rax = multiplication accumulator
  285. * r9:r8 = c
  286. * rcx:rbx = d
  287. * r10-r14 = a0-a4
  288. * r15 = M (0xfffffffffffff)
  289. * rdi = r
  290. * rsi = a / t?
  291. */
  292. uint64_t tmp1, tmp2, tmp3;
  293. __asm__ __volatile__(
  294. "movq 0(%%rsi),%%r10\n"
  295. "movq 8(%%rsi),%%r11\n"
  296. "movq 16(%%rsi),%%r12\n"
  297. "movq 24(%%rsi),%%r13\n"
  298. "movq 32(%%rsi),%%r14\n"
  299. "movq $0xfffffffffffff,%%r15\n"
  300. /* d = (a0*2) * a3 */
  301. "leaq (%%r10,%%r10,1),%%rax\n"
  302. "mulq %%r13\n"
  303. "movq %%rax,%%rbx\n"
  304. "movq %%rdx,%%rcx\n"
  305. /* d += (a1*2) * a2 */
  306. "leaq (%%r11,%%r11,1),%%rax\n"
  307. "mulq %%r12\n"
  308. "addq %%rax,%%rbx\n"
  309. "adcq %%rdx,%%rcx\n"
  310. /* c = a4 * a4 */
  311. "movq %%r14,%%rax\n"
  312. "mulq %%r14\n"
  313. "movq %%rax,%%r8\n"
  314. "movq %%rdx,%%r9\n"
  315. /* d += (c & M) * R */
  316. "andq %%r15,%%rax\n"
  317. "movq $0x1000003d10,%%rdx\n"
  318. "mulq %%rdx\n"
  319. "addq %%rax,%%rbx\n"
  320. "adcq %%rdx,%%rcx\n"
  321. /* c >>= 52 (%%r8 only) */
  322. "shrdq $52,%%r9,%%r8\n"
  323. /* t3 (tmp1) = d & M */
  324. "movq %%rbx,%%rsi\n"
  325. "andq %%r15,%%rsi\n"
  326. "movq %%rsi,%q1\n"
  327. /* d >>= 52 */
  328. "shrdq $52,%%rcx,%%rbx\n"
  329. "xorq %%rcx,%%rcx\n"
  330. /* a4 *= 2 */
  331. "addq %%r14,%%r14\n"
  332. /* d += a0 * a4 */
  333. "movq %%r10,%%rax\n"
  334. "mulq %%r14\n"
  335. "addq %%rax,%%rbx\n"
  336. "adcq %%rdx,%%rcx\n"
  337. /* d+= (a1*2) * a3 */
  338. "leaq (%%r11,%%r11,1),%%rax\n"
  339. "mulq %%r13\n"
  340. "addq %%rax,%%rbx\n"
  341. "adcq %%rdx,%%rcx\n"
  342. /* d += a2 * a2 */
  343. "movq %%r12,%%rax\n"
  344. "mulq %%r12\n"
  345. "addq %%rax,%%rbx\n"
  346. "adcq %%rdx,%%rcx\n"
  347. /* d += c * R */
  348. "movq %%r8,%%rax\n"
  349. "movq $0x1000003d10,%%rdx\n"
  350. "mulq %%rdx\n"
  351. "addq %%rax,%%rbx\n"
  352. "adcq %%rdx,%%rcx\n"
  353. /* t4 = d & M (%%rsi) */
  354. "movq %%rbx,%%rsi\n"
  355. "andq %%r15,%%rsi\n"
  356. /* d >>= 52 */
  357. "shrdq $52,%%rcx,%%rbx\n"
  358. "xorq %%rcx,%%rcx\n"
  359. /* tx = t4 >> 48 (tmp3) */
  360. "movq %%rsi,%%rax\n"
  361. "shrq $48,%%rax\n"
  362. "movq %%rax,%q3\n"
  363. /* t4 &= (M >> 4) (tmp2) */
  364. "movq $0xffffffffffff,%%rax\n"
  365. "andq %%rax,%%rsi\n"
  366. "movq %%rsi,%q2\n"
  367. /* c = a0 * a0 */
  368. "movq %%r10,%%rax\n"
  369. "mulq %%r10\n"
  370. "movq %%rax,%%r8\n"
  371. "movq %%rdx,%%r9\n"
  372. /* d += a1 * a4 */
  373. "movq %%r11,%%rax\n"
  374. "mulq %%r14\n"
  375. "addq %%rax,%%rbx\n"
  376. "adcq %%rdx,%%rcx\n"
  377. /* d += (a2*2) * a3 */
  378. "leaq (%%r12,%%r12,1),%%rax\n"
  379. "mulq %%r13\n"
  380. "addq %%rax,%%rbx\n"
  381. "adcq %%rdx,%%rcx\n"
  382. /* u0 = d & M (%%rsi) */
  383. "movq %%rbx,%%rsi\n"
  384. "andq %%r15,%%rsi\n"
  385. /* d >>= 52 */
  386. "shrdq $52,%%rcx,%%rbx\n"
  387. "xorq %%rcx,%%rcx\n"
  388. /* u0 = (u0 << 4) | tx (%%rsi) */
  389. "shlq $4,%%rsi\n"
  390. "movq %q3,%%rax\n"
  391. "orq %%rax,%%rsi\n"
  392. /* c += u0 * (R >> 4) */
  393. "movq $0x1000003d1,%%rax\n"
  394. "mulq %%rsi\n"
  395. "addq %%rax,%%r8\n"
  396. "adcq %%rdx,%%r9\n"
  397. /* r[0] = c & M */
  398. "movq %%r8,%%rax\n"
  399. "andq %%r15,%%rax\n"
  400. "movq %%rax,0(%%rdi)\n"
  401. /* c >>= 52 */
  402. "shrdq $52,%%r9,%%r8\n"
  403. "xorq %%r9,%%r9\n"
  404. /* a0 *= 2 */
  405. "addq %%r10,%%r10\n"
  406. /* c += a0 * a1 */
  407. "movq %%r10,%%rax\n"
  408. "mulq %%r11\n"
  409. "addq %%rax,%%r8\n"
  410. "adcq %%rdx,%%r9\n"
  411. /* d += a2 * a4 */
  412. "movq %%r12,%%rax\n"
  413. "mulq %%r14\n"
  414. "addq %%rax,%%rbx\n"
  415. "adcq %%rdx,%%rcx\n"
  416. /* d += a3 * a3 */
  417. "movq %%r13,%%rax\n"
  418. "mulq %%r13\n"
  419. "addq %%rax,%%rbx\n"
  420. "adcq %%rdx,%%rcx\n"
  421. /* c += (d & M) * R */
  422. "movq %%rbx,%%rax\n"
  423. "andq %%r15,%%rax\n"
  424. "movq $0x1000003d10,%%rdx\n"
  425. "mulq %%rdx\n"
  426. "addq %%rax,%%r8\n"
  427. "adcq %%rdx,%%r9\n"
  428. /* d >>= 52 */
  429. "shrdq $52,%%rcx,%%rbx\n"
  430. "xorq %%rcx,%%rcx\n"
  431. /* r[1] = c & M */
  432. "movq %%r8,%%rax\n"
  433. "andq %%r15,%%rax\n"
  434. "movq %%rax,8(%%rdi)\n"
  435. /* c >>= 52 */
  436. "shrdq $52,%%r9,%%r8\n"
  437. "xorq %%r9,%%r9\n"
  438. /* c += a0 * a2 (last use of %%r10) */
  439. "movq %%r10,%%rax\n"
  440. "mulq %%r12\n"
  441. "addq %%rax,%%r8\n"
  442. "adcq %%rdx,%%r9\n"
  443. /* fetch t3 (%%r10, overwrites a0),t4 (%%rsi) */
  444. "movq %q2,%%rsi\n"
  445. "movq %q1,%%r10\n"
  446. /* c += a1 * a1 */
  447. "movq %%r11,%%rax\n"
  448. "mulq %%r11\n"
  449. "addq %%rax,%%r8\n"
  450. "adcq %%rdx,%%r9\n"
  451. /* d += a3 * a4 */
  452. "movq %%r13,%%rax\n"
  453. "mulq %%r14\n"
  454. "addq %%rax,%%rbx\n"
  455. "adcq %%rdx,%%rcx\n"
  456. /* c += (d & M) * R */
  457. "movq %%rbx,%%rax\n"
  458. "andq %%r15,%%rax\n"
  459. "movq $0x1000003d10,%%rdx\n"
  460. "mulq %%rdx\n"
  461. "addq %%rax,%%r8\n"
  462. "adcq %%rdx,%%r9\n"
  463. /* d >>= 52 (%%rbx only) */
  464. "shrdq $52,%%rcx,%%rbx\n"
  465. /* r[2] = c & M */
  466. "movq %%r8,%%rax\n"
  467. "andq %%r15,%%rax\n"
  468. "movq %%rax,16(%%rdi)\n"
  469. /* c >>= 52 */
  470. "shrdq $52,%%r9,%%r8\n"
  471. "xorq %%r9,%%r9\n"
  472. /* c += t3 */
  473. "addq %%r10,%%r8\n"
  474. /* c += d * R */
  475. "movq %%rbx,%%rax\n"
  476. "movq $0x1000003d10,%%rdx\n"
  477. "mulq %%rdx\n"
  478. "addq %%rax,%%r8\n"
  479. "adcq %%rdx,%%r9\n"
  480. /* r[3] = c & M */
  481. "movq %%r8,%%rax\n"
  482. "andq %%r15,%%rax\n"
  483. "movq %%rax,24(%%rdi)\n"
  484. /* c >>= 52 (%%r8 only) */
  485. "shrdq $52,%%r9,%%r8\n"
  486. /* c += t4 (%%r8 only) */
  487. "addq %%rsi,%%r8\n"
  488. /* r[4] = c */
  489. "movq %%r8,32(%%rdi)\n"
  490. : "+S"(a), "=m"(tmp1), "=m"(tmp2), "=m"(tmp3)
  491. : "D"(r)
  492. : "%rax", "%rbx", "%rcx", "%rdx", "%r8", "%r9", "%r10", "%r11", "%r12", "%r13", "%r14", "%r15", "cc", "memory"
  493. );
  494. }
  495. #endif