20#include "fasp_functs.h"
27static void fasp_sortrow (
INT num,
INT *q);
28static void fasp_check_col_index (
INT row,
INT num,
INT *q);
84 printf(
"### DEBUG: [-Begin-] %s ...\n", __FUNCTION__);
144 INT ju0, k, j1, j2, j, ii, i, lenl, lenu, jj, jrow, jpos, n2, jlev, NE;
150 if (lfil < 0)
goto F998;
170 if (ia[1] == 0) cinindex=1 ;
174 for (i=1; i<=NE; ++i) ++ia[i];
176 for (i=1; i<=NE; ++i) ++ja[i];
188 for(j = 1; j<=2*n; ++j) jw[j] = 0;
193 for(ii = 1; ii <= n; ++ii) {
205 for(j = j1; j <= j2; ++j) {
208 if (t == 0.0)
continue;
215 }
else if (k == ii) {
220 jpos = ii + lenu - 1;
234 if (jj > lenl)
goto F160;
245 for(j = jj + 1; j <= lenl; ++j) {
262 jw[n2 + jj] = jw[n2 + k];
274 fact = w[jj]*alu[jrow];
276 if (jlev > lfil)
goto F150;
279 for(k = ju[jrow]; k <= jlu[jrow + 1] - 1; ++k ) {
288 if (lenu > n)
goto F995;
293 jw[n2 + i] = jlev + levs[k] + 1;
296 w[jpos] = w[jpos] - s;
297 jw[n2 + jpos] =
MIN(jw[n2 + jpos], jlev + levs[k] + 1);
304 if (lenl > n)
goto F995;
308 jw[n2 + lenl] = jlev + levs[k] + 1;
311 w[jpos] = w[jpos] - s;
312 jw[n2 + jpos] =
MIN(jw[n2 + jpos], jlev + levs[k] + 1);
323 for(k = 1; k <= lenu; ++k) jw[n + jw[ii + k - 1]] = 0;
326 for(k = 1; k <= lenl; ++k ) {
327 if (ju0 > iwk)
goto F996;
328 if (jw[n2 + k] <= lfil) {
339 for(k = ii + 1; k <= ii + lenu - 1; ++k ) {
340 if (ju0 > iwk)
goto F997;
342 if (jw[n2 + k] <= lfil) {
345 levs[ju0] = jw[n2 + k];
351 if (w[ii] == 0.0)
goto F999;
365 for ( i = 1; i <= *nzlu; ++i ) --jlu[i];
387 printf(
"### DEBUG: [--End--] %s ...\n", __FUNCTION__);
394 printf(
"### ERROR: Incomprehensible error. [%s]\n", __FUNCTION__);
400 printf(
"### ERROR: Insufficient storage in L. [%s]\n", __FUNCTION__);
406 printf(
"### ERROR: Insufficient storage in U. [%s]\n", __FUNCTION__);
412 printf(
"### ERROR: Illegal lfil entered. [%s]\n", __FUNCTION__);
418 printf(
"### ERROR: Zero row encountered in A or U. [%s]\n", __FUNCTION__);
480 printf(
"### DEBUG: [-Begin-] %s ...\n", __FUNCTION__);
564 INT ju0, k, j1, j2, j, ii, i, lenl, lenu, jj, jrow, jpos, NE, len;
565 REAL t, s, fact, tmp;
570 if (lfil < 0)
goto F998;
587 if (ia[1] == 0) cinindex=1 ;
592 for (i=1; i<=NE; ++i) ++ia[i];
594 for (i=1; i<=NE; ++i) ++ja[i];
605 for (j = 1; j<=n; ++j) jw[n + j] = 0;
610 for (ii = 1; ii <= n; ++ii ) {
614 for ( k = j1; k<= j2; ++k) tmp = tmp +
ABS(a[k]);
615 tmp = tmp/(
REAL)(j2 - j1 + 1);
616 tnorm[ii] = tmp*droptol;;
619 for (ii = 1; ii<=n; ++ii) {
630 for(j = j1; j<=j2; ++j) {
638 }
else if (k == ii) {
642 jpos = ii + lenu - 1;
654 if (jj > lenl)
goto F160;
666 for(j = jj + 1; j<=lenl; ++j) {
691 fact = w[jj]*alu[jrow];
693 if (
ABS(fact) <= droptol)
goto F150;
696 for ( k = ju[jrow]; k <= jlu[jrow + 1] - 1; ++k) {
706 if (lenu > n)
goto F995;
713 w[jpos] = w[jpos] - s;
720 if (lenl > n)
goto F995;
726 w[jpos] = w[jpos] - s;
742 for (k = 1; k <= lenu; ++k ) jw[n + jw[ii + k - 1]] = 0;
746 len =
MIN(lenl, lfil);
749 fasp_qsplit(&w[1], &jw[1], lenl, len);
752 for (k = 1; k <= len; ++k ) {
753 if (ju0 > iwk)
goto F996;
764 for (k = 1; k <= lenu - 1; ++k) {
766 if (
ABS(w[ii + k]) > tnorm[ii] ) {
768 w[ii + len] = w[ii + k];
769 jw[ii + len] = jw[ii + k];
774 len =
MIN(lenu, lfil);
776 fasp_qsplit(&w[ii + 1], &jw[ii + 1], lenu - 1, len);
780 if (len + ju0 > iwk)
goto F997;
781 for (k = ii + 1; k<=ii + len - 1; ++k) {
790 if (w[ii] == 0.0) w[ii] = tnorm[ii];
804 for(i = 1; i <= *nz; ++i) --jlu[i];
826 printf(
"### DEBUG: [--End--] %s ...\n", __FUNCTION__);
832 printf(
"### ERROR: Input matrix may be wrong. [%s]\n", __FUNCTION__);
837 printf(
"### ERROR: Insufficient storage in L. [%s]\n", __FUNCTION__);
842 printf(
"### ERROR: Insufficient storage in U. [%s]\n", __FUNCTION__);
848 printf(
"### ERROR: Illegal lfil entered. [%s]\n", __FUNCTION__);
922 printf(
"### DEBUG: [-Begin-] %s ...\n", __FUNCTION__);
1012 INT k, i, j, jrow, ju0, ii, j1, j2, jpos, len, imax, lenu, lenl, jj, icut,NE;
1013 REAL s, tmp, tnorm, xmax, xmax0, fact, t;
1018 if (lfil < 0)
goto F998;
1037 if (ia[1] == 0) cinindex=1 ;
1042 for (i=1; i<=NE; ++i) ++ia[i];
1044 for (i=1; i<=NE; ++i) ++ja[i];
1056 for ( j = 1; j <= n; ++j ) {
1065 for (ii = 1; ii <= n; ++ii ) {
1067 j2 = ia[ii + 1] - 1;
1070 for (k = j1; k <= j2; ++k ) tnorm = tnorm +
ABS( a[k] );
1071 if (tnorm == 0.0)
goto F999;
1072 tnorm = tnorm/(
REAL)(j2 - j1 + 1);
1081 for (j = j1; j <= j2; ++j ) {
1082 k = iperm[n + ja[j]];
1089 }
else if (k == ii) {
1093 jpos = ii + lenu - 1;
1107 if (jj > lenl)
goto F160;
1117 for (j = jj + 1; j <= lenl; ++j) {
1142 fact = w[jj]*alu[jrow];
1145 if (
ABS(fact) <= droptol)
goto F150;
1149 for ( k = ju[jrow]; k <= jlu[jrow + 1] - 1; ++k ) {
1152 j = iperm[n + jlu[k]];
1160 if (lenu > n)
goto F995;
1166 w[jpos] = w[jpos] - s;
1174 if (lenl > n)
goto F995;
1180 w[jpos] = w[jpos] - s;
1197 for ( k = 1; k <= lenu; ++k ) jw[n + jw[ii + k - 1]] = 0;
1201 len =
MIN(lenl, lfil);
1204 fasp_qsplit(&w[1], &jw[1], lenl, len);
1207 for ( k = 1; k <= len; ++k ) {
1208 if (ju0 > iwk)
goto F996;
1210 jlu[ju0] = iperm[jw[k]];
1219 for(k = 1; k <= lenu - 1; ++k ) {
1220 if (
ABS(w[ii + k]) > droptol*tnorm) {
1222 w[ii + len] = w[ii + k];
1223 jw[ii + len] = jw[ii + k];
1228 len =
MIN(lenu, lfil);
1229 fasp_qsplit(&w[ii + 1], &jw[ii + 1], lenu-1, len);
1233 xmax =
ABS(w[imax]);
1235 icut = ii - 1 + mbloc - (ii - 1)%mbloc;
1237 for ( k = ii + 1; k <= ii + len - 1; ++k ) {
1239 if ((t > xmax) && (t*permtol > xmax0) && (jw[k] <= icut)) {
1253 iperm[ii] = iperm[j];
1257 iperm[n + iperm[ii]] = ii;
1258 iperm[n + iperm[j]] = j;
1261 if (len + ju0 > iwk)
goto F997;
1265 for ( k = ii + 1; k <= ii + len - 1; ++k ) {
1266 jlu[ju0] = iperm[jw[k]];
1272 if (w[ii] == 0.0) w[ii] = (1.0e-4 + droptol)*tnorm;
1273 alu[ii] = 1.0/w[ii];
1284 for ( k = jlu[1]; k <= jlu[n + 1] - 1; ++k ) jlu[k] = iperm[n + jlu[k]];
1287 for ( k = ia[1]; k <= ia[n + 1] - 1; ++k ) ja[k] = iperm[n + ja[k]];
1292 for (i = 1; i <= *nz; ++i ) --jlu[i];
1313 printf(
"### DEBUG: [--End--] %s ...\n", __FUNCTION__);
1319 printf(
"### ERROR: Input matrix may be wrong. [%s]\n", __FUNCTION__);
1324 printf(
"### ERROR: Insufficient storage in L. [%s]\n", __FUNCTION__);
1329 printf(
"### ERROR: Insufficient storage in U. [%s]\n", __FUNCTION__);
1334 printf(
"### ERROR: Illegal lfil entered. [%s]\n", __FUNCTION__);
1340 printf(
"### ERROR: Zero row encountered. [%s]\n", __FUNCTION__);
1383 printf(
"### DEBUG: [-Begin-] %s ...\n", __FUNCTION__);
1579 INT icolindj, ijlum, i, j, k, m, ibegin, iend, Ujbeg, Ujend,NE;
1580 INT head, prev, lm, actlev, lowct, k1, k2, levp1, lmk, nzi, rowct;
1582 INT *rowll, *lastcol, *levels;
1603 if (rwptr[1] == 0) cinindex=1 ;
1606 for (i=1; i<=NE; ++i) ++rwptr[i];
1607 NE = rwptr[n+1] - 1;
1608 for (i=1; i<=NE; ++i) ++colind[i];
1628 levp1 = levfill + 1;
1634 for (i = 1; i<=n; ++i) lastcol[i] = 0;
1639 for (i = 1; i <= n; ++i) {
1651 iend = rwptr[i + 1];
1656 nzi = iend - ibegin;
1684 printf(
"### DEBUG: %s %d row\n", __FUNCTION__, i);
1687 for ( j = ibegin; j <= iend; ++j) {
1688 icolindj = colind[j];
1689 lastcol[icolindj] = i;
1690 if (icolindj != i) {
1691 levels[icolindj] = 1;
1693 rowll[rowct] = icolindj;
1696 printf(
"### DEBUG: %d\n", icolindj);
1704 fasp_sortrow(nzi - 1, &rowll[1]);
1707 fasp_check_col_index(i, nzi-1, &rowll[1]);
1714 for (j = nzi - 1; j >= 1; --j) {
1725 *nzlu = *nzlu + nzi - 1;
1767 Ujend = ijlu[j + 1] - 1;
1795 for (m = Ujbeg; m <= Ujend; ++m) {
1810 actlev = lmk + levels[m];
1818 if (lastcol[ijlum] != i) {
1825 if (actlev <= levp1) {
1839 levels[ijlum] = actlev;
1848 while (lm <= ijlum) {
1857 rowll[prev] = ijlum;
1874 levels[ijlum] =
MIN(levels[ijlum], actlev);
1901 if (*nzlu > nzmax) {
1902 printf(
"### ERROR: More storage needed! [%s]\n", __FUNCTION__);
1911 ijlu[i + 1] = *nzlu + 1;
1917 uptr[i] = ijlu[i] + lowct;
1926 for (k = k1; k <= *nzlu; ++k) {
1928 levels[k] = levels[j];
1938 ijlu[i + 1] = *nzlu + 1;
1948 for ( i = 1; i <= *nzlu; ++i ) --ijlu[i];
1949 for ( i = 1; i <= n; ++i ) --uptr[i];
1950 NE = rwptr[n + 1] - 1;
1951 for ( i = 1; i <= NE; ++i ) --colind[i];
1953 for ( i = 1; i <= NE; ++i ) --rwptr[i];
1972 printf(
"### DEBUG: [--End--] %s ...\n", __FUNCTION__);
1998static void fasp_qsplit (
REAL *a,
2012 INT itmp, first, last, mid, j;
2020 if ((ncut < first) || (ncut > last))
return;
2025 abskey =
ABS(a[mid]);
2026 for (j = first + 1; j <= last; ++j ) {
2027 if (
ABS(a[j]) > abskey) {
2045 ind[mid] = ind[first];
2077static void fasp_sortrow (
INT num,
2081 printf(
"### DEBUG: [-Begin-] %s ...\n", __FUNCTION__);
2119 INT key, icn, ih, ii, i, j, jj;
2120 INT iinc[6] = {0,1, 4, 13, 40, 121};
2137 for(ii = 1; ii <= icn; ++ii) {
2138 ih = iinc[icn + 1 - ii];
2139 for(j = ih + 1; j <= num; ++j) {
2142 for(jj = 1; jj <= j - ih; jj += ih) {
2158 printf(
"### DEBUG: [--End--] %s ...\n", __FUNCTION__);
2175static void fasp_check_col_index (
INT row,
2180 printf(
"### DEBUG: [-Begin-] %s ...\n", __FUNCTION__);
2184 INT num_1 = num - 1;
2186 for ( ii = 0; ii < num_1; ++ii ) {
2187 if ( q[ii] == q[ii+1] ) {
2188 printf(
"### ERROR: Multiple entries with same col indices!\n");
2189 printf(
"### ERROR: row = %d, col = %d, %d!\n", row, q[ii], q[ii+1]);
2195 printf(
"### DEBUG: [--End--] %s ...\n", __FUNCTION__);
void fasp_mem_free(void *mem)
Free up previous allocated memory body and set pointer to NULL.
void * fasp_mem_calloc(const unsigned int size, const unsigned int type)
Allocate, initiate, and check memory.
void fasp_chkerr(const SHORT status, const char *fctname)
Check error status and print out error messages before quit.
void fasp_iluk(INT n, REAL *a, INT *ja, INT *ia, INT lfil, REAL *alu, INT *jlu, INT iwk, INT *ierr, INT *nzlu)
Get ILU factorization with level of fill-in k (ilu(k)) for a CSR matrix A.
void fasp_ilutp(INT n, REAL *a, INT *ja, INT *ia, INT lfil, REAL droptol, REAL permtol, INT mbloc, REAL *alu, INT *jlu, INT *iperm, INT iwk, INT *ierr, INT *nz)
Get incomplete LU factorization with pivoting dual truncations of a CSR matrix A.
void fasp_ilut(INT n, REAL *a, INT *ja, INT *ia, INT lfil, REAL droptol, REAL *alu, INT *jlu, INT iwk, INT *ierr, INT *nz)
Get incomplete LU factorization with dual truncations of a CSR matrix A.
void fasp_symbfactor(INT n, INT *colind, INT *rwptr, INT levfill, INT nzmax, INT *nzlu, INT *ijlu, INT *uptr, INT *ierr)
Symbolic factorization of a CSR matrix A in compressed sparse row format, with resulting factors stor...
Main header file for the FASP project.
#define SHORT
FASP integer and floating point numbers.
#define ERROR_SOLVER_ILUSETUP