1 #define PETSCKSP_DLL 2 3 /**********************************ivec.c************************************** 4 5 Author: Henry M. Tufo III 6 7 e-mail: hmt@cs.brown.edu 8 9 snail-mail: 10 Division of Applied Mathematics 11 Brown University 12 Providence, RI 02912 13 14 Last Modification: 15 6.21.97 16 ***********************************ivec.c*************************************/ 17 18 /**********************************ivec.c************************************** 19 File Description: 20 ----------------- 21 22 ***********************************ivec.c*************************************/ 23 #include "src/ksp/pc/impls/tfs/tfs.h" 24 25 /* sorting args ivec.c ivec.c ... */ 26 #define SORT_OPT 6 27 #define SORT_STACK 50000 28 29 30 /* allocate an address and size stack for sorter(s) */ 31 static void *offset_stack[2*SORT_STACK]; 32 static int size_stack[SORT_STACK]; 33 static long psize_stack[SORT_STACK]; 34 35 36 37 /**********************************ivec.c************************************** 38 Function ivec_dump() 39 40 Input : 41 Output: 42 Return: 43 Description: 44 ***********************************ivec.c*************************************/ 45 void 46 ivec_dump(int *v, int n, int tag, int tag2, char * s) 47 { 48 int i; 49 printf("%2d %2d %s %2d :: ",tag,tag2,s,my_id); 50 for (i=0;i<n;i++) 51 {printf("%2d ",v[i]);} 52 printf("\n"); 53 fflush(stdout); 54 } 55 56 57 58 /**********************************ivec.c************************************** 59 Function ivec_lb_ub() 60 61 Input : 62 Output: 63 Return: 64 Description: 65 ***********************************ivec.c*************************************/ 66 void 67 ivec_lb_ub( int *arg1, int n, int *lb, int *ub) 68 { 69 int min = INT_MAX; 70 int max = INT_MIN; 71 72 while (n--) 73 { 74 min = PetscMin(min,*arg1); 75 max = PetscMax(max,*arg1); 76 arg1++; 77 } 78 79 *lb=min; 80 *ub=max; 81 } 82 83 84 85 /**********************************ivec.c************************************** 86 Function ivec_copy() 87 88 Input : 89 Output: 90 Return: 91 Description: 92 ***********************************ivec.c*************************************/ 93 int *ivec_copy( int *arg1, int *arg2, int n) 94 { 95 while (n--) {*arg1++ = *arg2++;} 96 return(arg1); 97 } 98 99 100 101 /**********************************ivec.c************************************** 102 Function ivec_zero() 103 104 Input : 105 Output: 106 Return: 107 Description: 108 ***********************************ivec.c*************************************/ 109 void 110 ivec_zero( int *arg1, int n) 111 { 112 while (n--) {*arg1++ = 0;} 113 } 114 115 116 117 /**********************************ivec.c************************************** 118 Function ivec_comp() 119 120 Input : 121 Output: 122 Return: 123 Description: 124 ***********************************ivec.c*************************************/ 125 void 126 ivec_comp( int *arg1, int n) 127 { 128 while (n--) {*arg1 = ~*arg1; arg1++;} 129 } 130 131 132 133 /**********************************ivec.c************************************** 134 Function ivec_neg_one() 135 136 Input : 137 Output: 138 Return: 139 Description: 140 ***********************************ivec.c*************************************/ 141 void 142 ivec_neg_one( int *arg1, int n) 143 { 144 while (n--) {*arg1++ = -1;} 145 } 146 147 148 149 /**********************************ivec.c************************************** 150 Function ivec_pos_one() 151 152 Input : 153 Output: 154 Return: 155 Description: 156 ***********************************ivec.c*************************************/ 157 void 158 ivec_pos_one( int *arg1, int n) 159 { 160 while (n--) {*arg1++ = 1;} 161 } 162 163 164 165 /**********************************ivec.c************************************** 166 Function ivec_c_index() 167 168 Input : 169 Output: 170 Return: 171 Description: 172 ***********************************ivec.c*************************************/ 173 void 174 ivec_c_index( int *arg1, int n) 175 { 176 int i=0; 177 178 179 while (n--) {*arg1++ = i++;} 180 } 181 182 183 184 /**********************************ivec.c************************************** 185 Function ivec_fortran_index() 186 187 Input : 188 Output: 189 Return: 190 Description: 191 ***********************************ivec.c*************************************/ 192 void 193 ivec_fortran_index( int *arg1, int n) 194 { 195 int i=0; 196 197 198 while (n--) {*arg1++ = ++i;} 199 } 200 201 202 203 /**********************************ivec.c************************************** 204 Function ivec_set() 205 206 Input : 207 Output: 208 Return: 209 Description: 210 ***********************************ivec.c*************************************/ 211 void 212 ivec_set( int *arg1, int arg2, int n) 213 { 214 while (n--) {*arg1++ = arg2;} 215 } 216 217 218 219 /**********************************ivec.c************************************** 220 Function ivec_cmp() 221 222 Input : 223 Output: 224 Return: 225 Description: 226 ***********************************ivec.c*************************************/ 227 int 228 ivec_cmp( int *arg1, int *arg2, int n) 229 { 230 while (n--) {if (*arg1++ != *arg2++) {return(FALSE);}} 231 return(TRUE); 232 } 233 234 235 236 /**********************************ivec.c************************************** 237 Function ivec_max() 238 239 Input : 240 Output: 241 Return: 242 Description: 243 ***********************************ivec.c*************************************/ 244 void 245 ivec_max( int *arg1, int *arg2, int n) 246 { 247 while (n--) {*arg1 = PetscMax(*arg1,*arg2); arg1++; arg2++;} 248 } 249 250 251 252 /**********************************ivec.c************************************** 253 Function ivec_min() 254 255 Input : 256 Output: 257 Return: 258 Description: 259 ***********************************ivec.c*************************************/ 260 void 261 ivec_min( int *arg1, int *arg2, int n) 262 { 263 while (n--) {*(arg1) = PetscMin(*arg1,*arg2); arg1++; arg2++;} 264 } 265 266 267 268 /**********************************ivec.c************************************** 269 Function ivec_mult() 270 271 Input : 272 Output: 273 Return: 274 Description: 275 ***********************************ivec.c*************************************/ 276 void 277 ivec_mult( int *arg1, int *arg2, int n) 278 { 279 while (n--) {*arg1++ *= *arg2++;} 280 } 281 282 283 284 /**********************************ivec.c************************************** 285 Function ivec_add() 286 287 Input : 288 Output: 289 Return: 290 Description: 291 ***********************************ivec.c*************************************/ 292 void 293 ivec_add( int *arg1, int *arg2, int n) 294 { 295 while (n--) {*arg1++ += *arg2++;} 296 } 297 298 299 300 /**********************************ivec.c************************************** 301 Function ivec_lxor() 302 303 Input : 304 Output: 305 Return: 306 Description: 307 ***********************************ivec.c*************************************/ 308 void 309 ivec_lxor( int *arg1, int *arg2, int n) 310 { 311 while (n--) {*arg1=((*arg1 || *arg2) && !(*arg1 && *arg2)); arg1++; arg2++;} 312 } 313 314 315 316 /**********************************ivec.c************************************** 317 Function ivec_xor() 318 319 Input : 320 Output: 321 Return: 322 Description: 323 ***********************************ivec.c*************************************/ 324 void 325 ivec_xor( int *arg1, int *arg2, int n) 326 { 327 while (n--) {*arg1++ ^= *arg2++;} 328 } 329 330 331 332 /**********************************ivec.c************************************** 333 Function ivec_or() 334 335 Input : 336 Output: 337 Return: 338 Description: 339 ***********************************ivec.c*************************************/ 340 void 341 ivec_or( int *arg1, int *arg2, int n) 342 { 343 while (n--) {*arg1++ |= *arg2++;} 344 } 345 346 347 348 /**********************************ivec.c************************************** 349 Function ivec_lor() 350 351 Input : 352 Output: 353 Return: 354 Description: 355 ***********************************ivec.c*************************************/ 356 void 357 ivec_lor( int *arg1, int *arg2, int n) 358 { 359 while (n--) {*arg1 = (*arg1 || *arg2); arg1++; arg2++;} 360 } 361 362 363 364 /**********************************ivec.c************************************** 365 Function ivec_or3() 366 367 Input : 368 Output: 369 Return: 370 Description: 371 ***********************************ivec.c*************************************/ 372 void 373 ivec_or3( int *arg1, int *arg2, int *arg3, 374 int n) 375 { 376 while (n--) {*arg1++ = (*arg2++ | *arg3++);} 377 } 378 379 380 381 /**********************************ivec.c************************************** 382 Function ivec_and() 383 384 Input : 385 Output: 386 Return: 387 Description: 388 ***********************************ivec.c*************************************/ 389 void 390 ivec_and( int *arg1, int *arg2, int n) 391 { 392 while (n--) {*arg1++ &= *arg2++;} 393 } 394 395 396 397 /**********************************ivec.c************************************** 398 Function ivec_land() 399 400 Input : 401 Output: 402 Return: 403 Description: 404 ***********************************ivec.c*************************************/ 405 void 406 ivec_land( int *arg1, int *arg2, int n) 407 { 408 while (n--) {*arg1 = (*arg1 && *arg2); arg1++; arg2++;} 409 } 410 411 412 413 /**********************************ivec.c************************************** 414 Function ivec_and3() 415 416 Input : 417 Output: 418 Return: 419 Description: 420 ***********************************ivec.c*************************************/ 421 void 422 ivec_and3( int *arg1, int *arg2, int *arg3, 423 int n) 424 { 425 while (n--) {*arg1++ = (*arg2++ & *arg3++);} 426 } 427 428 429 430 /**********************************ivec.c************************************** 431 Function ivec_sum 432 433 Input : 434 Output: 435 Return: 436 Description: 437 ***********************************ivec.c*************************************/ 438 int ivec_sum( int *arg1, int n) 439 { 440 int tmp = 0; 441 442 443 while (n--) {tmp += *arg1++;} 444 return(tmp); 445 } 446 447 448 449 /**********************************ivec.c************************************** 450 Function ivec_reduce_and 451 452 Input : 453 Output: 454 Return: 455 Description: 456 ***********************************ivec.c*************************************/ 457 int ivec_reduce_and( int *arg1, int n) 458 { 459 int tmp = ALL_ONES; 460 461 462 while (n--) {tmp &= *arg1++;} 463 return(tmp); 464 } 465 466 467 468 /**********************************ivec.c************************************** 469 Function ivec_reduce_or 470 471 Input : 472 Output: 473 Return: 474 Description: 475 ***********************************ivec.c*************************************/ 476 int ivec_reduce_or( int *arg1, int n) 477 { 478 int tmp = 0; 479 480 481 while (n--) {tmp |= *arg1++;} 482 return(tmp); 483 } 484 485 486 487 /**********************************ivec.c************************************** 488 Function ivec_prod 489 490 Input : 491 Output: 492 Return: 493 Description: 494 ***********************************ivec.c*************************************/ 495 int ivec_prod( int *arg1, int n) 496 { 497 int tmp = 1; 498 499 500 while (n--) {tmp *= *arg1++;} 501 return(tmp); 502 } 503 504 505 506 /**********************************ivec.c************************************** 507 Function ivec_u_sum 508 509 Input : 510 Output: 511 Return: 512 Description: 513 ***********************************ivec.c*************************************/ 514 int ivec_u_sum( unsigned *arg1, int n) 515 { 516 unsigned tmp = 0; 517 518 519 while (n--) {tmp += *arg1++;} 520 return(tmp); 521 } 522 523 524 525 /**********************************ivec.c************************************** 526 Function ivec_lb() 527 528 Input : 529 Output: 530 Return: 531 Description: 532 ***********************************ivec.c*************************************/ 533 int 534 ivec_lb( int *arg1, int n) 535 { 536 int min = INT_MAX; 537 538 539 while (n--) {min = PetscMin(min,*arg1); arg1++;} 540 return(min); 541 } 542 543 544 545 /**********************************ivec.c************************************** 546 Function ivec_ub() 547 548 Input : 549 Output: 550 Return: 551 Description: 552 ***********************************ivec.c*************************************/ 553 int 554 ivec_ub( int *arg1, int n) 555 { 556 int max = INT_MIN; 557 558 559 while (n--) {max = PetscMax(max,*arg1); arg1++;} 560 return(max); 561 } 562 563 564 565 /**********************************ivec.c************************************** 566 Function split_buf() 567 568 Input : 569 Output: 570 Return: 571 Description: 572 573 assumes that sizeof(int) == 4bytes!!! 574 ***********************************ivec.c*************************************/ 575 int 576 ivec_split_buf(int *buf1, int **buf2, int size) 577 { 578 *buf2 = (buf1 + (size>>3)); 579 return(size); 580 } 581 582 583 584 /**********************************ivec.c************************************** 585 Function ivec_non_uniform() 586 587 Input : 588 Output: 589 Return: 590 Description: 591 ***********************************ivec.c*************************************/ 592 void 593 ivec_non_uniform(int *arg1, int *arg2, int n, int *arg3) 594 { 595 int i, j, type; 596 597 598 /* LATER: if we're really motivated we can sort and then unsort */ 599 for (i=0;i<n;) 600 { 601 /* clump 'em for now */ 602 j=i+1; 603 type = arg3[i]; 604 while ((j<n)&&(arg3[j]==type)) 605 {j++;} 606 607 /* how many together */ 608 j -= i; 609 610 /* call appropriate ivec function */ 611 if (type == GL_MAX) 612 {ivec_max(arg1,arg2,j);} 613 else if (type == GL_MIN) 614 {ivec_min(arg1,arg2,j);} 615 else if (type == GL_MULT) 616 {ivec_mult(arg1,arg2,j);} 617 else if (type == GL_ADD) 618 {ivec_add(arg1,arg2,j);} 619 else if (type == GL_B_XOR) 620 {ivec_xor(arg1,arg2,j);} 621 else if (type == GL_B_OR) 622 {ivec_or(arg1,arg2,j);} 623 else if (type == GL_B_AND) 624 {ivec_and(arg1,arg2,j);} 625 else if (type == GL_L_XOR) 626 {ivec_lxor(arg1,arg2,j);} 627 else if (type == GL_L_OR) 628 {ivec_lor(arg1,arg2,j);} 629 else if (type == GL_L_AND) 630 {ivec_land(arg1,arg2,j);} 631 else 632 {error_msg_fatal("unrecognized type passed to ivec_non_uniform()!");} 633 634 arg1+=j; arg2+=j; i+=j; 635 } 636 } 637 638 639 640 /**********************************ivec.c************************************** 641 Function ivec_addr() 642 643 Input : 644 Output: 645 Return: 646 Description: 647 ***********************************ivec.c*************************************/ 648 vfp ivec_fct_addr( int type) 649 { 650 if (type == NON_UNIFORM) 651 {return((void (*)(void*, void *, int, ...))&ivec_non_uniform);} 652 else if (type == GL_MAX) 653 {return((void (*)(void*, void *, int, ...))&ivec_max);} 654 else if (type == GL_MIN) 655 {return((void (*)(void*, void *, int, ...))&ivec_min);} 656 else if (type == GL_MULT) 657 {return((void (*)(void*, void *, int, ...))&ivec_mult);} 658 else if (type == GL_ADD) 659 {return((void (*)(void*, void *, int, ...))&ivec_add);} 660 else if (type == GL_B_XOR) 661 {return((void (*)(void*, void *, int, ...))&ivec_xor);} 662 else if (type == GL_B_OR) 663 {return((void (*)(void*, void *, int, ...))&ivec_or);} 664 else if (type == GL_B_AND) 665 {return((void (*)(void*, void *, int, ...))&ivec_and);} 666 else if (type == GL_L_XOR) 667 {return((void (*)(void*, void *, int, ...))&ivec_lxor);} 668 else if (type == GL_L_OR) 669 {return((void (*)(void*, void *, int, ...))&ivec_lor);} 670 else if (type == GL_L_AND) 671 {return((void (*)(void*, void *, int, ...))&ivec_land);} 672 673 /* catch all ... not good if we get here */ 674 return(NULL); 675 } 676 677 678 /**********************************ivec.c************************************** 679 Function ct_bits() 680 681 Input : 682 Output: 683 Return: 684 Description: MUST FIX THIS!!! 685 ***********************************ivec.c*************************************/ 686 #if defined(notusing) 687 static 688 int 689 ivec_ct_bits( int *ptr, int n) 690 { 691 int tmp=0; 692 693 694 /* should expand to full 32 bit */ 695 while (n--) 696 { 697 if (*ptr&128) {tmp++;} 698 if (*ptr&64) {tmp++;} 699 if (*ptr&32) {tmp++;} 700 if (*ptr&16) {tmp++;} 701 if (*ptr&8) {tmp++;} 702 if (*ptr&4) {tmp++;} 703 if (*ptr&2) {tmp++;} 704 if (*ptr&1) {tmp++;} 705 ptr++; 706 } 707 708 return(tmp); 709 } 710 #endif 711 712 713 /****************************************************************************** 714 Function: ivec_sort(). 715 716 Input : offset of list to be sorted, number of elements to be sorted. 717 Output: sorted list (in ascending order). 718 Return: none. 719 Description: stack based (nonrecursive) quicksort w/brute-shell bottom. 720 ******************************************************************************/ 721 void 722 ivec_sort( int *ar, int size) 723 { 724 int *pi, *pj, temp; 725 int **top_a = (int **) offset_stack; 726 int *top_s = size_stack, *bottom_s = size_stack; 727 728 729 /* we're really interested in the offset of the last element */ 730 /* ==> length of the list is now size + 1 */ 731 size--; 732 733 /* do until we're done ... return when stack is exhausted */ 734 for (;;) 735 { 736 /* if list is large enough use quicksort partition exchange code */ 737 if (size > SORT_OPT) 738 { 739 /* start up pointer at element 1 and down at size */ 740 pi = ar+1; 741 pj = ar+size; 742 743 /* find middle element in list and swap w/ element 1 */ 744 SWAP(*(ar+(size>>1)),*pi) 745 746 /* order element 0,1,size-1 st {M,L,...,U} w/L<=M<=U */ 747 /* note ==> pivot_value in index 0 */ 748 if (*pi > *pj) 749 {SWAP(*pi,*pj)} 750 if (*ar > *pj) 751 {SWAP(*ar,*pj)} 752 else if (*pi > *ar) 753 {SWAP(*(ar),*(ar+1))} 754 755 /* partition about pivot_value ... */ 756 /* note lists of length 2 are not guaranteed to be sorted */ 757 for(;;) 758 { 759 /* walk up ... and down ... swap if equal to pivot! */ 760 do pi++; while (*pi<*ar); 761 do pj--; while (*pj>*ar); 762 763 /* if we've crossed we're done */ 764 if (pj<pi) break; 765 766 /* else swap */ 767 SWAP(*pi,*pj) 768 } 769 770 /* place pivot_value in it's correct location */ 771 SWAP(*ar,*pj) 772 773 /* test stack_size to see if we've exhausted our stack */ 774 if (top_s-bottom_s >= SORT_STACK) 775 {error_msg_fatal("ivec_sort() :: STACK EXHAUSTED!!!");} 776 777 /* push right hand child iff length > 1 */ 778 if ((*top_s = size-((int) (pi-ar)))) 779 { 780 *(top_a++) = pi; 781 size -= *top_s+2; 782 top_s++; 783 } 784 /* set up for next loop iff there is something to do */ 785 else if (size -= *top_s+2) 786 {;} 787 /* might as well pop - note NR_OPT >=2 ==> we're ok! */ 788 else 789 { 790 ar = *(--top_a); 791 size = *(--top_s); 792 } 793 } 794 795 /* else sort small list directly then pop another off stack */ 796 else 797 { 798 /* insertion sort for bottom */ 799 for (pj=ar+1;pj<=ar+size;pj++) 800 { 801 temp = *pj; 802 for (pi=pj-1;pi>=ar;pi--) 803 { 804 if (*pi <= temp) break; 805 *(pi+1)=*pi; 806 } 807 *(pi+1)=temp; 808 } 809 810 /* check to see if stack is exhausted ==> DONE */ 811 if (top_s==bottom_s) return; 812 813 /* else pop another list from the stack */ 814 ar = *(--top_a); 815 size = *(--top_s); 816 } 817 } 818 } 819 820 821 822 /****************************************************************************** 823 Function: ivec_sort_companion(). 824 825 Input : offset of list to be sorted, number of elements to be sorted. 826 Output: sorted list (in ascending order). 827 Return: none. 828 Description: stack based (nonrecursive) quicksort w/brute-shell bottom. 829 ******************************************************************************/ 830 void 831 ivec_sort_companion( int *ar, int *ar2, int size) 832 { 833 int *pi, *pj, temp, temp2; 834 int **top_a = (int **)offset_stack; 835 int *top_s = size_stack, *bottom_s = size_stack; 836 int *pi2, *pj2; 837 int mid; 838 839 840 /* we're really interested in the offset of the last element */ 841 /* ==> length of the list is now size + 1 */ 842 size--; 843 844 /* do until we're done ... return when stack is exhausted */ 845 for (;;) 846 { 847 /* if list is large enough use quicksort partition exchange code */ 848 if (size > SORT_OPT) 849 { 850 /* start up pointer at element 1 and down at size */ 851 mid = size>>1; 852 pi = ar+1; 853 pj = ar+mid; 854 pi2 = ar2+1; 855 pj2 = ar2+mid; 856 857 /* find middle element in list and swap w/ element 1 */ 858 SWAP(*pi,*pj) 859 SWAP(*pi2,*pj2) 860 861 /* order element 0,1,size-1 st {M,L,...,U} w/L<=M<=U */ 862 /* note ==> pivot_value in index 0 */ 863 pj = ar+size; 864 pj2 = ar2+size; 865 if (*pi > *pj) 866 {SWAP(*pi,*pj) SWAP(*pi2,*pj2)} 867 if (*ar > *pj) 868 {SWAP(*ar,*pj) SWAP(*ar2,*pj2)} 869 else if (*pi > *ar) 870 {SWAP(*(ar),*(ar+1)) SWAP(*(ar2),*(ar2+1))} 871 872 /* partition about pivot_value ... */ 873 /* note lists of length 2 are not guaranteed to be sorted */ 874 for(;;) 875 { 876 /* walk up ... and down ... swap if equal to pivot! */ 877 do {pi++; pi2++;} while (*pi<*ar); 878 do {pj--; pj2--;} while (*pj>*ar); 879 880 /* if we've crossed we're done */ 881 if (pj<pi) break; 882 883 /* else swap */ 884 SWAP(*pi,*pj) 885 SWAP(*pi2,*pj2) 886 } 887 888 /* place pivot_value in it's correct location */ 889 SWAP(*ar,*pj) 890 SWAP(*ar2,*pj2) 891 892 /* test stack_size to see if we've exhausted our stack */ 893 if (top_s-bottom_s >= SORT_STACK) 894 {error_msg_fatal("ivec_sort_companion() :: STACK EXHAUSTED!!!");} 895 896 /* push right hand child iff length > 1 */ 897 if ((*top_s = size-((int) (pi-ar)))) 898 { 899 *(top_a++) = pi; 900 *(top_a++) = pi2; 901 size -= *top_s+2; 902 top_s++; 903 } 904 /* set up for next loop iff there is something to do */ 905 else if (size -= *top_s+2) 906 {;} 907 /* might as well pop - note NR_OPT >=2 ==> we're ok! */ 908 else 909 { 910 ar2 = *(--top_a); 911 ar = *(--top_a); 912 size = *(--top_s); 913 } 914 } 915 916 /* else sort small list directly then pop another off stack */ 917 else 918 { 919 /* insertion sort for bottom */ 920 for (pj=ar+1, pj2=ar2+1;pj<=ar+size;pj++,pj2++) 921 { 922 temp = *pj; 923 temp2 = *pj2; 924 for (pi=pj-1,pi2=pj2-1;pi>=ar;pi--,pi2--) 925 { 926 if (*pi <= temp) break; 927 *(pi+1)=*pi; 928 *(pi2+1)=*pi2; 929 } 930 *(pi+1)=temp; 931 *(pi2+1)=temp2; 932 } 933 934 /* check to see if stack is exhausted ==> DONE */ 935 if (top_s==bottom_s) return; 936 937 /* else pop another list from the stack */ 938 ar2 = *(--top_a); 939 ar = *(--top_a); 940 size = *(--top_s); 941 } 942 } 943 } 944 945 946 947 /****************************************************************************** 948 Function: ivec_sort_companion_hack(). 949 950 Input : offset of list to be sorted, number of elements to be sorted. 951 Output: sorted list (in ascending order). 952 Return: none. 953 Description: stack based (nonrecursive) quicksort w/brute-shell bottom. 954 ******************************************************************************/ 955 void 956 ivec_sort_companion_hack( int *ar, int **ar2, 957 int size) 958 { 959 int *pi, *pj, temp, *ptr; 960 int **top_a = (int **)offset_stack; 961 int *top_s = size_stack, *bottom_s = size_stack; 962 int **pi2, **pj2; 963 int mid; 964 965 966 /* we're really interested in the offset of the last element */ 967 /* ==> length of the list is now size + 1 */ 968 size--; 969 970 /* do until we're done ... return when stack is exhausted */ 971 for (;;) 972 { 973 /* if list is large enough use quicksort partition exchange code */ 974 if (size > SORT_OPT) 975 { 976 /* start up pointer at element 1 and down at size */ 977 mid = size>>1; 978 pi = ar+1; 979 pj = ar+mid; 980 pi2 = ar2+1; 981 pj2 = ar2+mid; 982 983 /* find middle element in list and swap w/ element 1 */ 984 SWAP(*pi,*pj) 985 P_SWAP(*pi2,*pj2) 986 987 /* order element 0,1,size-1 st {M,L,...,U} w/L<=M<=U */ 988 /* note ==> pivot_value in index 0 */ 989 pj = ar+size; 990 pj2 = ar2+size; 991 if (*pi > *pj) 992 {SWAP(*pi,*pj) P_SWAP(*pi2,*pj2)} 993 if (*ar > *pj) 994 {SWAP(*ar,*pj) P_SWAP(*ar2,*pj2)} 995 else if (*pi > *ar) 996 {SWAP(*(ar),*(ar+1)) P_SWAP(*(ar2),*(ar2+1))} 997 998 /* partition about pivot_value ... */ 999 /* note lists of length 2 are not guaranteed to be sorted */ 1000 for(;;) 1001 { 1002 /* walk up ... and down ... swap if equal to pivot! */ 1003 do {pi++; pi2++;} while (*pi<*ar); 1004 do {pj--; pj2--;} while (*pj>*ar); 1005 1006 /* if we've crossed we're done */ 1007 if (pj<pi) break; 1008 1009 /* else swap */ 1010 SWAP(*pi,*pj) 1011 P_SWAP(*pi2,*pj2) 1012 } 1013 1014 /* place pivot_value in it's correct location */ 1015 SWAP(*ar,*pj) 1016 P_SWAP(*ar2,*pj2) 1017 1018 /* test stack_size to see if we've exhausted our stack */ 1019 if (top_s-bottom_s >= SORT_STACK) 1020 {error_msg_fatal("ivec_sort_companion_hack() :: STACK EXHAUSTED!!!");} 1021 1022 /* push right hand child iff length > 1 */ 1023 if ((*top_s = size-((int) (pi-ar)))) 1024 { 1025 *(top_a++) = pi; 1026 *(top_a++) = (int*) pi2; 1027 size -= *top_s+2; 1028 top_s++; 1029 } 1030 /* set up for next loop iff there is something to do */ 1031 else if (size -= *top_s+2) 1032 {;} 1033 /* might as well pop - note NR_OPT >=2 ==> we're ok! */ 1034 else 1035 { 1036 ar2 = (int **) *(--top_a); 1037 ar = *(--top_a); 1038 size = *(--top_s); 1039 } 1040 } 1041 1042 /* else sort small list directly then pop another off stack */ 1043 else 1044 { 1045 /* insertion sort for bottom */ 1046 for (pj=ar+1, pj2=ar2+1;pj<=ar+size;pj++,pj2++) 1047 { 1048 temp = *pj; 1049 ptr = *pj2; 1050 for (pi=pj-1,pi2=pj2-1;pi>=ar;pi--,pi2--) 1051 { 1052 if (*pi <= temp) break; 1053 *(pi+1)=*pi; 1054 *(pi2+1)=*pi2; 1055 } 1056 *(pi+1)=temp; 1057 *(pi2+1)=ptr; 1058 } 1059 1060 /* check to see if stack is exhausted ==> DONE */ 1061 if (top_s==bottom_s) return; 1062 1063 /* else pop another list from the stack */ 1064 ar2 = (int **)*(--top_a); 1065 ar = *(--top_a); 1066 size = *(--top_s); 1067 } 1068 } 1069 } 1070 1071 1072 1073 /****************************************************************************** 1074 Function: SMI_sort(). 1075 Input : offset of list to be sorted, number of elements to be sorted. 1076 Output: sorted list (in ascending order). 1077 Return: none. 1078 Description: stack based (nonrecursive) quicksort w/brute-shell bottom. 1079 ******************************************************************************/ 1080 void 1081 SMI_sort(void *ar1, void *ar2, int size, int type) 1082 { 1083 if (type == SORT_INTEGER) 1084 { 1085 if (ar2) 1086 {ivec_sort_companion((int*)ar1,(int*)ar2,size);} 1087 else 1088 {ivec_sort((int*)ar1,size);} 1089 } 1090 else if (type == SORT_INT_PTR) 1091 { 1092 if (ar2) 1093 {ivec_sort_companion_hack((int*)ar1,(int **)ar2,size);} 1094 else 1095 {ivec_sort((int*)ar1,size);} 1096 } 1097 1098 else 1099 { 1100 error_msg_fatal("SMI_sort only does SORT_INTEGER!"); 1101 } 1102 /* 1103 if (type == SORT_REAL) 1104 { 1105 if (ar2) 1106 {rvec_sort_companion(ar2,ar1,size);} 1107 else 1108 {rvec_sort(ar1,size);} 1109 } 1110 */ 1111 } 1112 1113 1114 1115 /**********************************ivec.c************************************** 1116 Function ivec_linear_search() 1117 1118 Input : 1119 Output: 1120 Return: 1121 Description: 1122 ***********************************ivec.c*************************************/ 1123 int 1124 ivec_linear_search( int item, int *list, int n) 1125 { 1126 int tmp = n-1; 1127 1128 while (n--) {if (*list++ == item) {return(tmp-n);}} 1129 return(-1); 1130 } 1131 1132 1133 1134 /**********************************ivec.c************************************** 1135 Function ivec_binary_search() 1136 1137 Input : 1138 Output: 1139 Return: 1140 Description: 1141 ***********************************ivec.c*************************************/ 1142 int 1143 ivec_binary_search( int item, int *list, int rh) 1144 { 1145 int mid, lh=0; 1146 1147 rh--; 1148 while (lh<=rh) 1149 { 1150 mid = (lh+rh)>>1; 1151 if (*(list+mid) == item) 1152 {return(mid);} 1153 if (*(list+mid) > item) 1154 {rh = mid-1;} 1155 else 1156 {lh = mid+1;} 1157 } 1158 return(-1); 1159 } 1160 1161 1162 1163 /**********************************ivec.c************************************** 1164 Function rvec_dump 1165 1166 Input : 1167 Output: 1168 Return: 1169 Description: 1170 ***********************************ivec.c*************************************/ 1171 void 1172 rvec_dump(PetscScalar *v, int n, int tag, int tag2, char * s) 1173 { 1174 int i; 1175 printf("%2d %2d %s %2d :: ",tag,tag2,s,my_id); 1176 for (i=0;i<n;i++) 1177 {printf("%f ",v[i]);} 1178 printf("\n"); 1179 fflush(stdout); 1180 } 1181 1182 1183 1184 /**********************************ivec.c************************************** 1185 Function rvec_lb_ub() 1186 1187 Input : 1188 Output: 1189 Return: 1190 Description: 1191 ***********************************ivec.c*************************************/ 1192 void 1193 rvec_lb_ub( PetscScalar *arg1, int n, PetscScalar *lb, PetscScalar *ub) 1194 { 1195 PetscScalar min = REAL_MAX; 1196 PetscScalar max = -REAL_MAX; 1197 1198 while (n--) 1199 { 1200 min = PetscMin(min,*arg1); 1201 max = PetscMax(max,*arg1); 1202 arg1++; 1203 } 1204 1205 *lb=min; 1206 *ub=max; 1207 } 1208 1209 1210 1211 /********************************ivec.c************************************** 1212 Function rvec_copy() 1213 1214 Input : 1215 Output: 1216 Return: 1217 Description: 1218 *********************************ivec.c*************************************/ 1219 void 1220 rvec_copy( PetscScalar *arg1, PetscScalar *arg2, int n) 1221 { 1222 while (n--) {*arg1++ = *arg2++;} 1223 } 1224 1225 1226 1227 /********************************ivec.c************************************** 1228 Function rvec_zero() 1229 1230 Input : 1231 Output: 1232 Return: 1233 Description: 1234 *********************************ivec.c*************************************/ 1235 void 1236 rvec_zero( PetscScalar *arg1, int n) 1237 { 1238 while (n--) {*arg1++ = 0.0;} 1239 } 1240 1241 1242 1243 /**********************************ivec.c************************************** 1244 Function rvec_one() 1245 1246 Input : 1247 Output: 1248 Return: 1249 Description: 1250 ***********************************ivec.c*************************************/ 1251 void 1252 rvec_one( PetscScalar *arg1, int n) 1253 { 1254 while (n--) {*arg1++ = 1.0;} 1255 } 1256 1257 1258 1259 /**********************************ivec.c************************************** 1260 Function rvec_neg_one() 1261 1262 Input : 1263 Output: 1264 Return: 1265 Description: 1266 ***********************************ivec.c*************************************/ 1267 void 1268 rvec_neg_one( PetscScalar *arg1, int n) 1269 { 1270 while (n--) {*arg1++ = -1.0;} 1271 } 1272 1273 1274 1275 /**********************************ivec.c************************************** 1276 Function rvec_set() 1277 1278 Input : 1279 Output: 1280 Return: 1281 Description: 1282 ***********************************ivec.c*************************************/ 1283 void 1284 rvec_set( PetscScalar *arg1, PetscScalar arg2, int n) 1285 { 1286 while (n--) {*arg1++ = arg2;} 1287 } 1288 1289 1290 1291 /**********************************ivec.c************************************** 1292 Function rvec_scale() 1293 1294 Input : 1295 Output: 1296 Return: 1297 Description: 1298 ***********************************ivec.c*************************************/ 1299 void 1300 rvec_scale( PetscScalar *arg1, PetscScalar arg2, int n) 1301 { 1302 while (n--) {*arg1++ *= arg2;} 1303 } 1304 1305 1306 1307 /********************************ivec.c************************************** 1308 Function rvec_add() 1309 1310 Input : 1311 Output: 1312 Return: 1313 Description: 1314 *********************************ivec.c*************************************/ 1315 void 1316 rvec_add( PetscScalar *arg1, PetscScalar *arg2, int n) 1317 { 1318 while (n--) {*arg1++ += *arg2++;} 1319 } 1320 1321 1322 1323 /********************************ivec.c************************************** 1324 Function rvec_dot() 1325 1326 Input : 1327 Output: 1328 Return: 1329 Description: 1330 *********************************ivec.c*************************************/ 1331 PetscScalar 1332 rvec_dot( PetscScalar *arg1, PetscScalar *arg2, int n) 1333 { 1334 PetscScalar dot=0.0; 1335 1336 while (n--) {dot+= *arg1++ * *arg2++;} 1337 1338 return(dot); 1339 } 1340 1341 1342 1343 /********************************ivec.c************************************** 1344 Function rvec_axpy() 1345 1346 Input : 1347 Output: 1348 Return: 1349 Description: 1350 *********************************ivec.c*************************************/ 1351 void 1352 rvec_axpy( PetscScalar *arg1, PetscScalar *arg2, PetscScalar scale, 1353 int n) 1354 { 1355 while (n--) {*arg1++ += scale * *arg2++;} 1356 } 1357 1358 1359 /********************************ivec.c************************************** 1360 Function rvec_mult() 1361 1362 Input : 1363 Output: 1364 Return: 1365 Description: 1366 *********************************ivec.c*************************************/ 1367 void 1368 rvec_mult( PetscScalar *arg1, PetscScalar *arg2, int n) 1369 { 1370 while (n--) {*arg1++ *= *arg2++;} 1371 } 1372 1373 1374 1375 /********************************ivec.c************************************** 1376 Function rvec_max() 1377 1378 Input : 1379 Output: 1380 Return: 1381 Description: 1382 *********************************ivec.c*************************************/ 1383 void 1384 rvec_max( PetscScalar *arg1, PetscScalar *arg2, int n) 1385 { 1386 while (n--) {*arg1 = PetscMax(*arg1,*arg2); arg1++; arg2++;} 1387 } 1388 1389 1390 1391 /********************************ivec.c************************************** 1392 Function rvec_max_abs() 1393 1394 Input : 1395 Output: 1396 Return: 1397 Description: 1398 *********************************ivec.c*************************************/ 1399 void 1400 rvec_max_abs( PetscScalar *arg1, PetscScalar *arg2, int n) 1401 { 1402 while (n--) {*arg1 = MAX_FABS(*arg1,*arg2); arg1++; arg2++;} 1403 } 1404 1405 1406 1407 /********************************ivec.c************************************** 1408 Function rvec_min() 1409 1410 Input : 1411 Output: 1412 Return: 1413 Description: 1414 *********************************ivec.c*************************************/ 1415 void 1416 rvec_min( PetscScalar *arg1, PetscScalar *arg2, int n) 1417 { 1418 while (n--) {*arg1 = PetscMin(*arg1,*arg2); arg1++; arg2++;} 1419 } 1420 1421 1422 1423 /********************************ivec.c************************************** 1424 Function rvec_min_abs() 1425 1426 Input : 1427 Output: 1428 Return: 1429 Description: 1430 *********************************ivec.c*************************************/ 1431 void 1432 rvec_min_abs( PetscScalar *arg1, PetscScalar *arg2, int n) 1433 { 1434 while (n--) {*arg1 = MIN_FABS(*arg1,*arg2); arg1++; arg2++;} 1435 } 1436 1437 1438 1439 /********************************ivec.c************************************** 1440 Function rvec_exists() 1441 1442 Input : 1443 Output: 1444 Return: 1445 Description: 1446 *********************************ivec.c*************************************/ 1447 void 1448 rvec_exists( PetscScalar *arg1, PetscScalar *arg2, int n) 1449 { 1450 while (n--) {*arg1 = EXISTS(*arg1,*arg2); arg1++; arg2++;} 1451 } 1452 1453 1454 1455 /**********************************ivec.c************************************** 1456 Function rvec_non_uniform() 1457 1458 Input : 1459 Output: 1460 Return: 1461 Description: 1462 ***********************************ivec.c*************************************/ 1463 void 1464 rvec_non_uniform(PetscScalar *arg1, PetscScalar *arg2, int n, int *arg3) 1465 { 1466 int i, j, type; 1467 1468 1469 /* LATER: if we're really motivated we can sort and then unsort */ 1470 for (i=0;i<n;) 1471 { 1472 /* clump 'em for now */ 1473 j=i+1; 1474 type = arg3[i]; 1475 while ((j<n)&&(arg3[j]==type)) 1476 {j++;} 1477 1478 /* how many together */ 1479 j -= i; 1480 1481 /* call appropriate ivec function */ 1482 if (type == GL_MAX) 1483 {rvec_max(arg1,arg2,j);} 1484 else if (type == GL_MIN) 1485 {rvec_min(arg1,arg2,j);} 1486 else if (type == GL_MULT) 1487 {rvec_mult(arg1,arg2,j);} 1488 else if (type == GL_ADD) 1489 {rvec_add(arg1,arg2,j);} 1490 else if (type == GL_MAX_ABS) 1491 {rvec_max_abs(arg1,arg2,j);} 1492 else if (type == GL_MIN_ABS) 1493 {rvec_min_abs(arg1,arg2,j);} 1494 else if (type == GL_EXISTS) 1495 {rvec_exists(arg1,arg2,j);} 1496 else 1497 {error_msg_fatal("unrecognized type passed to rvec_non_uniform()!");} 1498 1499 arg1+=j; arg2+=j; i+=j; 1500 } 1501 } 1502 1503 1504 1505 /**********************************ivec.c************************************** 1506 Function rvec_fct_addr() 1507 1508 Input : 1509 Output: 1510 Return: 1511 Description: 1512 ***********************************ivec.c*************************************/ 1513 vfp rvec_fct_addr( int type) 1514 { 1515 if (type == NON_UNIFORM) 1516 {return((void (*)(void*, void *, int, ...))&rvec_non_uniform);} 1517 else if (type == GL_MAX) 1518 {return((void (*)(void*, void *, int, ...))&rvec_max);} 1519 else if (type == GL_MIN) 1520 {return((void (*)(void*, void *, int, ...))&rvec_min);} 1521 else if (type == GL_MULT) 1522 {return((void (*)(void*, void *, int, ...))&rvec_mult);} 1523 else if (type == GL_ADD) 1524 {return((void (*)(void*, void *, int, ...))&rvec_add);} 1525 else if (type == GL_MAX_ABS) 1526 {return((void (*)(void*, void *, int, ...))&rvec_max_abs);} 1527 else if (type == GL_MIN_ABS) 1528 {return((void (*)(void*, void *, int, ...))&rvec_min_abs);} 1529 else if (type == GL_EXISTS) 1530 {return((void (*)(void*, void *, int, ...))&rvec_exists);} 1531 1532 /* catch all ... not good if we get here */ 1533 return(NULL); 1534 } 1535 1536 1537 /****************************************************************************** 1538 Function: my_sort(). 1539 Input : offset of list to be sorted, number of elements to be sorted. 1540 Output: sorted list (in ascending order). 1541 Return: none. 1542 Description: stack based (nonrecursive) quicksort w/brute-shell bottom. 1543 ******************************************************************************/ 1544 void 1545 rvec_sort( PetscScalar *ar, int Size) 1546 { 1547 PetscScalar *pi, *pj, temp; 1548 PetscScalar **top_a = (PetscScalar **)offset_stack; 1549 long *top_s = psize_stack, *bottom_s = psize_stack; 1550 long size = (long) Size; 1551 1552 /* we're really interested in the offset of the last element */ 1553 /* ==> length of the list is now size + 1 */ 1554 size--; 1555 1556 /* do until we're done ... return when stack is exhausted */ 1557 for (;;) 1558 { 1559 /* if list is large enough use quicksort partition exchange code */ 1560 if (size > SORT_OPT) 1561 { 1562 /* start up pointer at element 1 and down at size */ 1563 pi = ar+1; 1564 pj = ar+size; 1565 1566 /* find middle element in list and swap w/ element 1 */ 1567 SWAP(*(ar+(size>>1)),*pi) 1568 1569 pj = ar+size; 1570 1571 /* order element 0,1,size-1 st {M,L,...,U} w/L<=M<=U */ 1572 /* note ==> pivot_value in index 0 */ 1573 if (*pi > *pj) 1574 {SWAP(*pi,*pj)} 1575 if (*ar > *pj) 1576 {SWAP(*ar,*pj)} 1577 else if (*pi > *ar) 1578 {SWAP(*(ar),*(ar+1))} 1579 1580 /* partition about pivot_value ... */ 1581 /* note lists of length 2 are not guaranteed to be sorted */ 1582 for(;;) 1583 { 1584 /* walk up ... and down ... swap if equal to pivot! */ 1585 do pi++; while (*pi<*ar); 1586 do pj--; while (*pj>*ar); 1587 1588 /* if we've crossed we're done */ 1589 if (pj<pi) break; 1590 1591 /* else swap */ 1592 SWAP(*pi,*pj) 1593 } 1594 1595 /* place pivot_value in it's correct location */ 1596 SWAP(*ar,*pj) 1597 1598 /* test stack_size to see if we've exhausted our stack */ 1599 if (top_s-bottom_s >= SORT_STACK) 1600 {error_msg_fatal("\nSTACK EXHAUSTED!!!\n");} 1601 1602 /* push right hand child iff length > 1 */ 1603 if ((*top_s = size-(pi-ar))) 1604 { 1605 *(top_a++) = pi; 1606 size -= *top_s+2; 1607 top_s++; 1608 } 1609 /* set up for next loop iff there is something to do */ 1610 else if (size -= *top_s+2) 1611 {;} 1612 /* might as well pop - note NR_OPT >=2 ==> we're ok! */ 1613 else 1614 { 1615 ar = *(--top_a); 1616 size = *(--top_s); 1617 } 1618 } 1619 1620 /* else sort small list directly then pop another off stack */ 1621 else 1622 { 1623 /* insertion sort for bottom */ 1624 for (pj=ar+1;pj<=ar+size;pj++) 1625 { 1626 temp = *pj; 1627 for (pi=pj-1;pi>=ar;pi--) 1628 { 1629 if (*pi <= temp) break; 1630 *(pi+1)=*pi; 1631 } 1632 *(pi+1)=temp; 1633 } 1634 1635 /* check to see if stack is exhausted ==> DONE */ 1636 if (top_s==bottom_s) return; 1637 1638 /* else pop another list from the stack */ 1639 ar = *(--top_a); 1640 size = *(--top_s); 1641 } 1642 } 1643 } 1644 1645 1646 1647 /****************************************************************************** 1648 Function: my_sort(). 1649 Input : offset of list to be sorted, number of elements to be sorted. 1650 Output: sorted list (in ascending order). 1651 Return: none. 1652 Description: stack based (nonrecursive) quicksort w/brute-shell bottom. 1653 ******************************************************************************/ 1654 void 1655 rvec_sort_companion( PetscScalar *ar, int *ar2, int Size) 1656 { 1657 PetscScalar *pi, *pj, temp; 1658 PetscScalar **top_a = (PetscScalar **)offset_stack; 1659 long *top_s = psize_stack, *bottom_s = psize_stack; 1660 long size = (long) Size; 1661 1662 int *pi2, *pj2; 1663 int ptr; 1664 long mid; 1665 1666 1667 /* we're really interested in the offset of the last element */ 1668 /* ==> length of the list is now size + 1 */ 1669 size--; 1670 1671 /* do until we're done ... return when stack is exhausted */ 1672 for (;;) 1673 { 1674 /* if list is large enough use quicksort partition exchange code */ 1675 if (size > SORT_OPT) 1676 { 1677 /* start up pointer at element 1 and down at size */ 1678 mid = size>>1; 1679 pi = ar+1; 1680 pj = ar+mid; 1681 pi2 = ar2+1; 1682 pj2 = ar2+mid; 1683 1684 /* find middle element in list and swap w/ element 1 */ 1685 SWAP(*pi,*pj) 1686 P_SWAP(*pi2,*pj2) 1687 1688 /* order element 0,1,size-1 st {M,L,...,U} w/L<=M<=U */ 1689 /* note ==> pivot_value in index 0 */ 1690 pj = ar+size; 1691 pj2 = ar2+size; 1692 if (*pi > *pj) 1693 {SWAP(*pi,*pj) P_SWAP(*pi2,*pj2)} 1694 if (*ar > *pj) 1695 {SWAP(*ar,*pj) P_SWAP(*ar2,*pj2)} 1696 else if (*pi > *ar) 1697 {SWAP(*(ar),*(ar+1)) P_SWAP(*(ar2),*(ar2+1))} 1698 1699 /* partition about pivot_value ... */ 1700 /* note lists of length 2 are not guaranteed to be sorted */ 1701 for(;;) 1702 { 1703 /* walk up ... and down ... swap if equal to pivot! */ 1704 do {pi++; pi2++;} while (*pi<*ar); 1705 do {pj--; pj2--;} while (*pj>*ar); 1706 1707 /* if we've crossed we're done */ 1708 if (pj<pi) break; 1709 1710 /* else swap */ 1711 SWAP(*pi,*pj) 1712 P_SWAP(*pi2,*pj2) 1713 } 1714 1715 /* place pivot_value in it's correct location */ 1716 SWAP(*ar,*pj) 1717 P_SWAP(*ar2,*pj2) 1718 1719 /* test stack_size to see if we've exhausted our stack */ 1720 if (top_s-bottom_s >= SORT_STACK) 1721 {error_msg_fatal("\nSTACK EXHAUSTED!!!\n");} 1722 1723 /* push right hand child iff length > 1 */ 1724 if ((*top_s = size-(pi-ar))) 1725 { 1726 *(top_a++) = pi; 1727 *(top_a++) = (PetscScalar *) pi2; 1728 size -= *top_s+2; 1729 top_s++; 1730 } 1731 /* set up for next loop iff there is something to do */ 1732 else if (size -= *top_s+2) 1733 {;} 1734 /* might as well pop - note NR_OPT >=2 ==> we're ok! */ 1735 else 1736 { 1737 ar2 = (int*) *(--top_a); 1738 ar = *(--top_a); 1739 size = *(--top_s); 1740 } 1741 } 1742 1743 /* else sort small list directly then pop another off stack */ 1744 else 1745 { 1746 /* insertion sort for bottom */ 1747 for (pj=ar+1, pj2=ar2+1;pj<=ar+size;pj++,pj2++) 1748 { 1749 temp = *pj; 1750 ptr = *pj2; 1751 for (pi=pj-1,pi2=pj2-1;pi>=ar;pi--,pi2--) 1752 { 1753 if (*pi <= temp) break; 1754 *(pi+1)=*pi; 1755 *(pi2+1)=*pi2; 1756 } 1757 *(pi+1)=temp; 1758 *(pi2+1)=ptr; 1759 } 1760 1761 /* check to see if stack is exhausted ==> DONE */ 1762 if (top_s==bottom_s) return; 1763 1764 /* else pop another list from the stack */ 1765 ar2 = (int*) *(--top_a); 1766 ar = *(--top_a); 1767 size = *(--top_s); 1768 } 1769 } 1770 } 1771 1772 1773 1774 1775 1776 /**********************************ivec.c************************************** 1777 Function ivec_binary_search() 1778 1779 Input : 1780 Output: 1781 Return: 1782 Description: 1783 ***********************************ivec.c*************************************/ 1784 int 1785 rvec_binary_search( PetscScalar item, PetscScalar *list, int rh) 1786 { 1787 int mid, lh=0; 1788 1789 rh--; 1790 while (lh<=rh) 1791 { 1792 mid = (lh+rh)>>1; 1793 if (*(list+mid) == item) 1794 {return(mid);} 1795 if (*(list+mid) > item) 1796 {rh = mid-1;} 1797 else 1798 {lh = mid+1;} 1799 } 1800 return(-1); 1801 } 1802 1803 1804 1805 1806 1807