1
0

vm_jump_test.go 7.1 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380
  1. // Copyright 2016 The Go Authors. All rights reserved.
  2. // Use of this source code is governed by a BSD-style
  3. // license that can be found in the LICENSE file.
  4. package bpf_test
  5. import (
  6. "testing"
  7. "golang.org/x/net/bpf"
  8. )
  9. func TestVMJumpOne(t *testing.T) {
  10. vm, done, err := testVM(t, []bpf.Instruction{
  11. bpf.LoadAbsolute{
  12. Off: 8,
  13. Size: 1,
  14. },
  15. bpf.Jump{
  16. Skip: 1,
  17. },
  18. bpf.RetConstant{
  19. Val: 0,
  20. },
  21. bpf.RetConstant{
  22. Val: 9,
  23. },
  24. })
  25. if err != nil {
  26. t.Fatalf("failed to load BPF program: %v", err)
  27. }
  28. defer done()
  29. out, err := vm.Run([]byte{
  30. 0xff, 0xff, 0xff, 0xff,
  31. 0xff, 0xff, 0xff, 0xff,
  32. 1,
  33. })
  34. if err != nil {
  35. t.Fatalf("unexpected error while running program: %v", err)
  36. }
  37. if want, got := 1, out; want != got {
  38. t.Fatalf("unexpected number of output bytes:\n- want: %d\n- got: %d",
  39. want, got)
  40. }
  41. }
  42. func TestVMJumpOutOfProgram(t *testing.T) {
  43. _, _, err := testVM(t, []bpf.Instruction{
  44. bpf.Jump{
  45. Skip: 1,
  46. },
  47. bpf.RetA{},
  48. })
  49. if errStr(err) != "cannot jump 1 instructions; jumping past program bounds" {
  50. t.Fatalf("unexpected error: %v", err)
  51. }
  52. }
  53. func TestVMJumpIfTrueOutOfProgram(t *testing.T) {
  54. _, _, err := testVM(t, []bpf.Instruction{
  55. bpf.JumpIf{
  56. Cond: bpf.JumpEqual,
  57. SkipTrue: 2,
  58. },
  59. bpf.RetA{},
  60. })
  61. if errStr(err) != "cannot jump 2 instructions in true case; jumping past program bounds" {
  62. t.Fatalf("unexpected error: %v", err)
  63. }
  64. }
  65. func TestVMJumpIfFalseOutOfProgram(t *testing.T) {
  66. _, _, err := testVM(t, []bpf.Instruction{
  67. bpf.JumpIf{
  68. Cond: bpf.JumpEqual,
  69. SkipFalse: 3,
  70. },
  71. bpf.RetA{},
  72. })
  73. if errStr(err) != "cannot jump 3 instructions in false case; jumping past program bounds" {
  74. t.Fatalf("unexpected error: %v", err)
  75. }
  76. }
  77. func TestVMJumpIfEqual(t *testing.T) {
  78. vm, done, err := testVM(t, []bpf.Instruction{
  79. bpf.LoadAbsolute{
  80. Off: 8,
  81. Size: 1,
  82. },
  83. bpf.JumpIf{
  84. Cond: bpf.JumpEqual,
  85. Val: 1,
  86. SkipTrue: 1,
  87. },
  88. bpf.RetConstant{
  89. Val: 0,
  90. },
  91. bpf.RetConstant{
  92. Val: 9,
  93. },
  94. })
  95. if err != nil {
  96. t.Fatalf("failed to load BPF program: %v", err)
  97. }
  98. defer done()
  99. out, err := vm.Run([]byte{
  100. 0xff, 0xff, 0xff, 0xff,
  101. 0xff, 0xff, 0xff, 0xff,
  102. 1,
  103. })
  104. if err != nil {
  105. t.Fatalf("unexpected error while running program: %v", err)
  106. }
  107. if want, got := 1, out; want != got {
  108. t.Fatalf("unexpected number of output bytes:\n- want: %d\n- got: %d",
  109. want, got)
  110. }
  111. }
  112. func TestVMJumpIfNotEqual(t *testing.T) {
  113. vm, done, err := testVM(t, []bpf.Instruction{
  114. bpf.LoadAbsolute{
  115. Off: 8,
  116. Size: 1,
  117. },
  118. bpf.JumpIf{
  119. Cond: bpf.JumpNotEqual,
  120. Val: 1,
  121. SkipFalse: 1,
  122. },
  123. bpf.RetConstant{
  124. Val: 0,
  125. },
  126. bpf.RetConstant{
  127. Val: 9,
  128. },
  129. })
  130. if err != nil {
  131. t.Fatalf("failed to load BPF program: %v", err)
  132. }
  133. defer done()
  134. out, err := vm.Run([]byte{
  135. 0xff, 0xff, 0xff, 0xff,
  136. 0xff, 0xff, 0xff, 0xff,
  137. 1,
  138. })
  139. if err != nil {
  140. t.Fatalf("unexpected error while running program: %v", err)
  141. }
  142. if want, got := 1, out; want != got {
  143. t.Fatalf("unexpected number of output bytes:\n- want: %d\n- got: %d",
  144. want, got)
  145. }
  146. }
  147. func TestVMJumpIfGreaterThan(t *testing.T) {
  148. vm, done, err := testVM(t, []bpf.Instruction{
  149. bpf.LoadAbsolute{
  150. Off: 8,
  151. Size: 4,
  152. },
  153. bpf.JumpIf{
  154. Cond: bpf.JumpGreaterThan,
  155. Val: 0x00010202,
  156. SkipTrue: 1,
  157. },
  158. bpf.RetConstant{
  159. Val: 0,
  160. },
  161. bpf.RetConstant{
  162. Val: 12,
  163. },
  164. })
  165. if err != nil {
  166. t.Fatalf("failed to load BPF program: %v", err)
  167. }
  168. defer done()
  169. out, err := vm.Run([]byte{
  170. 0xff, 0xff, 0xff, 0xff,
  171. 0xff, 0xff, 0xff, 0xff,
  172. 0, 1, 2, 3,
  173. })
  174. if err != nil {
  175. t.Fatalf("unexpected error while running program: %v", err)
  176. }
  177. if want, got := 4, out; want != got {
  178. t.Fatalf("unexpected number of output bytes:\n- want: %d\n- got: %d",
  179. want, got)
  180. }
  181. }
  182. func TestVMJumpIfLessThan(t *testing.T) {
  183. vm, done, err := testVM(t, []bpf.Instruction{
  184. bpf.LoadAbsolute{
  185. Off: 8,
  186. Size: 4,
  187. },
  188. bpf.JumpIf{
  189. Cond: bpf.JumpLessThan,
  190. Val: 0xff010203,
  191. SkipTrue: 1,
  192. },
  193. bpf.RetConstant{
  194. Val: 0,
  195. },
  196. bpf.RetConstant{
  197. Val: 12,
  198. },
  199. })
  200. if err != nil {
  201. t.Fatalf("failed to load BPF program: %v", err)
  202. }
  203. defer done()
  204. out, err := vm.Run([]byte{
  205. 0xff, 0xff, 0xff, 0xff,
  206. 0xff, 0xff, 0xff, 0xff,
  207. 0, 1, 2, 3,
  208. })
  209. if err != nil {
  210. t.Fatalf("unexpected error while running program: %v", err)
  211. }
  212. if want, got := 4, out; want != got {
  213. t.Fatalf("unexpected number of output bytes:\n- want: %d\n- got: %d",
  214. want, got)
  215. }
  216. }
  217. func TestVMJumpIfGreaterOrEqual(t *testing.T) {
  218. vm, done, err := testVM(t, []bpf.Instruction{
  219. bpf.LoadAbsolute{
  220. Off: 8,
  221. Size: 4,
  222. },
  223. bpf.JumpIf{
  224. Cond: bpf.JumpGreaterOrEqual,
  225. Val: 0x00010203,
  226. SkipTrue: 1,
  227. },
  228. bpf.RetConstant{
  229. Val: 0,
  230. },
  231. bpf.RetConstant{
  232. Val: 12,
  233. },
  234. })
  235. if err != nil {
  236. t.Fatalf("failed to load BPF program: %v", err)
  237. }
  238. defer done()
  239. out, err := vm.Run([]byte{
  240. 0xff, 0xff, 0xff, 0xff,
  241. 0xff, 0xff, 0xff, 0xff,
  242. 0, 1, 2, 3,
  243. })
  244. if err != nil {
  245. t.Fatalf("unexpected error while running program: %v", err)
  246. }
  247. if want, got := 4, out; want != got {
  248. t.Fatalf("unexpected number of output bytes:\n- want: %d\n- got: %d",
  249. want, got)
  250. }
  251. }
  252. func TestVMJumpIfLessOrEqual(t *testing.T) {
  253. vm, done, err := testVM(t, []bpf.Instruction{
  254. bpf.LoadAbsolute{
  255. Off: 8,
  256. Size: 4,
  257. },
  258. bpf.JumpIf{
  259. Cond: bpf.JumpLessOrEqual,
  260. Val: 0xff010203,
  261. SkipTrue: 1,
  262. },
  263. bpf.RetConstant{
  264. Val: 0,
  265. },
  266. bpf.RetConstant{
  267. Val: 12,
  268. },
  269. })
  270. if err != nil {
  271. t.Fatalf("failed to load BPF program: %v", err)
  272. }
  273. defer done()
  274. out, err := vm.Run([]byte{
  275. 0xff, 0xff, 0xff, 0xff,
  276. 0xff, 0xff, 0xff, 0xff,
  277. 0, 1, 2, 3,
  278. })
  279. if err != nil {
  280. t.Fatalf("unexpected error while running program: %v", err)
  281. }
  282. if want, got := 4, out; want != got {
  283. t.Fatalf("unexpected number of output bytes:\n- want: %d\n- got: %d",
  284. want, got)
  285. }
  286. }
  287. func TestVMJumpIfBitsSet(t *testing.T) {
  288. vm, done, err := testVM(t, []bpf.Instruction{
  289. bpf.LoadAbsolute{
  290. Off: 8,
  291. Size: 2,
  292. },
  293. bpf.JumpIf{
  294. Cond: bpf.JumpBitsSet,
  295. Val: 0x1122,
  296. SkipTrue: 1,
  297. },
  298. bpf.RetConstant{
  299. Val: 0,
  300. },
  301. bpf.RetConstant{
  302. Val: 10,
  303. },
  304. })
  305. if err != nil {
  306. t.Fatalf("failed to load BPF program: %v", err)
  307. }
  308. defer done()
  309. out, err := vm.Run([]byte{
  310. 0xff, 0xff, 0xff, 0xff,
  311. 0xff, 0xff, 0xff, 0xff,
  312. 0x01, 0x02,
  313. })
  314. if err != nil {
  315. t.Fatalf("unexpected error while running program: %v", err)
  316. }
  317. if want, got := 2, out; want != got {
  318. t.Fatalf("unexpected number of output bytes:\n- want: %d\n- got: %d",
  319. want, got)
  320. }
  321. }
  322. func TestVMJumpIfBitsNotSet(t *testing.T) {
  323. vm, done, err := testVM(t, []bpf.Instruction{
  324. bpf.LoadAbsolute{
  325. Off: 8,
  326. Size: 2,
  327. },
  328. bpf.JumpIf{
  329. Cond: bpf.JumpBitsNotSet,
  330. Val: 0x1221,
  331. SkipTrue: 1,
  332. },
  333. bpf.RetConstant{
  334. Val: 0,
  335. },
  336. bpf.RetConstant{
  337. Val: 10,
  338. },
  339. })
  340. if err != nil {
  341. t.Fatalf("failed to load BPF program: %v", err)
  342. }
  343. defer done()
  344. out, err := vm.Run([]byte{
  345. 0xff, 0xff, 0xff, 0xff,
  346. 0xff, 0xff, 0xff, 0xff,
  347. 0x01, 0x02,
  348. })
  349. if err != nil {
  350. t.Fatalf("unexpected error while running program: %v", err)
  351. }
  352. if want, got := 2, out; want != got {
  353. t.Fatalf("unexpected number of output bytes:\n- want: %d\n- got: %d",
  354. want, got)
  355. }
  356. }