1 /* $NetBSD: t_bpfjit.c,v 1.1 2014/06/30 21:30:51 alnsn Exp $ */ 2 3 /*- 4 * Copyright (c) 2014 Alexander Nasonov. 5 * All rights reserved. 6 * 7 * Redistribution and use in source and binary forms, with or without 8 * modification, are permitted provided that the following conditions 9 * are met: 10 * 1. Redistributions of source code must retain the above copyright 11 * notice, this list of conditions and the following disclaimer. 12 * 2. Redistributions in binary form must reproduce the above copyright 13 * notice, this list of conditions and the following disclaimer in the 14 * documentation and/or other materials provided with the distribution. 15 * 16 * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS 17 * OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED 18 * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE 19 * DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE 20 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL 21 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR 22 * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) 23 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT 24 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY 25 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF 26 * SUCH DAMAGE. 27 */ 28 #include <sys/cdefs.h> 29 __RCSID("$NetBSD: t_bpfjit.c,v 1.1 2014/06/30 21:30:51 alnsn Exp $"); 30 31 #include <sys/param.h> 32 #include <sys/mbuf.h> 33 #include <unistd.h> 34 35 #include <net/bpf.h> 36 #include <net/bpfjit.h> 37 38 #include <stdint.h> 39 #include <stdio.h> 40 #include <string.h> 41 42 #include <rump/rump.h> 43 #include <rump/rump_syscalls.h> 44 45 /* XXX: atf-c.h has collisions with mbuf */ 46 #undef m_type 47 #undef m_data 48 #include <atf-c.h> 49 50 #include "../../h_macros.h" 51 52 /* XXX These declarations don't look kosher. */ 53 bpfjit_func_t rumpns_bpfjit_generate_code(const bpf_ctx_t *, 54 const struct bpf_insn *, size_t); 55 void rumpns_bpfjit_free_code(bpfjit_func_t); 56 57 static bool 58 test_ldb_abs(size_t split) 59 { 60 static char P[] = { 1, 2, 3, 4, 5 }; 61 62 /* Return a product of all packet bytes. */ 63 static struct bpf_insn insns[] = { 64 BPF_STMT(BPF_LDX+BPF_W+BPF_IMM, 1), /* X <- 1 */ 65 66 BPF_STMT(BPF_LD+BPF_B+BPF_ABS, 0), /* A <- P[0] */ 67 BPF_STMT(BPF_ALU+BPF_MUL+BPF_X, 0), /* A <- A * X */ 68 BPF_STMT(BPF_MISC+BPF_TAX, 0), /* X <- A */ 69 70 BPF_STMT(BPF_LD+BPF_B+BPF_ABS, 1), /* A <- P[1] */ 71 BPF_STMT(BPF_ALU+BPF_MUL+BPF_X, 0), /* A <- A * X */ 72 BPF_STMT(BPF_MISC+BPF_TAX, 0), /* X <- A */ 73 74 BPF_STMT(BPF_LD+BPF_B+BPF_ABS, 2), /* A <- P[2] */ 75 BPF_STMT(BPF_ALU+BPF_MUL+BPF_X, 0), /* A <- A * X */ 76 BPF_STMT(BPF_MISC+BPF_TAX, 0), /* X <- A */ 77 78 BPF_STMT(BPF_LD+BPF_B+BPF_ABS, 3), /* A <- P[3] */ 79 BPF_STMT(BPF_ALU+BPF_MUL+BPF_X, 0), /* A <- A * X */ 80 BPF_STMT(BPF_MISC+BPF_TAX, 0), /* X <- A */ 81 82 BPF_STMT(BPF_LD+BPF_B+BPF_ABS, 4), /* A <- P[4] */ 83 BPF_STMT(BPF_ALU+BPF_MUL+BPF_X, 0), /* A <- A * X */ 84 BPF_STMT(BPF_RET+BPF_A, 0), /* ret A */ 85 }; 86 87 const size_t insn_count = sizeof(insns) / sizeof(insns[0]); 88 89 bpfjit_func_t fn; 90 bpf_args_t args; 91 struct mbuf mb1, mb2; 92 unsigned int res; 93 94 (void)memset(&mb1, 0, sizeof(mb1)); 95 mb1.m_hdr.mh_data = P; 96 mb1.m_next = (split < sizeof(P)) ? &mb2 : NULL; 97 mb1.m_len = (split < sizeof(P)) ? split : sizeof(P); 98 99 if (split < sizeof(P)) { 100 (void)memset(&mb2, 0, sizeof(mb2)); 101 mb2.m_next = NULL; 102 mb2.m_hdr.mh_data = &P[split]; 103 mb2.m_len = sizeof(P) - split; 104 } 105 106 args.pkt = (const uint8_t*)&mb1; 107 args.buflen = 0; 108 args.wirelen = sizeof(P); 109 110 rump_schedule(); 111 fn = rumpns_bpfjit_generate_code(NULL, insns, insn_count); 112 rump_unschedule(); 113 114 ATF_REQUIRE(fn != NULL); 115 116 res = fn(NULL, &args); 117 118 rump_schedule(); 119 rumpns_bpfjit_free_code(fn); 120 rump_unschedule(); 121 122 return res == 120; 123 } 124 125 static bool 126 test_ldh_abs(size_t split) 127 { 128 static char P[] = { 1, 2, 3, 4, 5 }; 129 130 static struct bpf_insn insns[] = { 131 BPF_STMT(BPF_LD+BPF_H+BPF_ABS, 0), /* A <- P[0:2] */ 132 BPF_STMT(BPF_ALU+BPF_ADD+BPF_X, 0), /* A <- A + X */ 133 BPF_STMT(BPF_MISC+BPF_TAX, 0), /* X <- A */ 134 135 BPF_STMT(BPF_LD+BPF_H+BPF_ABS, 1), /* A <- P[1:2] */ 136 BPF_STMT(BPF_ALU+BPF_ADD+BPF_X, 0), /* A <- A + X */ 137 BPF_STMT(BPF_MISC+BPF_TAX, 0), /* X <- A */ 138 139 BPF_STMT(BPF_LD+BPF_H+BPF_ABS, 2), /* A <- P[2:2] */ 140 BPF_STMT(BPF_ALU+BPF_ADD+BPF_X, 0), /* A <- A + X */ 141 BPF_STMT(BPF_MISC+BPF_TAX, 0), /* X <- A */ 142 143 BPF_STMT(BPF_LD+BPF_H+BPF_ABS, 3), /* A <- P[3:2] */ 144 BPF_STMT(BPF_ALU+BPF_ADD+BPF_X, 0), /* A <- A + X */ 145 BPF_STMT(BPF_RET+BPF_A, 0), /* ret A */ 146 }; 147 148 const size_t insn_count = sizeof(insns) / sizeof(insns[0]); 149 150 bpfjit_func_t fn; 151 bpf_args_t args; 152 struct mbuf mb1, mb2; 153 unsigned int res; 154 155 (void)memset(&mb1, 0, sizeof(mb1)); 156 mb1.m_hdr.mh_data = P; 157 mb1.m_next = (split < sizeof(P)) ? &mb2 : NULL; 158 mb1.m_len = (split < sizeof(P)) ? split : sizeof(P); 159 160 if (split < sizeof(P)) { 161 (void)memset(&mb2, 0, sizeof(mb2)); 162 mb2.m_next = NULL; 163 mb2.m_hdr.mh_data = &P[split]; 164 mb2.m_len = sizeof(P) - split; 165 } 166 167 args.pkt = (const uint8_t*)&mb1; 168 args.buflen = 0; 169 args.wirelen = sizeof(P); 170 171 rump_schedule(); 172 fn = rumpns_bpfjit_generate_code(NULL, insns, insn_count); 173 rump_unschedule(); 174 175 ATF_REQUIRE(fn != NULL); 176 177 res = fn(NULL, &args); 178 179 rump_schedule(); 180 rumpns_bpfjit_free_code(fn); 181 rump_unschedule(); 182 183 return res == 0x0a0e; /* 10 14 */ 184 } 185 186 static bool 187 test_ldw_abs(size_t split) 188 { 189 static char P[] = { 1, 2, 3, 4, 5 }; 190 191 static struct bpf_insn insns[] = { 192 BPF_STMT(BPF_LD+BPF_W+BPF_ABS, 0), /* A <- P[0:4] */ 193 BPF_STMT(BPF_ALU+BPF_ADD+BPF_X, 0), /* A <- A + X */ 194 BPF_STMT(BPF_MISC+BPF_TAX, 0), /* X <- A */ 195 196 BPF_STMT(BPF_LD+BPF_W+BPF_ABS, 1), /* A <- P[1:4] */ 197 BPF_STMT(BPF_ALU+BPF_ADD+BPF_X, 0), /* A <- A + X */ 198 BPF_STMT(BPF_RET+BPF_A, 0), /* ret A */ 199 }; 200 201 const size_t insn_count = sizeof(insns) / sizeof(insns[0]); 202 203 bpfjit_func_t fn; 204 bpf_args_t args; 205 struct mbuf mb1, mb2; 206 unsigned int res; 207 208 (void)memset(&mb1, 0, sizeof(mb1)); 209 mb1.m_hdr.mh_data = P; 210 mb1.m_next = (split < sizeof(P)) ? &mb2 : NULL; 211 mb1.m_len = (split < sizeof(P)) ? split : sizeof(P); 212 213 if (split < sizeof(P)) { 214 (void)memset(&mb2, 0, sizeof(mb2)); 215 mb2.m_next = NULL; 216 mb2.m_hdr.mh_data = &P[split]; 217 mb2.m_len = sizeof(P) - split; 218 } 219 220 args.pkt = (const uint8_t*)&mb1; 221 args.buflen = 0; 222 args.wirelen = sizeof(P); 223 224 rump_schedule(); 225 fn = rumpns_bpfjit_generate_code(NULL, insns, insn_count); 226 rump_unschedule(); 227 228 ATF_REQUIRE(fn != NULL); 229 230 res = fn(NULL, &args); 231 printf("0x%08x\n", res); 232 233 rump_schedule(); 234 rumpns_bpfjit_free_code(fn); 235 rump_unschedule(); 236 237 return res == 0x03050709; 238 } 239 240 static bool 241 test_ldb_ind(size_t split) 242 { 243 static char P[] = { 1, 2, 3, 4, 5 }; 244 245 /* Return a sum of all packet bytes. */ 246 static struct bpf_insn insns[] = { 247 BPF_STMT(BPF_LD+BPF_B+BPF_IND, 0), /* A <- P[0+X] */ 248 BPF_STMT(BPF_ST, 0), /* M[0] <- A */ 249 250 BPF_STMT(BPF_LD+BPF_B+BPF_IND, 1), /* A <- P[1+X] */ 251 BPF_STMT(BPF_LDX+BPF_W+BPF_MEM, 0), /* X <- M[0] */ 252 BPF_STMT(BPF_ALU+BPF_ADD+BPF_X, 0), /* A <- A + X */ 253 BPF_STMT(BPF_ST, 0), /* M[0] <- A */ 254 255 BPF_STMT(BPF_LDX+BPF_W+BPF_IMM, 1), /* X <- 1 */ 256 BPF_STMT(BPF_LD+BPF_B+BPF_IND, 1), /* A <- P[1+X] */ 257 BPF_STMT(BPF_LDX+BPF_W+BPF_MEM, 0), /* X <- M[0] */ 258 BPF_STMT(BPF_ALU+BPF_ADD+BPF_X, 0), /* A <- A + X */ 259 BPF_STMT(BPF_ST, 0), /* M[0] <- A */ 260 261 BPF_STMT(BPF_LDX+BPF_W+BPF_IMM, 1), /* X <- 1 */ 262 BPF_STMT(BPF_LD+BPF_B+BPF_IND, 2), /* A <- P[2+X] */ 263 BPF_STMT(BPF_LDX+BPF_W+BPF_MEM, 0), /* X <- M[0] */ 264 BPF_STMT(BPF_ALU+BPF_ADD+BPF_X, 0), /* A <- A + X */ 265 BPF_STMT(BPF_ST, 0), /* M[0] <- A */ 266 267 BPF_STMT(BPF_LDX+BPF_W+BPF_IMM, 1), /* X <- 1 */ 268 BPF_STMT(BPF_LD+BPF_B+BPF_IND, 3), /* A <- P[3+X] */ 269 BPF_STMT(BPF_LDX+BPF_W+BPF_MEM, 0), /* X <- M[0] */ 270 BPF_STMT(BPF_ALU+BPF_ADD+BPF_X, 0), /* A <- A + X */ 271 BPF_STMT(BPF_RET+BPF_A, 0), /* ret A */ 272 }; 273 274 const size_t insn_count = sizeof(insns) / sizeof(insns[0]); 275 276 bpfjit_func_t fn; 277 bpf_args_t args; 278 struct mbuf mb1, mb2; 279 unsigned int res; 280 281 (void)memset(&mb1, 0, sizeof(mb1)); 282 mb1.m_hdr.mh_data = P; 283 mb1.m_next = (split < sizeof(P)) ? &mb2 : NULL; 284 mb1.m_len = (split < sizeof(P)) ? split : sizeof(P); 285 286 if (split < sizeof(P)) { 287 (void)memset(&mb2, 0, sizeof(mb2)); 288 mb2.m_next = NULL; 289 mb2.m_hdr.mh_data = &P[split]; 290 mb2.m_len = sizeof(P) - split; 291 } 292 293 args.pkt = (const uint8_t*)&mb1; 294 args.buflen = 0; 295 args.wirelen = sizeof(P); 296 297 rump_schedule(); 298 fn = rumpns_bpfjit_generate_code(NULL, insns, insn_count); 299 rump_unschedule(); 300 301 ATF_REQUIRE(fn != NULL); 302 303 res = fn(NULL, &args); 304 305 rump_schedule(); 306 rumpns_bpfjit_free_code(fn); 307 rump_unschedule(); 308 309 return res == 15; 310 } 311 312 static bool 313 test_ldw_ind(size_t split) 314 { 315 static char P[] = { 1, 2, 3, 4, 5 }; 316 317 static struct bpf_insn insns[] = { 318 BPF_STMT(BPF_LD+BPF_W+BPF_IND, 0), /* A <- P[X+0:4] */ 319 BPF_STMT(BPF_ST, 0), /* M[0] <- A */ 320 321 BPF_STMT(BPF_LDX+BPF_W+BPF_IMM, 1), /* X <- 1 */ 322 BPF_STMT(BPF_LD+BPF_W+BPF_IND, 0), /* A <- P[X+0:4] */ 323 BPF_STMT(BPF_LDX+BPF_W+BPF_MEM, 0), /* X <- M[0] */ 324 BPF_STMT(BPF_ALU+BPF_ADD+BPF_X, 0), /* A <- A + X */ 325 BPF_STMT(BPF_ST, 0), /* M[0] <- A */ 326 327 BPF_STMT(BPF_LDX+BPF_W+BPF_IMM, 0), /* X <- 0 */ 328 BPF_STMT(BPF_LD+BPF_W+BPF_IND, 1), /* A <- P[X+1:4] */ 329 BPF_STMT(BPF_LDX+BPF_W+BPF_MEM, 0), /* X <- M[0] */ 330 BPF_STMT(BPF_ALU+BPF_ADD+BPF_X, 0), /* A <- A + X */ 331 BPF_STMT(BPF_RET+BPF_A, 0), /* ret A */ 332 }; 333 334 const size_t insn_count = sizeof(insns) / sizeof(insns[0]); 335 336 bpfjit_func_t fn; 337 bpf_args_t args; 338 struct mbuf mb1, mb2; 339 unsigned int res; 340 341 (void)memset(&mb1, 0, sizeof(mb1)); 342 mb1.m_hdr.mh_data = P; 343 mb1.m_next = (split < sizeof(P)) ? &mb2 : NULL; 344 mb1.m_len = (split < sizeof(P)) ? split : sizeof(P); 345 346 if (split < sizeof(P)) { 347 (void)memset(&mb2, 0, sizeof(mb2)); 348 mb2.m_next = NULL; 349 mb2.m_hdr.mh_data = &P[split]; 350 mb2.m_len = sizeof(P) - split; 351 } 352 353 args.pkt = (const uint8_t*)&mb1; 354 args.buflen = 0; 355 args.wirelen = sizeof(P); 356 357 rump_schedule(); 358 fn = rumpns_bpfjit_generate_code(NULL, insns, insn_count); 359 rump_unschedule(); 360 361 ATF_REQUIRE(fn != NULL); 362 363 res = fn(NULL, &args); 364 365 rump_schedule(); 366 rumpns_bpfjit_free_code(fn); 367 rump_unschedule(); 368 369 return res == 0x05080b0e; 370 } 371 372 static bool 373 test_ldh_ind(size_t split) 374 { 375 static char P[] = { 1, 2, 3, 4, 5 }; 376 377 static struct bpf_insn insns[] = { 378 BPF_STMT(BPF_LD+BPF_H+BPF_IND, 0), /* A <- P[X+0:2] */ 379 BPF_STMT(BPF_ST, 0), /* M[0] <- A */ 380 381 BPF_STMT(BPF_LD+BPF_H+BPF_IND, 1), /* A <- P[X+1:2] */ 382 BPF_STMT(BPF_LDX+BPF_W+BPF_MEM, 0), /* X <- M[0] */ 383 BPF_STMT(BPF_ALU+BPF_ADD+BPF_X, 0), /* A <- A + X */ 384 BPF_STMT(BPF_ST, 0), /* M[0] <- A */ 385 386 BPF_STMT(BPF_LDX+BPF_W+BPF_IMM, 1), /* X <- 1 */ 387 BPF_STMT(BPF_LD+BPF_H+BPF_IND, 1), /* A <- P[X+1:2] */ 388 BPF_STMT(BPF_LDX+BPF_W+BPF_MEM, 0), /* X <- M[0] */ 389 BPF_STMT(BPF_ALU+BPF_ADD+BPF_X, 0), /* A <- A + X */ 390 BPF_STMT(BPF_ST, 0), /* M[0] <- A */ 391 392 BPF_STMT(BPF_LDX+BPF_W+BPF_IMM, 1), /* X <- 1 */ 393 BPF_STMT(BPF_LD+BPF_H+BPF_IND, 2), /* A <- P[X+2:2] */ 394 BPF_STMT(BPF_LDX+BPF_W+BPF_MEM, 0), /* X <- M[0] */ 395 BPF_STMT(BPF_ALU+BPF_ADD+BPF_X, 0), /* A <- A + X */ 396 BPF_STMT(BPF_RET+BPF_A, 0), /* ret A */ 397 }; 398 399 const size_t insn_count = sizeof(insns) / sizeof(insns[0]); 400 401 bpfjit_func_t fn; 402 bpf_args_t args; 403 struct mbuf mb1, mb2; 404 unsigned int res; 405 406 (void)memset(&mb1, 0, sizeof(mb1)); 407 mb1.m_hdr.mh_data = P; 408 mb1.m_next = (split < sizeof(P)) ? &mb2 : NULL; 409 mb1.m_len = (split < sizeof(P)) ? split : sizeof(P); 410 411 if (split < sizeof(P)) { 412 (void)memset(&mb2, 0, sizeof(mb2)); 413 mb2.m_next = NULL; 414 mb2.m_hdr.mh_data = &P[split]; 415 mb2.m_len = sizeof(P) - split; 416 } 417 418 args.pkt = (const uint8_t*)&mb1; 419 args.buflen = 0; 420 args.wirelen = sizeof(P); 421 422 rump_schedule(); 423 fn = rumpns_bpfjit_generate_code(NULL, insns, insn_count); 424 rump_unschedule(); 425 426 ATF_REQUIRE(fn != NULL); 427 428 res = fn(NULL, &args); 429 430 rump_schedule(); 431 rumpns_bpfjit_free_code(fn); 432 rump_unschedule(); 433 434 return res == 0x0a0e; /* 10 14 */ 435 } 436 437 static bool 438 test_msh(size_t split) 439 { 440 static char P[] = { 1, 2, 3, 4, 5 }; 441 442 /* Return a product of all packet bytes. */ 443 static struct bpf_insn insns[] = { 444 BPF_STMT(BPF_LD+BPF_IMM, 1), /* A <- 1 */ 445 446 BPF_STMT(BPF_LDX+BPF_B+BPF_MSH, 0), /* X <- 4*(P[0]&0xf) */ 447 BPF_STMT(BPF_ALU+BPF_MUL+BPF_X, 0), /* A <- A * X */ 448 BPF_STMT(BPF_ALU+BPF_DIV+BPF_K, 4), /* A <- A / 4 */ 449 450 BPF_STMT(BPF_LDX+BPF_B+BPF_MSH, 1), /* X <- 4*(P[1]&0xf) */ 451 BPF_STMT(BPF_ALU+BPF_MUL+BPF_X, 0), /* A <- A * X */ 452 BPF_STMT(BPF_ALU+BPF_DIV+BPF_K, 4), /* A <- A / 4 */ 453 454 BPF_STMT(BPF_LDX+BPF_B+BPF_MSH, 2), /* X <- 4*(P[2]&0xf) */ 455 BPF_STMT(BPF_ALU+BPF_MUL+BPF_X, 0), /* A <- A * X */ 456 BPF_STMT(BPF_ALU+BPF_DIV+BPF_K, 4), /* A <- A / 4 */ 457 458 BPF_STMT(BPF_LDX+BPF_B+BPF_MSH, 3), /* X <- 4*(P[3]&0xf) */ 459 BPF_STMT(BPF_ALU+BPF_MUL+BPF_X, 0), /* A <- A * X */ 460 BPF_STMT(BPF_ALU+BPF_DIV+BPF_K, 4), /* A <- A / 4 */ 461 462 BPF_STMT(BPF_LDX+BPF_B+BPF_MSH, 4), /* X <- 4*(P[4]&0xf) */ 463 BPF_STMT(BPF_ALU+BPF_MUL+BPF_X, 0), /* A <- A * X */ 464 BPF_STMT(BPF_ALU+BPF_DIV+BPF_K, 4), /* A <- A / 4 */ 465 466 BPF_STMT(BPF_RET+BPF_A, 0), /* ret A */ 467 }; 468 469 const size_t insn_count = sizeof(insns) / sizeof(insns[0]); 470 471 bpfjit_func_t fn; 472 bpf_args_t args; 473 struct mbuf mb1, mb2; 474 unsigned int res; 475 476 (void)memset(&mb1, 0, sizeof(mb1)); 477 mb1.m_hdr.mh_data = P; 478 mb1.m_next = (split < sizeof(P)) ? &mb2 : NULL; 479 mb1.m_len = (split < sizeof(P)) ? split : sizeof(P); 480 481 if (split < sizeof(P)) { 482 (void)memset(&mb2, 0, sizeof(mb2)); 483 mb2.m_next = NULL; 484 mb2.m_hdr.mh_data = &P[split]; 485 mb2.m_len = sizeof(P) - split; 486 } 487 488 args.pkt = (const uint8_t*)&mb1; 489 args.buflen = 0; 490 args.wirelen = sizeof(P); 491 492 rump_schedule(); 493 fn = rumpns_bpfjit_generate_code(NULL, insns, insn_count); 494 rump_unschedule(); 495 496 res = fn(NULL, &args); 497 498 rump_schedule(); 499 rumpns_bpfjit_free_code(fn); 500 rump_unschedule(); 501 502 return res == 120; 503 } 504 505 ATF_TC(bpfjit_mbuf_ldb_abs); 506 ATF_TC_HEAD(bpfjit_mbuf_ldb_abs, tc) 507 { 508 509 atf_tc_set_md_var(tc, "descr", "Check that BPF_LD+BPF_B+BPF_ABS " 510 "loads bytes from mbuf correctly"); 511 } 512 513 ATF_TC_BODY(bpfjit_mbuf_ldb_abs, tc) 514 { 515 516 RZ(rump_init()); 517 518 ATF_CHECK(test_ldb_abs(0)); 519 ATF_CHECK(test_ldb_abs(1)); 520 ATF_CHECK(test_ldb_abs(2)); 521 ATF_CHECK(test_ldb_abs(3)); 522 ATF_CHECK(test_ldb_abs(4)); 523 ATF_CHECK(test_ldb_abs(5)); 524 } 525 526 ATF_TC(bpfjit_mbuf_ldh_abs); 527 ATF_TC_HEAD(bpfjit_mbuf_ldh_abs, tc) 528 { 529 530 atf_tc_set_md_var(tc, "descr", "Check that BPF_LD+BPF_H+BPF_ABS " 531 "loads halfwords from mbuf correctly"); 532 } 533 534 ATF_TC_BODY(bpfjit_mbuf_ldh_abs, tc) 535 { 536 537 RZ(rump_init()); 538 539 ATF_CHECK(test_ldh_abs(0)); 540 ATF_CHECK(test_ldh_abs(1)); 541 ATF_CHECK(test_ldh_abs(2)); 542 ATF_CHECK(test_ldh_abs(3)); 543 ATF_CHECK(test_ldh_abs(4)); 544 ATF_CHECK(test_ldh_abs(5)); 545 } 546 547 ATF_TC(bpfjit_mbuf_ldw_abs); 548 ATF_TC_HEAD(bpfjit_mbuf_ldw_abs, tc) 549 { 550 551 atf_tc_set_md_var(tc, "descr", "Check that BPF_LD+BPF_W+BPF_ABS " 552 "loads words from mbuf correctly"); 553 } 554 555 ATF_TC_BODY(bpfjit_mbuf_ldw_abs, tc) 556 { 557 558 RZ(rump_init()); 559 560 ATF_CHECK(test_ldw_abs(0)); 561 ATF_CHECK(test_ldw_abs(1)); 562 ATF_CHECK(test_ldw_abs(2)); 563 ATF_CHECK(test_ldw_abs(3)); 564 ATF_CHECK(test_ldw_abs(4)); 565 ATF_CHECK(test_ldw_abs(5)); 566 } 567 568 ATF_TC(bpfjit_mbuf_ldb_ind); 569 ATF_TC_HEAD(bpfjit_mbuf_ldb_ind, tc) 570 { 571 572 atf_tc_set_md_var(tc, "descr", "Check that BPF_LD+BPF_B+BPF_IND " 573 "loads bytes from mbuf correctly"); 574 } 575 576 ATF_TC_BODY(bpfjit_mbuf_ldb_ind, tc) 577 { 578 579 RZ(rump_init()); 580 581 ATF_CHECK(test_ldb_ind(0)); 582 ATF_CHECK(test_ldb_ind(1)); 583 ATF_CHECK(test_ldb_ind(2)); 584 ATF_CHECK(test_ldb_ind(3)); 585 ATF_CHECK(test_ldb_ind(4)); 586 ATF_CHECK(test_ldb_ind(5)); 587 } 588 589 ATF_TC(bpfjit_mbuf_ldh_ind); 590 ATF_TC_HEAD(bpfjit_mbuf_ldh_ind, tc) 591 { 592 593 atf_tc_set_md_var(tc, "descr", "Check that BPF_LD+BPF_H+BPF_IND " 594 "loads halfwords from mbuf correctly"); 595 } 596 597 ATF_TC_BODY(bpfjit_mbuf_ldh_ind, tc) 598 { 599 600 RZ(rump_init()); 601 602 ATF_CHECK(test_ldh_ind(0)); 603 ATF_CHECK(test_ldh_ind(1)); 604 ATF_CHECK(test_ldh_ind(2)); 605 ATF_CHECK(test_ldh_ind(3)); 606 ATF_CHECK(test_ldh_ind(4)); 607 ATF_CHECK(test_ldh_ind(5)); 608 } 609 610 ATF_TC(bpfjit_mbuf_ldw_ind); 611 ATF_TC_HEAD(bpfjit_mbuf_ldw_ind, tc) 612 { 613 614 atf_tc_set_md_var(tc, "descr", "Check that BPF_LD+BPF_W+BPF_IND " 615 "loads words from mbuf correctly"); 616 } 617 618 ATF_TC_BODY(bpfjit_mbuf_ldw_ind, tc) 619 { 620 621 RZ(rump_init()); 622 623 ATF_CHECK(test_ldw_ind(0)); 624 ATF_CHECK(test_ldw_ind(1)); 625 ATF_CHECK(test_ldw_ind(2)); 626 ATF_CHECK(test_ldw_ind(3)); 627 ATF_CHECK(test_ldw_ind(4)); 628 ATF_CHECK(test_ldw_ind(5)); 629 } 630 631 ATF_TC(bpfjit_mbuf_msh); 632 ATF_TC_HEAD(bpfjit_mbuf_msh, tc) 633 { 634 635 atf_tc_set_md_var(tc, "descr", "Check that BPF_LDX+BPF_B+BPF_MSH " 636 "loads bytes from mbuf correctly"); 637 } 638 639 ATF_TC_BODY(bpfjit_mbuf_msh, tc) 640 { 641 642 RZ(rump_init()); 643 644 ATF_CHECK(test_msh(0)); 645 ATF_CHECK(test_msh(1)); 646 ATF_CHECK(test_msh(2)); 647 ATF_CHECK(test_msh(3)); 648 ATF_CHECK(test_msh(4)); 649 ATF_CHECK(test_msh(5)); 650 } 651 652 ATF_TP_ADD_TCS(tp) 653 { 654 655 ATF_TP_ADD_TC(tp, bpfjit_mbuf_ldb_abs); 656 ATF_TP_ADD_TC(tp, bpfjit_mbuf_ldh_abs); 657 ATF_TP_ADD_TC(tp, bpfjit_mbuf_ldw_abs); 658 ATF_TP_ADD_TC(tp, bpfjit_mbuf_ldb_ind); 659 ATF_TP_ADD_TC(tp, bpfjit_mbuf_ldh_ind); 660 ATF_TP_ADD_TC(tp, bpfjit_mbuf_ldw_ind); 661 ATF_TP_ADD_TC(tp, bpfjit_mbuf_msh); 662 663 return atf_no_error(); 664 } 665