#include "BSprivate.h" /*+ BStrans_perm_cl - Find the complete mapping from clique to i-node Input Parameters: . A - a sparse matrix . gnum - the global numbering . procinfo - the usual processor stuff Returns: the mapping from clique to i-node +*/ #define __TREE_RETURN #include "BStree.h" BScl_2_inode *BStrans_perm_cl(BSspmat *A, BSnumbering *gnum, BSprocinfo *procinfo) { BStree tree; BStree_ptr node_ptr; int *iptr; BSbb *row_bb; int i, j; int count; BSsprow *row; int *colptr; int *addrs, *answs; void (*map)(int,int *,int *,BSprocinfo *,BSmapping *); void (*glmap)(int,int *,int *,BSprocinfo *,BSmapping *); int num_cols; int num_nz; int cval, lval, row_gval; int found; BScl_2_inode *trans; int max_row_len; int *map_work; /* initialize BB */ row_bb = BSinit_bb(A->num_rows,A->map); CHKERRN(0); BSpost_noaddr_bb(row_bb,A->num_rows,gnum->numbers); CHKERRN(0); /* set up requests */ num_nz = BSnonlocalnz(A,&max_row_len,procinfo); CHKERRN(0); MY_MALLOCN(addrs,(int *),sizeof(int)*num_nz,1); MY_MALLOCN(answs,(int *),sizeof(int)*num_nz,2); MY_MALLOCN(map_work,(int *),sizeof(int)*max_row_len,2); count = 0; map = A->map->fglobal2proc; for (i=0;inum_rows;i++) { row = A->rows[i]; colptr = row->col; (*map)(row->length,colptr,map_work,procinfo,A->map); CHKERRN(0); for (j=0;jlength;j++) { if (map_work[j] != procinfo->my_id) { addrs[count] = colptr[j]; count++; } } } /* query BB */ BSquery_match_bb(row_bb,count,addrs,answs,procinfo); CHKERRN(0); MY_FREEN(addrs); BSfree_bb(row_bb); CHKERRN(0); count = 0; map = A->map->fglobal2proc; glmap = A->map->fglobal2local; num_cols = 0; MY_INIT_TREE(tree,sizeof(int)); for (i=0;inum_rows;i++) { row = A->rows[i]; colptr = row->col; row_gval = gnum->numbers[i]; (*map)(row->length,colptr,map_work,procinfo,A->map); CHKERRN(0); for (j=0;jlength;j++) { if (map_work[j] != procinfo->my_id) { cval = answs[count]; count++; } else { (*glmap)(1,&(colptr[j]),&lval,procinfo,A->map); CHKERRN(0); cval = gnum->numbers[lval]; } if(A->icc_storage) { if (row_gval >= cval) { MY_INSERT_TREE_NODE(tree,cval,found,node_ptr,num_cols); if (!found) { iptr = (int *) MY_GET_TREE_DATA(node_ptr); (*iptr) = map_work[j]; } } } else { /* Do not need row_gval >= cval check for nonsymmetric case */ MY_INSERT_TREE_NODE(tree,cval,found,node_ptr,num_cols); if (!found) { iptr = (int *) MY_GET_TREE_DATA(node_ptr); (*iptr) = map_work[j]; } } } } MY_FREEN(answs); MY_FREEN(map_work); /* copy the linked list into the array structure */ MY_MALLOCN(trans,(BScl_2_inode *),sizeof(BScl_2_inode),5); MY_MALLOCN(trans->g_offset,(int *),sizeof(int)*(num_cols+1),6); MY_MALLOCN(trans->proc,(int *),sizeof(int)*(num_cols+1),6); MY_MALLOCN(trans->inode_index,(int *),sizeof(int)*(num_cols+1),6); MY_MALLOCN(trans->d_mats,(BSdense *),sizeof(BSdense)*(num_cols+1),6); trans->num_cols = num_cols; trans->g_offset[num_cols] = INT_MAX; count = 0; MY_FIRST_IN_TREE(tree,node_ptr); while (! IS_TREE_PTR_NULL(node_ptr)) { trans->g_offset[count] = MY_GET_TREE_KEY(node_ptr); iptr = (int *) MY_GET_TREE_DATA(node_ptr); trans->proc[count] = (*iptr); count++; MY_NEXT_IN_TREE(node_ptr); } MY_FREE_TREE(tree); return(trans); }