1 2 /* HOW TO COMPILE: 3 4 * 32bit build: 5 gcc -Winline -Wall -g -O -mregnames -maltivec 6 * 64bit build: 7 gcc -Winline -Wall -g -O -mregnames -maltivec -m64 8 9 This program is useful, but the register usage conventions in 10 it are a complete dog. In particular, _patch_op_imm has to 11 be inlined, else you wind up with it segfaulting in 12 completely different places due to corruption (of r20 in the 13 case I chased). 14 */ 15 16 /* 17 * test-ppc.c: 18 * PPC tests for qemu-PPC CPU emulation checks 19 * 20 * Copyright (c) 2005 Jocelyn Mayer 21 * 22 * This program is free software; you can redistribute it and/or 23 * modify it under the terms of the GNU General Public License V2 24 * as published by the Free Software Foundation 25 * 26 * This program is distributed in the hope that it will be useful, 27 * but WITHOUT ANY WARRANTY; without even the implied warranty of 28 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 29 * GNU General Public License for more details. 30 * 31 * You should have received a copy of the GNU General Public License 32 * along with this program; if not, write to the Free Software 33 * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA 34 */ 35 36 /* 37 * Theory of operations: 38 * a few registers are reserved for the test program: 39 * r14 => r18 40 * f14 => f18 41 * I do preload test values in r14 thru r17 (or less, depending on the number 42 * of register operands needed), patch the test opcode if any immediate 43 * operands are required, execute the tested opcode. 44 * XER, CCR and FPSCR are cleared before every test. 45 * I always get the result in r17 and also save XER and CCR for fixed-point 46 * operations. I also check FPSCR for floating points operations. 47 * 48 * Improvments: 49 * a more clever FPSCR management is needed: for now, I always test 50 * the round-to-zero case. Other rounding modes also need to be tested. 51 */ 52 53 /* 54 * Operation details 55 * ----------------- 56 * The 'test' functions (via all_tests[]) are wrappers of single asm instns 57 * 58 * The 'loops' (e.g. int_loops) do the actual work: 59 * - loops over as many arguments as the instn needs (regs | imms) 60 * - sets up the environment (reset cr,xer, assign src regs...) 61 * - maybe modifies the asm instn to test different imm args 62 * - calls the test function 63 * - retrieves relevant register data (rD,cr,xer,...) 64 * - prints argument and result data. 65 * 66 * More specifically... 67 * 68 * all_tests[i] holds insn tests 69 * - of which each holds: {instn_test_arr[], description, flags} 70 * 71 * flags hold 3 instn classifiers: {family, type, arg_type} 72 * 73 * // The main test loop: 74 * do_tests( user_ctl_flags ) { 75 * foreach(curr_test = all_test[i]) { 76 * 77 * // flags are used to control what tests are run: 78 * if (curr_test->flags && !user_ctl_flags) 79 * continue; 80 * 81 * // a 'loop_family_arr' is chosen based on the 'family' flag... 82 * switch(curr_test->flags->family) { 83 * case x: loop_family_arr = int_loops; 84 * ... 85 * } 86 * 87 * // ...and the actual test_loop to run is found by indexing into 88 * // the loop_family_arr with the 'arg_type' flag: 89 * test_loop = loop_family[curr_test->flags->arg_type] 90 * 91 * // finally, loop over all instn tests for this test: 92 * foreach (instn_test = curr_test->instn_test_arr[i]) { 93 * 94 * // and call the test_loop with the current instn_test function,name 95 * test_loop( instn_test->func, instn_test->name ) 96 * } 97 * } 98 * } 99 * 100 * 101 * Details of intruction patching for immediate operands 102 * ----------------------------------------------------- 103 * All the immediate insn test functions are of the form {imm_insn, blr} 104 * In order to patch one of these functions, we simply copy both insns 105 * to a stack buffer, and rewrite the immediate part of imm_insn. 106 * We then execute our stack buffer. 107 * All ppc instructions are 32bits wide, which makes this fairly easy. 108 * 109 * Example: 110 * extern void test_addi (void); 111 * asm(".section \".text\"\n" 112 * " .align 2\n" 113 * " .type test_addi,@function\n" 114 * "test_addi:\n" 115 * " addi\n" 116 * " blr\n" 117 * " .previous\n" 118 * ); 119 * 120 * We are interested only in: 121 * " addi 17, 14, 0\n" 122 * " blr\n" 123 * 124 * In a loop test, we may see: 125 * uint32_t func_buf[2]; // our new stack based 'function' 126 * for imm... // loop over imm 127 * init_function( &func, func_buf ); // copy insns, set func ptr 128 * patch_op_imm16(&func_buf[0], imm); // patch 'addi' insn 129 * ... 130 * (*func)(); // exec our rewritten code 131 * 132 * patch_op_imm16() itself simply takes the uint32_t insn and overwrites 133 * the immediate field with the new value (which, for 'addi', is the 134 * low 16 bits). 135 * 136 * So in the loop test, if 'imm' is currently 9, and p[0] is: 137 * 0x3A2E0000 => addi 17, 14, 0 138 * 139 * after patch_op_imm16(), func_buf[0] becomes: 140 * 0x3A2E0009 => addi 17, 14, 9 141 * 142 * Note: init_function() needs to be called on every iteration 143 * - don't ask me why! 144 */ 145 146 147 /**********************************************************************/ 148 /* Uncomment to enable many arguments for altivec insns */ 149 #define USAGE_SIMPLE 150 151 /* Uncomment to enable many arguments for altivec insns */ 152 //#define ALTIVEC_ARGS_LARGE 153 154 /* Uncomment to enable output of CR flags for float tests */ 155 //#define TEST_FLOAT_FLAGS 156 157 /* Uncomment to enable debug output */ 158 //#define DEBUG_ARGS_BUILD 159 //#define DEBUG_FILTER 160 161 /* These should be set at build time */ 162 //#define NO_FLOAT 163 //#define HAS_ALTIVEC // CFLAGS += -maltivec 164 //#define IS_PPC405 165 /**********************************************************************/ 166 167 168 #include <stdint.h> 169 #include "tests/sys_mman.h" 170 #include "tests/malloc.h" // memalign16 171 172 #define STATIC_ASSERT(e) sizeof(struct { int:-!(e); }) 173 174 /* Something of the same size as void*, so can be safely be coerced 175 * to/from a pointer type. Also same size as the host's gp registers. 176 * According to the AltiVec section of the GCC manual, the syntax does 177 * not allow the use of a typedef name as a type specifier in conjunction 178 * with the vector keyword, so typedefs uint[32|64]_t are #undef'ed here 179 * and redefined using #define. 180 */ 181 #undef uint32_t 182 #undef uint64_t 183 #define uint32_t unsigned int 184 #define uint64_t unsigned long long int 185 186 #ifndef __powerpc64__ 187 typedef uint32_t HWord_t; 188 #else 189 typedef uint64_t HWord_t; 190 #endif /* __powerpc64__ */ 191 192 enum { 193 compile_time_test1 = STATIC_ASSERT(sizeof(uint32_t) == 4), 194 compile_time_test2 = STATIC_ASSERT(sizeof(uint64_t) == 8), 195 }; 196 197 #define ALLCR "cr0","cr1","cr2","cr3","cr4","cr5","cr6","cr7" 198 199 #define SET_CR(_arg) \ 200 __asm__ __volatile__ ("mtcr %0" : : "b"(_arg) : ALLCR ); 201 202 #define SET_XER(_arg) \ 203 __asm__ __volatile__ ("mtxer %0" : : "b"(_arg) : "xer" ); 204 205 #define GET_CR(_lval) \ 206 __asm__ __volatile__ ("mfcr %0" : "=b"(_lval) ) 207 208 #define GET_XER(_lval) \ 209 __asm__ __volatile__ ("mfxer %0" : "=b"(_lval) ) 210 211 #define GET_CR_XER(_lval_cr,_lval_xer) \ 212 do { GET_CR(_lval_cr); GET_XER(_lval_xer); } while (0) 213 214 #define SET_CR_ZERO \ 215 SET_CR(0) 216 217 #define SET_XER_ZERO \ 218 SET_XER(0) 219 220 #define SET_CR_XER_ZERO \ 221 do { SET_CR_ZERO; SET_XER_ZERO; } while (0) 222 223 #define SET_FPSCR_ZERO \ 224 do { double _d = 0.0; \ 225 __asm__ __volatile__ ("mtfsf 0xFF, %0" : : "f"(_d) ); \ 226 } while (0) 227 228 229 /* XXXX these must all be callee-save regs! */ 230 register double f14 __asm__ ("fr14"); 231 register double f15 __asm__ ("fr15"); 232 register double f16 __asm__ ("fr16"); 233 register double f17 __asm__ ("fr17"); 234 register HWord_t r14 __asm__ ("r14"); 235 register HWord_t r15 __asm__ ("r15"); 236 register HWord_t r16 __asm__ ("r16"); 237 register HWord_t r17 __asm__ ("r17"); 238 239 #include "config.h" // HAS_ALTIVEC 240 #if defined (HAS_ALTIVEC) 241 # include <altivec.h> 242 #endif 243 #include <assert.h> 244 #include <ctype.h> // isspace 245 #include <stdio.h> 246 #include <stdlib.h> 247 #include <string.h> 248 #include <unistd.h> // getopt 249 250 251 #ifndef __powerpc64__ 252 #define ASSEMBLY_FUNC(__fname, __insn) \ 253 asm(".section \".text\"\n" \ 254 "\t.align 2\n" \ 255 "\t.type "__fname",@function\n" \ 256 __fname":\n" \ 257 "\t"__insn"\n" \ 258 "\tblr\n" \ 259 "\t.previous\n" \ 260 ) 261 #else 262 #define ASSEMBLY_FUNC(__fname, __insn) \ 263 asm(".section \".text\"\n" \ 264 "\t.align 2\n" \ 265 "\t.global "__fname"\n" \ 266 "\t.section \".opd\",\"aw\"\n" \ 267 "\t.align 3\n" \ 268 ""__fname":\n" \ 269 "\t.quad ."__fname",.TOC.@tocbase,0\n" \ 270 "\t.previous\n" \ 271 "\t.type ."__fname",@function\n" \ 272 "\t.global ."__fname"\n" \ 273 "."__fname":\n" \ 274 "\t"__insn"\n" \ 275 "\tblr\n" \ 276 ) 277 #endif // #ifndef __powerpc64__ 278 279 280 /* Return a pointer to a 1-page area where is is safe to both write 281 and execute instructions. Area is filled with 'trap' insns. */ 282 static 283 uint32_t* get_rwx_area ( void ) 284 { 285 int i; 286 static uint32_t* p = NULL; 287 if (p == NULL) { 288 p = mmap(NULL, 4096, PROT_READ|PROT_WRITE|PROT_EXEC, 289 MAP_PRIVATE|MAP_ANONYMOUS, -1, 0); 290 assert(p != MAP_FAILED); 291 } 292 293 for (i = 0; i < 4096/sizeof(uint32_t); i++) 294 p[i] = 0x7fe00008; /* trap */ 295 296 return p; 297 } 298 299 300 /* -------------- BEGIN #include "test-ppc.h" -------------- */ 301 /* 302 * test-ppc.h: 303 * PPC tests for qemu-PPC CPU emulation checks - definitions 304 * 305 * Copyright (c) 2005 Jocelyn Mayer 306 * 307 * This program is free software; you can redistribute it and/or 308 * modify it under the terms of the GNU General Public License V2 309 * as published by the Free Software Foundation 310 * 311 * This program is distributed in the hope that it will be useful, 312 * but WITHOUT ANY WARRANTY; without even the implied warranty of 313 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 314 * GNU General Public License for more details. 315 * 316 * You should have received a copy of the GNU General Public License 317 * along with this program; if not, write to the Free Software 318 * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA 319 */ 320 321 #if !defined (__TEST_PPC_H__) 322 #define __TEST_PPC_H__ 323 324 #include <stdint.h> 325 326 typedef void (*test_func_t) (void); 327 typedef struct test_t test_t; 328 typedef struct test_table_t test_table_t; 329 struct test_t { 330 test_func_t func; 331 const char *name; 332 }; 333 334 struct test_table_t { 335 test_t *tests; 336 const char *name; 337 uint32_t flags; 338 }; 339 340 typedef void (*test_loop_t) (const char *name, test_func_t func, 341 uint32_t flags); 342 343 enum test_flags { 344 /* Nb arguments */ 345 PPC_ONE_ARG = 0x00000001, 346 PPC_TWO_ARGS = 0x00000002, 347 PPC_THREE_ARGS = 0x00000003, 348 PPC_CMP_ARGS = 0x00000004, // family: compare 349 PPC_CMPI_ARGS = 0x00000005, // family: compare 350 PPC_TWO_I16 = 0x00000006, // family: arith/logical 351 PPC_SPECIAL = 0x00000007, // family: logical 352 PPC_LD_ARGS = 0x00000008, // family: ldst 353 PPC_LDX_ARGS = 0x00000009, // family: ldst 354 PPC_ST_ARGS = 0x0000000A, // family: ldst 355 PPC_STX_ARGS = 0x0000000B, // family: ldst 356 PPC_NB_ARGS = 0x0000000F, 357 /* Type */ 358 PPC_ARITH = 0x00000100, 359 PPC_LOGICAL = 0x00000200, 360 PPC_COMPARE = 0x00000300, 361 PPC_CROP = 0x00000400, 362 PPC_LDST = 0x00000500, 363 PPC_TYPE = 0x00000F00, 364 /* Family */ 365 PPC_INTEGER = 0x00010000, 366 PPC_FLOAT = 0x00020000, 367 PPC_405 = 0x00030000, 368 PPC_ALTIVEC = 0x00040000, 369 PPC_FALTIVEC = 0x00050000, 370 PPC_FAMILY = 0x000F0000, 371 /* Flags: these may be combined, so use separate bitfields. */ 372 PPC_CR = 0x01000000, 373 PPC_XER_CA = 0x02000000, 374 }; 375 376 #endif /* !defined (__TEST_PPC_H__) */ 377 378 /* -------------- END #include "test-ppc.h" -------------- */ 379 380 381 382 383 #if defined (DEBUG_ARGS_BUILD) 384 #define AB_DPRINTF(fmt, args...) do { fprintf(stderr, fmt , ##args); } while (0) 385 #else 386 #define AB_DPRINTF(fmt, args...) do { } while (0) 387 #endif 388 389 #if defined (DEBUG_FILTER) 390 #define FDPRINTF(fmt, args...) do { fprintf(stderr, fmt , ##args); } while (0) 391 #else 392 #define FDPRINTF(fmt, args...) do { } while (0) 393 #endif 394 395 396 /* Produce the 64-bit pattern corresponding to the supplied double. */ 397 static uint64_t double_to_bits ( double d ) 398 { 399 union { uint64_t i; double d; } u; 400 assert(8 == sizeof(uint64_t)); 401 assert(8 == sizeof(double)); 402 assert(8 == sizeof(u)); 403 u.d = d; 404 return u.i; 405 } 406 407 #if 0 408 static float bits_to_float ( uint32_t i ) 409 { 410 union { uint32_t i; float f; } u; 411 assert(4 == sizeof(uint32_t)); 412 assert(4 == sizeof(float)); 413 assert(4 == sizeof(u)); 414 u.i = i; 415 return u.f; 416 } 417 #endif 418 419 420 #if defined (HAS_ALTIVEC) 421 static void AB_DPRINTF_VEC32x4 ( vector unsigned int v ) 422 { 423 #if defined (DEBUG_ARGS_BUILD) 424 int i; 425 unsigned int* p_int = (unsigned int*)&v; 426 AB_DPRINTF("val"); 427 for (i=0; i<4; i++) { 428 AB_DPRINTF(" %08x", p_int[i]); 429 } 430 AB_DPRINTF("\n"); 431 #endif 432 } 433 #endif 434 435 436 #define unused __attribute__ (( unused )) 437 438 439 /* -------------- BEGIN #include "ops-ppc.c" -------------- */ 440 441 /* #include "test-ppc.h" */ 442 443 static void test_add (void) 444 { 445 __asm__ __volatile__ ("add 17, 14, 15"); 446 } 447 448 static void test_addo (void) 449 { 450 __asm__ __volatile__ ("addo 17, 14, 15"); 451 } 452 453 static void test_addc (void) 454 { 455 __asm__ __volatile__ ("addc 17, 14, 15"); 456 } 457 458 static void test_addco (void) 459 { 460 __asm__ __volatile__ ("addco 17, 14, 15"); 461 } 462 463 static void test_divw (void) 464 { 465 __asm__ __volatile__ ("divw 17, 14, 15"); 466 } 467 468 static void test_divwo (void) 469 { 470 __asm__ __volatile__ ("divwo 17, 14, 15"); 471 } 472 473 static void test_divwu (void) 474 { 475 __asm__ __volatile__ ("divwu 17, 14, 15"); 476 } 477 478 static void test_divwuo (void) 479 { 480 __asm__ __volatile__ ("divwuo 17, 14, 15"); 481 } 482 483 static void test_mulhw (void) 484 { 485 __asm__ __volatile__ ("mulhw 17, 14, 15"); 486 } 487 488 static void test_mulhwu (void) 489 { 490 __asm__ __volatile__ ("mulhwu 17, 14, 15"); 491 } 492 493 static void test_mullw (void) 494 { 495 __asm__ __volatile__ ("mullw 17, 14, 15"); 496 } 497 498 static void test_mullwo (void) 499 { 500 __asm__ __volatile__ ("mullwo 17, 14, 15"); 501 } 502 503 static void test_subf (void) 504 { 505 __asm__ __volatile__ ("subf 17, 14, 15"); 506 } 507 508 static void test_subfo (void) 509 { 510 __asm__ __volatile__ ("subfo 17, 14, 15"); 511 } 512 513 static void test_subfc (void) 514 { 515 __asm__ __volatile__ ("subfc 17, 14, 15"); 516 } 517 518 static void test_subfco (void) 519 { 520 __asm__ __volatile__ ("subfco 17, 14, 15"); 521 } 522 523 #ifdef __powerpc64__ 524 static void test_mulld (void) 525 { 526 __asm__ __volatile__ ("mulld 17, 14, 15"); 527 } 528 529 static void test_mulhd (void) 530 { 531 __asm__ __volatile__ ("mulhd 17, 14, 15"); 532 } 533 534 static void test_mulhdu (void) 535 { 536 __asm__ __volatile__ ("mulhdu 17, 14, 15"); 537 } 538 539 static void test_divd (void) 540 { 541 __asm__ __volatile__ ("divd 17, 14, 15"); 542 } 543 544 static void test_divdu (void) 545 { 546 __asm__ __volatile__ ("divdu 17, 14, 15"); 547 } 548 #endif // #ifdef __powerpc64__ 549 550 static test_t tests_ia_ops_two[] = { 551 { &test_add , " add", }, 552 { &test_addo , " addo", }, 553 { &test_addc , " addc", }, 554 { &test_addco , " addco", }, 555 { &test_divw , " divw", }, 556 { &test_divwo , " divwo", }, 557 { &test_divwu , " divwu", }, 558 { &test_divwuo , " divwuo", }, 559 { &test_mulhw , " mulhw", }, 560 { &test_mulhwu , " mulhwu", }, 561 { &test_mullw , " mullw", }, 562 { &test_mullwo , " mullwo", }, 563 { &test_subf , " subf", }, 564 { &test_subfo , " subfo", }, 565 { &test_subfc , " subfc", }, 566 { &test_subfco , " subfco", }, 567 #ifdef __powerpc64__ 568 { &test_mulhd , " mulhd", }, 569 { &test_mulhdu , " mulhdu", }, 570 { &test_mulld , " mulld", }, 571 { &test_divd , " divd", }, 572 { &test_divdu , " divdu", }, 573 #endif // #ifdef __powerpc64__ 574 { NULL, NULL, }, 575 }; 576 577 static void test_add_ (void) 578 { 579 __asm__ __volatile__ ("add. 17, 14, 15"); 580 } 581 582 static void test_addo_ (void) 583 { 584 __asm__ __volatile__ ("addo. 17, 14, 15"); 585 } 586 587 static void test_addc_ (void) 588 { 589 __asm__ __volatile__ ("addc. 17, 14, 15"); 590 } 591 592 static void test_addco_ (void) 593 { 594 __asm__ __volatile__ ("addco. 17, 14, 15"); 595 } 596 597 static void test_divw_ (void) 598 { 599 __asm__ __volatile__ ("divw. 17, 14, 15"); 600 } 601 602 static void test_divwo_ (void) 603 { 604 __asm__ __volatile__ ("divwo. 17, 14, 15"); 605 } 606 607 static void test_divwu_ (void) 608 { 609 __asm__ __volatile__ ("divwu. 17, 14, 15"); 610 } 611 612 static void test_divwuo_ (void) 613 { 614 __asm__ __volatile__ ("divwuo. 17, 14, 15"); 615 } 616 617 static void test_mulhw_ (void) 618 { 619 __asm__ __volatile__ ("mulhw. 17, 14, 15"); 620 } 621 622 static void test_mulhwu_ (void) 623 { 624 __asm__ __volatile__ ("mulhwu. 17, 14, 15"); 625 } 626 627 static void test_mullw_ (void) 628 { 629 __asm__ __volatile__ ("mullw. 17, 14, 15"); 630 } 631 632 static void test_mullwo_ (void) 633 { 634 __asm__ __volatile__ ("mullwo. 17, 14, 15"); 635 } 636 637 static void test_subf_ (void) 638 { 639 __asm__ __volatile__ ("subf. 17, 14, 15"); 640 } 641 642 static void test_subfo_ (void) 643 { 644 __asm__ __volatile__ ("subfo. 17, 14, 15"); 645 } 646 647 static void test_subfc_ (void) 648 { 649 __asm__ __volatile__ ("subfc. 17, 14, 15"); 650 } 651 652 static void test_subfco_ (void) 653 { 654 __asm__ __volatile__ ("subfco. 17, 14, 15"); 655 } 656 657 #ifdef __powerpc64__ 658 static void test_mulhd_ (void) 659 { 660 __asm__ __volatile__ ("mulhd. 17, 14, 15"); 661 } 662 663 static void test_mulhdu_ (void) 664 { 665 __asm__ __volatile__ ("mulhdu. 17, 14, 15"); 666 } 667 668 static void test_mulld_ (void) 669 { 670 __asm__ __volatile__ ("mulld. 17, 14, 15"); 671 } 672 673 static void test_divd_ (void) 674 { 675 __asm__ __volatile__ ("divd. 17, 14, 15"); 676 } 677 678 static void test_divdu_ (void) 679 { 680 __asm__ __volatile__ ("divdu. 17, 14, 15"); 681 } 682 #endif // #ifdef __powerpc64__ 683 684 static test_t tests_iar_ops_two[] = { 685 { &test_add_ , " add.", }, 686 { &test_addo_ , " addo.", }, 687 { &test_addc_ , " addc.", }, 688 { &test_addco_ , " addco.", }, 689 { &test_divw_ , " divw.", }, 690 { &test_divwo_ , " divwo.", }, 691 { &test_divwu_ , " divwu.", }, 692 { &test_divwuo_ , " divwuo.", }, 693 { &test_mulhw_ , " mulhw.", }, 694 { &test_mulhwu_ , " mulhwu.", }, 695 { &test_mullw_ , " mullw.", }, 696 { &test_mullwo_ , " mullwo.", }, 697 { &test_subf_ , " subf.", }, 698 { &test_subfo_ , " subfo.", }, 699 { &test_subfc_ , " subfc.", }, 700 { &test_subfco_ , " subfco.", }, 701 #ifdef __powerpc64__ 702 { &test_mulhd_ , " mulhd.", }, 703 { &test_mulhdu_ , " mulhdu.", }, 704 { &test_mulld_ , " mulld.", }, 705 { &test_divd_ , " divd.", }, 706 { &test_divdu_ , " divdu.", }, 707 #endif // #ifdef __powerpc64__ 708 { NULL, NULL, }, 709 }; 710 711 static void test_adde (void) 712 { 713 __asm__ __volatile__ ("adde 17, 14, 15"); 714 } 715 716 static void test_addeo (void) 717 { 718 __asm__ __volatile__ ("addeo 17, 14, 15"); 719 } 720 721 static void test_subfe (void) 722 { 723 __asm__ __volatile__ ("subfe 17, 14, 15"); 724 } 725 726 static void test_subfeo (void) 727 { 728 __asm__ __volatile__ ("subfeo 17, 14, 15"); 729 } 730 731 static test_t tests_iac_ops_two[] = { 732 { &test_adde , " adde", }, 733 { &test_addeo , " addeo", }, 734 { &test_subfe , " subfe", }, 735 { &test_subfeo , " subfeo", }, 736 { NULL, NULL, }, 737 }; 738 739 static void test_adde_ (void) 740 { 741 __asm__ __volatile__ ("adde. 17, 14, 15"); 742 } 743 744 static void test_addeo_ (void) 745 { 746 __asm__ __volatile__ ("addeo. 17, 14, 15"); 747 } 748 749 static void test_subfe_ (void) 750 { 751 __asm__ __volatile__ ("subfe. 17, 14, 15"); 752 } 753 754 static void test_subfeo_ (void) 755 { 756 __asm__ __volatile__ ("subfeo. 17, 14, 15"); 757 } 758 759 static test_t tests_iacr_ops_two[] = { 760 { &test_adde_ , " adde.", }, 761 { &test_addeo_ , " addeo.", }, 762 { &test_subfe_ , " subfe.", }, 763 { &test_subfeo_ , " subfeo.", }, 764 { NULL, NULL, }, 765 }; 766 767 static void test_and (void) 768 { 769 __asm__ __volatile__ ("and 17, 14, 15"); 770 } 771 772 static void test_andc (void) 773 { 774 __asm__ __volatile__ ("andc 17, 14, 15"); 775 } 776 777 static void test_eqv (void) 778 { 779 __asm__ __volatile__ ("eqv 17, 14, 15"); 780 } 781 782 static void test_nand (void) 783 { 784 __asm__ __volatile__ ("nand 17, 14, 15"); 785 } 786 787 static void test_nor (void) 788 { 789 __asm__ __volatile__ ("nor 17, 14, 15"); 790 } 791 792 static void test_or (void) 793 { 794 __asm__ __volatile__ ("or 17, 14, 15"); 795 } 796 797 static void test_orc (void) 798 { 799 __asm__ __volatile__ ("orc 17, 14, 15"); 800 } 801 802 static void test_xor (void) 803 { 804 __asm__ __volatile__ ("xor 17, 14, 15"); 805 } 806 807 static void test_slw (void) 808 { 809 __asm__ __volatile__ ("slw 17, 14, 15"); 810 } 811 812 static void test_sraw (void) 813 { 814 __asm__ __volatile__ ("sraw 17, 14, 15"); 815 } 816 817 static void test_srw (void) 818 { 819 __asm__ __volatile__ ("srw 17, 14, 15"); 820 } 821 822 #ifdef __powerpc64__ 823 static void test_sld (void) 824 { 825 __asm__ __volatile__ ("sld 17, 14, 15"); 826 } 827 828 static void test_srad (void) 829 { 830 __asm__ __volatile__ ("srad 17, 14, 15"); 831 } 832 833 static void test_srd (void) 834 { 835 __asm__ __volatile__ ("srd 17, 14, 15"); 836 } 837 #endif // #ifdef __powerpc64__ 838 839 static test_t tests_il_ops_two[] = { 840 { &test_and , " and", }, 841 { &test_andc , " andc", }, 842 { &test_eqv , " eqv", }, 843 { &test_nand , " nand", }, 844 { &test_nor , " nor", }, 845 { &test_or , " or", }, 846 { &test_orc , " orc", }, 847 { &test_xor , " xor", }, 848 { &test_slw , " slw", }, 849 { &test_sraw , " sraw", }, 850 { &test_srw , " srw", }, 851 #ifdef __powerpc64__ 852 { &test_sld , " sld", }, 853 { &test_srad , " srad", }, 854 { &test_srd , " srd", }, 855 #endif // #ifdef __powerpc64__ 856 { NULL, NULL, }, 857 }; 858 859 static void test_and_ (void) 860 { 861 __asm__ __volatile__ ("and. 17, 14, 15"); 862 } 863 864 static void test_andc_ (void) 865 { 866 __asm__ __volatile__ ("andc. 17, 14, 15"); 867 } 868 869 static void test_eqv_ (void) 870 { 871 __asm__ __volatile__ ("eqv. 17, 14, 15"); 872 } 873 874 static void test_nand_ (void) 875 { 876 __asm__ __volatile__ ("nand. 17, 14, 15"); 877 } 878 879 static void test_nor_ (void) 880 { 881 __asm__ __volatile__ ("nor. 17, 14, 15"); 882 } 883 884 static void test_or_ (void) 885 { 886 __asm__ __volatile__ ("or. 17, 14, 15"); 887 } 888 889 static void test_orc_ (void) 890 { 891 __asm__ __volatile__ ("orc. 17, 14, 15"); 892 } 893 894 static void test_xor_ (void) 895 { 896 __asm__ __volatile__ ("xor. 17, 14, 15"); 897 } 898 899 static void test_slw_ (void) 900 { 901 __asm__ __volatile__ ("slw. 17, 14, 15"); 902 } 903 904 static void test_sraw_ (void) 905 { 906 __asm__ __volatile__ ("sraw. 17, 14, 15"); 907 } 908 909 static void test_srw_ (void) 910 { 911 __asm__ __volatile__ ("srw. 17, 14, 15"); 912 } 913 914 #ifdef __powerpc64__ 915 static void test_sld_ (void) 916 { 917 __asm__ __volatile__ ("sld. 17, 14, 15"); 918 } 919 920 static void test_srad_ (void) 921 { 922 __asm__ __volatile__ ("srad. 17, 14, 15"); 923 } 924 925 static void test_srd_ (void) 926 { 927 __asm__ __volatile__ ("srd. 17, 14, 15"); 928 } 929 #endif // #ifdef __powerpc64__ 930 931 static test_t tests_ilr_ops_two[] = { 932 { &test_and_ , " and.", }, 933 { &test_andc_ , " andc.", }, 934 { &test_eqv_ , " eqv.", }, 935 { &test_nand_ , " nand.", }, 936 { &test_nor_ , " nor.", }, 937 { &test_or_ , " or.", }, 938 { &test_orc_ , " orc.", }, 939 { &test_xor_ , " xor.", }, 940 { &test_slw_ , " slw.", }, 941 { &test_sraw_ , " sraw.", }, 942 { &test_srw_ , " srw.", }, 943 #ifdef __powerpc64__ 944 { &test_sld_ , " sld.", }, 945 { &test_srad_ , " srad.", }, 946 { &test_srd_ , " srd.", }, 947 #endif // #ifdef __powerpc64__ 948 { NULL, NULL, }, 949 }; 950 951 static void test_cmpw (void) 952 { 953 __asm__ __volatile__ ("cmpw 2, 14, 15"); 954 } 955 956 static void test_cmplw (void) 957 { 958 __asm__ __volatile__ ("cmplw 2, 14, 15"); 959 } 960 961 #ifdef __powerpc64__ 962 static void test_cmpd (void) 963 { 964 __asm__ __volatile__ ("cmpd 2, 14, 15"); 965 } 966 967 static void test_cmpld (void) 968 { 969 __asm__ __volatile__ ("cmpld 2, 14, 15"); 970 } 971 #endif // #ifdef __powerpc64__ 972 973 static test_t tests_icr_ops_two[] = { 974 { &test_cmpw , " cmpw", }, 975 { &test_cmplw , " cmplw", }, 976 #ifdef __powerpc64__ 977 { &test_cmpd , " cmpd", }, 978 { &test_cmpld , " cmpld", }, 979 #endif // #ifdef __powerpc64__ 980 { NULL, NULL, }, 981 }; 982 983 extern void test_cmpwi (void); 984 ASSEMBLY_FUNC("test_cmpwi", "cmpwi 2, 14, 0"); 985 986 extern void test_cmplwi (void); 987 ASSEMBLY_FUNC("test_cmplwi", "cmplwi 2, 14, 0"); 988 989 #ifdef __powerpc64__ 990 extern void test_cmpdi (void); 991 ASSEMBLY_FUNC("test_cmpdi", "cmpdi 2, 14, 0"); 992 993 extern void test_cmpldi (void); 994 ASSEMBLY_FUNC("test_cmpldi", "cmpldi 2, 14, 0"); 995 #endif // #ifdef __powerpc64__ 996 997 static test_t tests_icr_ops_two_i16[] = { 998 { &test_cmpwi , " cmpwi", }, 999 { &test_cmplwi , " cmplwi", }, 1000 #ifdef __powerpc64__ 1001 { &test_cmpdi , " cmpdi", }, 1002 { &test_cmpldi , " cmpldi", }, 1003 #endif // #ifdef __powerpc64__ 1004 { NULL, NULL, }, 1005 }; 1006 1007 extern void test_addi (void); 1008 ASSEMBLY_FUNC("test_addi", "addi 17, 14, 0"); 1009 1010 extern void test_addic (void); 1011 ASSEMBLY_FUNC("test_addic", "addic 17, 14, 0"); 1012 1013 extern void test_addis (void); 1014 ASSEMBLY_FUNC("test_addis", "addis 17, 14, 0"); 1015 1016 extern void test_mulli (void); 1017 ASSEMBLY_FUNC("test_mulli", "mulli 17, 14, 0"); 1018 1019 extern void test_subfic (void); 1020 ASSEMBLY_FUNC("test_subfic", "subfic 17, 14, 0"); 1021 1022 static test_t tests_ia_ops_two_i16[] = { 1023 { &test_addi , " addi", }, 1024 { &test_addic , " addic", }, 1025 { &test_addis , " addis", }, 1026 { &test_mulli , " mulli", }, 1027 { &test_subfic , " subfic", }, 1028 { NULL, NULL, }, 1029 }; 1030 1031 extern void test_addic_ (void); 1032 ASSEMBLY_FUNC("test_addic_", "addic. 17, 14, 0"); 1033 1034 static test_t tests_iar_ops_two_i16[] = { 1035 { &test_addic_ , " addic.", }, 1036 { NULL, NULL, }, 1037 }; 1038 1039 extern void test_ori (void); 1040 ASSEMBLY_FUNC("test_ori", "ori 17, 14, 0"); 1041 1042 extern void test_oris (void); 1043 ASSEMBLY_FUNC("test_oris", "oris 17, 14, 0"); 1044 1045 extern void test_xori (void); 1046 ASSEMBLY_FUNC("test_xori", "xori 17, 14, 0"); 1047 1048 extern void test_xoris (void); 1049 ASSEMBLY_FUNC("test_xoris", "xoris 17, 14, 0"); 1050 1051 static test_t tests_il_ops_two_i16[] = { 1052 { &test_ori , " ori", }, 1053 { &test_oris , " oris", }, 1054 { &test_xori , " xori", }, 1055 { &test_xoris , " xoris", }, 1056 { NULL, NULL, }, 1057 }; 1058 1059 extern void test_andi_ (void); 1060 ASSEMBLY_FUNC("test_andi_", "andi. 17, 14, 0"); 1061 1062 extern void test_andis_ (void); 1063 ASSEMBLY_FUNC("test_andis_", "andis. 17, 14, 0"); 1064 1065 static test_t tests_ilr_ops_two_i16[] = { 1066 { &test_andi_ , " andi.", }, 1067 { &test_andis_ , " andis.", }, 1068 { NULL, NULL, }, 1069 }; 1070 1071 static void test_crand (void) 1072 { 1073 __asm__ __volatile__ ("crand 17, 14, 15"); 1074 } 1075 1076 static void test_crandc (void) 1077 { 1078 __asm__ __volatile__ ("crandc 17, 14, 15"); 1079 } 1080 1081 static void test_creqv (void) 1082 { 1083 __asm__ __volatile__ ("creqv 17, 14, 15"); 1084 } 1085 1086 static void test_crnand (void) 1087 { 1088 __asm__ __volatile__ ("crnand 17, 14, 15"); 1089 } 1090 1091 static void test_crnor (void) 1092 { 1093 __asm__ __volatile__ ("crnor 17, 14, 15"); 1094 } 1095 1096 static void test_cror (void) 1097 { 1098 __asm__ __volatile__ ("cror 17, 14, 15"); 1099 } 1100 1101 static void test_crorc (void) 1102 { 1103 __asm__ __volatile__ ("crorc 17, 14, 15"); 1104 } 1105 1106 static void test_crxor (void) 1107 { 1108 __asm__ __volatile__ ("crxor 17, 14, 15"); 1109 } 1110 1111 static test_t tests_crl_ops_two[] = { 1112 { &test_crand , " crand", }, 1113 { &test_crandc , " crandc", }, 1114 { &test_creqv , " creqv", }, 1115 { &test_crnand , " crnand", }, 1116 { &test_crnor , " crnor", }, 1117 { &test_cror , " cror", }, 1118 { &test_crorc , " crorc", }, 1119 { &test_crxor , " crxor", }, 1120 { NULL, NULL, }, 1121 }; 1122 1123 static void test_addme (void) 1124 { 1125 __asm__ __volatile__ ("addme 17, 14"); 1126 } 1127 1128 static void test_addmeo (void) 1129 { 1130 __asm__ __volatile__ ("addmeo 17, 14"); 1131 } 1132 1133 static void test_addze (void) 1134 { 1135 __asm__ __volatile__ ("addze 17, 14"); 1136 } 1137 1138 static void test_addzeo (void) 1139 { 1140 __asm__ __volatile__ ("addzeo 17, 14"); 1141 } 1142 1143 static void test_subfme (void) 1144 { 1145 __asm__ __volatile__ ("subfme 17, 14"); 1146 } 1147 1148 static void test_subfmeo (void) 1149 { 1150 __asm__ __volatile__ ("subfmeo 17, 14"); 1151 } 1152 1153 static void test_subfze (void) 1154 { 1155 __asm__ __volatile__ ("subfze 17, 14"); 1156 } 1157 1158 static void test_subfzeo (void) 1159 { 1160 __asm__ __volatile__ ("subfzeo 17, 14"); 1161 } 1162 1163 static test_t tests_iac_ops_one[] = { 1164 { &test_addme , " addme", }, 1165 { &test_addmeo , " addmeo", }, 1166 { &test_addze , " addze", }, 1167 { &test_addzeo , " addzeo", }, 1168 { &test_subfme , " subfme", }, 1169 { &test_subfmeo , " subfmeo", }, 1170 { &test_subfze , " subfze", }, 1171 { &test_subfzeo , " subfzeo", }, 1172 { NULL, NULL, }, 1173 }; 1174 1175 static void test_addme_ (void) 1176 { 1177 __asm__ __volatile__ ("addme. 17, 14"); 1178 } 1179 1180 static void test_addmeo_ (void) 1181 { 1182 __asm__ __volatile__ ("addmeo. 17, 14"); 1183 } 1184 1185 static void test_addze_ (void) 1186 { 1187 __asm__ __volatile__ ("addze. 17, 14"); 1188 } 1189 1190 static void test_addzeo_ (void) 1191 { 1192 __asm__ __volatile__ ("addzeo. 17, 14"); 1193 } 1194 1195 static void test_subfme_ (void) 1196 { 1197 __asm__ __volatile__ ("subfme. 17, 14"); 1198 } 1199 1200 static void test_subfmeo_ (void) 1201 { 1202 __asm__ __volatile__ ("subfmeo. 17, 14"); 1203 } 1204 1205 static void test_subfze_ (void) 1206 { 1207 __asm__ __volatile__ ("subfze. 17, 14"); 1208 } 1209 1210 static void test_subfzeo_ (void) 1211 { 1212 __asm__ __volatile__ ("subfzeo. 17, 14"); 1213 } 1214 1215 static test_t tests_iacr_ops_one[] = { 1216 { &test_addme_ , " addme.", }, 1217 { &test_addmeo_ , " addmeo.", }, 1218 { &test_addze_ , " addze.", }, 1219 { &test_addzeo_ , " addzeo.", }, 1220 { &test_subfme_ , " subfme.", }, 1221 { &test_subfmeo_ , " subfmeo.", }, 1222 { &test_subfze_ , " subfze.", }, 1223 { &test_subfzeo_ , " subfzeo.", }, 1224 { NULL, NULL, }, 1225 }; 1226 1227 static void test_cntlzw (void) 1228 { 1229 __asm__ __volatile__ ("cntlzw 17, 14"); 1230 } 1231 1232 static void test_extsb (void) 1233 { 1234 __asm__ __volatile__ ("extsb 17, 14"); 1235 } 1236 1237 static void test_extsh (void) 1238 { 1239 __asm__ __volatile__ ("extsh 17, 14"); 1240 } 1241 1242 static void test_neg (void) 1243 { 1244 __asm__ __volatile__ ("neg 17, 14"); 1245 } 1246 1247 static void test_nego (void) 1248 { 1249 __asm__ __volatile__ ("nego 17, 14"); 1250 } 1251 1252 #ifdef __powerpc64__ 1253 static void test_cntlzd (void) 1254 { 1255 __asm__ __volatile__ ("cntlzd 17, 14"); 1256 } 1257 1258 static void test_extsw (void) 1259 { 1260 __asm__ __volatile__ ("extsw 17, 14"); 1261 } 1262 #endif // #ifdef __powerpc64__ 1263 1264 static test_t tests_il_ops_one[] = { 1265 { &test_cntlzw , " cntlzw", }, 1266 { &test_extsb , " extsb", }, 1267 { &test_extsh , " extsh", }, 1268 { &test_neg , " neg", }, 1269 { &test_nego , " nego", }, 1270 #ifdef __powerpc64__ 1271 { &test_cntlzd , " cntlzd", }, 1272 { &test_extsw , " extsw", }, 1273 #endif // #ifdef __powerpc64__ 1274 { NULL, NULL, }, 1275 }; 1276 1277 static void test_cntlzw_ (void) 1278 { 1279 __asm__ __volatile__ ("cntlzw. 17, 14"); 1280 } 1281 1282 static void test_extsb_ (void) 1283 { 1284 __asm__ __volatile__ ("extsb. 17, 14"); 1285 } 1286 1287 static void test_extsh_ (void) 1288 { 1289 __asm__ __volatile__ ("extsh. 17, 14"); 1290 } 1291 1292 static void test_neg_ (void) 1293 { 1294 __asm__ __volatile__ ("neg. 17, 14"); 1295 } 1296 1297 static void test_nego_ (void) 1298 { 1299 __asm__ __volatile__ ("nego. 17, 14"); 1300 } 1301 1302 #ifdef __powerpc64__ 1303 static void test_cntlzd_ (void) 1304 { 1305 __asm__ __volatile__ ("cntlzd. 17, 14"); 1306 } 1307 1308 static void test_extsw_ (void) 1309 { 1310 __asm__ __volatile__ ("extsw. 17, 14"); 1311 } 1312 #endif // #ifdef __powerpc64__ 1313 1314 static test_t tests_ilr_ops_one[] = { 1315 { &test_cntlzw_ , " cntlzw.", }, 1316 { &test_extsb_ , " extsb.", }, 1317 { &test_extsh_ , " extsh.", }, 1318 { &test_neg_ , " neg.", }, 1319 { &test_nego_ , " nego.", }, 1320 #ifdef __powerpc64__ 1321 { &test_cntlzd_ , " cntlzd.", }, 1322 { &test_extsw_ , " extsw.", }, 1323 #endif // #ifdef __powerpc64__ 1324 { NULL, NULL, }, 1325 }; 1326 1327 extern void test_rlwimi (void); 1328 ASSEMBLY_FUNC("test_rlwimi", "rlwimi 17, 14, 0, 0, 0"); 1329 1330 extern void test_rlwinm (void); 1331 ASSEMBLY_FUNC("test_rlwinm", "rlwinm 17, 14, 0, 0, 0"); 1332 1333 extern void test_rlwnm (void); 1334 ASSEMBLY_FUNC("test_rlwnm", "rlwnm 17, 14, 15, 0, 0"); 1335 1336 extern void test_srawi (void); 1337 ASSEMBLY_FUNC("test_srawi", "srawi 17, 14, 0"); 1338 1339 static void test_mfcr (void) 1340 { 1341 __asm__ __volatile__ ("mfcr 17"); 1342 } 1343 1344 static void test_mfspr (void) 1345 { 1346 __asm__ __volatile__ ("mfspr 17, 1"); 1347 } 1348 1349 static void test_mtspr (void) 1350 { 1351 __asm__ __volatile__ ("mtspr 1, 14"); 1352 } 1353 1354 #ifdef __powerpc64__ 1355 extern void test_rldcl (void); 1356 ASSEMBLY_FUNC("test_rldcl", "rldcl 17, 14, 15, 0"); 1357 1358 extern void test_rldcr (void); 1359 ASSEMBLY_FUNC("test_rldcr", "rldcr 17, 14, 15, 0"); 1360 1361 extern void test_rldic (void); 1362 ASSEMBLY_FUNC("test_rldic", "rldic 17, 14, 0, 0"); 1363 1364 extern void test_rldicl (void); 1365 ASSEMBLY_FUNC("test_rldicl", "rldicl 17, 14, 0, 0"); 1366 1367 extern void test_rldicr (void); 1368 ASSEMBLY_FUNC("test_rldicr", "rldicr 17, 14, 0, 0"); 1369 1370 extern void test_rldimi (void); 1371 ASSEMBLY_FUNC("test_rldimi", "rldimi 17, 14, 0, 0"); 1372 1373 extern void test_sradi (void); 1374 ASSEMBLY_FUNC("test_sradi", "sradi 17, 14, 0"); 1375 #endif // #ifdef __powerpc64__ 1376 1377 static test_t tests_il_ops_spe[] = { 1378 { &test_rlwimi , " rlwimi", }, 1379 { &test_rlwinm , " rlwinm", }, 1380 { &test_rlwnm , " rlwnm", }, 1381 { &test_srawi , " srawi", }, 1382 { &test_mfcr , " mfcr", }, 1383 { &test_mfspr , " mfspr", }, 1384 { &test_mtspr , " mtspr", }, 1385 #ifdef __powerpc64__ 1386 { &test_rldcl , " rldcl", }, 1387 { &test_rldcr , " rldcr", }, 1388 { &test_rldic , " rldic", }, 1389 { &test_rldicl , " rldicl", }, 1390 { &test_rldicr , " rldicr", }, 1391 { &test_rldimi , " rldimi", }, 1392 { &test_sradi , " sradi", }, 1393 #endif // #ifdef __powerpc64__ 1394 { NULL, NULL, }, 1395 }; 1396 1397 extern void test_rlwimi_ (void); 1398 ASSEMBLY_FUNC("test_rlwimi_", "rlwimi. 17, 14, 0, 0, 0"); 1399 1400 extern void test_rlwinm_ (void); 1401 ASSEMBLY_FUNC("test_rlwinm_", "rlwinm. 17, 14, 0, 0, 0"); 1402 1403 extern void test_rlwnm_ (void); 1404 ASSEMBLY_FUNC("test_rlwnm_", "rlwnm. 17, 14, 15, 0, 0"); 1405 1406 extern void test_srawi_ (void); 1407 ASSEMBLY_FUNC("test_srawi_", "srawi. 17, 14, 0"); 1408 1409 extern void test_mcrf (void); 1410 ASSEMBLY_FUNC("test_mcrf", "mcrf 0, 0"); 1411 1412 extern void test_mcrxr (void); 1413 ASSEMBLY_FUNC("test_mcrxr", "mcrxr 0"); 1414 1415 extern void test_mtcrf (void); 1416 ASSEMBLY_FUNC("test_mtcrf", "mtcrf 0, 14"); 1417 1418 #ifdef __powerpc64__ 1419 extern void test_rldcl_ (void); 1420 ASSEMBLY_FUNC("test_rldcl_", "rldcl. 17, 14, 15, 0"); 1421 1422 extern void test_rldcr_ (void); 1423 ASSEMBLY_FUNC("test_rldcr_", "rldcr. 17, 14, 15, 0"); 1424 1425 extern void test_rldic_ (void); 1426 ASSEMBLY_FUNC("test_rldic_", "rldic. 17, 14, 0, 0"); 1427 1428 extern void test_rldicl_ (void); 1429 ASSEMBLY_FUNC("test_rldicl_", "rldicl. 17, 14, 0, 0"); 1430 1431 extern void test_rldicr_ (void); 1432 ASSEMBLY_FUNC("test_rldicr_", "rldicr. 17, 14, 0, 0"); 1433 1434 extern void test_rldimi_ (void); 1435 ASSEMBLY_FUNC("test_rldimi_", "rldimi. 17, 14, 0, 0"); 1436 1437 extern void test_sradi_ (void); 1438 ASSEMBLY_FUNC("test_sradi_", "sradi. 17, 14, 0"); 1439 #endif // #ifdef __powerpc64__ 1440 1441 static test_t tests_ilr_ops_spe[] = { 1442 { &test_rlwimi_ , " rlwimi.", }, 1443 { &test_rlwinm_ , " rlwinm.", }, 1444 { &test_rlwnm_ , " rlwnm.", }, 1445 { &test_srawi_ , " srawi.", }, 1446 { &test_mcrf , " mcrf", }, 1447 { &test_mcrxr , " mcrxr", }, 1448 { &test_mtcrf , " mtcrf", }, 1449 #ifdef __powerpc64__ 1450 { &test_rldcl_ , " rldcl.", }, 1451 { &test_rldcr_ , " rldcr.", }, 1452 { &test_rldic_ , " rldic.", }, 1453 { &test_rldicl_ , " rldicl.", }, 1454 { &test_rldicr_ , " rldicr.", }, 1455 { &test_rldimi_ , " rldimi.", }, 1456 { &test_sradi_ , " sradi.", }, 1457 #endif // #ifdef __powerpc64__ 1458 { NULL, NULL, }, 1459 }; 1460 1461 extern void test_lbz (void); 1462 ASSEMBLY_FUNC("test_lbz", "lbz 17,0(14)"); 1463 1464 extern void test_lbzu (void); 1465 ASSEMBLY_FUNC("test_lbzu", "lbzu 17,0(14)"); 1466 1467 extern void test_lha (void); 1468 ASSEMBLY_FUNC("test_lha", "lha 17,0(14)"); 1469 1470 extern void test_lhau (void); 1471 ASSEMBLY_FUNC("test_lhau", "lhau 17,0(14)"); 1472 1473 extern void test_lhz (void); 1474 ASSEMBLY_FUNC("test_lhz", "lhz 17,0(14)"); 1475 1476 extern void test_lhzu (void); 1477 ASSEMBLY_FUNC("test_lhzu", "lhzu 17,0(14)"); 1478 1479 extern void test_lwz (void); 1480 ASSEMBLY_FUNC("test_lwz", "lwz 17,0(14)"); 1481 1482 extern void test_lwzu (void); 1483 ASSEMBLY_FUNC("test_lwzu", "lwzu 17,0(14)"); 1484 1485 #ifdef __powerpc64__ 1486 extern void test_ld (void); 1487 ASSEMBLY_FUNC("test_ld", "ld 17,0(14)"); 1488 1489 extern void test_ldu (void); 1490 ASSEMBLY_FUNC("test_ldu", "ldu 17,0(14)"); 1491 1492 extern void test_lwa (void); 1493 ASSEMBLY_FUNC("test_lwa", "lwa 17,0(14)"); 1494 #endif // #ifdef __powerpc64__ 1495 1496 static test_t tests_ild_ops_two_i16[] = { 1497 { &test_lbz , " lbz", }, 1498 { &test_lbzu , " lbzu", }, 1499 { &test_lha , " lha", }, 1500 { &test_lhau , " lhau", }, 1501 { &test_lhz , " lhz", }, 1502 { &test_lhzu , " lhzu", }, 1503 { &test_lwz , " lwz", }, 1504 { &test_lwzu , " lwzu", }, 1505 #ifdef __powerpc64__ 1506 { &test_ld , " ld", }, 1507 { &test_ldu , " ldu", }, 1508 { &test_lwa , " lwa", }, 1509 #endif // #ifdef __powerpc64__ 1510 { NULL, NULL, }, 1511 }; 1512 1513 static void test_lbzx (void) 1514 { 1515 __asm__ __volatile__ ("lbzx 17,14,15"); 1516 } 1517 1518 static void test_lbzux (void) 1519 { 1520 __asm__ __volatile__ ("lbzux 17,14,15"); 1521 } 1522 1523 static void test_lhax (void) 1524 { 1525 __asm__ __volatile__ ("lhax 17,14,15"); 1526 } 1527 1528 static void test_lhaux (void) 1529 { 1530 __asm__ __volatile__ ("lhaux 17,14,15"); 1531 } 1532 1533 static void test_lhzx (void) 1534 { 1535 __asm__ __volatile__ ("lhzx 17,14,15"); 1536 } 1537 1538 static void test_lhzux (void) 1539 { 1540 __asm__ __volatile__ ("lhzux 17,14,15"); 1541 } 1542 1543 static void test_lwzx (void) 1544 { 1545 __asm__ __volatile__ ("lwzx 17,14,15"); 1546 } 1547 1548 static void test_lwzux (void) 1549 { 1550 __asm__ __volatile__ ("lwzux 17,14,15"); 1551 } 1552 1553 #ifdef __powerpc64__ 1554 static void test_ldx (void) 1555 { 1556 __asm__ __volatile__ ("ldx 17,14,15"); 1557 } 1558 1559 static void test_ldux (void) 1560 { 1561 __asm__ __volatile__ ("ldux 17,14,15"); 1562 } 1563 1564 static void test_lwax (void) 1565 { 1566 __asm__ __volatile__ ("lwax 17,14,15"); 1567 } 1568 1569 static void test_lwaux (void) 1570 { 1571 __asm__ __volatile__ ("lwaux 17,14,15"); 1572 } 1573 #endif // #ifdef __powerpc64__ 1574 1575 static test_t tests_ild_ops_two[] = { 1576 { &test_lbzx , " lbzx", }, 1577 { &test_lbzux , " lbzux", }, 1578 { &test_lhax , " lhax", }, 1579 { &test_lhaux , " lhaux", }, 1580 { &test_lhzx , " lhzx", }, 1581 { &test_lhzux , " lhzux", }, 1582 { &test_lwzx , " lwzx", }, 1583 { &test_lwzux , " lwzux", }, 1584 #ifdef __powerpc64__ 1585 { &test_ldx , " ldx", }, 1586 { &test_ldux , " ldux", }, 1587 { &test_lwax , " lwax", }, 1588 { &test_lwaux , " lwaux", }, 1589 #endif // #ifdef __powerpc64__ 1590 { NULL, NULL, }, 1591 }; 1592 1593 extern void test_stb (void); 1594 ASSEMBLY_FUNC("test_stb", "stb 14,0(15)"); 1595 1596 extern void test_stbu (void); 1597 ASSEMBLY_FUNC("test_stbu", "stbu 14,0(15)"); 1598 1599 extern void test_sth (void); 1600 ASSEMBLY_FUNC("test_sth", "sth 14,0(15)"); 1601 1602 extern void test_sthu (void); 1603 ASSEMBLY_FUNC("test_sthu", "sthu 14,0(15)"); 1604 1605 extern void test_stw (void); 1606 ASSEMBLY_FUNC("test_stw", "stw 14,0(15)"); 1607 1608 extern void test_stwu (void); 1609 ASSEMBLY_FUNC("test_stwu", "stwu 14,0(15)"); 1610 1611 #ifdef __powerpc64__ 1612 extern void test_std (void); 1613 ASSEMBLY_FUNC("test_std", "std 14,0(15)"); 1614 1615 extern void test_stdu (void); 1616 ASSEMBLY_FUNC("test_stdu", "stdu 14,0(15)"); 1617 #endif // #ifdef __powerpc64__ 1618 1619 static test_t tests_ist_ops_three_i16[] = { 1620 { &test_stb , " stb", }, 1621 { &test_stbu , " stbu", }, 1622 { &test_sth , " sth", }, 1623 { &test_sthu , " sthu", }, 1624 { &test_stw , " stw", }, 1625 { &test_stwu , " stwu", }, 1626 #ifdef __powerpc64__ 1627 { &test_std , " std", }, 1628 { &test_stdu , " stdu", }, 1629 #endif // #ifdef __powerpc64__ 1630 { NULL, NULL, }, 1631 }; 1632 1633 static void test_stbx (void) 1634 { 1635 __asm__ __volatile__ ("stbx 14,15,16"); 1636 } 1637 1638 static void test_stbux (void) 1639 { 1640 __asm__ __volatile__ ("stbux 14,15,16"); 1641 } 1642 1643 static void test_sthx (void) 1644 { 1645 __asm__ __volatile__ ("sthx 14,15,16"); 1646 } 1647 1648 static void test_sthux (void) 1649 { 1650 __asm__ __volatile__ ("sthux 14,15,16"); 1651 } 1652 1653 static void test_stwx (void) 1654 { 1655 __asm__ __volatile__ ("stwx 14,15,16"); 1656 } 1657 1658 static void test_stwux (void) 1659 { 1660 __asm__ __volatile__ ("stwux 14,15,16"); 1661 } 1662 1663 #ifdef __powerpc64__ 1664 static void test_stdx (void) 1665 { 1666 __asm__ __volatile__ ("stdx 14,15,16"); 1667 } 1668 1669 static void test_stdux (void) 1670 { 1671 __asm__ __volatile__ ("stdux 14,15,16"); 1672 } 1673 #endif // #ifdef __powerpc64__ 1674 1675 static test_t tests_ist_ops_three[] = { 1676 { &test_stbx , " stbx", }, 1677 { &test_stbux , " stbux", }, 1678 { &test_sthx , " sthx", }, 1679 { &test_sthux , " sthux", }, 1680 { &test_stwx , " stwx", }, 1681 { &test_stwux , " stwux", }, 1682 #ifdef __powerpc64__ 1683 { &test_stdx , " stdx", }, 1684 { &test_stdux , " stdux", }, 1685 #endif // #ifdef __powerpc64__ 1686 { NULL, NULL, }, 1687 }; 1688 1689 #if !defined (NO_FLOAT) 1690 static void test_fsel (void) 1691 { 1692 __asm__ __volatile__ ("fsel 17, 14, 15, 16"); 1693 } 1694 1695 static void test_fmadd (void) 1696 { 1697 __asm__ __volatile__ ("fmadd 17, 14, 15, 16"); 1698 } 1699 1700 static void test_fmadds (void) 1701 { 1702 __asm__ __volatile__ ("fmadds 17, 14, 15, 16"); 1703 } 1704 1705 static void test_fmsub (void) 1706 { 1707 __asm__ __volatile__ ("fmsub 17, 14, 15, 16"); 1708 } 1709 1710 static void test_fmsubs (void) 1711 { 1712 __asm__ __volatile__ ("fmsubs 17, 14, 15, 16"); 1713 } 1714 1715 static void test_fnmadd (void) 1716 { 1717 __asm__ __volatile__ ("fnmadd 17, 14, 15, 16"); 1718 } 1719 1720 static void test_fnmadds (void) 1721 { 1722 __asm__ __volatile__ ("fnmadds 17, 14, 15, 16"); 1723 } 1724 1725 static void test_fnmsub (void) 1726 { 1727 __asm__ __volatile__ ("fnmsub 17, 14, 15, 16"); 1728 } 1729 1730 static void test_fnmsubs (void) 1731 { 1732 __asm__ __volatile__ ("fnmsubs 17, 14, 15, 16"); 1733 } 1734 1735 static test_t tests_fa_ops_three[] = { 1736 { &test_fsel , " fsel", }, 1737 { &test_fmadd , " fmadd", }, 1738 { &test_fmadds , " fmadds", }, 1739 { &test_fmsub , " fmsub", }, 1740 { &test_fmsubs , " fmsubs", }, 1741 { &test_fnmadd , " fnmadd", }, 1742 { &test_fnmadds , " fnmadds", }, 1743 { &test_fnmsub , " fnmsub", }, 1744 { &test_fnmsubs , " fnmsubs", }, 1745 { NULL, NULL, }, 1746 }; 1747 #endif /* !defined (NO_FLOAT) */ 1748 1749 #if !defined (NO_FLOAT) 1750 static void test_fsel_ (void) 1751 { 1752 __asm__ __volatile__ ("fsel. 17, 14, 15, 16"); 1753 } 1754 1755 static void test_fmadd_ (void) 1756 { 1757 __asm__ __volatile__ ("fmadd. 17, 14, 15, 16"); 1758 } 1759 1760 static void test_fmadds_ (void) 1761 { 1762 __asm__ __volatile__ ("fmadds. 17, 14, 15, 16"); 1763 } 1764 1765 static void test_fmsub_ (void) 1766 { 1767 __asm__ __volatile__ ("fmsub. 17, 14, 15, 16"); 1768 } 1769 1770 static void test_fmsubs_ (void) 1771 { 1772 __asm__ __volatile__ ("fmsubs. 17, 14, 15, 16"); 1773 } 1774 1775 static void test_fnmadd_ (void) 1776 { 1777 __asm__ __volatile__ ("fnmadd. 17, 14, 15, 16"); 1778 } 1779 1780 static void test_fnmadds_ (void) 1781 { 1782 __asm__ __volatile__ ("fnmadds. 17, 14, 15, 16"); 1783 } 1784 1785 static void test_fnmsub_ (void) 1786 { 1787 __asm__ __volatile__ ("fnmsub. 17, 14, 15, 16"); 1788 } 1789 1790 static void test_fnmsubs_ (void) 1791 { 1792 __asm__ __volatile__ ("fnmsubs. 17, 14, 15, 16"); 1793 } 1794 1795 static test_t tests_far_ops_three[] = { 1796 { &test_fsel_ , " fsel.", }, 1797 { &test_fmadd_ , " fmadd.", }, 1798 { &test_fmadds_ , " fmadds.", }, 1799 { &test_fmsub_ , " fmsub.", }, 1800 { &test_fmsubs_ , " fmsubs.", }, 1801 { &test_fnmadd_ , " fnmadd.", }, 1802 { &test_fnmadds_ , " fnmadds.", }, 1803 { &test_fnmsub_ , " fnmsub.", }, 1804 { &test_fnmsubs_ , " fnmsubs.", }, 1805 { NULL, NULL, }, 1806 }; 1807 #endif /* !defined (NO_FLOAT) */ 1808 1809 #if !defined (NO_FLOAT) 1810 static void test_fadd (void) 1811 { 1812 __asm__ __volatile__ ("fadd 17, 14, 15"); 1813 } 1814 1815 static void test_fadds (void) 1816 { 1817 __asm__ __volatile__ ("fadds 17, 14, 15"); 1818 } 1819 1820 static void test_fsub (void) 1821 { 1822 __asm__ __volatile__ ("fsub 17, 14, 15"); 1823 } 1824 1825 static void test_fsubs (void) 1826 { 1827 __asm__ __volatile__ ("fsubs 17, 14, 15"); 1828 } 1829 1830 static void test_fmul (void) 1831 { 1832 __asm__ __volatile__ ("fmul 17, 14, 15"); 1833 } 1834 1835 static void test_fmuls (void) 1836 { 1837 __asm__ __volatile__ ("fmuls 17, 14, 15"); 1838 } 1839 1840 static void test_fdiv (void) 1841 { 1842 __asm__ __volatile__ ("fdiv 17, 14, 15"); 1843 } 1844 1845 static void test_fdivs (void) 1846 { 1847 __asm__ __volatile__ ("fdivs 17, 14, 15"); 1848 } 1849 1850 static test_t tests_fa_ops_two[] = { 1851 { &test_fadd , " fadd", }, 1852 { &test_fadds , " fadds", }, 1853 { &test_fsub , " fsub", }, 1854 { &test_fsubs , " fsubs", }, 1855 { &test_fmul , " fmul", }, 1856 { &test_fmuls , " fmuls", }, 1857 { &test_fdiv , " fdiv", }, 1858 { &test_fdivs , " fdivs", }, 1859 { NULL, NULL, }, 1860 }; 1861 #endif /* !defined (NO_FLOAT) */ 1862 1863 #if !defined (NO_FLOAT) 1864 static void test_fadd_ (void) 1865 { 1866 __asm__ __volatile__ ("fadd. 17, 14, 15"); 1867 } 1868 1869 static void test_fadds_ (void) 1870 { 1871 __asm__ __volatile__ ("fadds. 17, 14, 15"); 1872 } 1873 1874 static void test_fsub_ (void) 1875 { 1876 __asm__ __volatile__ ("fsub. 17, 14, 15"); 1877 } 1878 1879 static void test_fsubs_ (void) 1880 { 1881 __asm__ __volatile__ ("fsubs. 17, 14, 15"); 1882 } 1883 1884 static void test_fmul_ (void) 1885 { 1886 __asm__ __volatile__ ("fmul. 17, 14, 15"); 1887 } 1888 1889 static void test_fmuls_ (void) 1890 { 1891 __asm__ __volatile__ ("fmuls. 17, 14, 15"); 1892 } 1893 1894 static void test_fdiv_ (void) 1895 { 1896 __asm__ __volatile__ ("fdiv. 17, 14, 15"); 1897 } 1898 1899 static void test_fdivs_ (void) 1900 { 1901 __asm__ __volatile__ ("fdivs. 17, 14, 15"); 1902 } 1903 1904 static test_t tests_far_ops_two[] = { 1905 { &test_fadd_ , " fadd.", }, 1906 { &test_fadds_ , " fadds.", }, 1907 { &test_fsub_ , " fsub.", }, 1908 { &test_fsubs_ , " fsubs.", }, 1909 { &test_fmul_ , " fmul.", }, 1910 { &test_fmuls_ , " fmuls.", }, 1911 { &test_fdiv_ , " fdiv.", }, 1912 { &test_fdivs_ , " fdivs.", }, 1913 { NULL, NULL, }, 1914 }; 1915 #endif /* !defined (NO_FLOAT) */ 1916 1917 #if !defined (NO_FLOAT) 1918 static void test_fcmpo (void) 1919 { 1920 __asm__ __volatile__ ("fcmpo 2, 14, 15"); 1921 } 1922 1923 static void test_fcmpu (void) 1924 { 1925 __asm__ __volatile__ ("fcmpu 2, 14, 15"); 1926 } 1927 1928 static test_t tests_fcr_ops_two[] = { 1929 { &test_fcmpo , " fcmpo", }, 1930 { &test_fcmpu , " fcmpu", }, 1931 { NULL, NULL, }, 1932 }; 1933 #endif /* !defined (NO_FLOAT) */ 1934 1935 #if !defined (NO_FLOAT) 1936 1937 static void test_fres (void) 1938 { 1939 __asm__ __volatile__ ("fres 17, 14"); 1940 } 1941 1942 static void test_frsqrte (void) 1943 { 1944 __asm__ __volatile__ ("frsqrte 17, 14"); 1945 } 1946 1947 static void test_frsp (void) 1948 { 1949 __asm__ __volatile__ ("frsp 17, 14"); 1950 } 1951 1952 static void test_fctiw (void) 1953 { 1954 __asm__ __volatile__ ("fctiw 17, 14"); 1955 } 1956 1957 static void test_fctiwz (void) 1958 { 1959 __asm__ __volatile__ ("fctiwz 17, 14"); 1960 } 1961 1962 static void test_fmr (void) 1963 { 1964 __asm__ __volatile__ ("fmr 17, 14"); 1965 } 1966 1967 static void test_fneg (void) 1968 { 1969 __asm__ __volatile__ ("fneg 17, 14"); 1970 } 1971 1972 static void test_fabs (void) 1973 { 1974 __asm__ __volatile__ ("fabs 17, 14"); 1975 } 1976 1977 static void test_fnabs (void) 1978 { 1979 __asm__ __volatile__ ("fnabs 17, 14"); 1980 } 1981 1982 static void test_fsqrt (void) 1983 { 1984 __asm__ __volatile__ ("fsqrt 17, 14"); 1985 } 1986 1987 #ifdef __powerpc64__ 1988 static void test_fcfid (void) 1989 { 1990 __asm__ __volatile__ ("fcfid 17, 14"); 1991 } 1992 1993 static void test_fctid (void) 1994 { 1995 __asm__ __volatile__ ("fctid 17, 14"); 1996 } 1997 1998 static void test_fctidz (void) 1999 { 2000 __asm__ __volatile__ ("fctidz 17, 14"); 2001 } 2002 #endif // #ifdef __powerpc64__ 2003 2004 static test_t tests_fa_ops_one[] = { 2005 { &test_fres , " fres", }, 2006 { &test_frsqrte , " frsqrte", }, 2007 { &test_frsp , " frsp", }, 2008 { &test_fctiw , " fctiw", }, 2009 { &test_fctiwz , " fctiwz", }, 2010 { &test_fmr , " fmr", }, 2011 { &test_fneg , " fneg", }, 2012 { &test_fabs , " fabs", }, 2013 { &test_fnabs , " fnabs", }, 2014 { &test_fsqrt , " fsqrt", }, 2015 #ifdef __powerpc64__ 2016 { &test_fcfid , " fcfid", }, 2017 { &test_fctid , " fctid", }, 2018 { &test_fctidz , " fctidz", }, 2019 #endif // #ifdef __powerpc64__ 2020 { NULL, NULL, }, 2021 }; 2022 #endif /* !defined (NO_FLOAT) */ 2023 2024 #if !defined (NO_FLOAT) 2025 2026 static void test_fres_ (void) 2027 { 2028 __asm__ __volatile__ ("fres. 17, 14"); 2029 } 2030 2031 static void test_frsqrte_ (void) 2032 { 2033 __asm__ __volatile__ ("frsqrte. 17, 14"); 2034 } 2035 2036 static void test_frsp_ (void) 2037 { 2038 __asm__ __volatile__ ("frsp. 17, 14"); 2039 } 2040 2041 static void test_fctiw_ (void) 2042 { 2043 __asm__ __volatile__ ("fctiw. 17, 14"); 2044 } 2045 2046 static void test_fctiwz_ (void) 2047 { 2048 __asm__ __volatile__ ("fctiwz. 17, 14"); 2049 } 2050 2051 static void test_fmr_ (void) 2052 { 2053 __asm__ __volatile__ ("fmr. 17, 14"); 2054 } 2055 2056 static void test_fneg_ (void) 2057 { 2058 __asm__ __volatile__ ("fneg. 17, 14"); 2059 } 2060 2061 static void test_fabs_ (void) 2062 { 2063 __asm__ __volatile__ ("fabs. 17, 14"); 2064 } 2065 2066 static void test_fnabs_ (void) 2067 { 2068 __asm__ __volatile__ ("fnabs. 17, 14"); 2069 } 2070 2071 #ifdef __powerpc64__ 2072 static void test_fcfid_ (void) 2073 { 2074 __asm__ __volatile__ ("fcfid. 17, 14"); 2075 } 2076 2077 static void test_fctid_ (void) 2078 { 2079 __asm__ __volatile__ ("fctid. 17, 14"); 2080 } 2081 2082 static void test_fctidz_ (void) 2083 { 2084 __asm__ __volatile__ ("fctidz. 17, 14"); 2085 } 2086 #endif // #ifdef __powerpc64__ 2087 2088 static test_t tests_far_ops_one[] = { 2089 { &test_fres_ , " fres.", }, 2090 { &test_frsqrte_ , " frsqrte.", }, 2091 { &test_frsp_ , " frsp.", }, 2092 { &test_fctiw_ , " fctiw.", }, 2093 { &test_fctiwz_ , " fctiwz.", }, 2094 { &test_fmr_ , " fmr.", }, 2095 { &test_fneg_ , " fneg.", }, 2096 { &test_fabs_ , " fabs.", }, 2097 { &test_fnabs_ , " fnabs.", }, 2098 #ifdef __powerpc64__ 2099 { &test_fcfid_ , " fcfid.", }, 2100 { &test_fctid_ , " fctid.", }, 2101 { &test_fctidz_ , " fctidz.", }, 2102 #endif // #ifdef __powerpc64__ 2103 { NULL, NULL, }, 2104 }; 2105 #endif /* !defined (NO_FLOAT) */ 2106 2107 #if !defined (NO_FLOAT) 2108 static test_t tests_fl_ops_spe[] = { 2109 { NULL, NULL, }, 2110 }; 2111 #endif /* !defined (NO_FLOAT) */ 2112 2113 #if !defined (NO_FLOAT) 2114 static test_t tests_flr_ops_spe[] = { 2115 { NULL, NULL, }, 2116 }; 2117 #endif /* !defined (NO_FLOAT) */ 2118 2119 2120 #if !defined (NO_FLOAT) 2121 extern void test_lfs (void); 2122 ASSEMBLY_FUNC("test_lfs", "lfs 17,0(14)"); 2123 2124 extern void test_lfsu (void); 2125 ASSEMBLY_FUNC("test_lfsu", "lfsu 17,0(14)"); 2126 2127 extern void test_lfd (void); 2128 ASSEMBLY_FUNC("test_lfd", "lfd 17,0(14)"); 2129 2130 extern void test_lfdu (void); 2131 ASSEMBLY_FUNC("test_lfdu", "lfdu 17,0(14)"); 2132 2133 static test_t tests_fld_ops_two_i16[] = { 2134 { &test_lfs , " lfs", }, 2135 { &test_lfsu , " lfsu", }, 2136 { &test_lfd , " lfd", }, 2137 { &test_lfdu , " lfdu", }, 2138 { NULL, NULL, }, 2139 }; 2140 #endif /* !defined (NO_FLOAT) */ 2141 2142 #if !defined (NO_FLOAT) 2143 static void test_lfsx (void) 2144 { 2145 __asm__ __volatile__ ("lfsx 17,14,15"); 2146 } 2147 2148 static void test_lfsux (void) 2149 { 2150 __asm__ __volatile__ ("lfsux 17,14,15"); 2151 } 2152 2153 static void test_lfdx (void) 2154 { 2155 __asm__ __volatile__ ("lfdx 17,14,15"); 2156 } 2157 2158 static void test_lfdux (void) 2159 { 2160 __asm__ __volatile__ ("lfdux 17,14,15"); 2161 } 2162 2163 static test_t tests_fld_ops_two[] = { 2164 { &test_lfsx , " lfsx", }, 2165 { &test_lfsux , " lfsux", }, 2166 { &test_lfdx , " lfdx", }, 2167 { &test_lfdux , " lfdux", }, 2168 { NULL, NULL, }, 2169 }; 2170 #endif /* !defined (NO_FLOAT) */ 2171 2172 #if !defined (NO_FLOAT) 2173 extern void test_stfs (void); 2174 ASSEMBLY_FUNC("test_stfs", "stfs 14,0(15)"); 2175 2176 extern void test_stfsu (void); 2177 ASSEMBLY_FUNC("test_stfsu", "stfsu 14,0(15)"); 2178 2179 extern void test_stfd (void); 2180 ASSEMBLY_FUNC("test_stfd", "stfd 14,0(15)"); 2181 2182 extern void test_stfdu (void); 2183 ASSEMBLY_FUNC("test_stfdu", "stfdu 14,0(15)"); 2184 2185 static test_t tests_fst_ops_three_i16[] = { 2186 { &test_stfs , " stfs", }, 2187 { &test_stfsu , " stfsu", }, 2188 { &test_stfd , " stfd", }, 2189 { &test_stfdu , " stfdu", }, 2190 { NULL, NULL, }, 2191 }; 2192 #endif /* !defined (NO_FLOAT) */ 2193 2194 #if !defined (NO_FLOAT) 2195 static void test_stfsx (void) 2196 { 2197 __asm__ __volatile__ ("stfsx 14,15,16"); 2198 } 2199 2200 static void test_stfsux (void) 2201 { 2202 __asm__ __volatile__ ("stfsux 14,15,16"); 2203 } 2204 2205 static void test_stfdx (void) 2206 { 2207 __asm__ __volatile__ ("stfdx 14,15,16"); 2208 } 2209 2210 static void test_stfdux (void) 2211 { 2212 __asm__ __volatile__ ("stfdux 14,15,16"); 2213 } 2214 2215 static test_t tests_fst_ops_three[] = { 2216 { &test_stfsx , " stfsx", }, 2217 { &test_stfsux , " stfsux", }, 2218 { &test_stfdx , " stfdx", }, 2219 { &test_stfdux , " stfdux", }, 2220 { NULL, NULL, }, 2221 }; 2222 #endif /* !defined (NO_FLOAT) */ 2223 2224 2225 #if defined (HAS_ALTIVEC) 2226 static void test_vmhaddshs (void) 2227 { 2228 __asm__ __volatile__ ("vmhaddshs 17, 14, 15, 16"); 2229 } 2230 2231 static void test_vmhraddshs (void) 2232 { 2233 __asm__ __volatile__ ("vmhraddshs 17, 14, 15, 16"); 2234 } 2235 2236 static void test_vmladduhm (void) 2237 { 2238 __asm__ __volatile__ ("vmladduhm 17, 14, 15, 16"); 2239 } 2240 2241 static void test_vmsumubm (void) 2242 { 2243 __asm__ __volatile__ ("vmsumubm 17, 14, 15, 16"); 2244 } 2245 2246 static void test_vmsumuhm (void) 2247 { 2248 __asm__ __volatile__ ("vmsumuhm 17, 14, 15, 16"); 2249 } 2250 2251 static void test_vmsumshs (void) 2252 { 2253 __asm__ __volatile__ ("vmsumshs 17, 14, 15, 16"); 2254 } 2255 2256 static void test_vmsumuhs (void) 2257 { 2258 __asm__ __volatile__ ("vmsumuhs 17, 14, 15, 16"); 2259 } 2260 2261 static void test_vmsummbm (void) 2262 { 2263 __asm__ __volatile__ ("vmsummbm 17, 14, 15, 16"); 2264 } 2265 2266 static void test_vmsumshm (void) 2267 { 2268 __asm__ __volatile__ ("vmsumshm 17, 14, 15, 16"); 2269 } 2270 2271 static test_t tests_aa_ops_three[] = { 2272 { &test_vmhaddshs , " vmhaddshs", }, 2273 { &test_vmhraddshs , " vmhraddshs", }, 2274 { &test_vmladduhm , " vmladduhm", }, 2275 { &test_vmsumubm , " vmsumubm", }, 2276 { &test_vmsumuhm , " vmsumuhm", }, 2277 { &test_vmsumshs , " vmsumshs", }, 2278 { &test_vmsumuhs , " vmsumuhs", }, 2279 { &test_vmsummbm , " vmsummbm", }, 2280 { &test_vmsumshm , " vmsumshm", }, 2281 { NULL, NULL, }, 2282 }; 2283 #endif /* defined (HAS_ALTIVEC) */ 2284 2285 #if defined (HAS_ALTIVEC) 2286 static void test_vperm (void) 2287 { 2288 __asm__ __volatile__ ("vperm 17, 14, 15, 16"); 2289 } 2290 2291 static void test_vsel (void) 2292 { 2293 __asm__ __volatile__ ("vsel 17, 14, 15, 16"); 2294 } 2295 2296 static test_t tests_al_ops_three[] = { 2297 { &test_vperm , " vperm", }, 2298 { &test_vsel , " vsel", }, 2299 { NULL, NULL, }, 2300 }; 2301 #endif /* defined (HAS_ALTIVEC) */ 2302 2303 #if defined (HAS_ALTIVEC) 2304 static void test_vaddubm (void) 2305 { 2306 __asm__ __volatile__ ("vaddubm 17, 14, 15"); 2307 } 2308 2309 static void test_vadduhm (void) 2310 { 2311 __asm__ __volatile__ ("vadduhm 17, 14, 15"); 2312 } 2313 2314 static void test_vadduwm (void) 2315 { 2316 __asm__ __volatile__ ("vadduwm 17, 14, 15"); 2317 } 2318 2319 static void test_vaddubs (void) 2320 { 2321 __asm__ __volatile__ ("vaddubs 17, 14, 15"); 2322 } 2323 2324 static void test_vadduhs (void) 2325 { 2326 __asm__ __volatile__ ("vadduhs 17, 14, 15"); 2327 } 2328 2329 static void test_vadduws (void) 2330 { 2331 __asm__ __volatile__ ("vadduws 17, 14, 15"); 2332 } 2333 2334 static void test_vaddsbs (void) 2335 { 2336 __asm__ __volatile__ ("vaddsbs 17, 14, 15"); 2337 } 2338 2339 static void test_vaddshs (void) 2340 { 2341 __asm__ __volatile__ ("vaddshs 17, 14, 15"); 2342 } 2343 2344 static void test_vaddsws (void) 2345 { 2346 __asm__ __volatile__ ("vaddsws 17, 14, 15"); 2347 } 2348 2349 static void test_vaddcuw (void) 2350 { 2351 __asm__ __volatile__ ("vaddcuw 17, 14, 15"); 2352 } 2353 2354 static void test_vsububm (void) 2355 { 2356 __asm__ __volatile__ ("vsububm 17, 14, 15"); 2357 } 2358 2359 static void test_vsubuhm (void) 2360 { 2361 __asm__ __volatile__ ("vsubuhm 17, 14, 15"); 2362 } 2363 2364 static void test_vsubuwm (void) 2365 { 2366 __asm__ __volatile__ ("vsubuwm 17, 14, 15"); 2367 } 2368 2369 static void test_vsububs (void) 2370 { 2371 __asm__ __volatile__ ("vsububs 17, 14, 15"); 2372 } 2373 2374 static void test_vsubuhs (void) 2375 { 2376 __asm__ __volatile__ ("vsubuhs 17, 14, 15"); 2377 } 2378 2379 static void test_vsubuws (void) 2380 { 2381 __asm__ __volatile__ ("vsubuws 17, 14, 15"); 2382 } 2383 2384 static void test_vsubsbs (void) 2385 { 2386 __asm__ __volatile__ ("vsubsbs 17, 14, 15"); 2387 } 2388 2389 static void test_vsubshs (void) 2390 { 2391 __asm__ __volatile__ ("vsubshs 17, 14, 15"); 2392 } 2393 2394 static void test_vsubsws (void) 2395 { 2396 __asm__ __volatile__ ("vsubsws 17, 14, 15"); 2397 } 2398 2399 static void test_vsubcuw (void) 2400 { 2401 __asm__ __volatile__ ("vsubcuw 17, 14, 15"); 2402 } 2403 2404 static void test_vmuloub (void) 2405 { 2406 __asm__ __volatile__ ("vmuloub 17, 14, 15"); 2407 } 2408 2409 static void test_vmulouh (void) 2410 { 2411 __asm__ __volatile__ ("vmulouh 17, 14, 15"); 2412 } 2413 2414 static void test_vmulosb (void) 2415 { 2416 __asm__ __volatile__ ("vmulosb 17, 14, 15"); 2417 } 2418 2419 static void test_vmulosh (void) 2420 { 2421 __asm__ __volatile__ ("vmulosh 17, 14, 15"); 2422 } 2423 2424 static void test_vmuleub (void) 2425 { 2426 __asm__ __volatile__ ("vmuleub 17, 14, 15"); 2427 } 2428 2429 static void test_vmuleuh (void) 2430 { 2431 __asm__ __volatile__ ("vmuleuh 17, 14, 15"); 2432 } 2433 2434 static void test_vmulesb (void) 2435 { 2436 __asm__ __volatile__ ("vmulesb 17, 14, 15"); 2437 } 2438 2439 static void test_vmulesh (void) 2440 { 2441 __asm__ __volatile__ ("vmulesh 17, 14, 15"); 2442 } 2443 2444 static void test_vsumsws (void) 2445 { 2446 __asm__ __volatile__ ("vsumsws 17, 14, 15"); 2447 } 2448 2449 static void test_vsum2sws (void) 2450 { 2451 __asm__ __volatile__ ("vsum2sws 17, 14, 15"); 2452 } 2453 2454 static void test_vsum4ubs (void) 2455 { 2456 __asm__ __volatile__ ("vsum4ubs 17, 14, 15"); 2457 } 2458 2459 static void test_vsum4sbs (void) 2460 { 2461 __asm__ __volatile__ ("vsum4sbs 17, 14, 15"); 2462 } 2463 2464 static void test_vsum4shs (void) 2465 { 2466 __asm__ __volatile__ ("vsum4shs 17, 14, 15"); 2467 } 2468 2469 static void test_vavgub (void) 2470 { 2471 __asm__ __volatile__ ("vavgub 17, 14, 15"); 2472 } 2473 2474 static void test_vavguh (void) 2475 { 2476 __asm__ __volatile__ ("vavguh 17, 14, 15"); 2477 } 2478 2479 static void test_vavguw (void) 2480 { 2481 __asm__ __volatile__ ("vavguw 17, 14, 15"); 2482 } 2483 2484 static void test_vavgsb (void) 2485 { 2486 __asm__ __volatile__ ("vavgsb 17, 14, 15"); 2487 } 2488 2489 static void test_vavgsh (void) 2490 { 2491 __asm__ __volatile__ ("vavgsh 17, 14, 15"); 2492 } 2493 2494 static void test_vavgsw (void) 2495 { 2496 __asm__ __volatile__ ("vavgsw 17, 14, 15"); 2497 } 2498 2499 static void test_vmaxub (void) 2500 { 2501 __asm__ __volatile__ ("vmaxub 17, 14, 15"); 2502 } 2503 2504 static void test_vmaxuh (void) 2505 { 2506 __asm__ __volatile__ ("vmaxuh 17, 14, 15"); 2507 } 2508 2509 static void test_vmaxuw (void) 2510 { 2511 __asm__ __volatile__ ("vmaxuw 17, 14, 15"); 2512 } 2513 2514 static void test_vmaxsb (void) 2515 { 2516 __asm__ __volatile__ ("vmaxsb 17, 14, 15"); 2517 } 2518 2519 static void test_vmaxsh (void) 2520 { 2521 __asm__ __volatile__ ("vmaxsh 17, 14, 15"); 2522 } 2523 2524 static void test_vmaxsw (void) 2525 { 2526 __asm__ __volatile__ ("vmaxsw 17, 14, 15"); 2527 } 2528 2529 static void test_vminub (void) 2530 { 2531 __asm__ __volatile__ ("vminub 17, 14, 15"); 2532 } 2533 2534 static void test_vminuh (void) 2535 { 2536 __asm__ __volatile__ ("vminuh 17, 14, 15"); 2537 } 2538 2539 static void test_vminuw (void) 2540 { 2541 __asm__ __volatile__ ("vminuw 17, 14, 15"); 2542 } 2543 2544 static void test_vminsb (void) 2545 { 2546 __asm__ __volatile__ ("vminsb 17, 14, 15"); 2547 } 2548 2549 static void test_vminsh (void) 2550 { 2551 __asm__ __volatile__ ("vminsh 17, 14, 15"); 2552 } 2553 2554 static void test_vminsw (void) 2555 { 2556 __asm__ __volatile__ ("vminsw 17, 14, 15"); 2557 } 2558 2559 static test_t tests_aa_ops_two[] = { 2560 { &test_vaddubm , " vaddubm", }, 2561 { &test_vadduhm , " vadduhm", }, 2562 { &test_vadduwm , " vadduwm", }, 2563 { &test_vaddubs , " vaddubs", }, 2564 { &test_vadduhs , " vadduhs", }, 2565 { &test_vadduws , " vadduws", }, 2566 { &test_vaddsbs , " vaddsbs", }, 2567 { &test_vaddshs , " vaddshs", }, 2568 { &test_vaddsws , " vaddsws", }, 2569 { &test_vaddcuw , " vaddcuw", }, 2570 { &test_vsububm , " vsububm", }, 2571 { &test_vsubuhm , " vsubuhm", }, 2572 { &test_vsubuwm , " vsubuwm", }, 2573 { &test_vsububs , " vsububs", }, 2574 { &test_vsubuhs , " vsubuhs", }, 2575 { &test_vsubuws , " vsubuws", }, 2576 { &test_vsubsbs , " vsubsbs", }, 2577 { &test_vsubshs , " vsubshs", }, 2578 { &test_vsubsws , " vsubsws", }, 2579 { &test_vsubcuw , " vsubcuw", }, 2580 { &test_vmuloub , " vmuloub", }, 2581 { &test_vmulouh , " vmulouh", }, 2582 { &test_vmulosb , " vmulosb", }, 2583 { &test_vmulosh , " vmulosh", }, 2584 { &test_vmuleub , " vmuleub", }, 2585 { &test_vmuleuh , " vmuleuh", }, 2586 { &test_vmulesb , " vmulesb", }, 2587 { &test_vmulesh , " vmulesh", }, 2588 { &test_vsumsws , " vsumsws", }, 2589 { &test_vsum2sws , " vsum2sws", }, 2590 { &test_vsum4ubs , " vsum4ubs", }, 2591 { &test_vsum4sbs , " vsum4sbs", }, 2592 { &test_vsum4shs , " vsum4shs", }, 2593 { &test_vavgub , " vavgub", }, 2594 { &test_vavguh , " vavguh", }, 2595 { &test_vavguw , " vavguw", }, 2596 { &test_vavgsb , " vavgsb", }, 2597 { &test_vavgsh , " vavgsh", }, 2598 { &test_vavgsw , " vavgsw", }, 2599 { &test_vmaxub , " vmaxub", }, 2600 { &test_vmaxuh , " vmaxuh", }, 2601 { &test_vmaxuw , " vmaxuw", }, 2602 { &test_vmaxsb , " vmaxsb", }, 2603 { &test_vmaxsh , " vmaxsh", }, 2604 { &test_vmaxsw , " vmaxsw", }, 2605 { &test_vminub , " vminub", }, 2606 { &test_vminuh , " vminuh", }, 2607 { &test_vminuw , " vminuw", }, 2608 { &test_vminsb , " vminsb", }, 2609 { &test_vminsh , " vminsh", }, 2610 { &test_vminsw , " vminsw", }, 2611 { NULL, NULL, }, 2612 }; 2613 #endif /* defined (HAS_ALTIVEC) */ 2614 2615 #if defined (HAS_ALTIVEC) 2616 static void test_vand (void) 2617 { 2618 __asm__ __volatile__ ("vand 17, 14, 15"); 2619 } 2620 2621 static void test_vor (void) 2622 { 2623 __asm__ __volatile__ ("vor 17, 14, 15"); 2624 } 2625 2626 static void test_vxor (void) 2627 { 2628 __asm__ __volatile__ ("vxor 17, 14, 15"); 2629 } 2630 2631 static void test_vandc (void) 2632 { 2633 __asm__ __volatile__ ("vandc 17, 14, 15"); 2634 } 2635 2636 static void test_vnor (void) 2637 { 2638 __asm__ __volatile__ ("vnor 17, 14, 15"); 2639 } 2640 2641 static void test_vrlb (void) 2642 { 2643 __asm__ __volatile__ ("vrlb 17, 14, 15"); 2644 } 2645 2646 static void test_vrlh (void) 2647 { 2648 __asm__ __volatile__ ("vrlh 17, 14, 15"); 2649 } 2650 2651 static void test_vrlw (void) 2652 { 2653 __asm__ __volatile__ ("vrlw 17, 14, 15"); 2654 } 2655 2656 static void test_vslb (void) 2657 { 2658 __asm__ __volatile__ ("vslb 17, 14, 15"); 2659 } 2660 2661 static void test_vslh (void) 2662 { 2663 __asm__ __volatile__ ("vslh 17, 14, 15"); 2664 } 2665 2666 static void test_vslw (void) 2667 { 2668 __asm__ __volatile__ ("vslw 17, 14, 15"); 2669 } 2670 2671 static void test_vsrb (void) 2672 { 2673 __asm__ __volatile__ ("vsrb 17, 14, 15"); 2674 } 2675 2676 static void test_vsrh (void) 2677 { 2678 __asm__ __volatile__ ("vsrh 17, 14, 15"); 2679 } 2680 2681 static void test_vsrw (void) 2682 { 2683 __asm__ __volatile__ ("vsrw 17, 14, 15"); 2684 } 2685 2686 static void test_vsrab (void) 2687 { 2688 __asm__ __volatile__ ("vsrab 17, 14, 15"); 2689 } 2690 2691 static void test_vsrah (void) 2692 { 2693 __asm__ __volatile__ ("vsrah 17, 14, 15"); 2694 } 2695 2696 static void test_vsraw (void) 2697 { 2698 __asm__ __volatile__ ("vsraw 17, 14, 15"); 2699 } 2700 2701 static void test_vpkuhum (void) 2702 { 2703 __asm__ __volatile__ ("vpkuhum 17, 14, 15"); 2704 } 2705 2706 static void test_vpkuwum (void) 2707 { 2708 __asm__ __volatile__ ("vpkuwum 17, 14, 15"); 2709 } 2710 2711 static void test_vpkuhus (void) 2712 { 2713 __asm__ __volatile__ ("vpkuhus 17, 14, 15"); 2714 } 2715 2716 static void test_vpkuwus (void) 2717 { 2718 __asm__ __volatile__ ("vpkuwus 17, 14, 15"); 2719 } 2720 2721 static void test_vpkshus (void) 2722 { 2723 __asm__ __volatile__ ("vpkshus 17, 14, 15"); 2724 } 2725 2726 static void test_vpkswus (void) 2727 { 2728 __asm__ __volatile__ ("vpkswus 17, 14, 15"); 2729 } 2730 2731 static void test_vpkshss (void) 2732 { 2733 __asm__ __volatile__ ("vpkshss 17, 14, 15"); 2734 } 2735 2736 static void test_vpkswss (void) 2737 { 2738 __asm__ __volatile__ ("vpkswss 17, 14, 15"); 2739 } 2740 2741 static void test_vpkpx (void) 2742 { 2743 __asm__ __volatile__ ("vpkpx 17, 14, 15"); 2744 } 2745 2746 static void test_vmrghb (void) 2747 { 2748 __asm__ __volatile__ ("vmrghb 17, 14, 15"); 2749 } 2750 2751 static void test_vmrghh (void) 2752 { 2753 __asm__ __volatile__ ("vmrghh 17, 14, 15"); 2754 } 2755 2756 static void test_vmrghw (void) 2757 { 2758 __asm__ __volatile__ ("vmrghw 17, 14, 15"); 2759 } 2760 2761 static void test_vmrglb (void) 2762 { 2763 __asm__ __volatile__ ("vmrglb 17, 14, 15"); 2764 } 2765 2766 static void test_vmrglh (void) 2767 { 2768 __asm__ __volatile__ ("vmrglh 17, 14, 15"); 2769 } 2770 2771 static void test_vmrglw (void) 2772 { 2773 __asm__ __volatile__ ("vmrglw 17, 14, 15"); 2774 } 2775 2776 static void test_vslo (void) 2777 { 2778 __asm__ __volatile__ ("vslo 17, 14, 15"); 2779 } 2780 2781 static void test_vsro (void) 2782 { 2783 __asm__ __volatile__ ("vsro 17, 14, 15"); 2784 } 2785 2786 static test_t tests_al_ops_two[] = { 2787 { &test_vand , " vand", }, 2788 { &test_vor , " vor", }, 2789 { &test_vxor , " vxor", }, 2790 { &test_vandc , " vandc", }, 2791 { &test_vnor , " vnor", }, 2792 { &test_vrlb , " vrlb", }, 2793 { &test_vrlh , " vrlh", }, 2794 { &test_vrlw , " vrlw", }, 2795 { &test_vslb , " vslb", }, 2796 { &test_vslh , " vslh", }, 2797 { &test_vslw , " vslw", }, 2798 { &test_vsrb , " vsrb", }, 2799 { &test_vsrh , " vsrh", }, 2800 { &test_vsrw , " vsrw", }, 2801 { &test_vsrab , " vsrab", }, 2802 { &test_vsrah , " vsrah", }, 2803 { &test_vsraw , " vsraw", }, 2804 { &test_vpkuhum , " vpkuhum", }, 2805 { &test_vpkuwum , " vpkuwum", }, 2806 { &test_vpkuhus , " vpkuhus", }, 2807 { &test_vpkuwus , " vpkuwus", }, 2808 { &test_vpkshus , " vpkshus", }, 2809 { &test_vpkswus , " vpkswus", }, 2810 { &test_vpkshss , " vpkshss", }, 2811 { &test_vpkswss , " vpkswss", }, 2812 { &test_vpkpx , " vpkpx", }, 2813 { &test_vmrghb , " vmrghb", }, 2814 { &test_vmrghh , " vmrghh", }, 2815 { &test_vmrghw , " vmrghw", }, 2816 { &test_vmrglb , " vmrglb", }, 2817 { &test_vmrglh , " vmrglh", }, 2818 { &test_vmrglw , " vmrglw", }, 2819 { &test_vslo , " vslo", }, 2820 { &test_vsro , " vsro", }, 2821 { NULL, NULL, }, 2822 }; 2823 #endif /* defined (HAS_ALTIVEC) */ 2824 2825 #if defined (HAS_ALTIVEC) 2826 static void test_vupkhsb (void) 2827 { 2828 __asm__ __volatile__ ("vupkhsb 17, 14"); 2829 } 2830 2831 static void test_vupkhsh (void) 2832 { 2833 __asm__ __volatile__ ("vupkhsh 17, 14"); 2834 } 2835 2836 static void test_vupkhpx (void) 2837 { 2838 __asm__ __volatile__ ("vupkhpx 17, 14"); 2839 } 2840 2841 static void test_vupklsb (void) 2842 { 2843 __asm__ __volatile__ ("vupklsb 17, 14"); 2844 } 2845 2846 static void test_vupklsh (void) 2847 { 2848 __asm__ __volatile__ ("vupklsh 17, 14"); 2849 } 2850 2851 static void test_vupklpx (void) 2852 { 2853 __asm__ __volatile__ ("vupklpx 17, 14"); 2854 } 2855 2856 static test_t tests_al_ops_one[] = { 2857 { &test_vupkhsb , " vupkhsb", }, 2858 { &test_vupkhsh , " vupkhsh", }, 2859 { &test_vupkhpx , " vupkhpx", }, 2860 { &test_vupklsb , " vupklsb", }, 2861 { &test_vupklsh , " vupklsh", }, 2862 { &test_vupklpx , " vupklpx", }, 2863 { NULL, NULL, }, 2864 }; 2865 #endif /* defined (HAS_ALTIVEC) */ 2866 2867 #if defined (HAS_ALTIVEC) 2868 static void test_vcmpgtub (void) 2869 { 2870 __asm__ __volatile__ ("vcmpgtub 17, 14, 15"); 2871 } 2872 2873 static void test_vcmpgtuh (void) 2874 { 2875 __asm__ __volatile__ ("vcmpgtuh 17, 14, 15"); 2876 } 2877 2878 static void test_vcmpgtuw (void) 2879 { 2880 __asm__ __volatile__ ("vcmpgtuw 17, 14, 15"); 2881 } 2882 2883 static void test_vcmpgtsb (void) 2884 { 2885 __asm__ __volatile__ ("vcmpgtsb 17, 14, 15"); 2886 } 2887 2888 static void test_vcmpgtsh (void) 2889 { 2890 __asm__ __volatile__ ("vcmpgtsh 17, 14, 15"); 2891 } 2892 2893 static void test_vcmpgtsw (void) 2894 { 2895 __asm__ __volatile__ ("vcmpgtsw 17, 14, 15"); 2896 } 2897 2898 static void test_vcmpequb (void) 2899 { 2900 __asm__ __volatile__ ("vcmpequb 17, 14, 15"); 2901 } 2902 2903 static void test_vcmpequh (void) 2904 { 2905 __asm__ __volatile__ ("vcmpequh 17, 14, 15"); 2906 } 2907 2908 static void test_vcmpequw (void) 2909 { 2910 __asm__ __volatile__ ("vcmpequw 17, 14, 15"); 2911 } 2912 2913 static test_t tests_ac_ops_two[] = { 2914 { &test_vcmpgtub , " vcmpgtub", }, 2915 { &test_vcmpgtuh , " vcmpgtuh", }, 2916 { &test_vcmpgtuw , " vcmpgtuw", }, 2917 { &test_vcmpgtsb , " vcmpgtsb", }, 2918 { &test_vcmpgtsh , " vcmpgtsh", }, 2919 { &test_vcmpgtsw , " vcmpgtsw", }, 2920 { &test_vcmpequb , " vcmpequb", }, 2921 { &test_vcmpequh , " vcmpequh", }, 2922 { &test_vcmpequw , " vcmpequw", }, 2923 { NULL, NULL, }, 2924 }; 2925 #endif /* defined (HAS_ALTIVEC) */ 2926 2927 #if defined (HAS_ALTIVEC) 2928 static void test_vcmpgtub_ (void) 2929 { 2930 __asm__ __volatile__ ("vcmpgtub. 17, 14, 15"); 2931 } 2932 2933 static void test_vcmpgtuh_ (void) 2934 { 2935 __asm__ __volatile__ ("vcmpgtuh. 17, 14, 15"); 2936 } 2937 2938 static void test_vcmpgtuw_ (void) 2939 { 2940 __asm__ __volatile__ ("vcmpgtuw. 17, 14, 15"); 2941 } 2942 2943 static void test_vcmpgtsb_ (void) 2944 { 2945 __asm__ __volatile__ ("vcmpgtsb. 17, 14, 15"); 2946 } 2947 2948 static void test_vcmpgtsh_ (void) 2949 { 2950 __asm__ __volatile__ ("vcmpgtsh. 17, 14, 15"); 2951 } 2952 2953 static void test_vcmpgtsw_ (void) 2954 { 2955 __asm__ __volatile__ ("vcmpgtsw. 17, 14, 15"); 2956 } 2957 2958 static void test_vcmpequb_ (void) 2959 { 2960 __asm__ __volatile__ ("vcmpequb. 17, 14, 15"); 2961 } 2962 2963 static void test_vcmpequh_ (void) 2964 { 2965 __asm__ __volatile__ ("vcmpequh. 17, 14, 15"); 2966 } 2967 2968 static void test_vcmpequw_ (void) 2969 { 2970 __asm__ __volatile__ ("vcmpequw. 17, 14, 15"); 2971 } 2972 2973 static test_t tests_acr_ops_two[] = { 2974 { &test_vcmpgtub_ , " vcmpgtub.", }, 2975 { &test_vcmpgtuh_ , " vcmpgtuh.", }, 2976 { &test_vcmpgtuw_ , " vcmpgtuw.", }, 2977 { &test_vcmpgtsb_ , " vcmpgtsb.", }, 2978 { &test_vcmpgtsh_ , " vcmpgtsh.", }, 2979 { &test_vcmpgtsw_ , " vcmpgtsw.", }, 2980 { &test_vcmpequb_ , " vcmpequb.", }, 2981 { &test_vcmpequh_ , " vcmpequh.", }, 2982 { &test_vcmpequw_ , " vcmpequw.", }, 2983 { NULL, NULL, }, 2984 }; 2985 #endif /* defined (HAS_ALTIVEC) */ 2986 2987 #if defined (HAS_ALTIVEC) 2988 static void test_vsl (void) 2989 { 2990 __asm__ __volatile__ ("vsl 17, 14, 15"); 2991 } 2992 2993 static void test_vsr (void) 2994 { 2995 __asm__ __volatile__ ("vsr 17, 14, 15"); 2996 } 2997 2998 extern void test_vspltb (void); 2999 ASSEMBLY_FUNC("test_vspltb", "vspltb 17, 14, 0"); 3000 3001 extern void test_vsplth (void); 3002 ASSEMBLY_FUNC("test_vsplth", "vsplth 17, 14, 0"); 3003 3004 extern void test_vspltw (void); 3005 ASSEMBLY_FUNC("test_vspltw", "vspltw 17, 14, 0"); 3006 3007 extern void test_vspltisb (void); 3008 ASSEMBLY_FUNC("test_vspltisb", "vspltisb 17, 0"); 3009 3010 extern void test_vspltish (void); 3011 ASSEMBLY_FUNC("test_vspltish", "vspltish 17, 0"); 3012 3013 extern void test_vspltisw (void); 3014 ASSEMBLY_FUNC("test_vspltisw", "vspltisw 17, 0"); 3015 3016 extern void test_vsldoi (void); 3017 ASSEMBLY_FUNC("test_vsldoi", "vsldoi 17, 14, 15, 0"); 3018 3019 static void test_lvsl (void) 3020 { 3021 __asm__ __volatile__ ("lvsl 17, 14, 15"); 3022 } 3023 3024 static void test_lvsr (void) 3025 { 3026 __asm__ __volatile__ ("lvsr 17, 14, 15"); 3027 } 3028 3029 static test_t tests_av_int_ops_spe[] = { 3030 { &test_vsl , " vsl", }, 3031 { &test_vsr , " vsr", }, 3032 { &test_vspltb , " vspltb", }, 3033 { &test_vsplth , " vsplth", }, 3034 { &test_vspltw , " vspltw", }, 3035 { &test_vspltisb , " vspltisb", }, 3036 { &test_vspltish , " vspltish", }, 3037 { &test_vspltisw , " vspltisw", }, 3038 { &test_vsldoi , " vsldoi", }, 3039 { &test_lvsl , " lvsl", }, 3040 { &test_lvsr , " lvsr", }, 3041 { NULL, NULL, }, 3042 }; 3043 #endif /* defined (HAS_ALTIVEC) */ 3044 3045 #if defined (HAS_ALTIVEC) 3046 static void test_lvebx (void) 3047 { 3048 __asm__ __volatile__ ("lvebx 17,14,15"); 3049 } 3050 3051 static void test_lvehx (void) 3052 { 3053 __asm__ __volatile__ ("lvehx 17,14,15"); 3054 } 3055 3056 static void test_lvewx (void) 3057 { 3058 __asm__ __volatile__ ("lvewx 17,14,15"); 3059 } 3060 3061 static void test_lvx (void) 3062 { 3063 __asm__ __volatile__ ("lvx 17,14,15"); 3064 } 3065 3066 static void test_lvxl (void) 3067 { 3068 __asm__ __volatile__ ("lvxl 17,14,15"); 3069 } 3070 3071 static test_t tests_ald_ops_two[] = { 3072 { &test_lvebx , " lvebx", }, 3073 { &test_lvehx , " lvehx", }, 3074 { &test_lvewx , " lvewx", }, 3075 { &test_lvx , " lvx", }, 3076 { &test_lvxl , " lvxl", }, 3077 { NULL, NULL, }, 3078 }; 3079 #endif /* defined (HAS_ALTIVEC) */ 3080 3081 #if defined (HAS_ALTIVEC) 3082 static void test_stvebx (void) 3083 { 3084 __asm__ __volatile__ ("stvebx 14,15,16"); 3085 } 3086 3087 static void test_stvehx (void) 3088 { 3089 __asm__ __volatile__ ("stvehx 14,15,16"); 3090 } 3091 3092 static void test_stvewx (void) 3093 { 3094 __asm__ __volatile__ ("stvewx 14,15,16"); 3095 } 3096 3097 static void test_stvx (void) 3098 { 3099 __asm__ __volatile__ ("stvx 14,15,16"); 3100 } 3101 3102 static void test_stvxl (void) 3103 { 3104 __asm__ __volatile__ ("stvxl 14,15,16"); 3105 } 3106 3107 static test_t tests_ast_ops_three[] = { 3108 { &test_stvebx , " stvebx", }, 3109 { &test_stvehx , " stvehx", }, 3110 { &test_stvewx , " stvewx", }, 3111 { &test_stvx , " stvx", }, 3112 { &test_stvxl , " stvxl", }, 3113 { NULL, NULL, }, 3114 }; 3115 #endif /* defined (HAS_ALTIVEC) */ 3116 3117 #if defined (HAS_ALTIVEC) 3118 #if 0 3119 static void test_vmaddfp (void) 3120 { 3121 __asm__ __volatile__ ("vmaddfp 17, 14, 15, 16"); 3122 } 3123 3124 static void test_vnmsubfp (void) 3125 { 3126 __asm__ __volatile__ ("vnmsubfp 17, 14, 15, 16"); 3127 } 3128 #endif 3129 3130 static test_t tests_afa_ops_three[] = { 3131 // { &test_vmaddfp , " vmaddfp", }, // TODO: Not yet supported 3132 // { &test_vnmsubfp , " vnmsubfp", }, // TODO: Not yet supported 3133 { NULL, NULL, }, 3134 }; 3135 #endif /* defined (HAS_ALTIVEC) */ 3136 3137 #if defined (HAS_ALTIVEC) 3138 static void test_vaddfp (void) 3139 { 3140 __asm__ __volatile__ ("vaddfp 17, 14, 15"); 3141 } 3142 3143 static void test_vsubfp (void) 3144 { 3145 __asm__ __volatile__ ("vsubfp 17, 14, 15"); 3146 } 3147 3148 static void test_vmaxfp (void) 3149 { 3150 __asm__ __volatile__ ("vmaxfp 17, 14, 15"); 3151 } 3152 3153 static void test_vminfp (void) 3154 { 3155 __asm__ __volatile__ ("vminfp 17, 14, 15"); 3156 } 3157 3158 static test_t tests_afa_ops_two[] = { 3159 { &test_vaddfp , " vaddfp", }, 3160 { &test_vsubfp , " vsubfp", }, 3161 { &test_vmaxfp , " vmaxfp", }, 3162 { &test_vminfp , " vminfp", }, 3163 { NULL, NULL, }, 3164 }; 3165 #endif /* defined (HAS_ALTIVEC) */ 3166 3167 #if defined (HAS_ALTIVEC) 3168 static void test_vrfin (void) 3169 { 3170 __asm__ __volatile__ ("vrfin 17, 14"); 3171 } 3172 3173 static void test_vrfiz (void) 3174 { 3175 __asm__ __volatile__ ("vrfiz 17, 14"); 3176 } 3177 3178 static void test_vrfip (void) 3179 { 3180 __asm__ __volatile__ ("vrfip 17, 14"); 3181 } 3182 3183 static void test_vrfim (void) 3184 { 3185 __asm__ __volatile__ ("vrfim 17, 14"); 3186 } 3187 3188 static void test_vrefp (void) 3189 { 3190 __asm__ __volatile__ ("vrefp 17, 14"); 3191 } 3192 3193 static void test_vrsqrtefp (void) 3194 { 3195 __asm__ __volatile__ ("vrsqrtefp 17, 14"); 3196 } 3197 3198 #if 0 // TODO: Not yet supported 3199 static void test_vlogefp (void) 3200 { 3201 __asm__ __volatile__ ("vlogefp 17, 14"); 3202 } 3203 3204 static void test_vexptefp (void) 3205 { 3206 __asm__ __volatile__ ("vexptefp 17, 14"); 3207 } 3208 #endif 3209 3210 static test_t tests_afa_ops_one[] = { 3211 { &test_vrfin , " vrfin", }, 3212 { &test_vrfiz , " vrfiz", }, 3213 { &test_vrfip , " vrfip", }, 3214 { &test_vrfim , " vrfim", }, 3215 { &test_vrefp , " vrefp", }, 3216 { &test_vrsqrtefp , " vrsqrtefp", }, 3217 // { &test_vlogefp , " vlogefp", }, // TODO: Not yet supported 3218 // { &test_vexptefp , " vexptefp", }, // TODO: Not yet supported 3219 { NULL, NULL, }, 3220 }; 3221 #endif /* defined (HAS_ALTIVEC) */ 3222 3223 #if defined (HAS_ALTIVEC) 3224 static void test_vcmpgtfp (void) 3225 { 3226 __asm__ __volatile__ ("vcmpgtfp 17, 14, 15"); 3227 } 3228 3229 static void test_vcmpeqfp (void) 3230 { 3231 __asm__ __volatile__ ("vcmpeqfp 17, 14, 15"); 3232 } 3233 3234 static void test_vcmpgefp (void) 3235 { 3236 __asm__ __volatile__ ("vcmpgefp 17, 14, 15"); 3237 } 3238 3239 static void test_vcmpbfp (void) 3240 { 3241 __asm__ __volatile__ ("vcmpbfp 17, 14, 15"); 3242 } 3243 3244 static test_t tests_afc_ops_two[] = { 3245 { &test_vcmpgtfp , " vcmpgtfp", }, 3246 { &test_vcmpeqfp , " vcmpeqfp", }, 3247 { &test_vcmpgefp , " vcmpgefp", }, 3248 { &test_vcmpbfp , " vcmpbfp", }, 3249 { NULL, NULL, }, 3250 }; 3251 #endif /* defined (HAS_ALTIVEC) */ 3252 3253 #if defined (HAS_ALTIVEC) 3254 static void test_vcmpgtfp_ (void) 3255 { 3256 __asm__ __volatile__ ("vcmpgtfp. 17, 14, 15"); 3257 } 3258 3259 static void test_vcmpeqfp_ (void) 3260 { 3261 __asm__ __volatile__ ("vcmpeqfp. 17, 14, 15"); 3262 } 3263 3264 static void test_vcmpgefp_ (void) 3265 { 3266 __asm__ __volatile__ ("vcmpgefp. 17, 14, 15"); 3267 } 3268 3269 static void test_vcmpbfp_ (void) 3270 { 3271 __asm__ __volatile__ ("vcmpbfp. 17, 14, 15"); 3272 } 3273 3274 static test_t tests_afcr_ops_two[] = { 3275 { &test_vcmpgtfp_ , " vcmpgtfp.", }, 3276 { &test_vcmpeqfp_ , " vcmpeqfp.", }, 3277 { &test_vcmpgefp_ , " vcmpgefp.", }, 3278 { &test_vcmpbfp_ , " vcmpbfp.", }, 3279 { NULL, NULL, }, 3280 }; 3281 #endif /* defined (HAS_ALTIVEC) */ 3282 3283 #if defined (HAS_ALTIVEC) 3284 extern void test_vcfux (void); 3285 ASSEMBLY_FUNC("test_vcfux", "vcfux 17, 14, 0"); 3286 3287 extern void test_vcfsx (void); 3288 ASSEMBLY_FUNC("test_vcfsx", "vcfsx 17, 14, 0"); 3289 3290 extern void test_vctuxs (void); 3291 ASSEMBLY_FUNC("test_vctuxs", "vctuxs 17, 14, 0"); 3292 3293 extern void test_vctsxs (void); 3294 ASSEMBLY_FUNC("test_vctsxs", "vctsxs 17, 14, 0"); 3295 3296 static test_t tests_av_float_ops_spe[] = { 3297 { &test_vcfux , " vcfux", }, 3298 { &test_vcfsx , " vcfsx", }, 3299 { &test_vctuxs , " vctuxs", }, 3300 { &test_vctsxs , " vctsxs", }, 3301 { NULL, NULL, }, 3302 }; 3303 #endif /* defined (HAS_ALTIVEC) */ 3304 3305 #if defined (IS_PPC405) 3306 static void test_macchw (void) 3307 { 3308 __asm__ __volatile__ ("macchw 17, 14, 15"); 3309 } 3310 3311 static void test_macchwo (void) 3312 { 3313 __asm__ __volatile__ ("macchwo 17, 14, 15"); 3314 } 3315 3316 static void test_macchws (void) 3317 { 3318 __asm__ __volatile__ ("macchws 17, 14, 15"); 3319 } 3320 3321 static void test_macchwso (void) 3322 { 3323 __asm__ __volatile__ ("macchwso 17, 14, 15"); 3324 } 3325 3326 static void test_macchwsu (void) 3327 { 3328 __asm__ __volatile__ ("macchwsu 17, 14, 15"); 3329 } 3330 3331 static void test_macchwsuo (void) 3332 { 3333 __asm__ __volatile__ ("macchwsuo 17, 14, 15"); 3334 } 3335 3336 static void test_macchwu (void) 3337 { 3338 __asm__ __volatile__ ("macchwu 17, 14, 15"); 3339 } 3340 3341 static void test_macchwuo (void) 3342 { 3343 __asm__ __volatile__ ("macchwuo 17, 14, 15"); 3344 } 3345 3346 static void test_machhw (void) 3347 { 3348 __asm__ __volatile__ ("machhw 17, 14, 15"); 3349 } 3350 3351 static void test_machhwo (void) 3352 { 3353 __asm__ __volatile__ ("machhwo 17, 14, 15"); 3354 } 3355 3356 static void test_machhws (void) 3357 { 3358 __asm__ __volatile__ ("machhws 17, 14, 15"); 3359 } 3360 3361 static void test_machhwso (void) 3362 { 3363 __asm__ __volatile__ ("machhwso 17, 14, 15"); 3364 } 3365 3366 static void test_machhwsu (void) 3367 { 3368 __asm__ __volatile__ ("machhwsu 17, 14, 15"); 3369 } 3370 3371 static void test_machhwsuo (void) 3372 { 3373 __asm__ __volatile__ ("machhwsuo 17, 14, 15"); 3374 } 3375 3376 static void test_machhwu (void) 3377 { 3378 __asm__ __volatile__ ("machhwu 17, 14, 15"); 3379 } 3380 3381 static void test_machhwuo (void) 3382 { 3383 __asm__ __volatile__ ("machhwuo 17, 14, 15"); 3384 } 3385 3386 static void test_maclhw (void) 3387 { 3388 __asm__ __volatile__ ("maclhw 17, 14, 15"); 3389 } 3390 3391 static void test_maclhwo (void) 3392 { 3393 __asm__ __volatile__ ("maclhwo 17, 14, 15"); 3394 } 3395 3396 static void test_maclhws (void) 3397 { 3398 __asm__ __volatile__ ("maclhws 17, 14, 15"); 3399 } 3400 3401 static void test_maclhwso (void) 3402 { 3403 __asm__ __volatile__ ("maclhwso 17, 14, 15"); 3404 } 3405 3406 static void test_maclhwsu (void) 3407 { 3408 __asm__ __volatile__ ("maclhwsu 17, 14, 15"); 3409 } 3410 3411 static void test_maclhwsuo (void) 3412 { 3413 __asm__ __volatile__ ("maclhwsuo 17, 14, 15"); 3414 } 3415 3416 static void test_maclhwu (void) 3417 { 3418 __asm__ __volatile__ ("maclhwu 17, 14, 15"); 3419 } 3420 3421 static void test_maclhwuo (void) 3422 { 3423 __asm__ __volatile__ ("maclhwuo 17, 14, 15"); 3424 } 3425 3426 static void test_mulchw (void) 3427 { 3428 __asm__ __volatile__ ("mulchw 17, 14, 15"); 3429 } 3430 3431 static void test_mulchwu (void) 3432 { 3433 __asm__ __volatile__ ("mulchwu 17, 14, 15"); 3434 } 3435 3436 static void test_mulhhw (void) 3437 { 3438 __asm__ __volatile__ ("mulhhw 17, 14, 15"); 3439 } 3440 3441 static void test_mulhhwu (void) 3442 { 3443 __asm__ __volatile__ ("mulhhwu 17, 14, 15"); 3444 } 3445 3446 static void test_mullhw (void) 3447 { 3448 __asm__ __volatile__ ("mullhw 17, 14, 15"); 3449 } 3450 3451 static void test_mullhwu (void) 3452 { 3453 __asm__ __volatile__ ("mullhwu 17, 14, 15"); 3454 } 3455 3456 static void test_nmacchw (void) 3457 { 3458 __asm__ __volatile__ ("nmacchw 17, 14, 15"); 3459 } 3460 3461 static void test_nmacchwo (void) 3462 { 3463 __asm__ __volatile__ ("nmacchwo 17, 14, 15"); 3464 } 3465 3466 static void test_nmacchws (void) 3467 { 3468 __asm__ __volatile__ ("nmacchws 17, 14, 15"); 3469 } 3470 3471 static void test_nmacchwso (void) 3472 { 3473 __asm__ __volatile__ ("nmacchwso 17, 14, 15"); 3474 } 3475 3476 static void test_nmachhw (void) 3477 { 3478 __asm__ __volatile__ ("nmachhw 17, 14, 15"); 3479 } 3480 3481 static void test_nmachhwo (void) 3482 { 3483 __asm__ __volatile__ ("nmachhwo 17, 14, 15"); 3484 } 3485 3486 static void test_nmachhws (void) 3487 { 3488 __asm__ __volatile__ ("nmachhws 17, 14, 15"); 3489 } 3490 3491 static void test_nmachhwso (void) 3492 { 3493 __asm__ __volatile__ ("nmachhwso 17, 14, 15"); 3494 } 3495 3496 static void test_nmaclhw (void) 3497 { 3498 __asm__ __volatile__ ("nmaclhw 17, 14, 15"); 3499 } 3500 3501 static void test_nmaclhwo (void) 3502 { 3503 __asm__ __volatile__ ("nmaclhwo 17, 14, 15"); 3504 } 3505 3506 static void test_nmaclhws (void) 3507 { 3508 __asm__ __volatile__ ("nmaclhws 17, 14, 15"); 3509 } 3510 3511 static void test_nmaclhwso (void) 3512 { 3513 __asm__ __volatile__ ("nmaclhwso 17, 14, 15"); 3514 } 3515 3516 static test_t tests_p4m_ops_two[] = { 3517 { &test_macchw , " macchw", }, 3518 { &test_macchwo , " macchwo", }, 3519 { &test_macchws , " macchws", }, 3520 { &test_macchwso , " macchwso", }, 3521 { &test_macchwsu , " macchwsu", }, 3522 { &test_macchwsuo , " macchwsuo", }, 3523 { &test_macchwu , " macchwu", }, 3524 { &test_macchwuo , " macchwuo", }, 3525 { &test_machhw , " machhw", }, 3526 { &test_machhwo , " machhwo", }, 3527 { &test_machhws , " machhws", }, 3528 { &test_machhwso , " machhwso", }, 3529 { &test_machhwsu , " machhwsu", }, 3530 { &test_machhwsuo , " machhwsuo", }, 3531 { &test_machhwu , " machhwu", }, 3532 { &test_machhwuo , " machhwuo", }, 3533 { &test_maclhw , " maclhw", }, 3534 { &test_maclhwo , " maclhwo", }, 3535 { &test_maclhws , " maclhws", }, 3536 { &test_maclhwso , " maclhwso", }, 3537 { &test_maclhwsu , " maclhwsu", }, 3538 { &test_maclhwsuo , " maclhwsuo", }, 3539 { &test_maclhwu , " maclhwu", }, 3540 { &test_maclhwuo , " maclhwuo", }, 3541 { &test_mulchw , " mulchw", }, 3542 { &test_mulchwu , " mulchwu", }, 3543 { &test_mulhhw , " mulhhw", }, 3544 { &test_mulhhwu , " mulhhwu", }, 3545 { &test_mullhw , " mullhw", }, 3546 { &test_mullhwu , " mullhwu", }, 3547 { &test_nmacchw , " nmacchw", }, 3548 { &test_nmacchwo , " nmacchwo", }, 3549 { &test_nmacchws , " nmacchws", }, 3550 { &test_nmacchwso , " nmacchwso", }, 3551 { &test_nmachhw , " nmachhw", }, 3552 { &test_nmachhwo , " nmachhwo", }, 3553 { &test_nmachhws , " nmachhws", }, 3554 { &test_nmachhwso , " nmachhwso", }, 3555 { &test_nmaclhw , " nmaclhw", }, 3556 { &test_nmaclhwo , " nmaclhwo", }, 3557 { &test_nmaclhws , " nmaclhws", }, 3558 { &test_nmaclhwso , " nmaclhwso", }, 3559 { NULL, NULL, }, 3560 }; 3561 #endif /* defined (IS_PPC405) */ 3562 3563 #if defined (IS_PPC405) 3564 static void test_macchw_ (void) 3565 { 3566 __asm__ __volatile__ ("macchw. 17, 14, 15"); 3567 } 3568 3569 static void test_macchwo_ (void) 3570 { 3571 __asm__ __volatile__ ("macchwo. 17, 14, 15"); 3572 } 3573 3574 static void test_macchws_ (void) 3575 { 3576 __asm__ __volatile__ ("macchws. 17, 14, 15"); 3577 } 3578 3579 static void test_macchwso_ (void) 3580 { 3581 __asm__ __volatile__ ("macchwso. 17, 14, 15"); 3582 } 3583 3584 static void test_macchwsu_ (void) 3585 { 3586 __asm__ __volatile__ ("macchwsu. 17, 14, 15"); 3587 } 3588 3589 static void test_macchwsuo_ (void) 3590 { 3591 __asm__ __volatile__ ("macchwsuo. 17, 14, 15"); 3592 } 3593 3594 static void test_macchwu_ (void) 3595 { 3596 __asm__ __volatile__ ("macchwu. 17, 14, 15"); 3597 } 3598 3599 static void test_macchwuo_ (void) 3600 { 3601 __asm__ __volatile__ ("macchwuo. 17, 14, 15"); 3602 } 3603 3604 static void test_machhw_ (void) 3605 { 3606 __asm__ __volatile__ ("machhw. 17, 14, 15"); 3607 } 3608 3609 static void test_machhwo_ (void) 3610 { 3611 __asm__ __volatile__ ("machhwo. 17, 14, 15"); 3612 } 3613 3614 static void test_machhws_ (void) 3615 { 3616 __asm__ __volatile__ ("machhws. 17, 14, 15"); 3617 } 3618 3619 static void test_machhwso_ (void) 3620 { 3621 __asm__ __volatile__ ("machhwso. 17, 14, 15"); 3622 } 3623 3624 static void test_machhwsu_ (void) 3625 { 3626 __asm__ __volatile__ ("machhwsu. 17, 14, 15"); 3627 } 3628 3629 static void test_machhwsuo_ (void) 3630 { 3631 __asm__ __volatile__ ("machhwsuo. 17, 14, 15"); 3632 } 3633 3634 static void test_machhwu_ (void) 3635 { 3636 __asm__ __volatile__ ("machhwu. 17, 14, 15"); 3637 } 3638 3639 static void test_machhwuo_ (void) 3640 { 3641 __asm__ __volatile__ ("machhwuo. 17, 14, 15"); 3642 } 3643 3644 static void test_maclhw_ (void) 3645 { 3646 __asm__ __volatile__ ("maclhw. 17, 14, 15"); 3647 } 3648 3649 static void test_maclhwo_ (void) 3650 { 3651 __asm__ __volatile__ ("maclhwo. 17, 14, 15"); 3652 } 3653 3654 static void test_maclhws_ (void) 3655 { 3656 __asm__ __volatile__ ("maclhws. 17, 14, 15"); 3657 } 3658 3659 static void test_maclhwso_ (void) 3660 { 3661 __asm__ __volatile__ ("maclhwso. 17, 14, 15"); 3662 } 3663 3664 static void test_maclhwsu_ (void) 3665 { 3666 __asm__ __volatile__ ("maclhwsu. 17, 14, 15"); 3667 } 3668 3669 static void test_maclhwsuo_ (void) 3670 { 3671 __asm__ __volatile__ ("maclhwsuo. 17, 14, 15"); 3672 } 3673 3674 static void test_maclhwu_ (void) 3675 { 3676 __asm__ __volatile__ ("maclhwu. 17, 14, 15"); 3677 } 3678 3679 static void test_maclhwuo_ (void) 3680 { 3681 __asm__ __volatile__ ("maclhwuo. 17, 14, 15"); 3682 } 3683 3684 static void test_mulchw_ (void) 3685 { 3686 __asm__ __volatile__ ("mulchw. 17, 14, 15"); 3687 } 3688 3689 static void test_mulchwu_ (void) 3690 { 3691 __asm__ __volatile__ ("mulchwu. 17, 14, 15"); 3692 } 3693 3694 static void test_mulhhw_ (void) 3695 { 3696 __asm__ __volatile__ ("mulhhw. 17, 14, 15"); 3697 } 3698 3699 static void test_mulhhwu_ (void) 3700 { 3701 __asm__ __volatile__ ("mulhhwu. 17, 14, 15"); 3702 } 3703 3704 static void test_mullhw_ (void) 3705 { 3706 __asm__ __volatile__ ("mullhw. 17, 14, 15"); 3707 } 3708 3709 static void test_mullhwu_ (void) 3710 { 3711 __asm__ __volatile__ ("mullhwu. 17, 14, 15"); 3712 } 3713 3714 static void test_nmacchw_ (void) 3715 { 3716 __asm__ __volatile__ ("nmacchw. 17, 14, 15"); 3717 } 3718 3719 static void test_nmacchwo_ (void) 3720 { 3721 __asm__ __volatile__ ("nmacchwo. 17, 14, 15"); 3722 } 3723 3724 static void test_nmacchws_ (void) 3725 { 3726 __asm__ __volatile__ ("nmacchws. 17, 14, 15"); 3727 } 3728 3729 static void test_nmacchwso_ (void) 3730 { 3731 __asm__ __volatile__ ("nmacchwso. 17, 14, 15"); 3732 } 3733 3734 static void test_nmachhw_ (void) 3735 { 3736 __asm__ __volatile__ ("nmachhw. 17, 14, 15"); 3737 } 3738 3739 static void test_nmachhwo_ (void) 3740 { 3741 __asm__ __volatile__ ("nmachhwo. 17, 14, 15"); 3742 } 3743 3744 static void test_nmachhws_ (void) 3745 { 3746 __asm__ __volatile__ ("nmachhws. 17, 14, 15"); 3747 } 3748 3749 static void test_nmachhwso_ (void) 3750 { 3751 __asm__ __volatile__ ("nmachhwso. 17, 14, 15"); 3752 } 3753 3754 static void test_nmaclhw_ (void) 3755 { 3756 __asm__ __volatile__ ("nmaclhw. 17, 14, 15"); 3757 } 3758 3759 static void test_nmaclhwo_ (void) 3760 { 3761 __asm__ __volatile__ ("nmaclhwo. 17, 14, 15"); 3762 } 3763 3764 static void test_nmaclhws_ (void) 3765 { 3766 __asm__ __volatile__ ("nmaclhws. 17, 14, 15"); 3767 } 3768 3769 static void test_nmaclhwso_ (void) 3770 { 3771 __asm__ __volatile__ ("nmaclhwso. 17, 14, 15"); 3772 } 3773 3774 static test_t tests_p4mc_ops_two[] = { 3775 { &test_macchw_ , " macchw.", }, 3776 { &test_macchwo_ , " macchwo.", }, 3777 { &test_macchws_ , " macchws.", }, 3778 { &test_macchwso_ , " macchwso.", }, 3779 { &test_macchwsu_ , " macchwsu.", }, 3780 { &test_macchwsuo_ , " macchwsuo.", }, 3781 { &test_macchwu_ , " macchwu.", }, 3782 { &test_macchwuo_ , " macchwuo.", }, 3783 { &test_machhw_ , " machhw.", }, 3784 { &test_machhwo_ , " machhwo.", }, 3785 { &test_machhws_ , " machhws.", }, 3786 { &test_machhwso_ , " machhwso.", }, 3787 { &test_machhwsu_ , " machhwsu.", }, 3788 { &test_machhwsuo_ , " machhwsuo.", }, 3789 { &test_machhwu_ , " machhwu.", }, 3790 { &test_machhwuo_ , " machhwuo.", }, 3791 { &test_maclhw_ , " maclhw.", }, 3792 { &test_maclhwo_ , " maclhwo.", }, 3793 { &test_maclhws_ , " maclhws.", }, 3794 { &test_maclhwso_ , " maclhwso.", }, 3795 { &test_maclhwsu_ , " maclhwsu.", }, 3796 { &test_maclhwsuo_ , " maclhwsuo.", }, 3797 { &test_maclhwu_ , " maclhwu.", }, 3798 { &test_maclhwuo_ , " maclhwuo.", }, 3799 { &test_mulchw_ , " mulchw.", }, 3800 { &test_mulchwu_ , " mulchwu.", }, 3801 { &test_mulhhw_ , " mulhhw.", }, 3802 { &test_mulhhwu_ , " mulhhwu.", }, 3803 { &test_mullhw_ , " mullhw.", }, 3804 { &test_mullhwu_ , " mullhwu.", }, 3805 { &test_nmacchw_ , " nmacchw.", }, 3806 { &test_nmacchwo_ , " nmacchwo.", }, 3807 { &test_nmacchws_ , " nmacchws.", }, 3808 { &test_nmacchwso_ , " nmacchwso.", }, 3809 { &test_nmachhw_ , " nmachhw.", }, 3810 { &test_nmachhwo_ , " nmachhwo.", }, 3811 { &test_nmachhws_ , " nmachhws.", }, 3812 { &test_nmachhwso_ , " nmachhwso.", }, 3813 { &test_nmaclhw_ , " nmaclhw.", }, 3814 { &test_nmaclhwo_ , " nmaclhwo.", }, 3815 { &test_nmaclhws_ , " nmaclhws.", }, 3816 { &test_nmaclhwso_ , " nmaclhwso.", }, 3817 { NULL, NULL, }, 3818 }; 3819 #endif /* defined (IS_PPC405) */ 3820 3821 static test_table_t all_tests[] = { 3822 { 3823 tests_ia_ops_two , 3824 "PPC integer arith insns with two args", 3825 0x00010102, 3826 }, 3827 { 3828 tests_iar_ops_two , 3829 "PPC integer arith insns with two args with flags update", 3830 0x01010102, 3831 }, 3832 { 3833 tests_iac_ops_two , 3834 "PPC integer arith insns with two args and carry", 3835 0x02010102, 3836 }, 3837 { 3838 tests_iacr_ops_two , 3839 "PPC integer arith insns with two args and carry with flags update", 3840 0x03010102, 3841 }, 3842 { 3843 tests_il_ops_two , 3844 "PPC integer logical insns with two args", 3845 0x00010202, 3846 }, 3847 { 3848 tests_ilr_ops_two , 3849 "PPC integer logical insns with two args with flags update", 3850 0x01010202, 3851 }, 3852 { 3853 tests_icr_ops_two , 3854 "PPC integer compare insns (two args)", 3855 0x01010304, 3856 }, 3857 { 3858 tests_icr_ops_two_i16 , 3859 "PPC integer compare with immediate insns (two args)", 3860 0x01010305, 3861 }, 3862 { 3863 tests_ia_ops_two_i16 , 3864 "PPC integer arith insns\n with one register + one 16 bits immediate args", 3865 0x00010106, 3866 }, 3867 { 3868 tests_iar_ops_two_i16 , 3869 "PPC integer arith insns\n with one register + one 16 bits immediate args with flags update", 3870 0x01010106, 3871 }, 3872 { 3873 tests_il_ops_two_i16 , 3874 "PPC integer logical insns\n with one register + one 16 bits immediate args", 3875 0x00010206, 3876 }, 3877 { 3878 tests_ilr_ops_two_i16 , 3879 "PPC integer logical insns\n with one register + one 16 bits immediate args with flags update", 3880 0x01010206, 3881 }, 3882 { 3883 tests_crl_ops_two , 3884 "PPC condition register logical insns - two operands", 3885 0x01010202, 3886 }, 3887 { 3888 tests_iac_ops_one , 3889 "PPC integer arith insns with one arg and carry", 3890 0x02010101, 3891 }, 3892 { 3893 tests_iacr_ops_one , 3894 "PPC integer arith insns with one arg and carry with flags update", 3895 0x03010101, 3896 }, 3897 { 3898 tests_il_ops_one , 3899 "PPC integer logical insns with one arg", 3900 0x00010201, 3901 }, 3902 { 3903 tests_ilr_ops_one , 3904 "PPC integer logical insns with one arg with flags update", 3905 0x01010201, 3906 }, 3907 { 3908 tests_il_ops_spe , 3909 "PPC logical insns with special forms", 3910 0x00010207, 3911 }, 3912 { 3913 tests_ilr_ops_spe , 3914 "PPC logical insns with special forms with flags update", 3915 0x01010207, 3916 }, 3917 { 3918 tests_ild_ops_two_i16 , 3919 "PPC integer load insns\n with one register + one 16 bits immediate args with flags update", 3920 0x00010508, 3921 }, 3922 { 3923 tests_ild_ops_two , 3924 "PPC integer load insns with two register args", 3925 0x00010509, 3926 }, 3927 { 3928 tests_ist_ops_three_i16, 3929 "PPC integer store insns\n with one register + one 16 bits immediate args with flags update", 3930 0x0001050a, 3931 }, 3932 { 3933 tests_ist_ops_three , 3934 "PPC integer store insns with three register args", 3935 0x0001050b, 3936 }, 3937 #if !defined (NO_FLOAT) 3938 { 3939 tests_fa_ops_three , 3940 "PPC floating point arith insns with three args", 3941 0x00020103, 3942 }, 3943 #endif /* !defined (NO_FLOAT) */ 3944 #if !defined (NO_FLOAT) 3945 { 3946 tests_far_ops_three , 3947 "PPC floating point arith insns\n with three args with flags update", 3948 0x01020103, 3949 }, 3950 #endif /* !defined (NO_FLOAT) */ 3951 #if !defined (NO_FLOAT) 3952 { 3953 tests_fa_ops_two , 3954 "PPC floating point arith insns with two args", 3955 0x00020102, 3956 }, 3957 #endif /* !defined (NO_FLOAT) */ 3958 #if !defined (NO_FLOAT) 3959 { 3960 tests_far_ops_two , 3961 "PPC floating point arith insns\n with two args with flags update", 3962 0x01020102, 3963 }, 3964 #endif /* !defined (NO_FLOAT) */ 3965 #if !defined (NO_FLOAT) 3966 { 3967 tests_fcr_ops_two , 3968 "PPC floating point compare insns (two args)", 3969 0x01020304, 3970 }, 3971 #endif /* !defined (NO_FLOAT) */ 3972 #if !defined (NO_FLOAT) 3973 { 3974 tests_fa_ops_one , 3975 "PPC floating point arith insns with one arg", 3976 0x00020101, 3977 }, 3978 #endif /* !defined (NO_FLOAT) */ 3979 #if !defined (NO_FLOAT) 3980 { 3981 tests_far_ops_one , 3982 "PPC floating point arith insns\n with one arg with flags update", 3983 0x01020101, 3984 }, 3985 #endif /* !defined (NO_FLOAT) */ 3986 #if !defined (NO_FLOAT) 3987 { 3988 tests_fl_ops_spe , 3989 "PPC floating point status register manipulation insns", 3990 0x00020207, 3991 }, 3992 #endif /* !defined (NO_FLOAT) */ 3993 #if !defined (NO_FLOAT) 3994 { 3995 tests_flr_ops_spe , 3996 "PPC floating point status register manipulation insns\n with flags update", 3997 0x01020207, 3998 }, 3999 #endif /* !defined (NO_FLOAT) */ 4000 #if !defined (NO_FLOAT) 4001 { 4002 tests_fld_ops_two_i16 , 4003 "PPC float load insns\n with one register + one 16 bits immediate args with flags update", 4004 0x00020508, 4005 }, 4006 #endif /* !defined (NO_FLOAT) */ 4007 #if !defined (NO_FLOAT) 4008 { 4009 tests_fld_ops_two , 4010 "PPC float load insns with two register args", 4011 0x00020509, 4012 }, 4013 #endif /* !defined (NO_FLOAT) */ 4014 #if !defined (NO_FLOAT) 4015 { 4016 tests_fst_ops_three_i16, 4017 "PPC float store insns\n with one register + one 16 bits immediate args with flags update", 4018 0x0002050a, 4019 }, 4020 #endif /* !defined (NO_FLOAT) */ 4021 #if !defined (NO_FLOAT) 4022 { 4023 tests_fst_ops_three , 4024 "PPC float store insns with three register args", 4025 0x0002050b, 4026 }, 4027 #endif /* !defined (NO_FLOAT) */ 4028 #if defined (HAS_ALTIVEC) 4029 { 4030 tests_aa_ops_three , 4031 "PPC altivec integer arith insns with three args", 4032 0x00040103, 4033 }, 4034 #endif /* defined (HAS_ALTIVEC) */ 4035 #if defined (HAS_ALTIVEC) 4036 { 4037 tests_al_ops_three , 4038 "PPC altivec integer logical insns with three args", 4039 0x00040203, 4040 }, 4041 #endif /* defined (HAS_ALTIVEC) */ 4042 #if defined (HAS_ALTIVEC) 4043 { 4044 tests_aa_ops_two , 4045 "PPC altivec integer arith insns with two args", 4046 0x00040102, 4047 }, 4048 #endif /* defined (HAS_ALTIVEC) */ 4049 #if defined (HAS_ALTIVEC) 4050 { 4051 tests_al_ops_two , 4052 "PPC altivec integer logical insns with two args", 4053 0x00040202, 4054 }, 4055 #endif /* defined (HAS_ALTIVEC) */ 4056 #if defined (HAS_ALTIVEC) 4057 { 4058 tests_al_ops_one , 4059 "PPC altivec integer logical insns with one arg", 4060 0x00040201, 4061 }, 4062 #endif /* defined (HAS_ALTIVEC) */ 4063 #if defined (HAS_ALTIVEC) 4064 { 4065 tests_ac_ops_two , 4066 "Altivec integer compare insns", 4067 0x00040302, 4068 }, 4069 #endif /* defined (HAS_ALTIVEC) */ 4070 #if defined (HAS_ALTIVEC) 4071 { 4072 tests_acr_ops_two , 4073 "Altivec integer compare insns with flags update", 4074 0x01040302, 4075 }, 4076 #endif /* defined (HAS_ALTIVEC) */ 4077 #if defined (HAS_ALTIVEC) 4078 { 4079 tests_av_int_ops_spe , 4080 "Altivec integer special insns", 4081 0x00040207, 4082 }, 4083 #endif /* defined (HAS_ALTIVEC) */ 4084 #if defined (HAS_ALTIVEC) 4085 { 4086 tests_ald_ops_two , 4087 "Altivec load insns with two register args", 4088 0x00040509, 4089 }, 4090 #endif /* defined (HAS_ALTIVEC) */ 4091 #if defined (HAS_ALTIVEC) 4092 { 4093 tests_ast_ops_three , 4094 "Altivec store insns with three register args", 4095 0x0004050b, 4096 }, 4097 #endif /* defined (HAS_ALTIVEC) */ 4098 #if defined (HAS_ALTIVEC) 4099 { 4100 tests_afa_ops_three , 4101 "Altivec floating point arith insns with three args", 4102 0x00050103, 4103 }, 4104 #endif /* defined (HAS_ALTIVEC) */ 4105 #if defined (HAS_ALTIVEC) 4106 { 4107 tests_afa_ops_two , 4108 "Altivec floating point arith insns with two args", 4109 0x00050102, 4110 }, 4111 #endif /* defined (HAS_ALTIVEC) */ 4112 #if defined (HAS_ALTIVEC) 4113 { 4114 tests_afa_ops_one , 4115 "Altivec floating point arith insns with one arg", 4116 0x00050101, 4117 }, 4118 #endif /* defined (HAS_ALTIVEC) */ 4119 #if defined (HAS_ALTIVEC) 4120 { 4121 tests_afc_ops_two , 4122 "Altivec floating point compare insns", 4123 0x00050302, 4124 }, 4125 #endif /* defined (HAS_ALTIVEC) */ 4126 #if defined (HAS_ALTIVEC) 4127 { 4128 tests_afcr_ops_two , 4129 "Altivec floating point compare insns with flags update", 4130 0x01050302, 4131 }, 4132 #endif /* defined (HAS_ALTIVEC) */ 4133 #if defined (HAS_ALTIVEC) 4134 { 4135 tests_av_float_ops_spe, 4136 "Altivec float special insns", 4137 0x00050207, 4138 }, 4139 #endif /* defined (HAS_ALTIVEC) */ 4140 #if defined (IS_PPC405) 4141 { 4142 tests_p4m_ops_two , 4143 "PPC 405 mac insns with three args", 4144 0x00030102, 4145 }, 4146 #endif /* defined (IS_PPC405) */ 4147 #if defined (IS_PPC405) 4148 { 4149 tests_p4mc_ops_two , 4150 "PPC 405 mac insns with three args with flags update", 4151 0x01030102, 4152 }, 4153 #endif /* defined (IS_PPC405) */ 4154 { NULL, NULL, 0x00000000, }, 4155 }; 4156 4157 /* -------------- END #include "ops-ppc.c" -------------- */ 4158 4159 static int verbose = 0; 4160 static int arg_list_size = 0; 4161 4162 static double *fargs = NULL; 4163 static int nb_fargs = 0; 4164 static int nb_normal_fargs = 0; 4165 static HWord_t *iargs = NULL; 4166 static int nb_iargs = 0; 4167 static uint16_t *ii16 = NULL; 4168 static int nb_ii16 = 0; 4169 4170 #if defined (HAS_ALTIVEC) 4171 static vector unsigned int* viargs = NULL; 4172 static int nb_viargs = 0; 4173 static vector float* vfargs = NULL; 4174 static int nb_vfargs = 0; 4175 4176 //#define TEST_VSCR_SAT 4177 #endif 4178 4179 static inline void register_farg (void *farg, 4180 int s, uint16_t _exp, uint64_t mant) 4181 { 4182 uint64_t tmp; 4183 4184 tmp = ((uint64_t)s << 63) | ((uint64_t)_exp << 52) | mant; 4185 *(uint64_t *)farg = tmp; 4186 #ifndef __powerpc64__ 4187 AB_DPRINTF("%d %03x %013llx => %016llx %0e\n", 4188 #else 4189 AB_DPRINTF("%d %03x %013lx => %016lx %0e\n", 4190 #endif 4191 s, _exp, mant, *(uint64_t *)farg, *(double *)farg); 4192 } 4193 4194 static void build_fargs_table (void) 4195 { 4196 /* Double precision: 4197 * Sign goes from zero to one (1 bit) 4198 * Exponent goes from 0 to ((1 << 12) - 1) (11 bits) 4199 * Mantissa goes from 1 to ((1 << 52) - 1) (52 bits) 4200 * + special values: 4201 * +0.0 : 0 0x000 0x0000000000000 => 0x0000000000000000 4202 * -0.0 : 1 0x000 0x0000000000000 => 0x8000000000000000 4203 * +infinity : 0 0x7FF 0x0000000000000 => 0x7FF0000000000000 4204 * -infinity : 1 0x7FF 0x0000000000000 => 0xFFF0000000000000 4205 * +QNaN : 0 0x7FF 0x7FFFFFFFFFFFF => 0x7FF7FFFFFFFFFFFF 4206 * -QNaN : 1 0x7FF 0x7FFFFFFFFFFFF => 0xFFF7FFFFFFFFFFFF 4207 * +SNaN : 0 0x7FF 0x8000000000000 => 0x7FF8000000000000 4208 * -SNaN : 1 0x7FF 0x8000000000000 => 0xFFF8000000000000 4209 * (8 values) 4210 4211 * Ref only: 4212 * Single precision 4213 * Sign: 1 bit 4214 * Exponent: 8 bits 4215 * Mantissa: 23 bits 4216 * +0.0 : 0 0x00 0x000000 => 0x00000000 4217 * -0.0 : 1 0x00 0x000000 => 0x80000000 4218 * +infinity : 0 0xFF 0x000000 => 0x7F800000 4219 * -infinity : 1 0xFF 0x000000 => 0xFF800000 4220 * +QNaN : 0 0xFF 0x3FFFFF => 0x7FBFFFFF 4221 * -QNaN : 1 0xFF 0x3FFFFF => 0xFFBFFFFF 4222 * +SNaN : 0 0xFF 0x400000 => 0x7FC00000 4223 * -SNaN : 1 0xFF 0x400000 => 0xFFC00000 4224 */ 4225 uint64_t mant; 4226 uint16_t _exp, e0, e1; 4227 int s; 4228 int i=0; 4229 4230 /* Note: VEX isn't so hot with denormals, so don't bother 4231 testing them: set _exp > 0 4232 */ 4233 4234 if ( arg_list_size == 1 ) { // Large 4235 fargs = malloc(200 * sizeof(double)); 4236 for (s=0; s<2; s++) { 4237 for (e0=0; e0<2; e0++) { 4238 for (e1=0x001; ; e1 = ((e1 + 1) << 2) + 6) { 4239 if (e1 >= 0x400) 4240 e1 = 0x3fe; 4241 _exp = (e0 << 10) | e1; 4242 for (mant = 0x0000000000001ULL; mant < (1ULL << 52); 4243 /* Add 'random' bits */ 4244 mant = ((mant + 0x4A6) << 13) + 0x359) { 4245 register_farg(&fargs[i++], s, _exp, mant); 4246 } 4247 if (e1 == 0x3fe) 4248 break; 4249 } 4250 } 4251 } 4252 } else { // Default 4253 fargs = malloc(16 * sizeof(double)); 4254 for (s=0; s<2; s++) { // x2 4255 // for (e0=0; e0<2; e0++) { 4256 for (e1=0x001; ; e1 = ((e1 + 1) << 13) + 7) { // x2 4257 // for (e1=0x001; ; e1 = ((e1 + 1) << 5) + 7) { // x3 4258 if (e1 >= 0x400) 4259 e1 = 0x3fe; 4260 // _exp = (e0 << 10) | e1; 4261 _exp = e1; 4262 for (mant = 0x0000000000001ULL; mant < (1ULL << 52); 4263 /* Add 'random' bits */ 4264 mant = ((mant + 0x4A6) << 29) + 0x359) { // x2 4265 register_farg(&fargs[i++], s, _exp, mant); 4266 } 4267 if (e1 == 0x3fe) 4268 break; 4269 } 4270 // } 4271 } 4272 } 4273 4274 /* To iterate over non-special values only */ 4275 nb_normal_fargs = i; 4276 4277 4278 /* Special values */ 4279 /* +0.0 : 0 0x000 0x0000000000000 */ 4280 s = 0; 4281 _exp = 0x000; 4282 mant = 0x0000000000000ULL; 4283 register_farg(&fargs[i++], s, _exp, mant); 4284 /* -0.0 : 1 0x000 0x0000000000000 */ 4285 s = 1; 4286 _exp = 0x000; 4287 mant = 0x0000000000000ULL; 4288 register_farg(&fargs[i++], s, _exp, mant); 4289 /* +infinity : 0 0x7FF 0x0000000000000 */ 4290 s = 0; 4291 _exp = 0x7FF; 4292 mant = 0x0000000000000ULL; 4293 register_farg(&fargs[i++], s, _exp, mant); 4294 /* -infinity : 1 0x7FF 0x0000000000000 */ 4295 s = 1; 4296 _exp = 0x7FF; 4297 mant = 0x0000000000000ULL; 4298 register_farg(&fargs[i++], s, _exp, mant); 4299 /* +QNaN : 0 0x7FF 0x7FFFFFFFFFFFF */ 4300 s = 0; 4301 _exp = 0x7FF; 4302 mant = 0x7FFFFFFFFFFFFULL; 4303 register_farg(&fargs[i++], s, _exp, mant); 4304 /* -QNaN : 1 0x7FF 0x7FFFFFFFFFFFF */ 4305 s = 1; 4306 _exp = 0x7FF; 4307 mant = 0x7FFFFFFFFFFFFULL; 4308 register_farg(&fargs[i++], s, _exp, mant); 4309 /* +SNaN : 0 0x7FF 0x8000000000000 */ 4310 s = 0; 4311 _exp = 0x7FF; 4312 mant = 0x8000000000000ULL; 4313 register_farg(&fargs[i++], s, _exp, mant); 4314 /* -SNaN : 1 0x7FF 0x8000000000000 */ 4315 s = 1; 4316 _exp = 0x7FF; 4317 mant = 0x8000000000000ULL; 4318 register_farg(&fargs[i++], s, _exp, mant); 4319 AB_DPRINTF("Registered %d fargs values\n", i); 4320 4321 nb_fargs = i; 4322 } 4323 4324 static void build_iargs_table (void) 4325 { 4326 uint64_t tmp; 4327 int i=0; 4328 4329 #ifndef __powerpc64__ 4330 if (arg_list_size == 1) { // Large 4331 iargs = malloc(400 * sizeof(HWord_t)); 4332 for (tmp=0; ; tmp = tmp + 1 + (tmp >> 1)) { 4333 if (tmp >= 0x100000000ULL) 4334 tmp = 0xFFFFFFFF; 4335 iargs[i++] = (HWord_t)tmp; 4336 AB_DPRINTF("val %08x\n", (HWord_t)tmp); 4337 if (tmp == 0xFFFFFFFF) 4338 break; 4339 } 4340 } else { // Default 4341 iargs = malloc(10 * sizeof(HWord_t)); 4342 // for (tmp = 0; ; tmp = 71*tmp + 1 + (tmp>>1)) { // gives 8 4343 // for (tmp = 0; ; tmp = 100000*tmp + 1 + (tmp>>1)) { // gives 4 4344 for (tmp=0; ; tmp = 999999*tmp + 999999) { // gives 3 4345 if (tmp >= 0x100000000ULL) 4346 tmp = 0xFFFFFFFF; 4347 iargs[i++] = (HWord_t)tmp; 4348 AB_DPRINTF("val %08x\n", (HWord_t)tmp); 4349 if (tmp == 0xFFFFFFFF) 4350 break; 4351 } 4352 } 4353 #else 4354 if (arg_list_size == 1) { // Large 4355 iargs = malloc(800 * sizeof(HWord_t)); 4356 for (tmp=0; ; tmp = 2*tmp + 1 + (tmp >> 2)) { 4357 if ((long)tmp < 0 ) 4358 tmp = 0xFFFFFFFFFFFFFFFFULL; 4359 iargs[i++] = tmp; 4360 AB_DPRINTF("val %016lx\n", tmp); 4361 if (tmp == 0xFFFFFFFFFFFFFFFFULL) 4362 break; 4363 } 4364 } else { // Default 4365 iargs = malloc(20 * sizeof(HWord_t)); 4366 // for (tmp=0; ; tmp = 9999*tmp + 999999) { // gives 6 4367 for (tmp = 0; ; tmp = 123456789*tmp + 123456789999) { // gives 3 4368 if ((long)tmp < 0 ) 4369 tmp = 0xFFFFFFFFFFFFFFFFULL; 4370 iargs[i++] = tmp; 4371 AB_DPRINTF("val %016lx\n", tmp); 4372 if (tmp == 0xFFFFFFFFFFFFFFFFULL) 4373 break; 4374 } 4375 } 4376 #endif // #ifndef __powerpc64__ 4377 4378 AB_DPRINTF("Registered %d iargs values\n", i); 4379 nb_iargs = i; 4380 } 4381 4382 static void build_ii16_table (void) 4383 { 4384 uint32_t tmp; 4385 int i=0; 4386 4387 if (arg_list_size == 1) { // Large 4388 ii16 = malloc(200 * sizeof(uint32_t)); 4389 for (tmp=0; ; tmp = tmp + 1 + (tmp >> 2)) { 4390 if (tmp >= 0x10000) 4391 tmp = 0xFFFF; 4392 ii16[i++] = tmp; 4393 AB_DPRINTF("val %04x\n", tmp); 4394 if (tmp == 0xFFFF) 4395 break; 4396 } 4397 } else { // Default 4398 ii16 = malloc(10 * sizeof(uint32_t)); 4399 for (tmp=0; ; tmp = 999*tmp + 999) { // gives 3 4400 if (tmp >= 0x10000) 4401 tmp = 0xFFFF; 4402 ii16[i++] = tmp; 4403 AB_DPRINTF("val %04x\n", tmp); 4404 if (tmp == 0xFFFF) 4405 break; 4406 } 4407 } 4408 AB_DPRINTF("Registered %d ii16 values\n", i); 4409 nb_ii16 = i; 4410 } 4411 4412 #if defined (HAS_ALTIVEC) 4413 static void build_viargs_table (void) 4414 { 4415 #if !defined (ALTIVEC_ARGS_LARGE) 4416 unsigned int i=2; 4417 viargs = memalign16(i * sizeof(vector unsigned int)); 4418 viargs[0] = (vector unsigned int) { 0x01020304,0x05060708,0x090A0B0C,0x0E0D0E0F }; 4419 AB_DPRINTF_VEC32x4( viargs[0] ); 4420 viargs[1] = (vector unsigned int) { 0xF1F2F3F4,0xF5F6F7F8,0xF9FAFBFC,0xFEFDFEFF }; 4421 AB_DPRINTF_VEC32x4( viargs[1] ); 4422 #else 4423 unsigned int i,j; 4424 // build from iargs table (large/default already set) 4425 viargs = malloc(nb_iargs * sizeof(vector unsigned int)); 4426 for (i=0; i<nb_iargs; i++) { 4427 j = iargs[i]; 4428 viargs[i] = (vector unsigned int){ j, j*2, j*3, j*4 }; 4429 AB_DPRINTF_VEC32x4( viargs[i] ); 4430 } 4431 #endif 4432 4433 AB_DPRINTF("Registered %d viargs values\n", i); 4434 nb_viargs = i; 4435 } 4436 4437 static inline void register_vfarg (vector float* vfarg, 4438 int s, uint8_t _exp, uint32_t mant) 4439 { 4440 uint32_t tmp; 4441 vector uint32_t* vfargI = (vector uint32_t*)vfarg; 4442 4443 tmp = ((uint64_t)s << 31) | ((uint64_t)_exp << 23) | mant; 4444 *vfargI = (vector uint32_t){ tmp,tmp,tmp,tmp }; 4445 AB_DPRINTF("%d %02x %06x => %08x %0e\n", 4446 s, _exp, mant, *((uint32_t*)&tmp), *(float*)&tmp); 4447 } 4448 4449 static void build_vfargs_table (void) 4450 { 4451 /* Sign goes from zero to one 4452 * Exponent goes from 0 to ((1 << 9) - 1) 4453 * Mantissa goes from 1 to ((1 << 24) - 1) 4454 * + special values: 4455 * +0.0 : 0 0x00 0x000000 => 0x00000000 4456 * -0.0 : 1 0x00 0x000000 => 0x80000000 4457 * +infinity : 0 0xFF 0x000000 => 0x7F800000 4458 * -infinity : 1 0xFF 0x000000 => 0xFF800000 4459 * +SNaN : 0 0xFF 0x7FFFFF (non-zero) => 0x7FFFFFFF 4460 * -SNaN : 1 0xFF 0x7FFFFF (non-zero) => 0xFFFFFFFF 4461 * +QNaN : 0 0xFF 0x3FFFFF (non-zero) => 0x7FBFFFFF 4462 * -QNaN : 1 0xFF 0x3FFFFF (non-zero) => 0xFFBFFFFF 4463 * (8 values) 4464 */ 4465 uint32_t mant; 4466 uint16_t _exp; 4467 int s; 4468 int i=0; 4469 4470 4471 #if !defined (ALTIVEC_ARGS_LARGE) 4472 nb_vfargs = 12; 4473 vfargs = memalign16(nb_vfargs * sizeof(vector float)); 4474 4475 // 4 values: 4476 for (s=0; s<2; s++) { 4477 for (_exp=0x5; ; _exp += 0x9D ) { 4478 if (_exp > 0xDF) 4479 break; 4480 for (mant = 0x3FFFFF; mant < 0x7FFFFF; 4481 mant = /* random */ ((mant + 0x1A6) << 31) + 0x159) { 4482 register_vfarg(&vfargs[i++], s, (uint8_t)_exp, mant); 4483 } 4484 } 4485 } 4486 #else 4487 nb_vfargs = 50; 4488 vfargs = memalign16(nb_vfargs * sizeof(vector float)); 4489 4490 for (s=0; s<2; s++) { 4491 for (_exp=0x0; ; _exp += 0x3F ) { 4492 // for (_exp=0; ; _exp = ((_exp + 1) << 1) + 3) { 4493 if (_exp >= 0xFE) 4494 _exp = 0xFE; 4495 for (mant = 0x0; mant < 0x7FFFFF; 4496 mant = /* random */ ((mant + 0x4A6) << 5) + 0x359) { 4497 register_vfarg(&vfargs[i++], s, (uint8_t)_exp, mant); 4498 } 4499 if (_exp >= 0xFE) 4500 break; 4501 } 4502 } 4503 #endif 4504 4505 /* Special values */ 4506 /* +0.0 : 0 0x00 0x000000 */ 4507 s = 0; 4508 _exp = 0x00; 4509 mant = 0x000000; 4510 register_vfarg(&vfargs[i++], s, _exp, mant); 4511 /* -0.0 : 1 0x00 0x000000 */ 4512 s = 1; 4513 _exp = 0x00; 4514 mant = 0x000000; 4515 register_vfarg(&vfargs[i++], s, _exp, mant); 4516 4517 /* +infinity : 0 0xFF 0x000000 */ 4518 s = 0; 4519 _exp = 0xFF; 4520 mant = 0x000000; 4521 register_vfarg(&vfargs[i++], s, _exp, mant); 4522 /* -infinity : 1 0xFF 0x000000 */ 4523 s = 1; 4524 _exp = 0xFF; 4525 mant = 0x000000; 4526 register_vfarg(&vfargs[i++], s, _exp, mant); 4527 4528 /* NaN: _exponent all 1s, non-zero fraction */ 4529 /* SNaN is a NaN with the most significant fraction bit clear.*/ 4530 /* +SNaN : 0 0xFF 0x7FFFFF */ 4531 s = 0; 4532 _exp = 0xFF; 4533 mant = 0x7FFFFF; 4534 register_vfarg(&vfargs[i++], s, _exp, mant); 4535 /* -SNaN : 1 0xFF 0x7FFFFF */ 4536 s = 1; 4537 _exp = 0xFF; 4538 mant = 0x7FFFFF; 4539 register_vfarg(&vfargs[i++], s, _exp, mant); 4540 4541 /* QNaN is a NaN with the most significant fraction bit set */ 4542 /* +QNaN : 0 0xFF 0x3F0000 */ 4543 s = 0; 4544 _exp = 0xFF; 4545 mant = 0x3FFFFF; 4546 register_vfarg(&vfargs[i++], s, _exp, mant); 4547 /* -QNaN : 1 0xFF 0x3F0000 */ 4548 s = 1; 4549 _exp = 0xFF; 4550 mant = 0x3FFFFF; 4551 register_vfarg(&vfargs[i++], s, _exp, mant); 4552 AB_DPRINTF("Registered %d vfargs values\n", i); 4553 4554 assert(i <= nb_vfargs); 4555 nb_vfargs = i; 4556 } 4557 #endif 4558 4559 #if 0 4560 static void dump_iargs (void) 4561 { 4562 int i; 4563 for (i = 0; i < nb_iargs; i++) { 4564 printf("iarg %d: %08x %08x %08x\n", i, iargs[i], 4565 (unsigned int)&iargs[i], (unsigned int)iargs); 4566 } 4567 } 4568 4569 static void dump_iargs16 (void) 4570 { 4571 int i; 4572 for (i = 0; i < nb_ii16; i++) { 4573 printf("iarg16 %d: %08x %08x %08x\n", i, ii16[i], 4574 (unsigned int)&ii16[i], (unsigned int)ii16); 4575 } 4576 } 4577 4578 static void dump_vfargs (void) 4579 { 4580 vector float vf; 4581 float f; 4582 int i=0; 4583 for (i=0; i<nb_vfargs; i++) { 4584 vf = (vector float)vfargs[i]; 4585 f = ((float*)&vf)[0]; 4586 printf("vfarg %3d: %24f : %08x\n", i, f, ((unsigned int*)&f)[0]); 4587 } 4588 } 4589 #endif 4590 4591 static void test_int_three_args (const char* name, test_func_t func, 4592 unused uint32_t test_flags) 4593 { 4594 volatile HWord_t res; 4595 volatile uint32_t flags, xer; 4596 int i, j, k; 4597 4598 for (i=0; i<nb_iargs; i++) { 4599 for (j=0; j<nb_iargs; j++) { 4600 for (k=0; k<nb_iargs; k++) { 4601 r14 = iargs[i]; 4602 r15 = iargs[j]; 4603 r16 = iargs[k]; 4604 4605 SET_CR_XER_ZERO; 4606 (*func)(); 4607 GET_CR_XER(flags,xer); 4608 res = r17; 4609 4610 #ifndef __powerpc64__ 4611 printf("%s %08x, %08x, %08x => %08x (%08x %08x)\n", 4612 #else 4613 printf("%s %016llx, %016llx, %016llx => %016llx (%08x %08x)\n", 4614 #endif 4615 name, iargs[i], iargs[j], iargs[k], res, flags, xer); 4616 } 4617 if (verbose) printf("\n"); 4618 } 4619 } 4620 } 4621 4622 static void test_int_two_args (const char* name, test_func_t func, 4623 uint32_t test_flags) 4624 { 4625 volatile HWord_t res; 4626 volatile uint32_t flags, xer, xer_orig; 4627 int i, j, is_div, zap_hi32; 4628 4629 // catches div, divwu, divo, divwu, divwuo, and . variants 4630 is_div = strstr(name, "divw") != NULL; 4631 4632 zap_hi32 = strstr(name, "mulhw") != NULL; 4633 4634 xer_orig = 0x00000000; 4635 redo: 4636 for (i=0; i<nb_iargs; i++) { 4637 for (j=0; j<nb_iargs; j++) { 4638 4639 /* result of division by zero is implementation dependent. 4640 don't test it. */ 4641 if (is_div && iargs[j] == 0) 4642 continue; 4643 4644 r14 = iargs[i]; 4645 r15 = iargs[j]; 4646 4647 SET_XER(xer_orig); 4648 SET_CR_ZERO; 4649 (*func)(); 4650 GET_CR_XER(flags,xer); 4651 res = r17; 4652 4653 #ifndef __powerpc64__ 4654 printf("%s %08x, %08x => %08x (%08x %08x)\n", 4655 #else 4656 if (zap_hi32) res &= 0xFFFFFFFFULL; 4657 printf("%s %016llx, %016llx => %016llx (%08x %08x)\n", 4658 #endif 4659 name, iargs[i], iargs[j], res, flags, xer); 4660 } 4661 if (verbose) printf("\n"); 4662 } 4663 if ((test_flags & PPC_XER_CA) && xer_orig == 0x00000000) { 4664 xer_orig = 0x20000000; 4665 goto redo; 4666 } 4667 } 4668 4669 static void test_int_one_arg (const char* name, test_func_t func, 4670 uint32_t test_flags) 4671 { 4672 volatile HWord_t res; 4673 volatile uint32_t flags, xer, xer_orig; 4674 int i; 4675 4676 xer_orig = 0x00000000; 4677 redo: 4678 for (i=0; i<nb_iargs; i++) { 4679 r14 = iargs[i]; 4680 SET_XER(xer_orig); 4681 SET_CR_ZERO; 4682 (*func)(); 4683 res = r17; 4684 GET_CR_XER(flags,xer); 4685 4686 #ifndef __powerpc64__ 4687 printf("%s %08x => %08x (%08x %08x)\n", 4688 #else 4689 printf("%s %016llx => %016llx (%08x %08x)\n", 4690 #endif 4691 name, iargs[i], res, flags, xer); 4692 } 4693 if ((test_flags & PPC_XER_CA) && xer_orig == 0x00000000) { 4694 xer_orig = 0x20000000; 4695 goto redo; 4696 } 4697 } 4698 4699 static inline void invalidate_icache ( void *ptr, int nbytes ) 4700 { 4701 HWord_t startaddr = (HWord_t) ptr; 4702 HWord_t endaddr = startaddr + nbytes; 4703 HWord_t cls = 32; /*VG_(cache_line_size_ppc32);*/ 4704 HWord_t addr; 4705 4706 startaddr &= ~(cls - 1); 4707 for (addr = startaddr; addr < endaddr; addr += cls) 4708 asm volatile("dcbst 0,%0" : : "r" (addr)); 4709 asm volatile("sync"); 4710 for (addr = startaddr; addr < endaddr; addr += cls) 4711 asm volatile("icbi 0,%0" : : "r" (addr)); 4712 asm volatile("sync; isync"); 4713 } 4714 4715 /* for god knows what reason, if this isn't inlined, the 4716 program segfaults. */ 4717 static inline 4718 void _patch_op_imm (uint32_t *p_insn, uint16_t imm, int sh, int len) 4719 { 4720 uint32_t mask = ((1 << len) - 1) << sh; 4721 *p_insn = (*p_insn & ~mask) | ((imm<<sh) & mask); 4722 } 4723 4724 static inline 4725 void patch_op_imm (uint32_t* p_insn, uint16_t imm, int sh, int len) 4726 { 4727 _patch_op_imm(p_insn, imm, sh, len); 4728 invalidate_icache(p_insn, 4); 4729 } 4730 4731 static inline 4732 void patch_op_imm16 (uint32_t *p_insn, uint16_t imm) 4733 { 4734 patch_op_imm(p_insn, imm, 0, 16); 4735 } 4736 4737 4738 /* Copy the 2 insn function starting at p_func_F to func_buf[], and 4739 return a possibly different pointer, which, when called, runs the 4740 copy in func_buf[]. */ 4741 static inline 4742 test_func_t init_function( test_func_t p_func_F, uint32_t func_buf[] ) 4743 { 4744 uint32_t* p_func = (uint32_t*)p_func_F; 4745 #ifndef __powerpc64__ 4746 func_buf[0] = p_func[0]; 4747 func_buf[1] = p_func[1]; 4748 return (test_func_t)&func_buf[0]; 4749 #else 4750 /* p_func points to a function descriptor, the first word of which 4751 points to the real code. Copy the code itself but not the 4752 descriptor, and just swizzle the descriptor's entry pointer. */ 4753 uint64_t* descr = (uint64_t*)p_func; 4754 uint32_t* entry = (uint32_t*)(descr[0]); 4755 func_buf[0] = entry[0]; 4756 func_buf[1] = entry[1]; 4757 descr[0] = (uint64_t)&func_buf[0]; 4758 return (test_func_t)descr; 4759 #endif // #ifndef __powerpc64__ 4760 } 4761 4762 4763 static void test_int_one_reg_imm16 (const char* name, 4764 test_func_t func_IN, 4765 unused uint32_t test_flags) 4766 { 4767 volatile test_func_t func; 4768 uint32_t* func_buf = get_rwx_area(); 4769 volatile HWord_t res; 4770 volatile uint32_t flags, xer; 4771 int i, j; 4772 4773 for (i=0; i<nb_iargs; i++) { 4774 for (j=0; j<nb_ii16; j++) { 4775 /* Patch up the instruction */ 4776 func = init_function( func_IN, func_buf ); 4777 patch_op_imm16(&func_buf[0], ii16[j]); 4778 4779 r14 = iargs[i]; 4780 4781 SET_CR_XER_ZERO; 4782 (*func)(); 4783 GET_CR_XER(flags,xer); 4784 res = r17; 4785 4786 #ifndef __powerpc64__ 4787 printf("%s %08x, %08x => %08x (%08x %08x)\n", 4788 #else 4789 printf("%s %016llx, %08x => %016llx (%08x %08x)\n", 4790 #endif 4791 name, iargs[i], ii16[j], res, flags, xer); 4792 } 4793 if (verbose) printf("\n"); 4794 } 4795 } 4796 4797 /* Special test cases for: 4798 * rlwimi 4799 * rlwinm 4800 * rlwnm 4801 * srawi 4802 * mcrf 4803 * mcrfs 4804 * mcrxr_cb 4805 * mfcr_cb 4806 * mfspr_cb 4807 * mftb_cb 4808 * mtcrf_cb 4809 * mtspr_cb 4810 4811 __powerpc64__ only: 4812 * rldcl rA,rS,SH,MB 4813 * rldcr rA,rS,SH,ME 4814 * rldic rA,rS,SH,MB 4815 * rldicl rA,rS,SH,MB 4816 * rldicr rA,rS,SH,ME 4817 * rldimi rA,rS,SH,MB 4818 * sradi rA,rS,SH 4819 */ 4820 4821 static void rlwi_cb (const char* name, test_func_t func_IN, 4822 unused uint32_t test_flags) 4823 { 4824 volatile test_func_t func; 4825 uint32_t* func_buf = get_rwx_area(); 4826 volatile HWord_t res; 4827 volatile uint32_t flags, xer; 4828 int i, j, k, l, arg_step; 4829 4830 arg_step = (arg_list_size == 0) ? 31 : 3; 4831 4832 r17 = 0; // rlwimi takes r17 as input: start with a clean slate. 4833 4834 for (i=0; i<nb_iargs; i++) { 4835 for (j=0; j<32; j+=arg_step) { 4836 for (k=0; k<32; k+=arg_step) { 4837 for (l=0; l<32; l+=arg_step) { 4838 /* Patch up the instruction */ 4839 func = init_function( func_IN, func_buf ); 4840 _patch_op_imm(&func_buf[0], j, 11, 5); 4841 _patch_op_imm(&func_buf[0], k, 6, 5); 4842 patch_op_imm(&func_buf[0], l, 1, 5); 4843 4844 r14 = iargs[i]; 4845 4846 SET_CR_XER_ZERO; 4847 (*func)(); 4848 GET_CR_XER(flags,xer); 4849 res = r17; 4850 4851 #ifndef __powerpc64__ 4852 printf("%s %08x, %2d, %2d, %2d => %08x (%08x %08x)\n", 4853 #else 4854 printf("%s %016llx, %2d, %2d, %2d => %016llx (%08x %08x)\n", 4855 #endif 4856 name, iargs[i], j, k, l, res, flags, xer); 4857 } 4858 if (verbose) printf("\n"); 4859 } 4860 } 4861 } 4862 } 4863 4864 static void rlwnm_cb (const char* name, test_func_t func_IN, 4865 unused uint32_t test_flags) 4866 { 4867 volatile test_func_t func; 4868 uint32_t* func_buf = get_rwx_area(); 4869 volatile HWord_t res; 4870 volatile uint32_t flags, xer; 4871 int i, j, k, l, arg_step; 4872 4873 arg_step = (arg_list_size == 0) ? 31 : 3; 4874 4875 for (i=0; i<nb_iargs; i++) { 4876 for (j=0; j<nb_iargs; j++) { 4877 for (k=0; k<32; k+=arg_step) { 4878 for (l=0; l<32; l+=arg_step) { 4879 /* Patch up the instruction */ 4880 func = init_function( func_IN, func_buf ); 4881 _patch_op_imm(&func_buf[0], k, 6, 5); 4882 patch_op_imm(&func_buf[0], l, 1, 5); 4883 4884 r14 = iargs[i]; 4885 r15 = iargs[j]; 4886 4887 SET_CR_XER_ZERO; 4888 (*func)(); 4889 GET_CR_XER(flags,xer); 4890 res = r17; 4891 4892 #ifndef __powerpc64__ 4893 printf("%s %08x, %08x, %2d, %2d => %08x (%08x %08x)\n", 4894 #else 4895 printf("%s %016llx, %016llx, %2d, %2d => %016llx (%08x %08x)\n", 4896 #endif 4897 name, iargs[i], iargs[j], k, l, res, flags, xer); 4898 } 4899 if (verbose) printf("\n"); 4900 } 4901 } 4902 } 4903 } 4904 4905 static void srawi_cb (const char* name, test_func_t func_IN, 4906 unused uint32_t test_flags) 4907 { 4908 volatile test_func_t func; 4909 uint32_t* func_buf = get_rwx_area(); 4910 volatile HWord_t res; 4911 volatile uint32_t flags, xer; 4912 int i, j, arg_step; 4913 4914 arg_step = (arg_list_size == 0) ? 31 : 1; 4915 4916 for (i=0; i<nb_iargs; i++) { 4917 for (j=0; j<32; j+=arg_step) { 4918 /* Patch up the instruction */ 4919 func = init_function( func_IN, func_buf ); 4920 patch_op_imm(&func_buf[0], j, 11, 5); 4921 4922 r14 = iargs[i]; 4923 4924 SET_CR_XER_ZERO; 4925 (*func)(); 4926 GET_CR_XER(flags,xer); 4927 res = r17; 4928 4929 #ifndef __powerpc64__ 4930 printf("%s %08x, %2d => %08x (%08x %08x)\n", 4931 #else 4932 printf("%s %016llx, %2d => %016llx (%08x %08x)\n", 4933 #endif 4934 name, iargs[i], j, res, flags, xer); 4935 } 4936 if (verbose) printf("\n"); 4937 } 4938 } 4939 4940 static void mcrf_cb (const char* name, test_func_t func_IN, 4941 unused uint32_t test_flags) 4942 { 4943 volatile test_func_t func; 4944 uint32_t* func_buf = get_rwx_area(); 4945 volatile uint32_t flags, xer; 4946 int i, j, k, arg_step; 4947 4948 arg_step = (arg_list_size == 0) ? 7 : 1; 4949 4950 for (i=0; i<nb_iargs; i++) { 4951 for (j=0; j<8; j+=arg_step) { 4952 for (k=0; k<8; k+=arg_step) { 4953 /* Patch up the instruction */ 4954 func = init_function( func_IN, func_buf ); 4955 _patch_op_imm(&func_buf[0], j, 23, 3); 4956 patch_op_imm(&func_buf[0], k, 18, 3); 4957 4958 r14 = iargs[i]; 4959 4960 SET_CR(r14); 4961 SET_XER_ZERO; 4962 (*func)(); 4963 GET_CR_XER(flags,xer); 4964 4965 #ifndef __powerpc64__ 4966 printf("%s %d, %d (%08x) => (%08x %08x)\n", 4967 #else 4968 printf("%s %d, %d (%016llx) => (%08x %08x)\n", 4969 #endif 4970 name, j, k, iargs[i], flags, xer); 4971 } 4972 if (verbose) printf("\n"); 4973 } 4974 } 4975 } 4976 4977 static void mcrxr_cb (const char* name, test_func_t func_IN, 4978 unused uint32_t test_flags) 4979 { 4980 volatile test_func_t func; 4981 uint32_t* func_buf = get_rwx_area(); 4982 volatile uint32_t flags, xer; 4983 int i, j, k, arg_step; 4984 4985 arg_step = 1; //(arg_list_size == 0) ? 7 : 1; 4986 4987 for (i=0; i<16; i+=arg_step) { 4988 j = i << 28; 4989 for (k=0; k<8; k+=arg_step) { 4990 /* Patch up the instruction */ 4991 func = init_function( func_IN, func_buf ); 4992 patch_op_imm(&func_buf[0], k, 23, 3); 4993 4994 r14 = j; 4995 4996 SET_CR_ZERO; 4997 SET_XER(r14); 4998 (*func)(); 4999 GET_CR_XER(flags,xer); 5000 5001 printf("%s %d (%08x) => (%08x %08x)\n", 5002 name, k, j, flags, xer); 5003 } 5004 if (verbose) printf("\n"); 5005 } 5006 } 5007 5008 static void mfcr_cb (const char* name, test_func_t func, 5009 unused uint32_t test_flags) 5010 { 5011 volatile HWord_t res; 5012 volatile uint32_t flags, xer; 5013 int i; 5014 5015 for (i=0; i<nb_iargs; i++) { 5016 r14 = iargs[i]; 5017 5018 /* Set up flags for test */ 5019 SET_CR(r14); 5020 SET_XER_ZERO; 5021 (*func)(); 5022 GET_CR_XER(flags,xer); 5023 res = r17; 5024 5025 #ifndef __powerpc64__ 5026 printf("%s (%08x) => %08x (%08x %08x)\n", 5027 #else 5028 printf("%s (%016llx) => %016llx (%08x %08x)\n", 5029 #endif 5030 name, iargs[i], res, flags, xer); 5031 } 5032 } 5033 5034 // NOTE: Not using func: calling function kills lr 5035 static void mfspr_cb (const char* name, test_func_t func, 5036 unused uint32_t test_flags) 5037 { 5038 //volatile uint32_t res, flags, xer, ctr, lr, tmpcr, tmpxer; 5039 volatile HWord_t res; 5040 int j, k; 5041 func = func; // just to stop compiler complaining 5042 5043 // mtxer followed by mfxer 5044 for (k=0; k<nb_iargs; k++) { 5045 j = iargs[k]; 5046 __asm__ __volatile__( 5047 "mtxer %1\n" 5048 "\tmfxer %0" 5049 : /*out*/"=b"(res) : /*in*/"b"(j) : /*trashed*/"xer" 5050 ); 5051 res &= 0xE000007F; /* rest of the bits are undefined */ 5052 5053 #ifndef __powerpc64__ 5054 printf("%s 1 (%08x) -> mtxer -> mfxer => %08x\n", 5055 #else 5056 printf("%s 1 (%08x) -> mtxer -> mfxer => %016llx\n", 5057 #endif 5058 name, j, res); 5059 } 5060 5061 // mtlr followed by mflr 5062 for (k=0; k<nb_iargs; k++) { 5063 j = iargs[k]; 5064 __asm__ __volatile__( 5065 "mtlr %1\n" 5066 "\tmflr %0" 5067 : /*out*/"=b"(res) : /*in*/"b"(j) : /*trashed*/"lr" 5068 ); 5069 5070 #ifndef __powerpc64__ 5071 printf("%s 8 (%08x) -> mtlr -> mflr => %08x\n", 5072 #else 5073 printf("%s 8 (%08x) -> mtlr -> mflr => %016llx\n", 5074 #endif 5075 name, j, res); 5076 } 5077 5078 // mtctr followed by mfctr 5079 for (k=0; k<nb_iargs; k++) { 5080 j = iargs[k]; 5081 __asm__ __volatile__( 5082 "mtctr %1\n" 5083 "\tmfctr %0" 5084 : /*out*/"=b"(res) : /*in*/"b"(j) : /*trashed*/"ctr" 5085 ); 5086 5087 #ifndef __powerpc64__ 5088 printf("%s 9 (%08x) -> mtctr -> mfctr => %08x\n", 5089 #else 5090 printf("%s 9 (%08x) -> mtctr -> mfctr => %016llx\n", 5091 #endif 5092 name, j, res); 5093 } 5094 } 5095 5096 static void mtcrf_cb (const char* name, test_func_t func_IN, 5097 unused uint32_t test_flags) 5098 { 5099 volatile test_func_t func; 5100 uint32_t* func_buf = get_rwx_area(); 5101 volatile uint32_t flags, xer; 5102 int i, j, arg_step; 5103 5104 arg_step = (arg_list_size == 0) ? 99 : 1; 5105 5106 for (i=0; i<nb_iargs; i++) { 5107 for (j=0; j<256; j+=arg_step) { 5108 /* Patch up the instruction */ 5109 func = init_function( func_IN, func_buf ); 5110 patch_op_imm(&func_buf[0], j, 12, 8); 5111 5112 r14 = iargs[i]; 5113 5114 SET_CR_XER_ZERO; 5115 (*func)(); 5116 GET_CR_XER(flags,xer); 5117 5118 #ifndef __powerpc64__ 5119 printf("%s %3d, %08x => (%08x %08x)\n", 5120 #else 5121 printf("%s %3d, %016llx => (%08x %08x)\n", 5122 #endif 5123 name, j, iargs[i], flags, xer); 5124 } 5125 if (verbose) printf("\n"); 5126 } 5127 } 5128 5129 // NOTE: Not using func: calling function kills lr 5130 static void mtspr_cb (const char* name, test_func_t func, 5131 unused uint32_t test_flags) 5132 { 5133 } 5134 5135 #ifdef __powerpc64__ 5136 static void rldc_cb (const char* name, test_func_t func_IN, 5137 unused uint32_t test_flags) 5138 { 5139 volatile test_func_t func; 5140 uint32_t* func_buf = get_rwx_area(); 5141 volatile HWord_t res; 5142 volatile uint32_t flags, xer; 5143 int i, j, k, arg_step; 5144 5145 arg_step = (arg_list_size == 0) ? 7 : 3; 5146 5147 for (i=0; i<nb_iargs; i++) { 5148 for (j=0; j<nb_iargs; j++) { 5149 for (k=0; k<64; k+=arg_step) { 5150 /* Patch up the instruction */ 5151 func = init_function( func_IN, func_buf ); 5152 patch_op_imm(&func_buf[0], (((k & 0x1F)<<1) | ((k>>5)&1)), 5, 6); 5153 5154 r14 = iargs[i]; 5155 r15 = iargs[j]; 5156 5157 SET_CR_XER_ZERO; 5158 (*func)(); 5159 GET_CR_XER(flags,xer); 5160 res = r17; 5161 5162 printf("%s %016llx, %016llx, %2d => %016llx (%08x %08x)\n", 5163 name, iargs[i], iargs[j], k, res, flags, xer); 5164 } 5165 if (verbose) printf("\n"); 5166 } 5167 } 5168 } 5169 5170 static void rldi_cb (const char* name, test_func_t func_IN, 5171 unused uint32_t test_flags) 5172 { 5173 volatile test_func_t func; 5174 uint32_t* func_buf = get_rwx_area(); 5175 volatile HWord_t res; 5176 volatile uint32_t flags, xer; 5177 int i, j, k, arg_step; 5178 5179 arg_step = (arg_list_size == 0) ? 7 : 3; 5180 5181 for (i=0; i<nb_iargs; i++) { 5182 for (j=0; j<64; j+=arg_step) { // SH 5183 for (k=0; k<64; k+=arg_step) { // MB|ME 5184 /* Patch up the instruction */ 5185 func = init_function( func_IN, func_buf ); 5186 _patch_op_imm(&func_buf[0], (j & 0x1F), 11, 5); 5187 _patch_op_imm(&func_buf[0], ((j>>5)&1), 1, 1); 5188 patch_op_imm(&func_buf[0], (((k & 0x1F)<<1) | ((k>>5)&1)), 5, 6); 5189 5190 r14 = iargs[i]; 5191 5192 SET_CR_XER_ZERO; 5193 (*func)(); 5194 GET_CR_XER(flags,xer); 5195 res = r17; 5196 5197 printf("%s %016llx, %2d, %2d => %016llx (%08x %08x)\n", 5198 name, iargs[i], j, k, res, flags, xer); 5199 } 5200 if (verbose) printf("\n"); 5201 } 5202 } 5203 } 5204 5205 static void sradi_cb (const char* name, test_func_t func_IN, 5206 unused uint32_t test_flags) 5207 { 5208 volatile test_func_t func; 5209 uint32_t* func_buf = get_rwx_area(); 5210 volatile HWord_t res; 5211 volatile uint32_t flags, xer; 5212 int i, j, arg_step; 5213 5214 arg_step = (arg_list_size == 0) ? 7 : 3; 5215 5216 for (i=0; i<nb_iargs; i++) { 5217 for (j=0; j<64; j+=arg_step) { // SH 5218 /* Patch up the instruction */ 5219 func = init_function( func_IN, func_buf ); 5220 _patch_op_imm(&func_buf[0], (j & 0x1F), 11, 5); 5221 patch_op_imm(&func_buf[0], ((j>>5)&1), 1, 1); 5222 5223 r14 = iargs[i]; 5224 5225 SET_CR_XER_ZERO; 5226 (*func)(); 5227 GET_CR_XER(flags,xer); 5228 res = r17; 5229 5230 printf("%s %016llx, %2d => %016llx (%08x %08x)\n", 5231 name, iargs[i], j, res, flags, xer); 5232 } 5233 if (verbose) printf("\n"); 5234 } 5235 } 5236 #endif // #ifdef __powerpc64__ 5237 5238 5239 typedef struct special_t special_t; 5240 5241 struct special_t { 5242 const char *name; 5243 void (*test_cb)(const char* name, test_func_t func, 5244 unused uint32_t test_flags); 5245 }; 5246 5247 static void test_special (special_t *table, 5248 const char* name, test_func_t func, 5249 unused uint32_t test_flags) 5250 { 5251 const char *tmp; 5252 int i; 5253 5254 for (tmp = name; isspace(*tmp); tmp++) 5255 continue; 5256 for (i=0; table[i].name != NULL; i++) { 5257 #if 0 5258 fprintf(stderr, "look for handler for '%s' (%s)\n", name, 5259 table[i].name); 5260 #endif 5261 if (strcmp(table[i].name, tmp) == 0) { 5262 (*table[i].test_cb)(name, func, test_flags); 5263 return; 5264 } 5265 } 5266 fprintf(stderr, "ERROR: no test found for op '%s'\n", name); 5267 } 5268 5269 static special_t special_int_ops[] = { 5270 { 5271 "rlwimi", /* One register + 3 5 bits immediate arguments */ 5272 &rlwi_cb, 5273 }, 5274 { 5275 "rlwimi.", /* One register + 3 5 bits immediate arguments */ 5276 &rlwi_cb, 5277 }, 5278 { 5279 "rlwinm", /* One register + 3 5 bits immediate arguments */ 5280 &rlwi_cb, 5281 }, 5282 { 5283 "rlwinm.", /* One register + 3 5 bits immediate arguments */ 5284 &rlwi_cb, 5285 }, 5286 { 5287 "rlwnm", /* Two registers + 2 5 bits immediate arguments */ 5288 &rlwnm_cb, 5289 }, 5290 { 5291 "rlwnm.", /* Two registers + 2 5 bits immediate arguments */ 5292 &rlwnm_cb, 5293 }, 5294 { 5295 "srawi", /* One register + 1 5 bits immediate arguments */ 5296 &srawi_cb, 5297 }, 5298 { 5299 "srawi.", /* One register + 1 5 bits immediate arguments */ 5300 &srawi_cb, 5301 }, 5302 { 5303 "mcrf", /* 2 3 bits immediate arguments */ 5304 &mcrf_cb, 5305 }, 5306 #if 0 5307 { 5308 "mcrfs", /* 2 3 bits immediate arguments */ 5309 &mcrfs_cb, 5310 }, 5311 #endif 5312 { 5313 "mcrxr", /* 1 3 bits immediate argument */ 5314 &mcrxr_cb, 5315 }, 5316 { 5317 "mfcr", /* No arguments */ 5318 &mfcr_cb, 5319 }, 5320 { 5321 "mfspr", /* 1 10 bits immediate argument */ 5322 &mfspr_cb, 5323 }, 5324 #if 0 5325 { // Move from time base 5326 "mftb", /* 1 10 bits immediate arguments */ 5327 &mftb_cb, 5328 }, 5329 #endif 5330 { 5331 "mtcrf", /* One register + 1 8 bits immediate arguments */ 5332 &mtcrf_cb, 5333 }, 5334 { 5335 "mtspr", /* One register + 1 10 bits immediate arguments */ 5336 &mtspr_cb, 5337 }, 5338 #ifdef __powerpc64__ 5339 { 5340 "rldcl", /* Two registers + 1 6 bit immediate argument */ 5341 &rldc_cb, 5342 }, 5343 { 5344 "rldcl.", /* Two registers + 1 6 bit immediate argument */ 5345 &rldc_cb, 5346 }, 5347 { 5348 "rldcr", /* Two registers + 1 6 bit immediate argument */ 5349 &rldc_cb, 5350 }, 5351 { 5352 "rldcr.", /* Two registers + 1 6 bit immediate argument */ 5353 &rldc_cb, 5354 }, 5355 { 5356 "rldic", /* One register + 2 6 bit immediate arguments */ 5357 &rldi_cb, 5358 }, 5359 { 5360 "rldic.", /* One register + 2 6 bit immediate arguments */ 5361 &rldi_cb, 5362 }, 5363 { 5364 "rldicl", /* One register + 2 6 bit immediate arguments */ 5365 &rldi_cb, 5366 }, 5367 { 5368 "rldicl.", /* One register + 2 6 bit immediate arguments */ 5369 &rldi_cb, 5370 }, 5371 { 5372 "rldicr", /* One register + 2 6 bit immediate arguments */ 5373 &rldi_cb, 5374 }, 5375 { 5376 "rldicr.", /* One register + 2 6 bit immediate arguments */ 5377 &rldi_cb, 5378 }, 5379 { 5380 "rldimi", /* One register + 2 6 bit immediate arguments */ 5381 &rldi_cb, 5382 }, 5383 { 5384 "rldimi.", /* One register + 2 6 bit immediate arguments */ 5385 &rldi_cb, 5386 }, 5387 { 5388 "sradi", /* One register + 1 6 bit immediate argument */ 5389 &sradi_cb, 5390 }, 5391 { 5392 "sradi.", /* One register + 1 6 bit immediate argument */ 5393 &sradi_cb, 5394 }, 5395 #endif // #ifdef __powerpc64__ 5396 { 5397 NULL, 5398 NULL, 5399 }, 5400 }; 5401 5402 static void test_int_special (const char* name, test_func_t func, 5403 uint32_t test_flags) 5404 { 5405 test_special(special_int_ops, name, func, test_flags); 5406 } 5407 5408 5409 static void test_int_ld_one_reg_imm16 (const char* name, 5410 test_func_t func_IN, 5411 unused uint32_t test_flags) 5412 { 5413 volatile test_func_t func; 5414 uint32_t* func_buf = get_rwx_area(); 5415 volatile HWord_t res, base; 5416 volatile uint32_t flags, xer; 5417 int i, offs, is_lwa=0; 5418 5419 #ifdef __powerpc64__ 5420 is_lwa = strstr(name, "lwa") != NULL; 5421 #endif 5422 5423 // +ve d 5424 base = (HWord_t)&iargs[0]; 5425 for (i=0; i<nb_iargs; i++) { 5426 offs = i * sizeof(HWord_t); 5427 5428 /* Patch up the instruction */ 5429 func = init_function( func_IN, func_buf ); 5430 if (is_lwa) 5431 patch_op_imm(&func_buf[0], offs>>2, 2, 14); 5432 else 5433 patch_op_imm16(&func_buf[0], offs); 5434 5435 r14 = base; 5436 5437 SET_CR_XER_ZERO; 5438 (*func)(); 5439 GET_CR_XER(flags,xer); 5440 res = r17; 5441 5442 #ifndef __powerpc64__ 5443 printf("%s %2d, (%08x) => %08x, %2d (%08x %08x)\n", 5444 #else 5445 printf("%s %3d, (%016llx) => %016llx, %3lld (%08x %08x)\n", 5446 #endif 5447 name, offs, iargs[i], res, r14-base, flags, xer); 5448 } 5449 if (verbose) printf("\n"); 5450 5451 // -ve d 5452 base = (HWord_t)&iargs[nb_iargs-1]; 5453 for (i = -nb_iargs+1; i<=0; i++) { 5454 offs = i * sizeof(HWord_t); 5455 5456 /* Patch up the instruction */ 5457 func = init_function( func, func_buf ); 5458 patch_op_imm16(&func_buf[0], offs); 5459 5460 r14 = base; 5461 5462 SET_CR_XER_ZERO; 5463 (*func)(); 5464 GET_CR_XER(flags,xer); 5465 res = r17; 5466 5467 #ifndef __powerpc64__ 5468 printf("%s %2d, (%08x) => %08x, %2d (%08x %08x)\n", 5469 #else 5470 printf("%s %3d, (%016llx) => %016llx, %3lld (%08x %08x)\n", 5471 #endif 5472 name, offs, iargs[nb_iargs-1+i], res, r14-base, flags, xer); 5473 } 5474 } 5475 5476 static void test_int_ld_two_regs (const char* name, 5477 test_func_t func, 5478 unused uint32_t test_flags) 5479 { 5480 volatile HWord_t res, base; 5481 volatile uint32_t flags, xer; 5482 int i, offs; 5483 5484 // +ve d 5485 base = (HWord_t)&iargs[0]; 5486 for (i=0; i<nb_iargs; i++) { 5487 offs = i * sizeof(HWord_t); 5488 r14 = base; 5489 r15 = offs; 5490 5491 SET_CR_XER_ZERO; 5492 (*func)(); 5493 GET_CR_XER(flags,xer); 5494 res = r17; 5495 5496 #ifndef __powerpc64__ 5497 printf("%s %d (%08x) => %08x, %d (%08x %08x)\n", 5498 #else 5499 printf("%s %3d, (%016llx) => %016llx, %2lld (%08x %08x)\n", 5500 #endif 5501 name, offs, iargs[i], res, r14-base, flags, xer); 5502 } 5503 } 5504 5505 static void test_int_st_two_regs_imm16 (const char* name, 5506 test_func_t func_IN, 5507 unused uint32_t test_flags) 5508 { 5509 volatile test_func_t func; 5510 uint32_t* func_buf = get_rwx_area(); 5511 volatile uint32_t flags, xer; 5512 int i, offs, k; 5513 HWord_t *iargs_priv, base; 5514 5515 // private iargs table to store to 5516 iargs_priv = malloc(nb_iargs * sizeof(HWord_t)); 5517 5518 // +ve d 5519 base = (HWord_t)&iargs_priv[0]; 5520 for (i=0; i<nb_iargs; i++) { 5521 for (k=0; k<nb_iargs; k++) // clear array 5522 iargs_priv[k] = 0; 5523 5524 offs = i * sizeof(HWord_t); 5525 5526 /* Patch up the instruction */ 5527 func = init_function( func_IN, func_buf ); 5528 patch_op_imm16(&func_buf[0], offs); 5529 5530 r14 = iargs[i]; // read from iargs 5531 r15 = base; // store to r15 + offs 5532 5533 SET_CR_XER_ZERO; 5534 (*func)(); 5535 GET_CR_XER(flags,xer); 5536 5537 #ifndef __powerpc64__ 5538 printf("%s %08x, %2d => %08x, %2d (%08x %08x)\n", 5539 #else 5540 printf("%s %016llx, %3d => %016llx, %3lld (%08x %08x)\n", 5541 #endif 5542 name, iargs[i], offs, iargs_priv[i], r15-base, flags, xer); 5543 } 5544 if (verbose) printf("\n"); 5545 5546 // -ve d 5547 base = (HWord_t)&iargs_priv[nb_iargs-1]; 5548 for (i = -nb_iargs+1; i<=0; i++) { 5549 for (k=0; k<nb_iargs; k++) // clear array 5550 iargs_priv[k] = 0; 5551 5552 offs = i * sizeof(HWord_t); 5553 5554 /* Patch up the instruction */ 5555 func = init_function( func, func_buf ); 5556 patch_op_imm16(&func_buf[0], offs); 5557 5558 r14 = iargs[nb_iargs-1+i]; // read from iargs 5559 r15 = base; // store to r15 + offs 5560 5561 SET_CR_XER_ZERO; 5562 (*func)(); 5563 GET_CR_XER(flags,xer); 5564 5565 #ifndef __powerpc64__ 5566 printf("%s %08x, %2d => %08x, %2d (%08x %08x)\n", 5567 #else 5568 printf("%s %016llx, %3d => %016llx, %3lld (%08x %08x)\n", 5569 #endif 5570 name, iargs[nb_iargs-1+i], offs, iargs_priv[nb_iargs-1+i], 5571 r15-base, flags, xer); 5572 } 5573 free(iargs_priv); 5574 } 5575 5576 static void test_int_st_three_regs (const char* name, 5577 test_func_t func, 5578 unused uint32_t test_flags) 5579 { 5580 volatile uint32_t flags, xer; 5581 int i, offs, k; 5582 HWord_t *iargs_priv, base; 5583 5584 // private iargs table to store to 5585 iargs_priv = malloc(nb_iargs * sizeof(HWord_t)); 5586 5587 base = (HWord_t)&iargs_priv[0]; 5588 for (i=0; i<nb_iargs; i++) { 5589 for (k=0; k<nb_iargs; k++) // clear array 5590 iargs_priv[k] = 0; 5591 5592 offs = i * sizeof(HWord_t); 5593 r14 = iargs[i]; // read from iargs 5594 r15 = base; // store to r15 + offs 5595 r16 = offs; 5596 5597 SET_CR_XER_ZERO; 5598 (*func)(); 5599 GET_CR_XER(flags,xer); 5600 5601 #ifndef __powerpc64__ 5602 printf("%s %08x, %d => %08x, %d (%08x %08x)\n", 5603 #else 5604 printf("%s %016llx, %3d => %016llx, %2lld (%08x %08x)\n", 5605 #endif 5606 name, iargs[i], offs, iargs_priv[i], r15-base, flags, xer); 5607 } 5608 free(iargs_priv); 5609 } 5610 5611 5612 /* Used in do_tests, indexed by flags->nb_args 5613 Elements correspond to enum test_flags::num args 5614 */ 5615 static test_loop_t int_loops[] = { 5616 &test_int_one_arg, 5617 &test_int_two_args, 5618 &test_int_three_args, 5619 &test_int_two_args, 5620 &test_int_one_reg_imm16, 5621 &test_int_one_reg_imm16, 5622 &test_int_special, 5623 &test_int_ld_one_reg_imm16, 5624 &test_int_ld_two_regs, 5625 &test_int_st_two_regs_imm16, 5626 &test_int_st_three_regs, 5627 }; 5628 5629 #if !defined (NO_FLOAT) 5630 static void test_float_three_args (const char* name, test_func_t func, 5631 unused uint32_t test_flags) 5632 { 5633 double res; 5634 uint64_t u0, u1, u2, ur; 5635 volatile uint32_t flags; 5636 int i, j, k; 5637 5638 /* Note: using nb_normal_fargs: 5639 - not testing special values for these insns 5640 */ 5641 5642 for (i=0; i<nb_normal_fargs; i+=3) { 5643 for (j=0; j<nb_normal_fargs; j+=5) { 5644 for (k=0; k<nb_normal_fargs; k+=7) { 5645 u0 = *(uint64_t *)(&fargs[i]); 5646 u1 = *(uint64_t *)(&fargs[j]); 5647 u2 = *(uint64_t *)(&fargs[k]); 5648 f14 = fargs[i]; 5649 f15 = fargs[j]; 5650 f16 = fargs[k]; 5651 5652 SET_FPSCR_ZERO; 5653 SET_CR_XER_ZERO; 5654 (*func)(); 5655 GET_CR(flags); 5656 res = f17; 5657 ur = *(uint64_t *)(&res); 5658 5659 /* Note: zapping the bottom byte of the result, 5660 as vex's accuracy isn't perfect */ 5661 ur &= 0xFFFFFFFFFFFFFF00ULL; 5662 5663 #ifndef __powerpc64__ 5664 printf("%s %016llx, %016llx, %016llx => %016llx", 5665 #else 5666 printf("%s %016llx, %016llx, %016llx => %016llx", 5667 #endif 5668 name, u0, u1, u2, ur); 5669 #if defined TEST_FLOAT_FLAGS 5670 printf(" (%08x)", flags); 5671 #endif 5672 printf("\n"); 5673 } 5674 if (verbose) printf("\n"); 5675 } 5676 } 5677 } 5678 5679 static void test_float_two_args (const char* name, test_func_t func, 5680 unused uint32_t test_flags) 5681 { 5682 double res; 5683 uint64_t u0, u1, ur; 5684 volatile uint32_t flags; 5685 int i, j; 5686 5687 for (i=0; i<nb_fargs; i+=3) { 5688 for (j=0; j<nb_fargs; j+=5) { 5689 u0 = *(uint64_t *)(&fargs[i]); 5690 u1 = *(uint64_t *)(&fargs[j]); 5691 f14 = fargs[i]; 5692 f15 = fargs[j]; 5693 5694 SET_FPSCR_ZERO; 5695 SET_CR_XER_ZERO; 5696 (*func)(); 5697 GET_CR(flags); 5698 res = f17; 5699 ur = *(uint64_t *)(&res); 5700 5701 #ifndef __powerpc64__ 5702 printf("%s %016llx, %016llx => %016llx", 5703 #else 5704 printf("%s %016llx, %016llx => %016llx", 5705 #endif 5706 name, u0, u1, ur); 5707 #if defined TEST_FLOAT_FLAGS 5708 printf(" (%08x)", flags); 5709 #endif 5710 printf("\n"); 5711 } 5712 if (verbose) printf("\n"); 5713 } 5714 } 5715 5716 static void test_float_one_arg (const char* name, test_func_t func, 5717 unused uint32_t test_flags) 5718 { 5719 double res; 5720 uint64_t u0, ur; 5721 volatile uint32_t flags; 5722 int i; 5723 unsigned zap_hi_32bits, zap_lo_44bits, zap_lo_47bits; 5724 5725 /* if we're testing fctiw or fctiwz, zap the hi 32bits, 5726 as they're undefined */ 5727 zap_hi_32bits = strstr(name, " fctiw") != NULL ? 1 : 0; 5728 zap_lo_44bits = strstr(name, " fres") != NULL ? 1 : 0; 5729 zap_lo_47bits = strstr(name, " frsqrte") != NULL ? 1 : 0; 5730 5731 assert(zap_hi_32bits + zap_lo_44bits + zap_lo_47bits <= 1); 5732 5733 for (i=0; i<nb_fargs; i++) { 5734 u0 = *(uint64_t *)(&fargs[i]); 5735 f14 = fargs[i]; 5736 5737 SET_FPSCR_ZERO; 5738 SET_CR_XER_ZERO; 5739 (*func)(); 5740 GET_CR(flags); 5741 res = f17; 5742 ur = *(uint64_t *)(&res); 5743 5744 if (zap_hi_32bits) 5745 ur &= 0x00000000FFFFFFFFULL; 5746 if (zap_lo_44bits) 5747 ur &= 0xFFFFF00000000000ULL; 5748 if (zap_lo_47bits) 5749 ur &= 0xFFFF800000000000ULL; 5750 5751 #ifndef __powerpc64__ 5752 printf("%s %016llx => %016llx", 5753 #else 5754 printf("%s %016llx => %016llx", 5755 #endif 5756 name, u0, ur); 5757 #if defined TEST_FLOAT_FLAGS 5758 printf(" (%08x)", flags); 5759 #endif 5760 printf("\n"); 5761 } 5762 } 5763 5764 /* Special test cases for: 5765 * mffs 5766 * mtfsb0 5767 * mtfsb1 5768 */ 5769 static special_t special_float_ops[] = { 5770 #if 0 5771 { 5772 "mffs", /* One 5 bits immediate argument */ 5773 &mffs_cb, 5774 }, 5775 { 5776 "mffs.", /* One 5 bits immediate argument */ 5777 &mffs_cb, 5778 }, 5779 { 5780 "mtfsb0", /* One 5 bits immediate argument */ 5781 &mffs_cb, 5782 }, 5783 { 5784 "mtfsb0.", /* One 5 bits immediate argument */ 5785 &mffs_cb, 5786 }, 5787 { 5788 "mtfsb1", /* One 5 bits immediate argument */ 5789 &mffs_cb, 5790 }, 5791 { 5792 "mtfsb1.", /* One 5 bits immediate argument */ 5793 &mffs_cb, 5794 }, 5795 { 5796 "mtfsf", /* One register + 1 8 bits immediate argument */ 5797 &mtfsf_cb, 5798 }, 5799 { 5800 "mtfsf.", /* One register + 1 8 bits immediate argument */ 5801 &mtfsf_cb, 5802 }, 5803 { 5804 "mtfsfi", /* One 5 bits argument + 1 5 bits argument */ 5805 &mtfsfi_cb, 5806 }, 5807 { 5808 "mtfsfi.", /* One 5 bits argument + 1 5 bits argument */ 5809 &mtfsfi_cb, 5810 }, 5811 #endif 5812 { 5813 NULL, 5814 NULL, 5815 }, 5816 }; 5817 5818 static void test_float_special (const char* name, test_func_t func, 5819 uint32_t test_flags) 5820 { 5821 test_special(special_float_ops, name, func, test_flags); 5822 } 5823 5824 5825 static void test_float_ld_one_reg_imm16 (const char* name, 5826 test_func_t func_IN, 5827 unused uint32_t test_flags) 5828 { 5829 volatile test_func_t func; 5830 uint32_t* func_buf = get_rwx_area(); 5831 uint32_t base; 5832 volatile uint32_t flags, xer; 5833 volatile double src, res; 5834 int i, offs; 5835 5836 /* offset within [1-nb_fargs:nb_fargs] */ 5837 for (i=1-nb_fargs; i<nb_fargs; i++) { 5838 offs = i * 8; // offset = i * sizeof(double) 5839 if (i < 0) { 5840 src = fargs[nb_fargs-1 + i]; 5841 base = (HWord_t)&fargs[nb_fargs-1]; 5842 } else { 5843 src = fargs[i]; 5844 base = (HWord_t)&fargs[0]; 5845 } 5846 5847 /* Patch up the instruction */ 5848 func = init_function( func_IN, func_buf ); 5849 patch_op_imm16(&func_buf[0], offs); 5850 5851 // load from fargs[idx] => r14 + offs 5852 r14 = base; 5853 5854 SET_CR_XER_ZERO; 5855 (*func)(); 5856 GET_CR_XER(flags,xer); 5857 res = f17; 5858 5859 #ifndef __powerpc64__ 5860 printf("%s %016llx, %4d => %016llx, %4d", 5861 #else 5862 printf("%s %016llx, %4d => %016llx, %4lld", 5863 #endif 5864 name, double_to_bits(src), offs, 5865 double_to_bits(res), r14-base); 5866 #if defined TEST_FLOAT_FLAGS 5867 printf(" (%08x %08x)", flags, xer); 5868 #endif 5869 printf("\n"); 5870 } 5871 if (verbose) printf("\n"); 5872 } 5873 5874 static void test_float_ld_two_regs (const char* name, 5875 test_func_t func, 5876 unused uint32_t test_flags) 5877 { 5878 volatile HWord_t base; 5879 volatile uint32_t flags, xer; 5880 volatile double src, res; 5881 int i, offs; 5882 5883 /* offset within [1-nb_fargs:nb_fargs] */ 5884 for (i=1-nb_fargs; i<nb_fargs; i++) { 5885 offs = i * 8; // offset = i * sizeof(double) 5886 if (i < 0) { // base reg = start of array 5887 src = fargs[nb_fargs-1 + i]; 5888 base = (HWord_t)&fargs[nb_fargs-1]; 5889 } else { 5890 src = fargs[i]; 5891 base = (HWord_t)&fargs[0]; 5892 } 5893 5894 r14 = base; 5895 r15 = offs; 5896 5897 SET_CR_XER_ZERO; 5898 (*func)(); 5899 GET_CR_XER(flags,xer); 5900 res = f17; 5901 5902 #ifndef __powerpc64__ 5903 printf("%s %016llx, %4d => %016llx, %4d", 5904 #else 5905 printf("%s %016llx, %4lld => %016llx, %4lld", 5906 #endif 5907 name, double_to_bits(src), r15/*offs*/, 5908 double_to_bits(res), r14-base); 5909 #if defined TEST_FLOAT_FLAGS 5910 printf(" (%08x %08x)", flags, xer); 5911 #endif 5912 printf("\n"); 5913 } 5914 } 5915 5916 static void test_float_st_two_regs_imm16 (const char* name, 5917 test_func_t func_IN, 5918 unused uint32_t test_flags) 5919 { 5920 volatile test_func_t func; 5921 uint32_t* func_buf = get_rwx_area(); 5922 HWord_t base; 5923 volatile uint32_t flags, xer; 5924 double src, *p_dst; 5925 int i, offs; 5926 double *fargs_priv; 5927 int nb_tmp_fargs = nb_fargs; 5928 5929 5930 /* if we're storing an fp single-precision, don't want nans 5931 - the vex implementation doesn't like them (yet) 5932 Note: This is actually a bigger problem: the vex implementation 5933 rounds these insns twice. This leads to many rounding errors. 5934 For the small fargs set, however, this doesn't show up. 5935 */ 5936 if (strstr(name, "stfs") != NULL) 5937 nb_tmp_fargs = nb_normal_fargs; 5938 5939 5940 // private fargs table to store to 5941 fargs_priv = malloc(nb_tmp_fargs * sizeof(double)); 5942 5943 /* offset within [1-nb_tmp_fargs:nb_tmp_fargs] */ 5944 for (i=1-nb_tmp_fargs; i<nb_tmp_fargs; i++) { 5945 offs = i * 8; // offset = i * sizeof(double) 5946 if (i < 0) { 5947 src = fargs [nb_tmp_fargs-1 + i]; 5948 p_dst = &fargs_priv[nb_tmp_fargs-1 + i]; 5949 base = (HWord_t)&fargs_priv[nb_tmp_fargs-1]; 5950 } else { 5951 src = fargs [i]; 5952 p_dst = &fargs_priv[i]; 5953 base = (HWord_t)&fargs_priv[0]; 5954 } 5955 *p_dst = 0; // clear dst 5956 5957 /* Patch up the instruction */ 5958 func = init_function( func_IN, func_buf ); 5959 patch_op_imm16(&func_buf[0], offs); 5960 5961 // read from fargs[idx] => f14 5962 // store to fargs_priv[idx] => r15 + offs 5963 f14 = src; 5964 r15 = base; 5965 5966 SET_CR_XER_ZERO; 5967 (*func)(); 5968 GET_CR_XER(flags,xer); 5969 5970 #ifndef __powerpc64__ 5971 printf("%s %016llx, %4d => %016llx, %4d", 5972 #else 5973 printf("%s %016llx, %4d => %016llx, %4lld", 5974 #endif 5975 name, double_to_bits(src), offs, 5976 double_to_bits(*p_dst), r15-base); 5977 #if defined TEST_FLOAT_FLAGS 5978 printf(" (%08x %08x)", flags, xer); 5979 #endif 5980 printf("\n"); 5981 } 5982 free(fargs_priv); 5983 } 5984 5985 static void test_float_st_three_regs (const char* name, 5986 test_func_t func, 5987 unused uint32_t test_flags) 5988 { 5989 volatile HWord_t base; 5990 volatile uint32_t flags, xer; 5991 double src, *p_dst; 5992 int i, offs; 5993 double *fargs_priv; 5994 int nb_tmp_fargs = nb_fargs; 5995 5996 5997 /* if we're storing an fp single-precision, don't want nans 5998 - the vex implementation doesn't like them (yet) 5999 Note: This is actually a bigger problem: the vex implementation 6000 rounds these insns twice. This leads to many rounding errors. 6001 For the small fargs set, however, this doesn't show up. 6002 */ 6003 if (strstr(name, "stfs") != NULL) // stfs(u)(x) 6004 nb_tmp_fargs = nb_normal_fargs; 6005 6006 6007 // private fargs table to store to 6008 fargs_priv = malloc(nb_tmp_fargs * sizeof(double)); 6009 6010 // /* offset within [1-nb_tmp_fargs:nb_tmp_fargs] */ 6011 // for (i=1-nb_tmp_fargs; i<nb_tmp_fargs; i++) { 6012 for (i=0; i<nb_tmp_fargs; i++) { 6013 offs = i * 8; // offset = i * sizeof(double) 6014 if (i < 0) { 6015 src = fargs [nb_tmp_fargs-1 + i]; 6016 p_dst = &fargs_priv[nb_tmp_fargs-1 + i]; 6017 base = (HWord_t)&fargs_priv[nb_tmp_fargs-1]; 6018 } else { 6019 src = fargs [i]; 6020 p_dst = &fargs_priv[i]; 6021 base = (HWord_t)&fargs_priv[0]; 6022 } 6023 *p_dst = 0; // clear dst 6024 6025 f14 = src; // read from fargs 6026 r15 = base; // store to r15 + offs 6027 r16 = offs; 6028 6029 SET_CR_XER_ZERO; 6030 (*func)(); 6031 GET_CR_XER(flags,xer); 6032 6033 #ifndef __powerpc64__ 6034 printf("%s %016llx, %4d => %016llx, %4d", 6035 #else 6036 printf("%s %016llx, %4lld => %016llx, %4lld", 6037 #endif 6038 name, double_to_bits(src), r16/*offs*/, 6039 double_to_bits(*p_dst), r15-base); 6040 #if defined TEST_FLOAT_FLAGS 6041 printf(" (%08x %08x)", flags, xer); 6042 #endif 6043 printf("\n"); 6044 6045 6046 #if 0 6047 // print double precision result 6048 #ifndef __powerpc64__ 6049 printf("%s %016llx (%014e), %4d => %016llx (%014e), %08x (%08x %08x)\n", 6050 #else 6051 printf("%s %016llx (%014e), %4d => %016llx (%014e), %08x (%08x %08x)\n", 6052 #endif 6053 name, double_to_bits(src), src, offs, 6054 double_to_bits(*p_dst), *p_dst, r15, flags, xer); 6055 6056 // print single precision result 6057 #ifndef __powerpc64__ 6058 printf("%s %016llx (%014e), %4d => %08x (%f), %08x (%08x %08x)\n", 6059 #else 6060 printf("%s %016llx (%014e), %4d => %08x (%f), %08x (%08x %08x)\n", 6061 #endif 6062 name, double_to_bits(src), src, offs, 6063 (uint32_t)(double_to_bits(*p_dst) >> 32), 6064 bits_to_float( (uint32_t)(double_to_bits(*p_dst) >> 32) ), 6065 r15, flags, xer); 6066 #endif 6067 } 6068 free(fargs_priv); 6069 } 6070 6071 6072 /* Used in do_tests, indexed by flags->nb_args 6073 Elements correspond to enum test_flags::num args 6074 */ 6075 static test_loop_t float_loops[] = { 6076 &test_float_one_arg, 6077 &test_float_two_args, 6078 &test_float_three_args, 6079 &test_float_two_args, 6080 NULL, 6081 NULL, 6082 &test_float_special, 6083 &test_float_ld_one_reg_imm16, 6084 &test_float_ld_two_regs, 6085 &test_float_st_two_regs_imm16, 6086 &test_float_st_three_regs, 6087 }; 6088 #endif /* !defined (NO_FLOAT) */ 6089 6090 6091 #if defined (HAS_ALTIVEC) 6092 6093 /* Ref: vector insns to test setting CR, VSCR: 6094 volatile vector unsigned int v1 = 6095 // (vector unsigned int){ 0xFFFFFFFF,0xFFFFFFFF,0xFFFFFFFF,0xFFFFFFFF }; 6096 (vector unsigned int){ 0x80808080,0x80808080,0x80808080,0x80808080 }; 6097 volatile vector unsigned int v2 = 6098 // (vector unsigned int){ 0xFFFFFFFF,0xFFFFFFFF,0xFFFFFFFF,0xFFFFFFFF }; 6099 (vector unsigned int){ 0x01010101,0x01010101,0x01010101,0x01010101 }; 6100 //__asm__ __volatile__ ("vcmpequw. 31,%0,%1" : : "v" (v1), "v" (v2)); // sets CR[6] 6101 //__asm__ __volatile__ ("vpkswss 31,%0,%1" : : "v" (v1), "v" (v2)); // sets VSCR[SAT] 6102 __asm__ __volatile__ ("vsubsbs 31,%0,%1" : : "v" (v1), "v" (v2)); // sets VSCR[SAT] 6103 */ 6104 6105 //#define DEFAULT_VSCR 0x00010000 6106 #define DEFAULT_VSCR 0x0 6107 6108 static void test_av_int_one_arg (const char* name, test_func_t func, 6109 unused uint32_t test_flags) 6110 { 6111 volatile uint32_t flags, tmpcr; 6112 volatile vector unsigned int tmpvscr; 6113 volatile vector unsigned int vec_in, vec_out, vscr; 6114 unsigned int *src, *dst; 6115 int i; 6116 #if defined TEST_VSCR_SAT 6117 unsigned int* p_vscr; 6118 #endif 6119 6120 for (i=0; i<nb_viargs; i++) { 6121 /* Save flags */ 6122 __asm__ __volatile__ ("mfcr %0" : "=r" (tmpcr)); 6123 __asm__ __volatile__ ("mfvscr %0" : "=vr" (tmpvscr)); 6124 6125 vec_in = (vector unsigned int)viargs[i]; 6126 vec_out = (vector unsigned int){ 0,0,0,0 }; 6127 6128 // reset VSCR and CR 6129 vscr = (vector unsigned int){ 0,0,0,DEFAULT_VSCR }; 6130 flags = 0; 6131 __asm__ __volatile__ ("mtvscr %0" : : "v" (vscr) ); 6132 __asm__ __volatile__ ("mtcr %0" : : "r" (flags)); 6133 6134 // load input -> r14 6135 __asm__ __volatile__ ("vor 14,%0,%0" : : "v" (vec_in)); 6136 6137 // do stuff 6138 (*func)(); 6139 6140 // retrieve output <- r17 6141 __asm__ __volatile__ ("vor %0,17,17" : "=vr" (vec_out)); 6142 6143 // get CR,VSCR flags 6144 __asm__ __volatile__ ("mfcr %0" : "=r" (flags)); 6145 __asm__ __volatile__ ("mfvscr %0" : "=vr" (vscr)); 6146 6147 /* Restore flags */ 6148 __asm__ __volatile__ ("mtcr %0" : : "r" (tmpcr)); 6149 __asm__ __volatile__ ("mtvscr %0" : : "v" (tmpvscr)); 6150 6151 src = (unsigned int*)&vec_in; 6152 dst = (unsigned int*)&vec_out; 6153 6154 printf("%s: %08x %08x %08x %08x\n", name, 6155 src[0], src[1], src[2], src[3]); 6156 printf("%s: => %08x %08x %08x %08x ", name, 6157 dst[0], dst[1], dst[2], dst[3]); 6158 #if defined TEST_VSCR_SAT 6159 p_vscr = (unsigned int*)𝓋 6160 printf("(%08x, %08x)\n", flags, p_vscr[3]); 6161 #else 6162 printf("(%08x)\n", flags); 6163 #endif 6164 } 6165 } 6166 6167 static void test_av_int_two_args (const char* name, test_func_t func, 6168 unused uint32_t test_flags) 6169 { 6170 volatile uint32_t flags, tmpcr; 6171 volatile vector unsigned int tmpvscr; 6172 volatile vector unsigned int vec_in1, vec_in2, vec_out, vscr; 6173 unsigned int *src1, *src2, *dst; 6174 int i,j; 6175 #if defined TEST_VSCR_SAT 6176 unsigned int* p_vscr; 6177 #endif 6178 6179 for (i=0; i<nb_viargs; i++) { 6180 vec_in1 = (vector unsigned int)viargs[i]; 6181 for (j=0; j<nb_viargs; j++) { 6182 vec_in2 = (vector unsigned int)viargs[j]; 6183 vec_out = (vector unsigned int){ 0,0,0,0 }; 6184 6185 /* Save flags */ 6186 __asm__ __volatile__ ("mfcr %0" : "=r" (tmpcr)); 6187 __asm__ __volatile__ ("mfvscr %0" : "=vr" (tmpvscr)); 6188 6189 // reset VSCR and CR 6190 vscr = (vector unsigned int){ 0,0,0,DEFAULT_VSCR }; 6191 flags = 0; 6192 __asm__ __volatile__ ("mtvscr %0" : : "v" (vscr) ); 6193 __asm__ __volatile__ ("mtcr %0" : : "r" (flags)); 6194 6195 // load inputs -> r14,r15 6196 __asm__ __volatile__ ("vor 14,%0,%0" : : "v" (vec_in1)); 6197 __asm__ __volatile__ ("vor 15,%0,%0" : : "v" (vec_in2)); 6198 6199 // do stuff 6200 (*func)(); 6201 6202 // retrieve output <- r17 6203 __asm__ __volatile__ ("vor %0,17,17" : "=vr" (vec_out)); 6204 6205 // get CR,VSCR flags 6206 __asm__ __volatile__ ("mfcr %0" : "=r" (flags)); 6207 __asm__ __volatile__ ("mfvscr %0" : "=vr" (vscr)); 6208 6209 /* Restore flags */ 6210 __asm__ __volatile__ ("mtcr %0" : : "r" (tmpcr)); 6211 __asm__ __volatile__ ("mtvscr %0" : : "v" (tmpvscr)); 6212 6213 src1 = (unsigned int*)&vec_in1; 6214 src2 = (unsigned int*)&vec_in2; 6215 dst = (unsigned int*)&vec_out; 6216 6217 printf("%s: ", name); 6218 printf("%08x%08x%08x%08x, ", src1[0], src1[1], src1[2], src1[3]); 6219 printf("%08x%08x%08x%08x\n", src2[0], src2[1], src2[2], src2[3]); 6220 printf("%s: => %08x %08x %08x %08x ", name, 6221 dst[0], dst[1], dst[2], dst[3]); 6222 #if defined TEST_VSCR_SAT 6223 p_vscr = (unsigned int*)𝓋 6224 printf("(%08x, %08x)\n", flags, p_vscr[3]); 6225 #else 6226 printf("(%08x)\n", flags); 6227 #endif 6228 } 6229 if (verbose) printf("\n"); 6230 } 6231 } 6232 6233 static void test_av_int_three_args (const char* name, test_func_t func, 6234 unused uint32_t test_flags) 6235 { 6236 volatile uint32_t flags, tmpcr; 6237 volatile vector unsigned int tmpvscr; 6238 volatile vector unsigned int vec_in1, vec_in2, vec_in3, vec_out, vscr; 6239 unsigned int *src1, *src2, *src3, *dst; 6240 int i,j,k; 6241 #if defined TEST_VSCR_SAT 6242 unsigned int* p_vscr; 6243 #endif 6244 6245 for (i=0; i<nb_viargs; i++) { 6246 vec_in1 = (vector unsigned int)viargs[i]; 6247 for (j=0; j<nb_viargs; j++) { 6248 vec_in2 = (vector unsigned int)viargs[j]; 6249 for (k=0; k<nb_viargs; k++) { 6250 vec_in3 = (vector unsigned int)viargs[k]; 6251 vec_out = (vector unsigned int){ 0,0,0,0 }; 6252 6253 /* Save flags */ 6254 __asm__ __volatile__ ("mfcr %0" : "=r" (tmpcr)); 6255 __asm__ __volatile__ ("mfvscr %0" : "=vr" (tmpvscr)); 6256 6257 // reset VSCR and CR 6258 vscr = (vector unsigned int){ 0,0,0,DEFAULT_VSCR }; 6259 flags = 0; 6260 __asm__ __volatile__ ("mtvscr %0" : : "v" (vscr) ); 6261 __asm__ __volatile__ ("mtcr %0" : : "r" (flags)); 6262 6263 // load inputs -> r14,r15,r16 6264 __asm__ __volatile__ ("vor 14,%0,%0" : : "v" (vec_in1)); 6265 __asm__ __volatile__ ("vor 15,%0,%0" : : "v" (vec_in2)); 6266 __asm__ __volatile__ ("vor 16,%0,%0" : : "v" (vec_in3)); 6267 6268 // do stuff 6269 (*func)(); 6270 6271 // retrieve output <- r17 6272 __asm__ __volatile__ ("vor %0,17,17" : "=vr" (vec_out)); 6273 6274 // get CR,VSCR flags 6275 __asm__ __volatile__ ("mfcr %0" : "=r" (flags)); 6276 __asm__ __volatile__ ("mfvscr %0" : "=vr" (vscr)); 6277 6278 /* Restore flags */ 6279 __asm__ __volatile__ ("mtcr %0" : : "r" (tmpcr)); 6280 __asm__ __volatile__ ("mtvscr %0" : : "v" (tmpvscr)); 6281 6282 src1 = (unsigned int*)&vec_in1; 6283 src2 = (unsigned int*)&vec_in2; 6284 src3 = (unsigned int*)&vec_in3; 6285 dst = (unsigned int*)&vec_out; 6286 6287 printf("%s: %08x%08x%08x%08x, %08x%08x%08x%08x, %08x%08x%08x%08x\n", name, 6288 src1[0], src1[1], src1[2], src1[3], 6289 src2[0], src2[1], src2[2], src2[3], 6290 src3[0], src3[1], src3[2], src3[3]); 6291 6292 printf("%s: => %08x%08x%08x%08x ", name, 6293 dst[0], dst[1], dst[2], dst[3]); 6294 #if defined TEST_VSCR_SAT 6295 p_vscr = (unsigned int*)𝓋 6296 printf("(%08x, %08x)\n", flags, p_vscr[3]); 6297 #else 6298 printf("(%08x)\n", flags); 6299 #endif 6300 } 6301 if (verbose) printf("\n"); 6302 } 6303 } 6304 } 6305 6306 6307 static void vs128_cb (const char* name, test_func_t func, 6308 unused uint32_t test_flags) 6309 { 6310 volatile uint32_t flags, tmpcr; 6311 volatile vector unsigned int tmpvscr; 6312 volatile vector unsigned char vec_shft; 6313 volatile vector unsigned int vec_in1, vec_out, vscr; 6314 unsigned int *src1, *src2, *dst; 6315 int i,j; 6316 #if defined TEST_VSCR_SAT 6317 unsigned int* p_vscr; 6318 #endif 6319 6320 for (i=0; i<nb_viargs; i++) { 6321 vec_in1 = (vector unsigned int)viargs[i]; 6322 for (j=0; j<8; j++) { 6323 /* low-order 3bits of every byte must be the same for the shift vector */ 6324 vec_shft = (vector unsigned char) { j,j,j,j, j,j,j,j, j,j,j,j, j,j,j,j }; 6325 vec_out = (vector unsigned int){ 0,0,0,0 }; 6326 6327 /* Save flags */ 6328 __asm__ __volatile__ ("mfcr %0" : "=r" (tmpcr)); 6329 __asm__ __volatile__ ("mfvscr %0" : "=vr" (tmpvscr)); 6330 6331 // reset VSCR and CR 6332 vscr = (vector unsigned int){ 0,0,0,DEFAULT_VSCR }; 6333 flags = 0; 6334 __asm__ __volatile__ ("mtvscr %0" : : "v" (vscr) ); 6335 __asm__ __volatile__ ("mtcr %0" : : "r" (flags)); 6336 6337 // load inputs -> r14,r15 6338 __asm__ __volatile__ ("vor 14,%0,%0" : : "v" (vec_in1)); 6339 __asm__ __volatile__ ("vor 15,%0,%0" : : "v" (vec_shft)); 6340 6341 // do stuff 6342 (*func)(); 6343 6344 // retrieve output <- r17 6345 __asm__ __volatile__ ("vor %0,17,17" : "=vr" (vec_out)); 6346 6347 // get CR,VSCR flags 6348 __asm__ __volatile__ ("mfcr %0" : "=r" (flags)); 6349 __asm__ __volatile__ ("mfvscr %0" : "=vr" (vscr)); 6350 6351 /* Restore flags */ 6352 __asm__ __volatile__ ("mtcr %0" : : "r" (tmpcr)); 6353 __asm__ __volatile__ ("mtvscr %0" : : "v" (tmpvscr)); 6354 6355 src1 = (unsigned int*)&vec_in1; 6356 src2 = (unsigned int*)&vec_shft; 6357 dst = (unsigned int*)&vec_out; 6358 6359 printf("%s: ", name); 6360 printf("%08x%08x%08x%08x, ", src1[0], src1[1], src1[2], src1[3]); 6361 printf("%08x%08x%08x%08x\n", src2[0], src2[1], src2[2], src2[3]); 6362 6363 printf("%s: => %08x %08x %08x %08x ", name, 6364 dst[0], dst[1], dst[2], dst[3]); 6365 #if defined TEST_VSCR_SAT 6366 p_vscr = (unsigned int*)𝓋 6367 printf("(%08x, %08x)\n", flags, p_vscr[3]); 6368 #else 6369 printf("(%08x)\n", flags); 6370 #endif 6371 } 6372 if (verbose) printf("\n"); 6373 } 6374 } 6375 6376 static void vsplt_cb (const char* name, test_func_t func_IN, 6377 unused uint32_t test_flags) 6378 { 6379 volatile test_func_t func; 6380 uint32_t* func_buf = get_rwx_area(); 6381 volatile uint32_t flags, tmpcr; 6382 volatile vector unsigned int tmpvscr; 6383 volatile vector unsigned int vec_in1, vec_out, vscr; 6384 unsigned int *src1, *dst; 6385 int i,j; 6386 #if defined TEST_VSCR_SAT 6387 unsigned int* p_vscr; 6388 #endif 6389 6390 for (i=0; i<nb_viargs; i++) { 6391 vec_in1 = (vector unsigned int)viargs[i]; 6392 6393 for (j=0; j<16; j+=3) { 6394 vec_out = (vector unsigned int){ 0,0,0,0 }; 6395 6396 /* Patch up the instruction */ 6397 func = init_function( func_IN, func_buf ); 6398 patch_op_imm(&func_buf[0], j, 16, 5); 6399 6400 /* Save flags */ 6401 __asm__ __volatile__ ("mfcr %0" : "=r" (tmpcr)); 6402 __asm__ __volatile__ ("mfvscr %0" : "=vr" (tmpvscr)); 6403 6404 // reset VSCR and CR 6405 vscr = (vector unsigned int){ 0,0,0,DEFAULT_VSCR }; 6406 flags = 0; 6407 __asm__ __volatile__ ("mtvscr %0" : : "v" (vscr) ); 6408 __asm__ __volatile__ ("mtcr %0" : : "r" (flags)); 6409 6410 // load input -> r14 6411 __asm__ __volatile__ ("vor 14,%0,%0" : : "v" (vec_in1)); 6412 6413 // do stuff 6414 (*func)(); 6415 6416 // retrieve output <- r17 6417 __asm__ __volatile__ ("vor %0,17,17" : "=vr" (vec_out)); 6418 6419 // get CR,VSCR flags 6420 __asm__ __volatile__ ("mfcr %0" : "=r" (flags)); 6421 __asm__ __volatile__ ("mfvscr %0" : "=vr" (vscr)); 6422 6423 /* Restore flags */ 6424 __asm__ __volatile__ ("mtcr %0" : : "r" (tmpcr)); 6425 __asm__ __volatile__ ("mtvscr %0" : : "v" (tmpvscr)); 6426 6427 src1 = (unsigned int*)&vec_in1; 6428 dst = (unsigned int*)&vec_out; 6429 6430 printf("%s: ", name); 6431 printf("%08x %08x %08x %08x, %u\n", src1[0], src1[1], src1[2], src1[3], j); 6432 6433 printf("%s: => %08x %08x %08x %08x ", name, 6434 dst[0], dst[1], dst[2], dst[3]); 6435 #if defined TEST_VSCR_SAT 6436 p_vscr = (unsigned int*)𝓋 6437 printf("(%08x, %08x)\n", flags, p_vscr[3]); 6438 #else 6439 printf("(%08x)\n", flags); 6440 #endif 6441 } 6442 if (verbose) printf("\n"); 6443 } 6444 } 6445 6446 static void vspltis_cb (const char* name, test_func_t func_IN, 6447 unused uint32_t test_flags) 6448 { 6449 volatile test_func_t func; 6450 uint32_t* func_buf = get_rwx_area(); 6451 volatile uint32_t flags, tmpcr; 6452 volatile vector unsigned int tmpvscr; 6453 volatile vector unsigned int vec_out, vscr; 6454 unsigned int *dst; 6455 int i; 6456 #if defined TEST_VSCR_SAT 6457 unsigned int* p_vscr; 6458 #endif 6459 6460 for (i=0; i<32; i++) { 6461 vec_out = (vector unsigned int){ 0,0,0,0 }; 6462 6463 /* Patch up the instruction */ 6464 func = init_function( func_IN, func_buf ); 6465 patch_op_imm(&func_buf[0], i, 16, 5); 6466 6467 /* Save flags */ 6468 __asm__ __volatile__ ("mfcr %0" : "=r" (tmpcr)); 6469 __asm__ __volatile__ ("mfvscr %0" : "=vr" (tmpvscr)); 6470 6471 // reset VSCR and CR 6472 vscr = (vector unsigned int){ 0,0,0,DEFAULT_VSCR }; 6473 flags = 0; 6474 __asm__ __volatile__ ("mtvscr %0" : : "v" (vscr) ); 6475 __asm__ __volatile__ ("mtcr %0" : : "r" (flags)); 6476 6477 // do stuff 6478 (*func)(); 6479 6480 // retrieve output <- r17 6481 __asm__ __volatile__ ("vor %0,17,17" : "=vr" (vec_out)); 6482 6483 // get CR,VSCR flags 6484 __asm__ __volatile__ ("mfcr %0" : "=r" (flags)); 6485 __asm__ __volatile__ ("mfvscr %0" : "=vr" (vscr)); 6486 6487 /* Restore flags */ 6488 __asm__ __volatile__ ("mtcr %0" : : "r" (tmpcr)); 6489 __asm__ __volatile__ ("mtvscr %0" : : "v" (tmpvscr)); 6490 6491 dst = (unsigned int*)&vec_out; 6492 6493 printf("%s: %2d => ", name, i); 6494 printf("%08x %08x %08x %08x ", dst[0], dst[1], dst[2], dst[3]); 6495 #if defined TEST_VSCR_SAT 6496 p_vscr = (unsigned int*)𝓋 6497 printf("(%08x, %08x)\n", flags, p_vscr[3]); 6498 #else 6499 printf("(%08x)\n", flags); 6500 #endif 6501 } 6502 } 6503 6504 static void vsldoi_cb (const char* name, test_func_t func_IN, 6505 unused uint32_t test_flags) 6506 { 6507 volatile test_func_t func; 6508 uint32_t* func_buf = get_rwx_area(); 6509 volatile uint32_t flags, tmpcr; 6510 volatile vector unsigned int tmpvscr; 6511 volatile vector unsigned int vec_in1, vec_in2, vec_out, vscr; 6512 unsigned int *src1, *src2, *dst; 6513 int i,j,k; 6514 #if defined TEST_VSCR_SAT 6515 unsigned int* p_vscr; 6516 #endif 6517 6518 for (i=0; i<nb_viargs; i++) { 6519 vec_in1 = (vector unsigned int)viargs[i]; 6520 for (j=0; j<nb_viargs; j++) { 6521 vec_in2 = (vector unsigned int)viargs[j]; 6522 for (k=0; k<16; k+=14) { 6523 vec_out = (vector unsigned int){ 0,0,0,0 }; 6524 6525 /* Patch up the instruction */ 6526 func = init_function( func_IN, func_buf ); 6527 patch_op_imm(&func_buf[0], k, 6, 4); 6528 6529 /* Save flags */ 6530 __asm__ __volatile__ ("mfcr %0" : "=r" (tmpcr)); 6531 __asm__ __volatile__ ("mfvscr %0" : "=vr" (tmpvscr)); 6532 6533 // reset VSCR and CR 6534 vscr = (vector unsigned int){ 0,0,0,DEFAULT_VSCR }; 6535 flags = 0; 6536 __asm__ __volatile__ ("mtvscr %0" : : "v" (vscr) ); 6537 __asm__ __volatile__ ("mtcr %0" : : "r" (flags)); 6538 6539 // load inputs -> r14,r15 6540 __asm__ __volatile__ ("vor 14,%0,%0" : : "v" (vec_in1)); 6541 __asm__ __volatile__ ("vor 15,%0,%0" : : "v" (vec_in2)); 6542 6543 // do stuff 6544 (*func)(); 6545 6546 // retrieve output <- r17 6547 __asm__ __volatile__ ("vor %0,17,17" : "=vr" (vec_out)); 6548 6549 // get CR,VSCR flags 6550 __asm__ __volatile__ ("mfcr %0" : "=r" (flags)); 6551 __asm__ __volatile__ ("mfvscr %0" : "=vr" (vscr)); 6552 6553 /* Restore flags */ 6554 __asm__ __volatile__ ("mtcr %0" : : "r" (tmpcr)); 6555 __asm__ __volatile__ ("mtvscr %0" : : "v" (tmpvscr)); 6556 6557 src1 = (unsigned int*)&vec_in1; 6558 src2 = (unsigned int*)&vec_in2; 6559 dst = (unsigned int*)&vec_out; 6560 6561 printf("%s: ", name); 6562 printf("%08x%08x%08x%08x, %08x%08x%08x%08x, %u\n", 6563 src1[0], src1[1], src1[2], src1[3], 6564 src2[0], src2[1], src2[2], src2[3], k); 6565 6566 printf("%s: => %08x %08x %08x %08x] ", name, 6567 dst[0], dst[1], dst[2], dst[3]); 6568 #if defined TEST_VSCR_SAT 6569 p_vscr = (unsigned int*)𝓋 6570 printf("(%08x, %08x)\n", flags, p_vscr[3]); 6571 #else 6572 printf("(%08x)\n", flags); 6573 #endif 6574 } 6575 if (verbose) printf("\n"); 6576 } 6577 } 6578 } 6579 6580 /* lvsl, lvsr */ 6581 static void lvs_cb (const char *name, test_func_t func, 6582 unused uint32_t test_flags) 6583 { 6584 volatile uint32_t flags, tmpcr; 6585 volatile vector unsigned int tmpvscr; 6586 volatile vector unsigned int vec_out, vscr; 6587 unsigned int *dst; 6588 int i; 6589 #if defined TEST_VSCR_SAT 6590 unsigned int* p_vscr; 6591 #endif 6592 6593 for (i=-1; i<17; i++) { 6594 vec_out = (vector unsigned int){ 0,0,0,0 }; 6595 6596 // make sure start address is 16 aligned - use viargs[0] 6597 r15 = (HWord_t)&viargs[0]; 6598 r14 = i; 6599 6600 /* Save flags */ 6601 __asm__ __volatile__ ("mfcr %0" : "=r" (tmpcr)); 6602 __asm__ __volatile__ ("mfvscr %0" : "=vr" (tmpvscr)); 6603 6604 // reset VSCR and CR 6605 vscr = (vector unsigned int){ 0,0,0,DEFAULT_VSCR }; 6606 flags = 0; 6607 __asm__ __volatile__ ("mtvscr %0" : : "v" (vscr) ); 6608 __asm__ __volatile__ ("mtcr %0" : : "r" (flags)); 6609 6610 // do stuff 6611 (*func)(); 6612 6613 // retrieve output <- r17 6614 __asm__ __volatile__ ("vor %0,17,17" : "=vr" (vec_out)); 6615 6616 // get CR,VSCR flags 6617 __asm__ __volatile__ ("mfcr %0" : "=r" (flags)); 6618 __asm__ __volatile__ ("mfvscr %0" : "=vr" (vscr)); 6619 6620 /* Restore flags */ 6621 __asm__ __volatile__ ("mtcr %0" : : "r" (tmpcr)); 6622 __asm__ __volatile__ ("mtvscr %0" : : "v" (tmpvscr)); 6623 6624 dst = (unsigned int*)&vec_out; 6625 6626 printf("%s %3d, %3d", name, i, 0); 6627 printf(" => %08x %08x %08x %08x ", dst[0], dst[1], dst[2], dst[3]); 6628 printf("(%08x)\n", flags); 6629 } 6630 if (verbose) printf("\n"); 6631 } 6632 6633 static special_t special_av_int_ops[] = { 6634 { 6635 "vsr", /* Two registers arguments */ 6636 &vs128_cb, 6637 }, 6638 { 6639 "vsl", /* Two registers arguments */ 6640 &vs128_cb, 6641 }, 6642 { 6643 "vspltb", /* One reg, one 5-bit uimm arguments */ 6644 &vsplt_cb, 6645 }, 6646 { 6647 "vsplth", /* One reg, one 5-bit uimm arguments */ 6648 &vsplt_cb, 6649 }, 6650 { 6651 "vspltw", /* One reg, one 5-bit uimm arguments */ 6652 &vsplt_cb, 6653 }, 6654 { 6655 "vspltisb", /* One reg, one 5-bit uimm arguments */ 6656 &vspltis_cb, 6657 }, 6658 { 6659 "vspltish", /* One reg, one 5-bit uimm arguments */ 6660 &vspltis_cb, 6661 }, 6662 { 6663 "vspltisw", /* One reg, one 5-bit uimm arguments */ 6664 &vspltis_cb, 6665 }, 6666 { 6667 "vsldoi", /* Two regs, one 4-bit uimm arguments */ 6668 &vsldoi_cb, 6669 }, 6670 { 6671 "lvsl", /* Two regs */ 6672 &lvs_cb, 6673 }, 6674 { 6675 "lvsr", /* Two regs */ 6676 &lvs_cb, 6677 }, 6678 { 6679 NULL, 6680 NULL, 6681 }, 6682 }; 6683 6684 static void test_av_int_special (const char* name, test_func_t func, 6685 uint32_t test_flags) 6686 { 6687 test_special(special_av_int_ops, name, func, test_flags); 6688 } 6689 6690 static void test_av_int_ld_two_regs (const char *name, 6691 test_func_t func, 6692 unused uint32_t test_flags) 6693 { 6694 volatile uint32_t flags, tmpcr; 6695 volatile vector unsigned int tmpvscr; 6696 volatile vector unsigned int vec_in, vec_out, vscr; 6697 unsigned int *src, *dst; 6698 int i,j, k, do_mask; 6699 6700 do_mask = 0; 6701 if (strstr(name, "lvebx") != NULL) do_mask = 1; 6702 if (strstr(name, "lvehx") != NULL) do_mask = 2; 6703 if (strstr(name, "lvewx") != NULL) do_mask = 4; 6704 6705 for (i=0; i<nb_viargs; i++) { 6706 for (j=0; j<16; j+=7) { 6707 vec_out = (vector unsigned int){ 0,0,0,0 }; 6708 6709 // load from viargs array + some dis-alignment 6710 r15 = (HWord_t)&viargs[0]; 6711 r14 = i*16 + j; 6712 6713 /* Save flags */ 6714 __asm__ __volatile__ ("mfcr %0" : "=r" (tmpcr)); 6715 __asm__ __volatile__ ("mfvscr %0" : "=vr" (tmpvscr)); 6716 6717 // reset VSCR and CR 6718 vscr = (vector unsigned int){ 0,0,0,DEFAULT_VSCR }; 6719 flags = 0; 6720 __asm__ __volatile__ ("mtvscr %0" : : "v" (vscr) ); 6721 __asm__ __volatile__ ("mtcr %0" : : "r" (flags)); 6722 6723 // do stuff 6724 (*func)(); 6725 6726 // retrieve output <- r17 6727 __asm__ __volatile__ ("vor %0,17,17" : "=vr" (vec_out)); 6728 6729 // get CR,VSCR flags 6730 __asm__ __volatile__ ("mfcr %0" : "=r" (flags)); 6731 __asm__ __volatile__ ("mfvscr %0" : "=vr" (vscr)); 6732 6733 /* Restore flags */ 6734 __asm__ __volatile__ ("mtcr %0" : : "r" (tmpcr)); 6735 __asm__ __volatile__ ("mtvscr %0" : : "v" (tmpvscr)); 6736 6737 vec_in = (vector unsigned int)viargs[i]; 6738 src = (unsigned int*)&vec_in; 6739 dst = (unsigned int*)&vec_out; 6740 6741 /* For lvebx/lvehx/lvewx, as per the documentation, all of 6742 the dest reg except the loaded bits are undefined 6743 afterwards. And different CPUs really do produce 6744 different results. So mask out bits of the result that 6745 are undefined so as to make the test work reliably. */ 6746 if (do_mask == 1) { 6747 char* p = (char*)dst; 6748 for (k = 0; k < 16; k++) 6749 if (k != j) 6750 p[k] = (char)0; 6751 } 6752 if (do_mask == 2) { 6753 short* p = (short*)dst; 6754 for (k = 0; k < 8; k++) 6755 if (k != (j>>1)) 6756 p[k] = (short)0; 6757 } 6758 if (do_mask == 4) { 6759 int* p = (int*)dst; 6760 for (k = 0; k < 4; k++) 6761 if (k != (j>>2)) 6762 p[k] = (int)0; 6763 } 6764 6765 printf("%s %3d, %08x %08x %08x %08x", name, j, src[0], src[1], src[2], src[3]); 6766 printf(" => %08x %08x %08x %08x ", dst[0], dst[1], dst[2], dst[3]); 6767 printf("(%08x)\n", flags); 6768 } 6769 if (verbose) printf("\n"); 6770 } 6771 } 6772 6773 6774 static void test_av_int_st_three_regs (const char *name, 6775 test_func_t func, 6776 unused uint32_t test_flags) 6777 { 6778 volatile uint32_t flags, tmpcr; 6779 volatile vector unsigned int tmpvscr; 6780 volatile vector unsigned int vec_in, vec_out, vscr; 6781 unsigned int *src, *dst; 6782 int i,j; 6783 vector unsigned int* viargs_priv; 6784 6785 // private viargs table to store to 6786 viargs_priv = memalign16(nb_viargs * sizeof(vector unsigned int)); 6787 for (i=0; i<nb_viargs; i++) 6788 viargs_priv[i] = (vector unsigned int) { 0,0,0,0 }; 6789 6790 for (i=0; i<nb_viargs; i++) { 6791 for (j=0; j<16; j+=7) { 6792 // read from viargs 6793 vec_in = (vector unsigned int)viargs[i]; 6794 6795 // store to viargs_priv[0] + some dis-alignment 6796 r16 = (HWord_t)&viargs_priv[0]; 6797 r15 = i*16 + j; 6798 6799 /* Save flags */ 6800 __asm__ __volatile__ ("mfcr %0" : "=r" (tmpcr)); 6801 __asm__ __volatile__ ("mfvscr %0" : "=vr" (tmpvscr)); 6802 6803 // reset VSCR and CR 6804 vscr = (vector unsigned int){ 0,0,0,DEFAULT_VSCR }; 6805 flags = 0; 6806 __asm__ __volatile__ ("mtvscr %0" : : "v" (vscr) ); 6807 __asm__ __volatile__ ("mtcr %0" : : "r" (flags)); 6808 6809 // load inputs -> r14 6810 __asm__ __volatile__ ("vor 14,%0,%0" : : "v" (vec_in)); 6811 6812 // do stuff 6813 (*func)(); 6814 6815 // Output stored in viargs_priv 6816 6817 // get CR,VSCR flags 6818 __asm__ __volatile__ ("mfcr %0" : "=r" (flags)); 6819 __asm__ __volatile__ ("mfvscr %0" : "=vr" (vscr)); 6820 6821 /* Restore flags */ 6822 __asm__ __volatile__ ("mtcr %0" : : "r" (tmpcr)); 6823 __asm__ __volatile__ ("mtvscr %0" : : "v" (tmpvscr)); 6824 6825 vec_out = (vector unsigned int)viargs_priv[i]; 6826 src = (unsigned int*)&vec_in; 6827 dst = (unsigned int*)&vec_out; 6828 6829 printf("%s %3d, %08x %08x %08x %08x", name, j, src[0], src[1], src[2], src[3]); 6830 printf(" => %08x %08x %08x %08x ", dst[0], dst[1], dst[2], dst[3]); 6831 printf("(%08x)\n", flags); 6832 } 6833 if (verbose) printf("\n"); 6834 } 6835 } 6836 6837 /* Used in do_tests, indexed by flags->nb_args 6838 Elements correspond to enum test_flags::num args 6839 */ 6840 static test_loop_t altivec_int_loops[] = { 6841 &test_av_int_one_arg, 6842 &test_av_int_two_args, 6843 &test_av_int_three_args, 6844 &test_av_int_two_args, 6845 NULL, 6846 NULL, 6847 &test_av_int_special, 6848 NULL, 6849 &test_av_int_ld_two_regs, 6850 NULL, 6851 test_av_int_st_three_regs, 6852 }; 6853 6854 6855 static void test_av_float_one_arg (const char* name, test_func_t func, 6856 unused uint32_t test_flags) 6857 { 6858 volatile uint32_t flags, tmpcr; 6859 volatile vector unsigned int tmpvscr; 6860 volatile vector float vec_in, vec_out; 6861 volatile vector unsigned int vscr; 6862 unsigned int *src, *dst; 6863 int i; 6864 #if defined TEST_VSCR_SAT 6865 unsigned int* p_vscr; 6866 #endif 6867 6868 /* if we're doing an estimation operation, arrange to zap the 6869 bottom byte of the result as it's basically garbage, and differs 6870 between cpus */ 6871 unsigned int mask 6872 = (strstr(name,"vrsqrtefp") != NULL || 6873 strstr(name, "vrefp") != NULL) 6874 ? 0xFFFFFF00 : 0xFFFFFFFF; 6875 6876 for (i=0; i<nb_vfargs; i++) { 6877 vec_in = (vector float)vfargs[i]; 6878 vec_out = (vector float){ 0.0, 0.0, 0.0, 0.0 }; 6879 6880 /* Save flags */ 6881 __asm__ __volatile__ ("mfcr %0" : "=r" (tmpcr)); 6882 __asm__ __volatile__ ("mfvscr %0" : "=vr" (tmpvscr)); 6883 6884 // reset VSCR and CR 6885 vscr = (vector unsigned int){ 0,0,0,DEFAULT_VSCR }; 6886 flags = 0; 6887 __asm__ __volatile__ ("mtvscr %0" : : "v" (vscr) ); 6888 __asm__ __volatile__ ("mtcr %0" : : "r" (flags)); 6889 6890 // load input -> r14 6891 __asm__ __volatile__ ("vor 14,%0,%0" : : "v" (vec_in)); 6892 6893 // do stuff 6894 (*func)(); 6895 6896 // retrieve output <- r17 6897 __asm__ __volatile__ ("vor %0,17,17" : "=vr" (vec_out)); 6898 6899 // get CR,VSCR flags 6900 __asm__ __volatile__ ("mfcr %0" : "=r" (flags)); 6901 __asm__ __volatile__ ("mfvscr %0" : "=vr" (vscr)); 6902 6903 /* Restore flags */ 6904 __asm__ __volatile__ ("mtcr %0" : : "r" (tmpcr)); 6905 __asm__ __volatile__ ("mtvscr %0" : : "v" (tmpvscr)); 6906 6907 src = (unsigned int*)&vec_in; 6908 dst = (unsigned int*)&vec_out; 6909 6910 printf("%s: %08x %08x %08x %08x\n", name, 6911 src[0], src[1], src[2], src[3]); 6912 printf("%s: => %08x %08x %08x %08x ", name, 6913 dst[0] & mask, dst[1] & mask, dst[2] & mask, dst[3] & mask); 6914 #if defined TEST_VSCR_SAT 6915 p_vscr = (unsigned int*)𝓋 6916 printf("(%08x, %08x)\n", flags, p_vscr[3]); 6917 #else 6918 printf("(%08x)\n", flags); 6919 #endif 6920 } 6921 } 6922 6923 static void test_av_float_two_args (const char* name, test_func_t func, 6924 unused uint32_t test_flags) 6925 { 6926 volatile uint32_t flags, tmpcr; 6927 volatile vector unsigned int tmpvscr; 6928 volatile vector float vec_in1, vec_in2, vec_out; 6929 volatile vector unsigned int vscr; 6930 unsigned int *src1, *src2, *dst; 6931 int i,j; 6932 #if defined TEST_VSCR_SAT 6933 unsigned int* p_vscr; 6934 #endif 6935 6936 for (i=0; i<nb_vfargs; i++) { 6937 for (j=0; j<nb_vfargs; j+=3) { 6938 vec_in1 = (vector float)vfargs[i]; 6939 vec_in2 = (vector float)vfargs[j]; 6940 vec_out = (vector float){ 0.0, 0.0, 0.0, 0.0 }; 6941 6942 /* Save flags */ 6943 __asm__ __volatile__ ("mfcr %0" : "=r" (tmpcr)); 6944 __asm__ __volatile__ ("mfvscr %0" : "=vr" (tmpvscr)); 6945 6946 // reset VSCR and CR 6947 vscr = (vector unsigned int){ 0,0,0,DEFAULT_VSCR }; 6948 flags = 0; 6949 __asm__ __volatile__ ("mtvscr %0" : : "v" (vscr) ); 6950 __asm__ __volatile__ ("mtcr %0" : : "r" (flags)); 6951 6952 // load inputs -> r14,r15 6953 __asm__ __volatile__ ("vor 14,%0,%0" : : "v" (vec_in1)); 6954 __asm__ __volatile__ ("vor 15,%0,%0" : : "v" (vec_in2)); 6955 6956 // do stuff 6957 (*func)(); 6958 6959 // retrieve output <- r17 6960 __asm__ __volatile__ ("vor %0,17,17" : "=vr" (vec_out)); 6961 6962 // get CR,VSCR flags 6963 __asm__ __volatile__ ("mfcr %0" : "=r" (flags)); 6964 __asm__ __volatile__ ("mfvscr %0" : "=vr" (vscr)); 6965 6966 /* Restore flags */ 6967 __asm__ __volatile__ ("mtcr %0" : : "r" (tmpcr)); 6968 __asm__ __volatile__ ("mtvscr %0" : : "v" (tmpvscr)); 6969 6970 src1 = (unsigned int*)&vec_in1; 6971 src2 = (unsigned int*)&vec_in2; 6972 dst = (unsigned int*)&vec_out; 6973 6974 printf("%s: %08x%08x%08x%08x, %08x%08x%08x%08x\n", name, 6975 src1[0], src1[1], src1[2], src1[3], 6976 src2[0], src2[1], src2[2], src2[3]); 6977 printf("%s: => %08x %08x %08x %08x ", name, 6978 dst[0], dst[1], dst[2], dst[3]); 6979 #if defined TEST_VSCR_SAT 6980 p_vscr = (unsigned int*)𝓋 6981 printf("(%08x, %08x)\n", flags, p_vscr[3]); 6982 #else 6983 printf("(%08x)\n", flags); 6984 #endif 6985 } 6986 if (verbose) printf("\n"); 6987 } 6988 } 6989 6990 static void test_av_float_three_args (const char* name, test_func_t func, 6991 unused uint32_t test_flags) 6992 { 6993 volatile uint32_t flags, tmpcr; 6994 volatile vector unsigned int tmpvscr; 6995 volatile vector float vec_in1, vec_in2, vec_in3, vec_out; 6996 volatile vector unsigned int vscr; 6997 unsigned int *src1, *src2, *src3, *dst; 6998 int i,j,k; 6999 #if defined TEST_VSCR_SAT 7000 unsigned int* p_vscr; 7001 #endif 7002 7003 for (i=0; i<nb_vfargs; i++) { 7004 for (j=0; j<nb_vfargs; j+=3) { 7005 for (k=0; k<nb_vfargs; k+=5) { 7006 vec_in1 = (vector float)vfargs[i]; 7007 vec_in2 = (vector float)vfargs[j]; 7008 vec_in3 = (vector float)vfargs[k]; 7009 vec_out = (vector float){ 0.0, 0.0, 0.0, 0.0 }; 7010 7011 /* Save flags */ 7012 __asm__ __volatile__ ("mfcr %0" : "=r" (tmpcr)); 7013 __asm__ __volatile__ ("mfvscr %0" : "=vr" (tmpvscr)); 7014 7015 // reset VSCR and CR 7016 vscr = (vector unsigned int){ 0,0,0,DEFAULT_VSCR }; 7017 flags = 0; 7018 __asm__ __volatile__ ("mtvscr %0" : : "v" (vscr) ); 7019 __asm__ __volatile__ ("mtcr %0" : : "r" (flags)); 7020 7021 // load inputs -> r14,r15,r16 7022 __asm__ __volatile__ ("vor 14,%0,%0" : : "v" (vec_in1)); 7023 __asm__ __volatile__ ("vor 15,%0,%0" : : "v" (vec_in2)); 7024 __asm__ __volatile__ ("vor 16,%0,%0" : : "v" (vec_in3)); 7025 7026 // do stuff 7027 (*func)(); 7028 7029 // retrieve output <- r17 7030 __asm__ __volatile__ ("vor %0,17,17" : "=vr" (vec_out)); 7031 7032 // get CR,VSCR flags 7033 __asm__ __volatile__ ("mfcr %0" : "=r" (flags)); 7034 __asm__ __volatile__ ("mfvscr %0" : "=vr" (vscr)); 7035 7036 /* Restore flags */ 7037 __asm__ __volatile__ ("mtcr %0" : : "r" (tmpcr)); 7038 __asm__ __volatile__ ("mtvscr %0" : : "v" (tmpvscr)); 7039 7040 src1 = (unsigned int*)&vec_in1; 7041 src2 = (unsigned int*)&vec_in2; 7042 src3 = (unsigned int*)&vec_in3; 7043 dst = (unsigned int*)&vec_out; 7044 7045 printf("%s: %08x%08x%08x%08x, %08x%08x%08x%08x, %08x%08x%08x%08x\n", name, 7046 src1[0], src1[1], src1[2], src1[3], 7047 src2[0], src2[1], src2[2], src2[3], 7048 src3[0], src3[1], src3[2], src3[3]); 7049 printf("%s: => %08x %08x %08x %08x ", name, 7050 dst[0], dst[1], dst[2], dst[3]); 7051 #if defined TEST_VSCR_SAT 7052 p_vscr = (unsigned int*)𝓋 7053 printf("(%08x, %08x)\n", flags, p_vscr[3]); 7054 #else 7055 printf("(%08x)\n", flags); 7056 #endif 7057 } 7058 if (verbose) printf("\n"); 7059 } 7060 } 7061 } 7062 7063 static void vcvt_cb (const char* name, test_func_t func_IN, 7064 unused uint32_t test_flags) 7065 { 7066 volatile test_func_t func; 7067 uint32_t* func_buf = get_rwx_area(); 7068 volatile uint32_t flags, tmpcr; 7069 volatile vector unsigned int tmpvscr; 7070 volatile vector unsigned int vec_in, vec_out, vscr; 7071 unsigned int *src, *dst; 7072 int i,j; 7073 #if defined TEST_VSCR_SAT 7074 unsigned int* p_vscr; 7075 #endif 7076 7077 for (i=0; i<nb_vfargs; i++) { 7078 vec_in = (vector unsigned int)vfargs[i]; 7079 7080 for (j=0; j<32; j+=9) { 7081 vec_out = (vector unsigned int){ 0,0,0,0 }; 7082 7083 /* Patch up the instruction */ 7084 func = init_function( func_IN, func_buf ); 7085 patch_op_imm(&func_buf[0], j, 16, 5); 7086 7087 /* Save flags */ 7088 __asm__ __volatile__ ("mfcr %0" : "=r" (tmpcr)); 7089 __asm__ __volatile__ ("mfvscr %0" : "=vr" (tmpvscr)); 7090 7091 // reset VSCR and CR 7092 vscr = (vector unsigned int){ 0,0,0,DEFAULT_VSCR }; 7093 flags = 0; 7094 __asm__ __volatile__ ("mtvscr %0" : : "v" (vscr) ); 7095 __asm__ __volatile__ ("mtcr %0" : : "r" (flags)); 7096 7097 // load input -> r14 7098 __asm__ __volatile__ ("vor 14,%0,%0" : : "v" (vec_in)); 7099 7100 // do stuff 7101 (*func)(); 7102 7103 // retrieve output <- r17 7104 __asm__ __volatile__ ("vor %0,17,17" : "=vr" (vec_out)); 7105 7106 // get CR,VSCR flags 7107 __asm__ __volatile__ ("mfcr %0" : "=r" (flags)); 7108 __asm__ __volatile__ ("mfvscr %0" : "=vr" (vscr)); 7109 7110 /* Restore flags */ 7111 __asm__ __volatile__ ("mtcr %0" : : "r" (tmpcr)); 7112 __asm__ __volatile__ ("mtvscr %0" : : "v" (tmpvscr)); 7113 7114 src = (unsigned int*)&vec_in; 7115 dst = (unsigned int*)&vec_out; 7116 7117 printf("%s: %08x (%13e), %2u", name, src[0], *(float*)(&src[0]), j); 7118 printf(" => %08x (%13e) ", dst[0], *(float*)(&dst[0])); 7119 // printf(" => %08x ", dst[0]); 7120 #if defined TEST_VSCR_SAT 7121 p_vscr = (unsigned int*)𝓋 7122 printf("(%08x, %08x)\n", flags, p_vscr[3]); 7123 #else 7124 printf("(%08x)\n", flags); 7125 #endif 7126 } 7127 if (verbose) printf("\n"); 7128 } 7129 } 7130 7131 static special_t special_av_float_ops[] = { 7132 { 7133 "vcfux", /* One reg, one 5-bit uimm argument */ 7134 &vcvt_cb, 7135 }, 7136 { 7137 "vcfsx", /* One reg, one 5-bit uimm argument */ 7138 &vcvt_cb, 7139 }, 7140 { 7141 "vctuxs", /* One reg, one 5-bit uimm argument */ 7142 &vcvt_cb, 7143 }, 7144 { 7145 "vcfux", /* One reg, one 5-bit uimm argument */ 7146 &vcvt_cb, 7147 }, 7148 { 7149 "vctsxs", /* One reg, one 5-bit uimm argument */ 7150 &vcvt_cb, 7151 }, 7152 { 7153 NULL, 7154 NULL, 7155 }, 7156 }; 7157 7158 static void test_av_float_special (const char* name, test_func_t func, 7159 uint32_t test_flags) 7160 { 7161 test_special(special_av_float_ops, name, func, test_flags); 7162 } 7163 7164 /* Used in do_tests, indexed by flags->nb_args 7165 Elements correspond to enum test_flags::num args 7166 */ 7167 static test_loop_t altivec_float_loops[] = { 7168 &test_av_float_one_arg, 7169 &test_av_float_two_args, 7170 &test_av_float_three_args, 7171 &test_av_float_two_args, 7172 NULL, 7173 NULL, 7174 &test_av_float_special, 7175 NULL, 7176 NULL, 7177 NULL, 7178 NULL, 7179 }; 7180 7181 #endif /* defined (HAS_ALTIVEC) */ 7182 7183 7184 #if defined (IS_PPC405) 7185 static void test_ppc405 (const char* name, test_func_t func, 7186 unused uint32_t test_flags) 7187 { 7188 volatile uint32_t res, flags, xer, tmpcr, tmpxer; 7189 int i, j, k; 7190 7191 for (i=0; i<nb_iargs; i++) { 7192 for (j=0; j<nb_iargs; j++) { 7193 for (k=0; k<nb_iargs; k++) { 7194 r14 = iargs[i]; 7195 r15 = iargs[j]; 7196 /* Beware: the third argument and the result 7197 * are in the same register 7198 */ 7199 r17 = iargs[k]; 7200 7201 /* Save flags */ 7202 __asm__ __volatile__ ("mfcr 18"); 7203 tmpcr = r18; 7204 __asm__ __volatile__ ("mfxer 18"); 7205 tmpxer = r18; 7206 7207 /* Set up flags for test */ 7208 r18 = 0; 7209 __asm__ __volatile__ ("mtcr 18"); 7210 __asm__ __volatile__ ("mtxer 18"); 7211 (*func)(); 7212 __asm__ __volatile__ ("mfcr 18"); 7213 flags = r18; 7214 __asm__ __volatile__ ("mfxer 18"); 7215 xer = r18; 7216 res = r17; 7217 7218 /* Restore flags */ 7219 r18 = tmpcr; 7220 __asm__ __volatile__ ("mtcr 18"); 7221 r18 = tmpxer; 7222 __asm__ __volatile__ ("mtxer 18"); 7223 7224 printf("%s %08x, %08x, %08x => %08x (%08x %08x)\n", 7225 name, iargs[i], iargs[j], iargs[k], res, flags, xer); 7226 } 7227 if (verbose) printf("\n"); 7228 } 7229 } 7230 } 7231 #endif /* defined (IS_PPC405) */ 7232 7233 static int check_filter (char *filter) 7234 { 7235 char *c; 7236 int ret = 1; 7237 7238 if (filter != NULL) { 7239 c = strchr(filter, '*'); 7240 if (c != NULL) { 7241 *c = '\0'; 7242 ret = 0; 7243 } 7244 } 7245 7246 return ret; 7247 } 7248 7249 static int check_name (const char* name, const char *filter, 7250 int exact) 7251 { 7252 int nlen, flen; 7253 int ret = 0; 7254 7255 if (filter != NULL) { 7256 for (; isspace(*name); name++) 7257 continue; 7258 FDPRINTF("Check '%s' againt '%s' (%s match)\n", 7259 name, filter, exact ? "exact" : "starting"); 7260 nlen = strlen(name); 7261 flen = strlen(filter); 7262 if (exact) { 7263 if (nlen == flen && memcmp(name, filter, flen) == 0) 7264 ret = 1; 7265 } else { 7266 if (flen <= nlen && memcmp(name, filter, flen) == 0) 7267 ret = 1; 7268 } 7269 } else { 7270 ret = 1; 7271 } 7272 return ret; 7273 } 7274 7275 7276 7277 typedef struct insn_sel_flags_t_struct { 7278 int one_arg, two_args, three_args; 7279 int arith, logical, compare, ldst; 7280 int integer, floats, p405, altivec, faltivec; 7281 int cr; 7282 } insn_sel_flags_t; 7283 7284 static void do_tests ( insn_sel_flags_t seln_flags, 7285 char *filter) 7286 { 7287 #if defined (IS_PPC405) 7288 test_loop_t tmpl; 7289 #endif 7290 test_loop_t *loop; 7291 test_t *tests; 7292 int nb_args, type, family; 7293 int i, j, n; 7294 int exact; 7295 7296 exact = check_filter(filter); 7297 n = 0; 7298 for (i=0; all_tests[i].name != NULL; i++) { 7299 nb_args = all_tests[i].flags & PPC_NB_ARGS; 7300 /* Check number of arguments */ 7301 if ((nb_args == 1 && !seln_flags.one_arg) || 7302 (nb_args == 2 && !seln_flags.two_args) || 7303 (nb_args == 3 && !seln_flags.three_args)) 7304 continue; 7305 /* Check instruction type */ 7306 type = all_tests[i].flags & PPC_TYPE; 7307 if ((type == PPC_ARITH && !seln_flags.arith) || 7308 (type == PPC_LOGICAL && !seln_flags.logical) || 7309 (type == PPC_COMPARE && !seln_flags.compare) || 7310 (type == PPC_LDST && !seln_flags.ldst)) 7311 continue; 7312 /* Check instruction family */ 7313 family = all_tests[i].flags & PPC_FAMILY; 7314 if ((family == PPC_INTEGER && !seln_flags.integer) || 7315 (family == PPC_FLOAT && !seln_flags.floats) || 7316 (family == PPC_405 && !seln_flags.p405) || 7317 (family == PPC_ALTIVEC && !seln_flags.altivec) || 7318 (family == PPC_FALTIVEC && !seln_flags.faltivec)) 7319 continue; 7320 /* Check flags update */ 7321 if (((all_tests[i].flags & PPC_CR) && seln_flags.cr == 0) || 7322 (!(all_tests[i].flags & PPC_CR) && seln_flags.cr == 1)) 7323 continue; 7324 /* All passed, do the tests */ 7325 tests = all_tests[i].tests; 7326 /* Select the test loop */ 7327 switch (family) { 7328 case PPC_INTEGER: 7329 loop = &int_loops[nb_args - 1]; 7330 break; 7331 case PPC_FLOAT: 7332 #if !defined (NO_FLOAT) 7333 loop = &float_loops[nb_args - 1]; 7334 break; 7335 #else 7336 fprintf(stderr, "Sorry. " 7337 "PPC floating point instructions tests " 7338 "are disabled on your host\n"); 7339 #endif /* !defined (NO_FLOAT) */ 7340 7341 case PPC_405: 7342 #if defined (IS_PPC405) 7343 tmpl = &test_ppc405; 7344 loop = &tmpl; 7345 break; 7346 #else 7347 fprintf(stderr, "Sorry. " 7348 "PPC405 instructions tests are disabled on your host\n"); 7349 continue; 7350 #endif /* defined (IS_PPC405) */ 7351 case PPC_ALTIVEC: 7352 #if defined (HAS_ALTIVEC) 7353 loop = &altivec_int_loops[nb_args - 1]; 7354 break; 7355 #else 7356 fprintf(stderr, "Sorry. " 7357 "Altivec instructions tests are disabled on your host\n"); 7358 continue; 7359 #endif 7360 case PPC_FALTIVEC: 7361 #if defined (HAS_ALTIVEC) 7362 loop = &altivec_float_loops[nb_args - 1]; 7363 break; 7364 #else 7365 fprintf(stderr, "Sorry. " 7366 "Altivec float instructions tests " 7367 "are disabled on your host\n"); 7368 #endif 7369 continue; 7370 default: 7371 printf("ERROR: unknown insn family %08x\n", family); 7372 continue; 7373 } 7374 if (1 || verbose > 0) 7375 printf("%s:\n", all_tests[i].name); 7376 for (j=0; tests[j].name != NULL; j++) { 7377 if (check_name(tests[j].name, filter, exact)) { 7378 if (verbose > 1) 7379 printf("Test instruction %s\n", tests[j].name); 7380 (*loop)(tests[j].name, tests[j].func, all_tests[i].flags); 7381 printf("\n"); 7382 n++; 7383 } 7384 } 7385 if (verbose) printf("\n"); 7386 } 7387 printf("All done. Tested %d different instructions\n", n); 7388 } 7389 7390 7391 static void usage (void) 7392 { 7393 #if !defined (USAGE_SIMPLE) 7394 fprintf(stderr, 7395 "jm-insns [-1] [-2] [-3] [-*] [-t <type>] [-f <family>] [-u] " 7396 "[-n <filter>] [-r <test_rigour>] [-h]\n" 7397 "\t-1: test opcodes with one argument\n" 7398 "\t-2: test opcodes with two arguments\n" 7399 "\t-3: test opcodes with three arguments\n" 7400 "\t-*: launch test without checking the number of arguments\n" 7401 "\t-t: launch test for instructions of type <type>\n" 7402 "\t recognized types:\n" 7403 "\t\tarith (or a)\n" 7404 "\t\tlogical (or l)\n" 7405 "\t\tcompare (or c)\n" 7406 "\t\tstoreload (or s)\n" 7407 "\t-f: launch test for instructions of family <family>\n" 7408 "\t recognized families:\n" 7409 "\t\tinteger (or i)\n" 7410 "\t\tfloat (or f)\n" 7411 "\t\tppc405 (or mac)\n" 7412 "\t\taltivec (or a)\n" 7413 "\t-u: test instructions that update flags\n" 7414 "\t-n: filter instructions with <filter>\n" 7415 "\t <filter> can be in two forms:\n" 7416 "\t\tname : filter functions that exactly match <name>\n" 7417 "\t\tname* : filter functions that start with <name>\n" 7418 "\t-r: set size of arg tables to use to define <test_rigour>\n" 7419 "\t recognized types:\n" 7420 "\t\tlarge (or l)\n" 7421 "\t\tsmall (or s) - default\n" 7422 "\t-v: verbose (-v -v for more)\n" 7423 "\t-h: print this help\n" 7424 ); 7425 #else // #if !defined (USAGE_SIMPLE) 7426 fprintf(stderr, 7427 "Usage: jm-insns [OPTION]\n" 7428 "\t-i: test integer instructions (default)\n" 7429 "\t-f: test floating point instructions\n" 7430 "\t-a: test altivec instructions\n" 7431 "\t-A: test all (int, fp, altivec) instructions\n" 7432 "\t-v: be verbose\n" 7433 "\t-h: display this help and exit\n" 7434 ); 7435 #endif // #if !defined (USAGE_SIMPLE) 7436 } 7437 7438 7439 7440 int main (int argc, char **argv) 7441 { 7442 #if !defined (USAGE_SIMPLE) 7443 //////////////////////////////////////////////////////////////////////// 7444 unsigned char *tmp, *filter = NULL; 7445 insn_sel_flags_t flags; 7446 int c; 7447 7448 // check HWord_t really is a host word 7449 assert(sizeof(void*) == sizeof(HWord_t)); 7450 7451 flags.one_arg = 0; 7452 flags.two_args = 0; 7453 flags.three_args = 0; 7454 flags.arith = 0; 7455 flags.logical = 0; 7456 flags.compare = 0; 7457 flags.ldst = 0; 7458 flags.integer = 0; 7459 flags.floats = 0; 7460 flags.p405 = 0; 7461 flags.altivec = 0; 7462 flags.faltivec = 0; 7463 flags.cr = -1; 7464 7465 while ((c = getopt(argc, argv, "123t:f:n:r:uvh")) != -1) { 7466 switch (c) { 7467 case '1': 7468 flags.one_arg = 1; 7469 break; 7470 case '2': 7471 flags.two_args = 1; 7472 break; 7473 case '3': 7474 flags.three_args = 1; 7475 break; 7476 case 't': 7477 tmp = optarg; 7478 if (strcmp(tmp, "arith") == 0 || strcmp(tmp, "a") == 0) { 7479 flags.arith = 1; 7480 } else if (strcmp(tmp, "logical") == 0 || strcmp(tmp, "l") == 0) { 7481 flags.logical = 1; 7482 } else if (strcmp(tmp, "compare") == 0 || strcmp(tmp, "c") == 0) { 7483 flags.compare = 1; 7484 } else if (strcmp(tmp, "storeload") == 0 || strcmp(tmp, "s") == 0) { 7485 flags.ldst = 1; 7486 } else { 7487 goto bad_arg; 7488 } 7489 break; 7490 case 'f': 7491 tmp = optarg; 7492 if (strcmp(tmp, "integer") == 0 || strcmp(tmp, "i") == 0) { 7493 flags.integer = 1; 7494 } else if (strcmp(tmp, "float") == 0 || strcmp(tmp, "f") == 0) { 7495 flags.floats = 1; 7496 } else if (strcmp(tmp, "ppc405") == 0 || strcmp(tmp, "mac") == 0) { 7497 flags.p405 = 1; 7498 } else if (strcmp(tmp, "altivec") == 0 || strcmp(tmp, "a") == 0) { 7499 flags.altivec = 1; 7500 flags.faltivec = 1; 7501 } else { 7502 goto bad_arg; 7503 } 7504 break; 7505 case 'n': 7506 filter = optarg; 7507 break; 7508 case 'r': 7509 tmp = optarg; 7510 if (strcmp(tmp, "large") == 0 || strcmp(tmp, "l") == 0) { 7511 arg_list_size = 1; 7512 } else if (strcmp(tmp, "small") == 0 || strcmp(tmp, "s") == 0) { 7513 arg_list_size = 0; 7514 } else { 7515 goto bad_arg; 7516 } 7517 break; 7518 7519 case 'u': 7520 flags.cr = 1; 7521 break; 7522 case 'h': 7523 usage(); 7524 return 0; 7525 case 'v': 7526 verbose++; 7527 break; 7528 default: 7529 usage(); 7530 fprintf(stderr, "Unknown argument: '%c'\n", c); 7531 return 1; 7532 bad_arg: 7533 usage(); 7534 fprintf(stderr, "Bad argument for '%c': '%s'\n", c, tmp); 7535 return 1; 7536 } 7537 } 7538 if (argc != optind) { 7539 usage(); 7540 fprintf(stderr, "Bad number of arguments\n"); 7541 return 1; 7542 } 7543 7544 // Default n_args 7545 if (flags.one_arg == 0 && flags.two_args == 0 && flags.three_args == 0) { 7546 flags.one_arg = 1; 7547 flags.two_args = 1; 7548 flags.three_args = 1; 7549 } 7550 // Default type 7551 if (flags.arith == 0 && flags.logical == 0 && 7552 flags.compare == 0 && flags.ldst == 0) { 7553 flags.arith = 1; 7554 flags.logical = 1; 7555 flags.compare = 1; 7556 flags.ldst = 1; 7557 } 7558 // Default family 7559 if (flags.integer == 0 && flags.floats == 0 && 7560 flags.p405 == 0 && flags.altivec == 0 && flags.faltivec == 0) { 7561 flags.integer = 1; 7562 flags.floats = 1; 7563 flags.p405 = 1; 7564 flags.altivec = 1; 7565 flags.faltivec = 1; 7566 } 7567 // Default cr update 7568 if (flags.cr == -1) 7569 flags.cr = 2; // both 7570 7571 #else // #if !defined (USAGE_SIMPLE) 7572 //////////////////////////////////////////////////////////////////////// 7573 /* Simple usage: 7574 ./jm-insns -i => int insns 7575 ./jm-insns -f => fp insns 7576 ./jm-insns -a => av insns 7577 ./jm-insns -A => int, fp and avinsns 7578 */ 7579 char *filter = NULL; 7580 insn_sel_flags_t flags; 7581 int c; 7582 7583 // Args 7584 flags.one_arg = 1; 7585 flags.two_args = 1; 7586 flags.three_args = 1; 7587 // Type 7588 flags.arith = 1; 7589 flags.logical = 1; 7590 flags.compare = 1; 7591 flags.ldst = 1; 7592 // Family 7593 flags.integer = 0; 7594 flags.floats = 0; 7595 flags.p405 = 0; 7596 flags.altivec = 0; 7597 flags.faltivec = 0; 7598 // Flags 7599 flags.cr = 2; 7600 7601 while ((c = getopt(argc, argv, "ifahvA")) != -1) { 7602 switch (c) { 7603 case 'i': 7604 flags.integer = 1; 7605 break; 7606 case 'f': 7607 flags.floats = 1; 7608 break; 7609 case 'a': 7610 flags.altivec = 1; 7611 flags.faltivec = 1; 7612 break; 7613 case 'A': 7614 flags.integer = 1; 7615 flags.floats = 1; 7616 flags.altivec = 1; 7617 flags.faltivec = 1; 7618 break; 7619 case 'h': 7620 usage(); 7621 return 0; 7622 case 'v': 7623 verbose++; 7624 break; 7625 default: 7626 usage(); 7627 fprintf(stderr, "Unknown argument: '%c'\n", c); 7628 return 1; 7629 } 7630 } 7631 7632 arg_list_size = 0; 7633 #endif // #if !defined (USAGE_SIMPLE) 7634 7635 7636 build_iargs_table(); 7637 build_fargs_table(); 7638 build_ii16_table(); 7639 #if defined (HAS_ALTIVEC) 7640 if (flags.altivec || flags.faltivec) { 7641 build_viargs_table(); 7642 build_vfargs_table(); 7643 } 7644 #endif 7645 // dump_iargs(); 7646 // dump_iargs16(); 7647 // dump_vfargs(); 7648 7649 if (verbose > 1) { 7650 printf("\nInstruction Selection:\n"); 7651 printf(" n_args: \n"); 7652 printf(" one_arg = %d\n", flags.one_arg); 7653 printf(" two_args = %d\n", flags.two_args); 7654 printf(" three_args = %d\n", flags.three_args); 7655 printf(" type: \n"); 7656 printf(" arith = %d\n", flags.arith); 7657 printf(" logical = %d\n", flags.logical); 7658 printf(" compare = %d\n", flags.compare); 7659 printf(" ldst = %d\n", flags.ldst); 7660 printf(" family: \n"); 7661 printf(" integer = %d\n", flags.integer); 7662 printf(" floats = %d\n", flags.floats); 7663 printf(" p405 = %d\n", flags.p405); 7664 printf(" altivec = %d\n", flags.altivec); 7665 printf(" faltivec = %d\n", flags.faltivec); 7666 printf(" cr update: \n"); 7667 printf(" cr = %d\n", flags.cr); 7668 printf("\n"); 7669 printf(" num args: \n"); 7670 printf(" iargs - %d\n", nb_iargs); 7671 printf(" fargs - %d\n", nb_fargs); 7672 #if defined (HAS_ALTIVEC) 7673 printf(" viargs - %d\n", nb_viargs); 7674 printf(" vfargs - %d\n", nb_vfargs); 7675 #endif 7676 printf("\n"); 7677 } 7678 7679 do_tests( flags, filter ); 7680 7681 return 0; 7682 } 7683