IFPACK  Development
 All Classes Files Functions Variables Enumerations Friends
Euclid_apply.c
00001 /*@HEADER
00002 // ***********************************************************************
00003 //
00004 //       Ifpack: Object-Oriented Algebraic Preconditioner Package
00005 //                 Copyright (2002) Sandia Corporation
00006 //
00007 // Under terms of Contract DE-AC04-94AL85000, there is a non-exclusive
00008 // license for use of this work by or on behalf of the U.S. Government.
00009 //
00010 // Redistribution and use in source and binary forms, with or without
00011 // modification, are permitted provided that the following conditions are
00012 // met:
00013 //
00014 // 1. Redistributions of source code must retain the above copyright
00015 // notice, this list of conditions and the following disclaimer.
00016 //
00017 // 2. Redistributions in binary form must reproduce the above copyright
00018 // notice, this list of conditions and the following disclaimer in the
00019 // documentation and/or other materials provided with the distribution.
00020 //
00021 // 3. Neither the name of the Corporation nor the names of the
00022 // contributors may be used to endorse or promote products derived from
00023 // this software without specific prior written permission.
00024 //
00025 // THIS SOFTWARE IS PROVIDED BY SANDIA CORPORATION "AS IS" AND ANY
00026 // EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
00027 // IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
00028 // PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL SANDIA CORPORATION OR THE
00029 // CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
00030 // EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
00031 // PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
00032 // PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
00033 // LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
00034 // NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
00035 // SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
00036 //
00037 // Questions? Contact Michael A. Heroux (maherou@sandia.gov)
00038 //
00039 // ***********************************************************************
00040 //@HEADER
00041 */
00042 
00043 #include "Euclid_dh.h"
00044 #include "Mat_dh.h"
00045 #include "Factor_dh.h"
00046 #include "Parser_dh.h"
00047 #include "TimeLog_dh.h"
00048 #include "SubdomainGraph_dh.h"
00049 
00050 
00051 static void scale_rhs_private (Euclid_dh ctx, double *rhs);
00052 static void permute_vec_n2o_private (Euclid_dh ctx, double *xIN,
00053                      double *xOUT);
00054 static void permute_vec_o2n_private (Euclid_dh ctx, double *xIN,
00055                      double *xOUT);
00056 
00057 #undef __FUNC__
00058 #define __FUNC__ "Euclid_dhApply"
00059 void
00060 Euclid_dhApply (Euclid_dh ctx, double *rhs, double *lhs)
00061 {
00062   START_FUNC_DH double *rhs_, *lhs_;
00063   double t1, t2;
00064 
00065   t1 = MPI_Wtime ();
00066 
00067   /* default settings; for everything except PILU */
00068   ctx->from = 0;
00069   ctx->to = ctx->m;
00070 
00071   /* case 1: no preconditioning */
00072   if (!strcmp (ctx->algo_ilu, "none") || !strcmp (ctx->algo_par, "none"))
00073     {
00074       int i, m = ctx->m;
00075       for (i = 0; i < m; ++i)
00076     lhs[i] = rhs[i];
00077       goto END_OF_FUNCTION;
00078     }
00079 
00080   /*----------------------------------------------------------------
00081    * permute and scale rhs vector
00082    *----------------------------------------------------------------*/
00083   /* permute rhs vector */
00084   if (ctx->sg != NULL)
00085     {
00086 
00087       permute_vec_n2o_private (ctx, rhs, lhs);
00088       CHECK_V_ERROR;
00089       rhs_ = lhs;
00090       lhs_ = ctx->work2;
00091     }
00092   else
00093     {
00094       rhs_ = rhs;
00095       lhs_ = lhs;
00096     }
00097 
00098   /* scale rhs vector */
00099   if (ctx->isScaled)
00100     {
00101 
00102       scale_rhs_private (ctx, rhs_);
00103       CHECK_V_ERROR;
00104     }
00105 
00106   /* note: rhs_ is permuted, scaled; the input, "rhs" vector has
00107      not been disturbed.
00108    */
00109 
00110   /*----------------------------------------------------------------
00111    * big switch to choose the appropriate triangular solve
00112    *----------------------------------------------------------------*/
00113 
00114   /* sequential and mpi block jacobi cases */
00115   if (np_dh == 1 || !strcmp (ctx->algo_par, "bj"))
00116     {
00117       Factor_dhSolveSeq (rhs_, lhs_, ctx);
00118       CHECK_V_ERROR;
00119     }
00120 
00121 
00122   /* pilu case */
00123   else
00124     {
00125       Factor_dhSolve (rhs_, lhs_, ctx);
00126       CHECK_V_ERROR;
00127     }
00128 
00129   /*----------------------------------------------------------------
00130    * unpermute lhs vector
00131    * (note: don't need to unscale, because we were clever)
00132    *----------------------------------------------------------------*/
00133   if (ctx->sg != NULL)
00134     {
00135       permute_vec_o2n_private (ctx, lhs_, lhs);
00136       CHECK_V_ERROR;
00137     }
00138 
00139 END_OF_FUNCTION:;
00140 
00141   t2 = MPI_Wtime ();
00142   /* collective timing for triangular solves */
00143   ctx->timing[TRI_SOLVE_T] += (t2 - t1);
00144 
00145   /* collective timing for setup+krylov+triSolves
00146      (intent is to time linear solve, but this is
00147      at best probelematical!)
00148    */
00149   ctx->timing[TOTAL_SOLVE_TEMP_T] = t2 - ctx->timing[SOLVE_START_T];
00150 
00151   /* total triangular solve count */
00152   ctx->its += 1;
00153   ctx->itsTotal += 1;
00154 
00155 END_FUNC_DH}
00156 
00157 
00158 #undef __FUNC__
00159 #define __FUNC__ "scale_rhs_private"
00160 void
00161 scale_rhs_private (Euclid_dh ctx, double *rhs)
00162 {
00163   START_FUNC_DH int i, m = ctx->m;
00164   REAL_DH *scale = ctx->scale;
00165 
00166   /* if matrix was scaled, must scale the rhs */
00167   if (scale != NULL)
00168     {
00169       for (i = 0; i < m; ++i)
00170     {
00171       rhs[i] *= scale[i];
00172     }
00173     }
00174 END_FUNC_DH}
00175 
00176 
00177 #undef __FUNC__
00178 #define __FUNC__ "permute_vec_o2n_private"
00179 void
00180 permute_vec_o2n_private (Euclid_dh ctx, double *xIN, double *xOUT)
00181 {
00182   START_FUNC_DH int i, m = ctx->m;
00183   int *o2n = ctx->sg->o2n_col;
00184   for (i = 0; i < m; ++i)
00185     xOUT[i] = xIN[o2n[i]];
00186 END_FUNC_DH}
00187 
00188 
00189 #undef __FUNC__
00190 #define __FUNC__ "permute_vec_n2o_private"
00191 void
00192 permute_vec_n2o_private (Euclid_dh ctx, double *xIN, double *xOUT)
00193 {
00194   START_FUNC_DH int i, m = ctx->m;
00195   int *n2o = ctx->sg->n2o_row;
00196   for (i = 0; i < m; ++i)
00197     xOUT[i] = xIN[n2o[i]];
00198 END_FUNC_DH}
 All Classes Files Functions Variables Enumerations Friends