cranelift.rs 16 KB

12345678910111213141516171819202122232425262728293031323334353637383940414243444546474849505152535455565758596061626364656667686970717273747576777879808182838485868788899091929394959697989910010110210310410510610710810911011111211311411511611711811912012112212312412512612712812913013113213313413513613713813914014114214314414514614714814915015115215315415515615715815916016116216316416516616716816917017117217317417517617717817918018118218318418518618718818919019119219319419519619719819920020120220320420520620720820921021121221321421521621721821922022122222322422522622722822923023123223323423523623723823924024124224324424524624724824925025125225325425525625725825926026126226326426526626726826927027127227327427527627727827928028128228328428528628728828929029129229329429529629729829930030130230330430530630730830931031131231331431531631731831932032132232332432532632732832933033133233333433533633733833934034134234334434534634734834935035135235335435535635735835936036136236336436536636736836937037137237337437537637737837938038138238338438538638738838939039139239339439539639739839940040140240340440540640740840941041141241341441541641741841942042142242342442542642742842943043143243343443543643743843944044144244344444544644744844945045145245345445545645745845946046146246346446546646746846947047147247347447547647747847948048148248348448548648748848949049149249349449549649749849950050150250350450550650750850951051151251351451551651751851952052152252352452552652752852953053153253353453553653753853954054154254354454554654754854955055155255355455555655755855956056156256356456556656756856957057157257357457557657757857958058158258358458558658758858959059159259359459559659759859960060160260360460560660760860961061161261361461561661761861962062162262362462562662762862963063163263363463563663763863964064164264364464564664764864965065165265365465565665765865966066166266366466566666766866967067167267367467567667767867968068168268368468568668768868969069169269369469569669769869970070170270370470570670770870971071171271371471571671771871972072172272372472572672772872973073173273373473573673773873974074174274374474574674774874975075175275375475575675775875976076176276376476576676776876977077177277377477577677777877978078178278378478578678778878979079179279379479579679779879980080180280380480580680780880981081181281381481581681781881982082182282382482582682782882983083183283383483583683783883984084184284384484584684784884985085185285385485585685785885986086186286386486586686786886987087187287387487587687787887988088188288388488588688788888989089189289389489589689789889990090190290390490590690790890991091191291391491591691791891992092192292392492592692792892993093193293393493593693793893994094194294394494594694794894995095195295395495595695795895996096196296396496596696796896997097197297397497597697797897998098198298398498598698798898999099199299399499599699799899910001001100210031004100510061007100810091010101110121013101410151016101710181019102010211022102310241025102610271028102910301031103210331034103510361037103810391040104110421043104410451046104710481049105010511052105310541055105610571058
  1. // SPDX-License-Identifier: (Apache-2.0 OR MIT)
  2. #![cfg_attr(feature = "cargo-clippy", allow(clippy::unreadable_literal))]
  3. #![cfg(feature = "cranelift")]
  4. extern crate rbpf;
  5. mod common;
  6. use rbpf::{assembler::assemble, helpers};
  7. macro_rules! test_cranelift {
  8. ($name:ident, $prog:expr, $expected:expr) => {
  9. #[test]
  10. fn $name() {
  11. let prog = assemble($prog).unwrap();
  12. let vm = rbpf::EbpfVmNoData::new(Some(&prog)).unwrap();
  13. assert_eq!(vm.execute_cranelift().unwrap(), $expected);
  14. }
  15. };
  16. ($name:ident, $prog:expr, $mem:expr, $expected:expr) => {
  17. #[test]
  18. fn $name() {
  19. let prog = assemble($prog).unwrap();
  20. let mem = &mut $mem;
  21. let vm = rbpf::EbpfVmRaw::new(Some(&prog)).unwrap();
  22. assert_eq!(vm.execute_cranelift(mem).unwrap(), $expected);
  23. }
  24. };
  25. }
  26. test_cranelift!(
  27. test_cranelift_add,
  28. "
  29. mov32 r0, 0
  30. mov32 r1, 2
  31. add32 r0, 1
  32. add32 r0, r1
  33. exit
  34. ",
  35. 0x3
  36. );
  37. test_cranelift!(
  38. test_cranelift_alu64_arith,
  39. "
  40. mov r0, 0
  41. mov r1, 1
  42. mov r2, 2
  43. mov r3, 3
  44. mov r4, 4
  45. mov r5, 5
  46. mov r6, 6
  47. mov r7, 7
  48. mov r8, 8
  49. mov r9, 9
  50. add r0, 23
  51. add r0, r7
  52. sub r0, 13
  53. sub r0, r1
  54. mul r0, 7
  55. mul r0, r3
  56. div r0, 2
  57. div r0, r4
  58. exit
  59. ",
  60. 0x2a
  61. );
  62. test_cranelift!(
  63. test_cranelift_alu64_bit,
  64. "
  65. mov r0, 0
  66. mov r1, 1
  67. mov r2, 2
  68. mov r3, 3
  69. mov r4, 4
  70. mov r5, 5
  71. mov r6, 6
  72. mov r7, 7
  73. mov r8, 8
  74. or r0, r5
  75. or r0, 0xa0
  76. and r0, 0xa3
  77. mov r9, 0x91
  78. and r0, r9
  79. lsh r0, 32
  80. lsh r0, 22
  81. lsh r0, r8
  82. rsh r0, 32
  83. rsh r0, 19
  84. rsh r0, r7
  85. xor r0, 0x03
  86. xor r0, r2
  87. exit
  88. ",
  89. 0x11
  90. );
  91. test_cranelift!(
  92. test_cranelift_alu_arith,
  93. "
  94. mov32 r0, 0
  95. mov32 r1, 1
  96. mov32 r2, 2
  97. mov32 r3, 3
  98. mov32 r4, 4
  99. mov32 r5, 5
  100. mov32 r6, 6
  101. mov32 r7, 7
  102. mov32 r8, 8
  103. mov32 r9, 9
  104. add32 r0, 23
  105. add32 r0, r7
  106. sub32 r0, 13
  107. sub32 r0, r1
  108. mul32 r0, 7
  109. mul32 r0, r3
  110. div32 r0, 2
  111. div32 r0, r4
  112. exit
  113. ",
  114. 0x2a
  115. );
  116. test_cranelift!(
  117. test_cranelift_alu_bit,
  118. "
  119. mov32 r0, 0
  120. mov32 r1, 1
  121. mov32 r2, 2
  122. mov32 r3, 3
  123. mov32 r4, 4
  124. mov32 r5, 5
  125. mov32 r6, 6
  126. mov32 r7, 7
  127. mov32 r8, 8
  128. or32 r0, r5
  129. or32 r0, 0xa0
  130. and32 r0, 0xa3
  131. mov32 r9, 0x91
  132. and32 r0, r9
  133. lsh32 r0, 22
  134. lsh32 r0, r8
  135. rsh32 r0, 19
  136. rsh32 r0, r7
  137. xor32 r0, 0x03
  138. xor32 r0, r2
  139. exit
  140. ",
  141. 0x11
  142. );
  143. test_cranelift!(
  144. test_cranelift_arsh32_high_shift,
  145. "
  146. mov r0, 8
  147. lddw r1, 0x100000001
  148. arsh32 r0, r1
  149. exit
  150. ",
  151. 0x4
  152. );
  153. test_cranelift!(
  154. test_cranelift_arsh,
  155. "
  156. mov32 r0, 0xf8
  157. lsh32 r0, 28
  158. arsh32 r0, 16
  159. exit
  160. ",
  161. 0xffff8000
  162. );
  163. test_cranelift!(
  164. test_cranelift_arsh64,
  165. "
  166. mov32 r0, 1
  167. lsh r0, 63
  168. arsh r0, 55
  169. mov32 r1, 5
  170. arsh r0, r1
  171. exit
  172. ",
  173. 0xfffffffffffffff8
  174. );
  175. test_cranelift!(
  176. test_cranelift_arsh_reg,
  177. "
  178. mov32 r0, 0xf8
  179. mov32 r1, 16
  180. lsh32 r0, 28
  181. arsh32 r0, r1
  182. exit
  183. ",
  184. 0xffff8000
  185. );
  186. test_cranelift!(
  187. test_cranelift_be16,
  188. "
  189. ldxh r0, [r1]
  190. be16 r0
  191. exit
  192. ",
  193. [0x11, 0x22],
  194. 0x1122
  195. );
  196. test_cranelift!(
  197. test_cranelift_be16_high,
  198. "
  199. ldxdw r0, [r1]
  200. be16 r0
  201. exit
  202. ",
  203. [0x11, 0x22, 0x33, 0x44, 0x55, 0x66, 0x77, 0x88],
  204. 0x1122
  205. );
  206. test_cranelift!(
  207. test_cranelift_be32,
  208. "
  209. ldxw r0, [r1]
  210. be32 r0
  211. exit
  212. ",
  213. [0x11, 0x22, 0x33, 0x44],
  214. 0x11223344
  215. );
  216. test_cranelift!(
  217. test_cranelift_be32_high,
  218. "
  219. ldxdw r0, [r1]
  220. be32 r0
  221. exit
  222. ",
  223. [0x11, 0x22, 0x33, 0x44, 0x55, 0x66, 0x77, 0x88],
  224. 0x11223344
  225. );
  226. test_cranelift!(
  227. test_cranelift_be64,
  228. "
  229. ldxdw r0, [r1]
  230. be64 r0
  231. exit
  232. ",
  233. [0x11, 0x22, 0x33, 0x44, 0x55, 0x66, 0x77, 0x88],
  234. 0x1122334455667788
  235. );
  236. #[test]
  237. fn test_cranelift_call() {
  238. let prog = assemble(
  239. "
  240. mov r1, 1
  241. mov r2, 2
  242. mov r3, 3
  243. mov r4, 4
  244. mov r5, 5
  245. call 0
  246. exit",
  247. )
  248. .unwrap();
  249. let mut vm = rbpf::EbpfVmNoData::new(Some(&prog)).unwrap();
  250. vm.register_helper(0, helpers::gather_bytes).unwrap();
  251. assert_eq!(vm.execute_cranelift().unwrap(), 0x0102030405);
  252. }
  253. #[test]
  254. #[should_panic(expected = "[CRANELIFT] Error: unknown helper function (id: 0x3f)")]
  255. fn test_cranelift_err_call_unreg() {
  256. let prog = assemble("
  257. mov r1, 1
  258. mov r2, 2
  259. mov r3, 3
  260. mov r4, 4
  261. mov r5, 5
  262. call 63
  263. exit
  264. ").unwrap();
  265. let vm = rbpf::EbpfVmNoData::new(Some(&prog)).unwrap();
  266. vm.execute_cranelift().unwrap();
  267. }
  268. #[test]
  269. fn test_cranelift_call_memfrob() {
  270. let prog = assemble(
  271. "
  272. mov r6, r1
  273. add r1, 2
  274. mov r2, 4
  275. call 1
  276. ldxdw r0, [r6]
  277. be64 r0
  278. exit",
  279. )
  280. .unwrap();
  281. let mut vm = rbpf::EbpfVmRaw::new(Some(&prog)).unwrap();
  282. vm.register_helper(1, helpers::memfrob).unwrap();
  283. let mem = &mut [0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, 0x08];
  284. assert_eq!(vm.execute_cranelift(mem).unwrap(), 0x102292e2f2c0708);
  285. }
  286. test_cranelift!(
  287. test_cranelift_div32_high_divisor,
  288. "
  289. mov r0, 12
  290. lddw r1, 0x100000004
  291. div32 r0, r1
  292. exit
  293. ",
  294. 0x3
  295. );
  296. test_cranelift!(
  297. test_cranelift_div32_imm,
  298. "
  299. lddw r0, 0x10000000c
  300. div32 r0, 4
  301. exit
  302. ",
  303. 0x3
  304. );
  305. test_cranelift!(
  306. test_cranelift_div32_reg,
  307. "
  308. lddw r0, 0x10000000c
  309. mov r1, 4
  310. div32 r0, r1
  311. exit
  312. ",
  313. 0x3
  314. );
  315. test_cranelift!(
  316. test_cranelift_div64_imm,
  317. "
  318. mov r0, 0xc
  319. lsh r0, 32
  320. div r0, 4
  321. exit
  322. ",
  323. 0x300000000
  324. );
  325. test_cranelift!(
  326. test_cranelift_div64_reg,
  327. "
  328. mov r0, 0xc
  329. lsh r0, 32
  330. mov r1, 4
  331. div r0, r1
  332. exit
  333. ",
  334. 0x300000000
  335. );
  336. test_cranelift!(
  337. test_cranelift_div64_by_zero_imm,
  338. "
  339. mov32 r0, 1
  340. div r0, 0
  341. exit
  342. ",
  343. 0x0
  344. );
  345. test_cranelift!(
  346. test_cranelift_div_by_zero_imm,
  347. "
  348. mov32 r0, 1
  349. div32 r0, 0
  350. exit
  351. ",
  352. 0x0
  353. );
  354. test_cranelift!(
  355. test_cranelift_mod64_by_zero_imm,
  356. "
  357. mov32 r0, 1
  358. mod r0, 0
  359. exit
  360. ",
  361. 0x1
  362. );
  363. test_cranelift!(
  364. test_cranelift_mod_by_zero_imm,
  365. "
  366. mov32 r0, 1
  367. mod32 r0, 0
  368. exit
  369. ",
  370. 0x1
  371. );
  372. test_cranelift!(
  373. test_cranelift_div64_by_zero_reg,
  374. "
  375. mov32 r0, 1
  376. mov32 r1, 0
  377. div r0, r1
  378. exit
  379. ",
  380. 0x0
  381. );
  382. test_cranelift!(
  383. test_cranelift_div_by_zero_reg,
  384. "
  385. mov32 r0, 1
  386. mov32 r1, 0
  387. div32 r0, r1
  388. exit
  389. ",
  390. 0x0
  391. );
  392. test_cranelift!(
  393. test_cranelift_mod64_by_zero_reg,
  394. "
  395. mov32 r0, 1
  396. mov32 r1, 0
  397. mod r0, r1
  398. exit
  399. ",
  400. 0x1
  401. );
  402. test_cranelift!(
  403. test_cranelift_mod_by_zero_reg,
  404. "
  405. mov32 r0, 1
  406. mov32 r1, 0
  407. mod32 r0, r1
  408. exit
  409. ",
  410. 0x1
  411. );
  412. test_cranelift!(
  413. test_cranelift_exit,
  414. "
  415. mov r0, 0
  416. exit
  417. ",
  418. 0x0
  419. );
  420. test_cranelift!(
  421. test_cranelift_lddw,
  422. "
  423. lddw r0, 0x1122334455667788
  424. exit
  425. ",
  426. 0x1122334455667788
  427. );
  428. test_cranelift!(
  429. test_cranelift_lddw2,
  430. "
  431. lddw r0, 0x0000000080000000
  432. exit
  433. ",
  434. 0x80000000
  435. );
  436. test_cranelift!(
  437. test_cranelift_ldxb_all,
  438. "
  439. mov r0, r1
  440. ldxb r9, [r0+0]
  441. lsh r9, 0
  442. ldxb r8, [r0+1]
  443. lsh r8, 4
  444. ldxb r7, [r0+2]
  445. lsh r7, 8
  446. ldxb r6, [r0+3]
  447. lsh r6, 12
  448. ldxb r5, [r0+4]
  449. lsh r5, 16
  450. ldxb r4, [r0+5]
  451. lsh r4, 20
  452. ldxb r3, [r0+6]
  453. lsh r3, 24
  454. ldxb r2, [r0+7]
  455. lsh r2, 28
  456. ldxb r1, [r0+8]
  457. lsh r1, 32
  458. ldxb r0, [r0+9]
  459. lsh r0, 36
  460. or r0, r1
  461. or r0, r2
  462. or r0, r3
  463. or r0, r4
  464. or r0, r5
  465. or r0, r6
  466. or r0, r7
  467. or r0, r8
  468. or r0, r9
  469. exit
  470. ",
  471. [0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, 0x08, 0x09],
  472. 0x9876543210
  473. );
  474. test_cranelift!(
  475. test_cranelift_ldxb,
  476. "
  477. ldxb r0, [r1+2]
  478. exit
  479. ",
  480. [0xaa, 0xbb, 0x11, 0xcc, 0xdd],
  481. 0x11
  482. );
  483. test_cranelift!(
  484. test_cranelift_ldxdw,
  485. "
  486. ldxdw r0, [r1+2]
  487. exit
  488. ",
  489. [0xaa, 0xbb, 0x11, 0x22, 0x33, 0x44, 0x55, 0x66, 0x77, 0x88, 0xcc, 0xdd],
  490. 0x8877665544332211
  491. );
  492. test_cranelift!(
  493. test_cranelift_ldxh_all,
  494. "
  495. mov r0, r1
  496. ldxh r9, [r0+0]
  497. be16 r9
  498. lsh r9, 0
  499. ldxh r8, [r0+2]
  500. be16 r8
  501. lsh r8, 4
  502. ldxh r7, [r0+4]
  503. be16 r7
  504. lsh r7, 8
  505. ldxh r6, [r0+6]
  506. be16 r6
  507. lsh r6, 12
  508. ldxh r5, [r0+8]
  509. be16 r5
  510. lsh r5, 16
  511. ldxh r4, [r0+10]
  512. be16 r4
  513. lsh r4, 20
  514. ldxh r3, [r0+12]
  515. be16 r3
  516. lsh r3, 24
  517. ldxh r2, [r0+14]
  518. be16 r2
  519. lsh r2, 28
  520. ldxh r1, [r0+16]
  521. be16 r1
  522. lsh r1, 32
  523. ldxh r0, [r0+18]
  524. be16 r0
  525. lsh r0, 36
  526. or r0, r1
  527. or r0, r2
  528. or r0, r3
  529. or r0, r4
  530. or r0, r5
  531. or r0, r6
  532. or r0, r7
  533. or r0, r8
  534. or r0, r9
  535. exit
  536. ",
  537. [
  538. 0x00, 0x00, 0x00, 0x01, 0x00, 0x02, 0x00, 0x03, 0x00, 0x04, 0x00, 0x05, 0x00, 0x06, 0x00,
  539. 0x07, 0x00, 0x08, 0x00, 0x09
  540. ],
  541. 0x9876543210
  542. );
  543. test_cranelift!(
  544. test_cranelift_ldxh_all2,
  545. "
  546. mov r0, r1
  547. ldxh r9, [r0+0]
  548. be16 r9
  549. ldxh r8, [r0+2]
  550. be16 r8
  551. ldxh r7, [r0+4]
  552. be16 r7
  553. ldxh r6, [r0+6]
  554. be16 r6
  555. ldxh r5, [r0+8]
  556. be16 r5
  557. ldxh r4, [r0+10]
  558. be16 r4
  559. ldxh r3, [r0+12]
  560. be16 r3
  561. ldxh r2, [r0+14]
  562. be16 r2
  563. ldxh r1, [r0+16]
  564. be16 r1
  565. ldxh r0, [r0+18]
  566. be16 r0
  567. or r0, r1
  568. or r0, r2
  569. or r0, r3
  570. or r0, r4
  571. or r0, r5
  572. or r0, r6
  573. or r0, r7
  574. or r0, r8
  575. or r0, r9
  576. exit
  577. ",
  578. [
  579. 0x00, 0x01, 0x00, 0x02, 0x00, 0x04, 0x00, 0x08, 0x00, 0x10, 0x00, 0x20, 0x00, 0x40, 0x00,
  580. 0x80, 0x01, 0x00, 0x02, 0x00
  581. ],
  582. 0x3ff
  583. );
  584. test_cranelift!(
  585. test_cranelift_ldxh,
  586. "
  587. ldxh r0, [r1+2]
  588. exit
  589. ",
  590. [0xaa, 0xbb, 0x11, 0x22, 0xcc, 0xdd],
  591. 0x2211
  592. );
  593. test_cranelift!(
  594. test_cranelift_ldxh_same_reg,
  595. "
  596. mov r0, r1
  597. sth [r0], 0x1234
  598. ldxh r0, [r0]
  599. exit
  600. ",
  601. [0xff, 0xff],
  602. 0x1234
  603. );
  604. test_cranelift!(
  605. test_cranelift_ldxw_all,
  606. "
  607. mov r0, r1
  608. ldxw r9, [r0+0]
  609. be32 r9
  610. ldxw r8, [r0+4]
  611. be32 r8
  612. ldxw r7, [r0+8]
  613. be32 r7
  614. ldxw r6, [r0+12]
  615. be32 r6
  616. ldxw r5, [r0+16]
  617. be32 r5
  618. ldxw r4, [r0+20]
  619. be32 r4
  620. ldxw r3, [r0+24]
  621. be32 r3
  622. ldxw r2, [r0+28]
  623. be32 r2
  624. ldxw r1, [r0+32]
  625. be32 r1
  626. ldxw r0, [r0+36]
  627. be32 r0
  628. or r0, r1
  629. or r0, r2
  630. or r0, r3
  631. or r0, r4
  632. or r0, r5
  633. or r0, r6
  634. or r0, r7
  635. or r0, r8
  636. or r0, r9
  637. exit
  638. ",
  639. [
  640. 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0x02, 0x00, 0x00, 0x00, 0x04, 0x00, 0x00, 0x00,
  641. 0x08, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0x02, 0x00, 0x00, 0x00, 0x04, 0x00, 0x00, 0x00,
  642. 0x08, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0x02, 0x00, 0x00
  643. ],
  644. 0x030f0f
  645. );
  646. test_cranelift!(
  647. test_cranelift_ldxw,
  648. "
  649. ldxw r0, [r1+2]
  650. exit
  651. ",
  652. [0xaa, 0xbb, 0x11, 0x22, 0x33, 0x44, 0xcc, 0xdd],
  653. 0x44332211
  654. );
  655. test_cranelift!(
  656. test_cranelift_le16,
  657. "
  658. ldxh r0, [r1]
  659. le16 r0
  660. exit
  661. ",
  662. [0x22, 0x11],
  663. 0x1122
  664. );
  665. test_cranelift!(
  666. test_cranelift_le32,
  667. "
  668. ldxw r0, [r1]
  669. le32 r0
  670. exit
  671. ",
  672. [0x44, 0x33, 0x22, 0x11],
  673. 0x11223344
  674. );
  675. test_cranelift!(
  676. test_cranelift_le64,
  677. "
  678. ldxdw r0, [r1]
  679. le64 r0
  680. exit
  681. ",
  682. [0x88, 0x77, 0x66, 0x55, 0x44, 0x33, 0x22, 0x11],
  683. 0x1122334455667788
  684. );
  685. test_cranelift!(
  686. test_cranelift_lsh_reg,
  687. "
  688. mov r0, 0x1
  689. mov r7, 4
  690. lsh r0, r7
  691. exit
  692. ",
  693. 0x10
  694. );
  695. test_cranelift!(
  696. test_cranelift_mod,
  697. "
  698. mov32 r0, 5748
  699. mod32 r0, 92
  700. mov32 r1, 13
  701. mod32 r0, r1
  702. exit
  703. ",
  704. 0x5
  705. );
  706. test_cranelift!(
  707. test_cranelift_mod32,
  708. "
  709. lddw r0, 0x100000003
  710. mod32 r0, 3
  711. exit
  712. ",
  713. 0x0
  714. );
  715. test_cranelift!(
  716. test_cranelift_mod64,
  717. "
  718. mov32 r0, -1316649930
  719. lsh r0, 32
  720. or r0, 0x100dc5c8
  721. mov32 r1, 0xdde263e
  722. lsh r1, 32
  723. or r1, 0x3cbef7f3
  724. mod r0, r1
  725. mod r0, 0x658f1778
  726. exit
  727. ",
  728. 0x30ba5a04
  729. );
  730. test_cranelift!(
  731. test_cranelift_mov,
  732. "
  733. mov32 r1, 1
  734. mov32 r0, r1
  735. exit
  736. ",
  737. 0x1
  738. );
  739. test_cranelift!(
  740. test_cranelift_mul32_imm,
  741. "
  742. mov r0, 3
  743. mul32 r0, 4
  744. exit
  745. ",
  746. 0xc
  747. );
  748. test_cranelift!(
  749. test_cranelift_mul32_reg,
  750. "
  751. mov r0, 3
  752. mov r1, 4
  753. mul32 r0, r1
  754. exit
  755. ",
  756. 0xc
  757. );
  758. test_cranelift!(
  759. test_cranelift_mul32_reg_overflow,
  760. "
  761. mov r0, 0x40000001
  762. mov r1, 4
  763. mul32 r0, r1
  764. exit
  765. ",
  766. 0x4
  767. );
  768. test_cranelift!(
  769. test_cranelift_mul64_imm,
  770. "
  771. mov r0, 0x40000001
  772. mul r0, 4
  773. exit
  774. ",
  775. 0x100000004
  776. );
  777. test_cranelift!(
  778. test_cranelift_mul64_reg,
  779. "
  780. mov r0, 0x40000001
  781. mov r1, 4
  782. mul r0, r1
  783. exit
  784. ",
  785. 0x100000004
  786. );
  787. test_cranelift!(
  788. test_cranelift_stack,
  789. "
  790. mov r1, 51
  791. stdw [r10-16], 0xab
  792. stdw [r10-8], 0xcd
  793. and r1, 1
  794. lsh r1, 3
  795. mov r2, r10
  796. add r2, r1
  797. ldxdw r0, [r2-16]
  798. exit
  799. ",
  800. 0xcd
  801. );
  802. #[test]
  803. fn test_cranelift_stack2() {
  804. let prog = assemble(
  805. "
  806. stb [r10-4], 0x01
  807. stb [r10-3], 0x02
  808. stb [r10-2], 0x03
  809. stb [r10-1], 0x04
  810. mov r1, r10
  811. mov r2, 0x4
  812. sub r1, r2
  813. call 1
  814. mov r1, 0
  815. ldxb r2, [r10-4]
  816. ldxb r3, [r10-3]
  817. ldxb r4, [r10-2]
  818. ldxb r5, [r10-1]
  819. call 0
  820. xor r0, 0x2a2a2a2a
  821. exit",
  822. )
  823. .unwrap();
  824. let mut vm = rbpf::EbpfVmNoData::new(Some(&prog)).unwrap();
  825. vm.register_helper(0, helpers::gather_bytes).unwrap();
  826. vm.register_helper(1, helpers::memfrob).unwrap();
  827. assert_eq!(vm.execute_cranelift().unwrap(), 0x01020304);
  828. }
  829. test_cranelift!(
  830. test_cranelift_stb,
  831. "
  832. stb [r1+2], 0x11
  833. ldxb r0, [r1+2]
  834. exit
  835. ",
  836. [0xaa, 0xbb, 0xff, 0xcc, 0xdd],
  837. 0x11
  838. );
  839. test_cranelift!(
  840. test_cranelift_stdw,
  841. "
  842. stdw [r1+2], 0x44332211
  843. ldxdw r0, [r1+2]
  844. exit
  845. ",
  846. [0xaa, 0xbb, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xcc, 0xdd],
  847. 0x44332211
  848. );
  849. test_cranelift!(
  850. test_cranelift_sth,
  851. "
  852. sth [r1+2], 0x2211
  853. ldxh r0, [r1+2]
  854. exit
  855. ",
  856. [0xaa, 0xbb, 0xff, 0xff, 0xcc, 0xdd],
  857. 0x2211
  858. );
  859. test_cranelift!(
  860. test_cranelift_stw,
  861. "
  862. stw [r1+2], 0x44332211
  863. ldxw r0, [r1+2]
  864. exit
  865. ",
  866. [0xaa, 0xbb, 0xff, 0xff, 0xff, 0xff, 0xcc, 0xdd],
  867. 0x44332211
  868. );
  869. test_cranelift!(
  870. test_cranelift_stxb,
  871. "
  872. mov32 r2, 0x11
  873. stxb [r1+2], r2
  874. ldxb r0, [r1+2]
  875. exit
  876. ",
  877. [0xaa, 0xbb, 0xff, 0xcc, 0xdd],
  878. 0x11
  879. );
  880. test_cranelift!(
  881. test_cranelift_stxb_all,
  882. "
  883. mov r0, 0xf0
  884. mov r2, 0xf2
  885. mov r3, 0xf3
  886. mov r4, 0xf4
  887. mov r5, 0xf5
  888. mov r6, 0xf6
  889. mov r7, 0xf7
  890. mov r8, 0xf8
  891. stxb [r1], r0
  892. stxb [r1+1], r2
  893. stxb [r1+2], r3
  894. stxb [r1+3], r4
  895. stxb [r1+4], r5
  896. stxb [r1+5], r6
  897. stxb [r1+6], r7
  898. stxb [r1+7], r8
  899. ldxdw r0, [r1]
  900. be64 r0
  901. exit
  902. ",
  903. [0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff],
  904. 0xf0f2f3f4f5f6f7f8
  905. );
  906. test_cranelift!(
  907. test_cranelift_stxb_all2,
  908. "
  909. mov r0, r1
  910. mov r1, 0xf1
  911. mov r9, 0xf9
  912. stxb [r0], r1
  913. stxb [r0+1], r9
  914. ldxh r0, [r0]
  915. be16 r0
  916. exit
  917. ",
  918. [0xff, 0xff],
  919. 0xf1f9
  920. );
  921. test_cranelift!(
  922. test_cranelift_stxb_chain,
  923. "
  924. mov r0, r1
  925. ldxb r9, [r0+0]
  926. stxb [r0+1], r9
  927. ldxb r8, [r0+1]
  928. stxb [r0+2], r8
  929. ldxb r7, [r0+2]
  930. stxb [r0+3], r7
  931. ldxb r6, [r0+3]
  932. stxb [r0+4], r6
  933. ldxb r5, [r0+4]
  934. stxb [r0+5], r5
  935. ldxb r4, [r0+5]
  936. stxb [r0+6], r4
  937. ldxb r3, [r0+6]
  938. stxb [r0+7], r3
  939. ldxb r2, [r0+7]
  940. stxb [r0+8], r2
  941. ldxb r1, [r0+8]
  942. stxb [r0+9], r1
  943. ldxb r0, [r0+9]
  944. exit
  945. ",
  946. [0x2a, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00],
  947. 0x2a
  948. );
  949. test_cranelift!(
  950. test_cranelift_stxdw,
  951. "
  952. mov r2, -2005440939
  953. lsh r2, 32
  954. or r2, 0x44332211
  955. stxdw [r1+2], r2
  956. ldxdw r0, [r1+2]
  957. exit
  958. ",
  959. [0xaa, 0xbb, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xcc, 0xdd],
  960. 0x8877665544332211
  961. );
  962. test_cranelift!(
  963. test_cranelift_stxh,
  964. "
  965. mov32 r2, 0x2211
  966. stxh [r1+2], r2
  967. ldxh r0, [r1+2]
  968. exit
  969. ",
  970. [0xaa, 0xbb, 0xff, 0xff, 0xcc, 0xdd],
  971. 0x2211
  972. );
  973. test_cranelift!(
  974. test_cranelift_stxw,
  975. "
  976. mov32 r2, 0x44332211
  977. stxw [r1+2], r2
  978. ldxw r0, [r1+2]
  979. exit
  980. ",
  981. [0xaa, 0xbb, 0xff, 0xff, 0xff, 0xff, 0xcc, 0xdd],
  982. 0x44332211
  983. );