diff --git a/CHOLMOD/.gitignore b/CHOLMOD/.gitignore index 35ad65d696..9ef9289f98 100644 --- a/CHOLMOD/.gitignore +++ b/CHOLMOD/.gitignore @@ -1,2 +1 @@ timelog.m -_*.tex diff --git a/CHOLMOD/CMakeLists.txt b/CHOLMOD/CMakeLists.txt index 11d3f8f9ad..902088cecf 100644 --- a/CHOLMOD/CMakeLists.txt +++ b/CHOLMOD/CMakeLists.txt @@ -12,10 +12,10 @@ # cmake 3.22 is required to find the BLAS/LAPACK cmake_minimum_required ( VERSION 3.22 ) -set ( CHOLMOD_DATE "Oct 23, 2023" ) -set ( CHOLMOD_VERSION_MAJOR 5 ) -set ( CHOLMOD_VERSION_MINOR 0 ) -set ( CHOLMOD_VERSION_SUB 0 ) +set ( CHOLMOD_DATE "Oct 15, 2023" ) +set ( CHOLMOD_VERSION_MAJOR 4 ) +set ( CHOLMOD_VERSION_MINOR 2 ) +set ( CHOLMOD_VERSION_SUB 2 ) message ( STATUS "Building CHOLMOD version: v" ${CHOLMOD_VERSION_MAJOR}. @@ -78,22 +78,22 @@ else ( ) find_package ( OpenMP ) endif ( ) -find_package ( SuiteSparse_config 7.3.0 +find_package ( SuiteSparse_config 7.2.0 PATHS ${CMAKE_SOURCE_DIR}/../SuiteSparse_config/build NO_DEFAULT_PATH ) if ( NOT TARGET SuiteSparse::SuiteSparseConfig ) find_package ( SuiteSparse_config 7.2.0 REQUIRED ) endif ( ) -find_package ( COLAMD 3.2.1 +find_package ( COLAMD 3.2.0 PATHS ${CMAKE_SOURCE_DIR}/../COLAMD/build NO_DEFAULT_PATH ) if ( NOT TARGET SuiteSparse::COLAMD ) - find_package ( COLAMD 3.2.1 REQUIRED ) + find_package ( COLAMD 3.2.0 REQUIRED ) endif ( ) -find_package ( AMD 3.2.1 +find_package ( AMD 3.2.0 PATHS ${CMAKE_SOURCE_DIR}/../AMD/build NO_DEFAULT_PATH ) if ( NOT TARGET SuiteSparse::AMD ) - find_package ( AMD 3.2.1 REQUIRED ) + find_package ( AMD 3.2.0 REQUIRED ) endif ( ) #------------------------------------------------------------------------------- @@ -196,16 +196,16 @@ endif ( ) if ( NOT NCAMD ) # find CAMD and CCOLAMD - find_package ( CAMD 3.2.1 + find_package ( CAMD 3.2.0 PATHS ${CMAKE_SOURCE_DIR}/../CAMD/build NO_DEFAULT_PATH ) if ( NOT TARGET SuiteSparse::CAMD ) - find_package ( CAMD 3.2.1 ) + find_package ( CAMD 3.2.0 ) endif ( ) - find_package ( CCOLAMD 3.2.1 + find_package ( CCOLAMD 3.2.0 PATHS ${CMAKE_SOURCE_DIR}/../CCOLAMD/build NO_DEFAULT_PATH ) if ( NOT TARGET SuiteSparse::CCOLAMD ) - find_package ( CCOLAMD 3.2.1 ) + find_package ( CCOLAMD 3.2.0 ) endif ( ) if ( NOT CAMD_FOUND OR NOT CCOLAMD_FOUND ) @@ -290,7 +290,7 @@ configure_file ( "Config/cholmod_version.tex.in" # include directories #------------------------------------------------------------------------------- -include_directories ( Check Cholesky Utility MatrixOps Modify Partition +include_directories ( Check Cholesky Core MatrixOps Modify Partition Supernodal Include ${CMAKE_SOURCE_DIR} ) #------------------------------------------------------------------------------- @@ -298,7 +298,7 @@ include_directories ( Check Cholesky Utility MatrixOps Modify Partition #------------------------------------------------------------------------------- file ( GLOB CHOLMOD_SOURCES "Check/cholmod_*.c" "Cholesky/cholmod_*.c" - "Utility/cholmod_*.c" "MatrixOps/cholmod_*.c" "Modify/cholmod_*.c" + "Core/cholmod_*.c" "MatrixOps/cholmod_*.c" "Modify/cholmod_*.c" "Partition/cholmod_*.c" "Supernodal/cholmod_*.c" ) add_library ( CHOLMOD SHARED ${CHOLMOD_SOURCES} ) diff --git a/CHOLMOD/Check/cholmod_check.c b/CHOLMOD/Check/cholmod_check.c index 56bc8e9a7f..857163e409 100644 --- a/CHOLMOD/Check/cholmod_check.c +++ b/CHOLMOD/Check/cholmod_check.c @@ -69,7 +69,7 @@ /* === printing definitions ================================================= */ /* ========================================================================== */ -#if defined ( CHOLMOD_INT64 ) +#if ( ITYPE == CHOLMOD_LONG ) #define I8 "%8ld" #define I_8 "%-8ld" #else @@ -204,7 +204,7 @@ static int check_common ) { double fl, lnz ; - uint8_t *Xwork ; + double *Xwork ; Int *Flag, *Head ; int64_t mark ; Int i, nrow, nmethods, ordering, xworksize, amd_backup, init_print ; @@ -502,15 +502,9 @@ static int check_common } P4 (" dbound: LDL' diagonal threshold: % .5g\n Entries with abs. value" - " less than dbound are replaced with +/- dbound.\n" - " (for double precision case)\n", + " less than dbound are replaced with +/- dbound.\n", Common->dbound) ; - P4 (" sbound: LDL' diagonal threshold: % .5g\n Entries with abs. value" - " less than sbound are replaced with +/- sbound.\n" - " (for single precision case)\n", - Common->sbound) ; - P4 (" grow0: memory reallocation: % .5g\n", Common->grow0) ; P4 (" grow1: memory reallocation: % .5g\n", Common->grow1) ; P4 (" grow2: memory reallocation: %g\n", (double) (Common->grow2)) ; @@ -558,8 +552,7 @@ static int check_common } } } - - xworksize = Common->xworkbytes ; + xworksize = Common->xworksize ; Xwork = Common->Xwork ; if (xworksize > 0) { @@ -571,7 +564,7 @@ static int check_common { if (Xwork [i] != 0.) { - PRINT0 (("Xwork ["ID"] = %d\n", i, Xwork [i])) ; + PRINT0 (("Xwork ["ID"] = %g\n", i, Xwork [i])) ; ERR ("workspace corrupted (Xwork)") ; } } @@ -749,6 +742,7 @@ static int64_t check_sparse switch (A->itype) { case CHOLMOD_INT: P4 ("%s", "\n scalar types: int, ") ; break ; + case CHOLMOD_INTLONG: ERR ("mixed int/long type unsupported") ; case CHOLMOD_LONG: P4 ("%s", "\n scalar types: int64_t, "); break ; default: ERR ("unknown itype") ; @@ -766,13 +760,13 @@ static int64_t check_sparse switch (A->dtype) { case CHOLMOD_DOUBLE: P4 ("%s", ", double\n") ; break ; - case CHOLMOD_SINGLE: P4 ("%s", ", single\n") ; break ; + case CHOLMOD_SINGLE: ERR ("float unsupported") ; default: ERR ("unknown dtype") ; } - if (A->itype != ITYPE) + if (A->itype != ITYPE || A->dtype != DTYPE) { - ERR ("integer type must match routine") ; + ERR ("integer and real type must match routine") ; } if (A->stype && nrow != ncol) @@ -1015,7 +1009,7 @@ static int check_dense switch (X->dtype) { case CHOLMOD_DOUBLE: P4 ("%s", ", double\n") ; break ; - case CHOLMOD_SINGLE: P4 ("%s", ", single\n") ; break ; + case CHOLMOD_SINGLE: ERR ("single unsupported") ; default: ERR ("unknown dtype") ; } @@ -1548,6 +1542,7 @@ static int check_factor switch (L->itype) { case CHOLMOD_INT: P4 ("%s", "\n scalar types: int, ") ; break ; + case CHOLMOD_INTLONG: ERR ("mixed int/long type unsupported") ; case CHOLMOD_LONG: P4 ("%s", "\n scalar types: int64_t, "); break ; default: ERR ("unknown itype") ; @@ -1565,13 +1560,13 @@ static int check_factor switch (L->dtype) { case CHOLMOD_DOUBLE: P4 ("%s", ", double\n") ; break ; - case CHOLMOD_SINGLE: P4 ("%s", ", single\n") ; break ; + case CHOLMOD_SINGLE: ERR ("single unsupported") ; default: ERR ("unknown dtype") ; } - if (L->itype != ITYPE) + if (L->itype != ITYPE || L->dtype != DTYPE) { - ERR ("integer type must match routine") ; + ERR ("integer and real type must match routine") ; } if (L->is_super) @@ -2123,6 +2118,7 @@ static int check_triplet switch (T->itype) { case CHOLMOD_INT: P4 ("%s", "\n scalar types: int, ") ; break ; + case CHOLMOD_INTLONG: ERR ("mixed int/long type unsupported") ; case CHOLMOD_LONG: P4 ("%s", "\n scalar types: int64_t, "); break ; default: ERR ("unknown itype") ; @@ -2140,13 +2136,13 @@ static int check_triplet switch (T->dtype) { case CHOLMOD_DOUBLE: P4 ("%s", ", double\n") ; break ; - case CHOLMOD_SINGLE: P4 ("%s", ", single\n") ; break ; + case CHOLMOD_SINGLE: ERR ("single unsupported") ; default: ERR ("unknown dtype") ; } - if (T->itype != ITYPE) + if (T->itype != ITYPE || T->dtype != DTYPE) { - ERR ("integer type must match routine") ; + ERR ("integer and real type must match routine") ; } if (T->stype && nrow != ncol) @@ -2454,7 +2450,7 @@ int CHOLMOD(dump_parent) void CHOLMOD(dump_real) ( const char *name, - double *X, int64_t nrow, int64_t ncol, int lower, + Real *X, int64_t nrow, int64_t ncol, int lower, int xentry, cholmod_common *Common ) { @@ -2658,19 +2654,16 @@ int CHOLMOD(dump_work) (int flag, int head, int64_t wsize, W = Common->Xwork ; mark = Common->mark ; -#if 0 - // FIXME: need float and double if (wsize < 0) { /* check all of Xwork */ - wsize = Common->xworkbytes ; + wsize = Common->xworksize ; } else { /* check on the first wsize doubles in Xwork */ - wsize = MIN (wsize, (Int) (Common->xworkbytes)) ; + wsize = MIN (wsize, (Int) (Common->xworksize)) ; } -#endif if (flag) { @@ -2680,6 +2673,7 @@ int CHOLMOD(dump_work) (int flag, int head, int64_t wsize, { PRINT0 (("Flag invalid, Flag ["ID"] = "ID", mark = "ID"\n", k, Flag [k], mark)) ; + ASSERT (0) ; return (FALSE) ; } } @@ -2692,25 +2686,23 @@ int CHOLMOD(dump_work) (int flag, int head, int64_t wsize, if (Head [k] != EMPTY) { PRINT0 (("Head invalid, Head ["ID"] = "ID"\n", k, Head [k])) ; + ASSERT (0) ; return (FALSE) ; } } } -#if 0 - // FIXME: need float and double for (k = 0 ; k < wsize ; k++) { if (W [k] != 0.) { PRINT0 (("W invalid, W ["ID"] = %g\n", k, W [k])) ; + ASSERT (0) ; return (FALSE) ; } } -#endif return (TRUE) ; } #endif #endif - diff --git a/CHOLMOD/Check/cholmod_l_check.c b/CHOLMOD/Check/cholmod_l_check.c index 881ee34799..5fb51ae16f 100644 --- a/CHOLMOD/Check/cholmod_l_check.c +++ b/CHOLMOD/Check/cholmod_l_check.c @@ -8,6 +8,6 @@ //------------------------------------------------------------------------------ -#define CHOLMOD_INT64 +#define DLONG #include "cholmod_check.c" diff --git a/CHOLMOD/Check/cholmod_l_read.c b/CHOLMOD/Check/cholmod_l_read.c index d0decedbc2..3af7074e67 100644 --- a/CHOLMOD/Check/cholmod_l_read.c +++ b/CHOLMOD/Check/cholmod_l_read.c @@ -8,6 +8,6 @@ //------------------------------------------------------------------------------ -#define CHOLMOD_INT64 +#define DLONG #include "cholmod_read.c" diff --git a/CHOLMOD/Check/cholmod_l_write.c b/CHOLMOD/Check/cholmod_l_write.c index 6ea5fa0880..a7937d6441 100644 --- a/CHOLMOD/Check/cholmod_l_write.c +++ b/CHOLMOD/Check/cholmod_l_write.c @@ -8,6 +8,6 @@ //------------------------------------------------------------------------------ -#define CHOLMOD_INT64 +#define DLONG #include "cholmod_write.c" diff --git a/CHOLMOD/Check/cholmod_read.c b/CHOLMOD/Check/cholmod_read.c index f1153dd616..e610a8d0cf 100644 --- a/CHOLMOD/Check/cholmod_read.c +++ b/CHOLMOD/Check/cholmod_read.c @@ -48,7 +48,7 @@ * complex symmetric matrices are always returned with both upper and lower * triangular parts present, with an stype of zero, since CHOLMOD does not * have a method for representing skew-symmetric and complex symmetric - * matrices. real symmetric and complex Hermitian matrices may optionally + * matrices. Real symmetric and complex Hermitian matrices may optionally * be returned with both parts present. * * Any other lines starting with "%" are treated as comments, and are ignored. diff --git a/CHOLMOD/Check/cholmod_write.c b/CHOLMOD/Check/cholmod_write.c index b19f2d0304..f6adc94805 100644 --- a/CHOLMOD/Check/cholmod_write.c +++ b/CHOLMOD/Check/cholmod_write.c @@ -140,7 +140,7 @@ static int print_value /* ---------------------------------------------------------------------- */ /* change -inf to -HUGE_DOUBLE, and change +inf and nan to +HUGE_DOUBLE */ - if (isnan (x) || x >= HUGE_DOUBLE) + if (CHOLMOD_IS_NAN (x) || x >= HUGE_DOUBLE) { x = HUGE_DOUBLE ; } @@ -341,7 +341,7 @@ static Int ntriplets * as A. * * Returns the symmetry in which the matrix was printed (1 to 7, see the - * CHOLMOD_MM_* codes in CHOLMOD/Include/cholmod.h), or -1 on failure. + * CHOLMOD_MM_* codes in CHOLMOD/Include/cholmod_core.h), or -1 on failure. * * If A and Z are sorted on input, and either unsymmetric (stype = 0) or * symmetric-lower (stype < 0), and if A and Z do not overlap, then the triplets diff --git a/CHOLMOD/Cholesky/cholmod_amd.c b/CHOLMOD/Cholesky/cholmod_amd.c index 6925e0ec3e..ef4eff0068 100644 --- a/CHOLMOD/Cholesky/cholmod_amd.c +++ b/CHOLMOD/Cholesky/cholmod_amd.c @@ -166,7 +166,7 @@ int CHOLMOD(amd) Control [AMD_AGGRESSIVE] = Common->method [Common->current].aggressive ; } -#if defined ( CHOLMOD_INT64 ) +#if ( ITYPE == CHOLMOD_LONG ) amd_l2 (n, C->p, C->i, Len, C->nzmax, cnz, Nv, Next, Perm, Head, Elen, Degree, Wi, Control, Info) ; #else diff --git a/CHOLMOD/Cholesky/cholmod_analyze.c b/CHOLMOD/Cholesky/cholmod_analyze.c index f61d8616d2..9f5f0dbb97 100644 --- a/CHOLMOD/Cholesky/cholmod_analyze.c +++ b/CHOLMOD/Cholesky/cholmod_analyze.c @@ -408,7 +408,7 @@ cholmod_factor *CHOLMOD(analyze_p2) Int *First, *Level, *Work4n, *Cmember, *CParent, *ColCount, *Lperm, *Parent, *Post, *Perm, *Lparent, *Lcolcount ; cholmod_factor *L ; - Int k, n, method, nmethods, status, default_strategy, ncol, uncol, + Int k, n, ordering, method, nmethods, status, default_strategy, ncol, uncol, skip_analysis, skip_best ; Int amd_backup ; size_t s ; @@ -477,9 +477,7 @@ cholmod_factor *CHOLMOD(analyze_p2) * being tried, then enable AMD backup */ amd_backup = (nmethods > 1) || (nmethods == 1 && (Common->method [0].ordering == CHOLMOD_METIS || - Common->method [0].ordering == CHOLMOD_NESDIS || - (Common->method [0].ordering == CHOLMOD_GIVEN && - UserPerm == NULL))) ; + Common->method [0].ordering == CHOLMOD_NESDIS)) ; } #ifdef NSUPERNODAL @@ -567,8 +565,6 @@ cholmod_factor *CHOLMOD(analyze_p2) /* determine the method to try */ /* ------------------------------------------------------------------ */ - Int ordering ; - Common->fl = EMPTY ; Common->lnz = EMPTY ; skip_analysis = FALSE ; @@ -578,6 +574,7 @@ cholmod_factor *CHOLMOD(analyze_p2) /* All methods failed: backup to AMD */ if (Common->selected == EMPTY && amd_backup) { + PRINT1 (("All methods requested failed: backup to AMD\n")) ; ordering = CHOLMOD_AMD ; } else @@ -590,6 +587,7 @@ cholmod_factor *CHOLMOD(analyze_p2) ordering = Common->method [method].ordering ; } Common->current = method ; + PRINT1 (("method "ID": Try method: "ID"\n", method, ordering)) ; /* ------------------------------------------------------------------ */ /* find the fill-reducing permutation */ @@ -618,6 +616,7 @@ cholmod_factor *CHOLMOD(analyze_p2) if (UserPerm == NULL) { /* this is not an error condition */ + PRINT1 (("skip, no user perm given\n")) ; continue ; } for (k = 0 ; k < n ; k++) @@ -653,6 +652,9 @@ cholmod_factor *CHOLMOD(analyze_p2) } else { + /* Alternative: + CHOLMOD(ccolamd) (A, fset, fsize, NULL, Perm, Common) ; + */ /* do not postorder, it is done later, below */ /* workspace: Iwork (4*nrow+uncol), Flag (nrow), Head (nrow+1)*/ CHOLMOD(colamd) (A, fset, fsize, FALSE, Perm, Common) ; @@ -705,6 +707,7 @@ cholmod_factor *CHOLMOD(analyze_p2) /* -------------------------------------------------------------- */ Common->status = CHOLMOD_INVALID ; + PRINT1 (("No such ordering: "ID"\n", ordering)) ; } ASSERT (CHOLMOD(dump_work) (TRUE, TRUE, 0, Common)) ; @@ -736,6 +739,7 @@ cholmod_factor *CHOLMOD(analyze_p2) ASSERT (Common->fl >= 0 && Common->lnz >= 0) ; Common->method [method].fl = Common->fl ; Common->method [method].lnz = Common->lnz ; + PRINT1 (("lnz %g fl %g\n", Common->lnz, Common->fl)) ; /* ------------------------------------------------------------------ */ /* pick the best method */ @@ -745,6 +749,7 @@ cholmod_factor *CHOLMOD(analyze_p2) if (Common->selected == EMPTY || Common->lnz < lnz_best) { Common->selected = method ; + PRINT1 (("this is best so far, method "ID"\n", method)) ; L->ordering = ordering ; lnz_best = Common->lnz ; for (k = 0 ; k < n ; k++) @@ -910,6 +915,8 @@ cholmod_factor *CHOLMOD(analyze_p2) /* workspace: Flag (nrow), Head (nrow), Iwork (5*nrow) */ CHOLMOD(super_symbolic2) (for_whom, S, F, Lparent, L, Common) ; + PRINT1 (("status %d\n", Common->status)) ; + CHOLMOD(free_sparse) (&A1, Common) ; CHOLMOD(free_sparse) (&A2, Common) ; } diff --git a/CHOLMOD/Cholesky/cholmod_colamd.c b/CHOLMOD/Cholesky/cholmod_colamd.c index 3653d7d3bc..c14b7d0d3f 100644 --- a/CHOLMOD/Cholesky/cholmod_colamd.c +++ b/CHOLMOD/Cholesky/cholmod_colamd.c @@ -92,7 +92,7 @@ int CHOLMOD(colamd) s = CHOLMOD(mult_size_t) (nrow, 4, &ok) ; s = CHOLMOD(add_size_t) (s, ncol, &ok) ; -#if defined ( CHOLMOD_INT64 ) +#if ( ITYPE == CHOLMOD_LONG ) alen = colamd_l_recommended (A->nzmax, ncol, nrow) ; colamd_l_set_defaults (knobs) ; #else @@ -151,7 +151,7 @@ int CHOLMOD(colamd) Int stats [COLAMD_STATS] ; Cp = C->p ; -#if defined ( CHOLMOD_INT64 ) +#if ( ITYPE == CHOLMOD_LONG ) colamd_l (ncol, nrow, alen, C->i, Cp, knobs, stats) ; #else colamd (ncol, nrow, alen, C->i, Cp, knobs, stats) ; diff --git a/CHOLMOD/Cholesky/cholmod_factorize.c b/CHOLMOD/Cholesky/cholmod_factorize.c index 491dd8400a..2d4782c031 100644 --- a/CHOLMOD/Cholesky/cholmod_factorize.c +++ b/CHOLMOD/Cholesky/cholmod_factorize.c @@ -386,7 +386,7 @@ int CHOLMOD(factorize_p) if (Common->status == CHOLMOD_OK) { grow2 = Common->grow2 ; - L->is_ll = (Common->final_ll) ? 1 : 0 ; + L->is_ll = BOOLEAN (Common->final_ll) ; if (L->xtype == CHOLMOD_PATTERN && Common->final_pack) { /* allocate a factor with exactly the space required */ diff --git a/CHOLMOD/Cholesky/cholmod_l_amd.c b/CHOLMOD/Cholesky/cholmod_l_amd.c index 8cdd7ca0ee..297f41050b 100644 --- a/CHOLMOD/Cholesky/cholmod_l_amd.c +++ b/CHOLMOD/Cholesky/cholmod_l_amd.c @@ -8,6 +8,6 @@ //------------------------------------------------------------------------------ -#define CHOLMOD_INT64 +#define DLONG #include "cholmod_amd.c" diff --git a/CHOLMOD/Cholesky/cholmod_l_analyze.c b/CHOLMOD/Cholesky/cholmod_l_analyze.c index 0a7d87d0ff..ef3ba5c30e 100644 --- a/CHOLMOD/Cholesky/cholmod_l_analyze.c +++ b/CHOLMOD/Cholesky/cholmod_l_analyze.c @@ -8,6 +8,6 @@ //------------------------------------------------------------------------------ -#define CHOLMOD_INT64 +#define DLONG #include "cholmod_analyze.c" diff --git a/CHOLMOD/Cholesky/cholmod_l_colamd.c b/CHOLMOD/Cholesky/cholmod_l_colamd.c index 990fab3d5f..58d4a2b500 100644 --- a/CHOLMOD/Cholesky/cholmod_l_colamd.c +++ b/CHOLMOD/Cholesky/cholmod_l_colamd.c @@ -8,6 +8,6 @@ //------------------------------------------------------------------------------ -#define CHOLMOD_INT64 +#define DLONG #include "cholmod_colamd.c" diff --git a/CHOLMOD/Cholesky/cholmod_l_etree.c b/CHOLMOD/Cholesky/cholmod_l_etree.c index 9c30c27cb8..057b544fa6 100644 --- a/CHOLMOD/Cholesky/cholmod_l_etree.c +++ b/CHOLMOD/Cholesky/cholmod_l_etree.c @@ -8,6 +8,6 @@ //------------------------------------------------------------------------------ -#define CHOLMOD_INT64 +#define DLONG #include "cholmod_etree.c" diff --git a/CHOLMOD/Cholesky/cholmod_l_factorize.c b/CHOLMOD/Cholesky/cholmod_l_factorize.c index b7572779b3..177ddf61b3 100644 --- a/CHOLMOD/Cholesky/cholmod_l_factorize.c +++ b/CHOLMOD/Cholesky/cholmod_l_factorize.c @@ -8,6 +8,6 @@ //------------------------------------------------------------------------------ -#define CHOLMOD_INT64 +#define DLONG #include "cholmod_factorize.c" diff --git a/CHOLMOD/Cholesky/cholmod_l_postorder.c b/CHOLMOD/Cholesky/cholmod_l_postorder.c index ebf4b2cbb2..207b1381e9 100644 --- a/CHOLMOD/Cholesky/cholmod_l_postorder.c +++ b/CHOLMOD/Cholesky/cholmod_l_postorder.c @@ -8,6 +8,6 @@ //------------------------------------------------------------------------------ -#define CHOLMOD_INT64 +#define DLONG #include "cholmod_postorder.c" diff --git a/CHOLMOD/Cholesky/cholmod_l_rcond.c b/CHOLMOD/Cholesky/cholmod_l_rcond.c index 63bb7b2d08..4ad8a08b64 100644 --- a/CHOLMOD/Cholesky/cholmod_l_rcond.c +++ b/CHOLMOD/Cholesky/cholmod_l_rcond.c @@ -8,6 +8,6 @@ //------------------------------------------------------------------------------ -#define CHOLMOD_INT64 +#define DLONG #include "cholmod_rcond.c" diff --git a/CHOLMOD/Cholesky/cholmod_l_resymbol.c b/CHOLMOD/Cholesky/cholmod_l_resymbol.c index 8b5f15c755..8425f83355 100644 --- a/CHOLMOD/Cholesky/cholmod_l_resymbol.c +++ b/CHOLMOD/Cholesky/cholmod_l_resymbol.c @@ -8,6 +8,6 @@ //------------------------------------------------------------------------------ -#define CHOLMOD_INT64 +#define DLONG #include "cholmod_resymbol.c" diff --git a/CHOLMOD/Cholesky/cholmod_l_rowcolcounts.c b/CHOLMOD/Cholesky/cholmod_l_rowcolcounts.c index 884ab3fb02..10536d045f 100644 --- a/CHOLMOD/Cholesky/cholmod_l_rowcolcounts.c +++ b/CHOLMOD/Cholesky/cholmod_l_rowcolcounts.c @@ -9,6 +9,6 @@ //------------------------------------------------------------------------------ -#define CHOLMOD_INT64 +#define DLONG #include "cholmod_rowcolcounts.c" diff --git a/CHOLMOD/Cholesky/cholmod_l_rowfac.c b/CHOLMOD/Cholesky/cholmod_l_rowfac.c index 5aa9253e0b..fb55f72212 100644 --- a/CHOLMOD/Cholesky/cholmod_l_rowfac.c +++ b/CHOLMOD/Cholesky/cholmod_l_rowfac.c @@ -8,6 +8,6 @@ //------------------------------------------------------------------------------ -#define CHOLMOD_INT64 +#define DLONG #include "cholmod_rowfac.c" diff --git a/CHOLMOD/Cholesky/cholmod_l_solve.c b/CHOLMOD/Cholesky/cholmod_l_solve.c index 01de1758ef..7d2e14e303 100644 --- a/CHOLMOD/Cholesky/cholmod_l_solve.c +++ b/CHOLMOD/Cholesky/cholmod_l_solve.c @@ -8,6 +8,6 @@ //------------------------------------------------------------------------------ -#define CHOLMOD_INT64 +#define DLONG #include "cholmod_solve.c" diff --git a/CHOLMOD/Cholesky/cholmod_l_spsolve.c b/CHOLMOD/Cholesky/cholmod_l_spsolve.c index 7c510d836d..1d43a57c91 100644 --- a/CHOLMOD/Cholesky/cholmod_l_spsolve.c +++ b/CHOLMOD/Cholesky/cholmod_l_spsolve.c @@ -8,6 +8,6 @@ //------------------------------------------------------------------------------ -#define CHOLMOD_INT64 +#define DLONG #include "cholmod_spsolve.c" diff --git a/CHOLMOD/Cholesky/cholmod_rcond.c b/CHOLMOD/Cholesky/cholmod_rcond.c index ae69bfbda5..c0ebb69746 100644 --- a/CHOLMOD/Cholesky/cholmod_rcond.c +++ b/CHOLMOD/Cholesky/cholmod_rcond.c @@ -33,7 +33,7 @@ #define FIRST_LMINMAX(Ljj,lmin,lmax) \ { \ double ljj = Ljj ; \ - if (isnan (ljj)) \ + if (IS_NAN (ljj)) \ { \ return (0) ; \ } \ @@ -44,7 +44,7 @@ #define LMINMAX(Ljj,lmin,lmax) \ { \ double ljj = Ljj ; \ - if (isnan (ljj)) \ + if (IS_NAN (ljj)) \ { \ return (0) ; \ } \ diff --git a/CHOLMOD/Cholesky/cholmod_resymbol.c b/CHOLMOD/Cholesky/cholmod_resymbol.c index cc142a5b79..7ecf85c150 100644 --- a/CHOLMOD/Cholesky/cholmod_resymbol.c +++ b/CHOLMOD/Cholesky/cholmod_resymbol.c @@ -440,7 +440,7 @@ int CHOLMOD(resymbol_noperm) /* flag the diagonal entry */ /* mark = CHOLMOD(clear_flag) (Common) ; */ - CLEAR_FLAG (Common) ; + CHOLMOD_CLEAR_FLAG (Common) ; mark = Common->mark ; Flag [k] = mark ; @@ -597,8 +597,8 @@ int CHOLMOD(resymbol_noperm) /* ---------------------------------------------------------------------- */ /* CHOLMOD(clear_flag) (Common) ; */ - CLEAR_FLAG (Common) ; - ASSERT (check_flag (Common)) ; + CHOLMOD_CLEAR_FLAG (Common) ; + DEBUG (CHOLMOD(dump_factor) (L, "ReSymbol final L (i, x):", Common)) ; ASSERT (CHOLMOD(dump_work) (TRUE, TRUE, 0, Common)) ; return (TRUE) ; diff --git a/CHOLMOD/Cholesky/cholmod_rowcolcounts.c b/CHOLMOD/Cholesky/cholmod_rowcolcounts.c index f98002ae56..57ffcf3737 100644 --- a/CHOLMOD/Cholesky/cholmod_rowcolcounts.c +++ b/CHOLMOD/Cholesky/cholmod_rowcolcounts.c @@ -507,8 +507,8 @@ int CHOLMOD(rowcolcounts) Common->mark = EMPTY ; /* CHOLMOD(clear_flag) (Common) ; */ - CLEAR_FLAG (Common) ; - ASSERT (check_flag (Common)) ; + CHOLMOD_CLEAR_FLAG (Common) ; + ASSERT (CHOLMOD(dump_work) (TRUE, TRUE, 0, Common)) ; /* ---------------------------------------------------------------------- */ @@ -532,4 +532,3 @@ int CHOLMOD(rowcolcounts) return (TRUE) ; } #endif - diff --git a/CHOLMOD/Cholesky/cholmod_rowfac.c b/CHOLMOD/Cholesky/cholmod_rowfac.c index 079d2c6860..30751bc4e5 100644 --- a/CHOLMOD/Cholesky/cholmod_rowfac.c +++ b/CHOLMOD/Cholesky/cholmod_rowfac.c @@ -297,8 +297,7 @@ int CHOLMOD(row_subtree) Flag = Common->Flag ; /* size nrow, Flag [i] < mark must hold */ /* mark = CHOLMOD(clear_flag) (Common) ; */ - CLEAR_FLAG (Common) ; - ASSERT (check_flag (Common)) ; + CHOLMOD_CLEAR_FLAG (Common) ; mark = Common->mark ; /* ---------------------------------------------------------------------- */ diff --git a/CHOLMOD/Cholesky/cholmod_solve.c b/CHOLMOD/Cholesky/cholmod_solve.c index d29c679abb..78cb85dddd 100644 --- a/CHOLMOD/Cholesky/cholmod_solve.c +++ b/CHOLMOD/Cholesky/cholmod_solve.c @@ -1153,12 +1153,13 @@ int CHOLMOD(solve2) /* returns TRUE on success, FALSE on failure */ /* convert a supernodal L to simplicial when using Bset */ if (L->is_super) { - // Can only use Bset on a simplicial factorization. The supernodal - // factor L is converted to simplicial, leaving the xtype unchanged - // (real, complex, or zomplex). Since the supernodal factorization - // is already LL', it is left in that form. This conversion uses - // the super_num_to_simplicial_num function in - // cholmod_change_factor. + /* Can only use Bset on a simplicial factorization. The supernodal + * factor L is converted to simplicial, leaving the xtype unchanged + * (real, complex, or zomplex). Since the supernodal factorization + * is already LL', it is left in that form. This conversion uses + * the ll_super_to_simplicial_numeric function in + * cholmod_change_factor. + */ CHOLMOD(change_factor) ( CHOLMOD_REAL, /* ignored, since L is already numeric */ TRUE, /* convert to LL' (no change to num. values) */ @@ -1547,13 +1548,6 @@ int CHOLMOD(solve2) /* returns TRUE on success, FALSE on failure */ Common->blas_ok = TRUE ; dual = (L->xtype == CHOLMOD_REAL && B->xtype != CHOLMOD_REAL) ? 2 : 1 ; Y = CHOLMOD(ensure_dense) (Y_Handle, n, dual*nrhs, n, L->xtype, Common); - - if (Common->status < CHOLMOD_OK) - { - /* out of memory */ - return (FALSE) ; - } - E = CHOLMOD(ensure_dense) (E_Handle, dual*nrhs, L->maxesize, dual*nrhs, L->xtype, Common) ; diff --git a/CHOLMOD/Cholesky/cholmod_spsolve.c b/CHOLMOD/Cholesky/cholmod_spsolve.c index 1f0d008936..744de84da2 100644 --- a/CHOLMOD/Cholesky/cholmod_spsolve.c +++ b/CHOLMOD/Cholesky/cholmod_spsolve.c @@ -232,7 +232,7 @@ cholmod_sparse *CHOLMOD(spsolve) /* returns the sparse solution X */ for (i = 0 ; i < n ; i++) { x = X4x [i + j_n] ; - if (x != 0) + if (IS_NONZERO (x)) { Xi [xnz] = i ; Xx [xnz] = x ; @@ -246,7 +246,7 @@ cholmod_sparse *CHOLMOD(spsolve) /* returns the sparse solution X */ { x = X4x [2*(i + j_n) ] ; z = X4x [2*(i + j_n)+1] ; - if ((x != 0) || (z != 0)) + if (IS_NONZERO (x) || IS_NONZERO (z)) { Xi [xnz] = i ; Xx [2*xnz ] = x ; @@ -261,7 +261,7 @@ cholmod_sparse *CHOLMOD(spsolve) /* returns the sparse solution X */ { x = X4x [i + j_n] ; z = X4z [i + j_n] ; - if ((x != 0) || (z != 0)) + if (IS_NONZERO (x) || IS_NONZERO (z)) { Xi [xnz] = i ; Xx [xnz] = x ; @@ -287,7 +287,7 @@ cholmod_sparse *CHOLMOD(spsolve) /* returns the sparse solution X */ for (i = 0 ; i < n ; i++) { x = X4x [i + j_n] ; - if (x != 0) + if (IS_NONZERO (x)) { EXPAND_AS_NEEDED ; Xi [xnz] = i ; @@ -302,7 +302,7 @@ cholmod_sparse *CHOLMOD(spsolve) /* returns the sparse solution X */ { x = X4x [2*(i + j_n) ] ; z = X4x [2*(i + j_n)+1] ; - if ((x != 0) || (z != 0)) + if (IS_NONZERO (x) || IS_NONZERO (z)) { EXPAND_AS_NEEDED ; Xi [xnz] = i ; @@ -318,7 +318,7 @@ cholmod_sparse *CHOLMOD(spsolve) /* returns the sparse solution X */ { x = X4x [i + j_n] ; z = X4z [i + j_n] ; - if ((x != 0) || (z != 0)) + if (IS_NONZERO (x) || IS_NONZERO (z)) { EXPAND_AS_NEEDED ; Xi [xnz] = i ; diff --git a/CHOLMOD/Cholesky/t_cholmod_rowfac.c b/CHOLMOD/Cholesky/t_cholmod_rowfac.c index 4b343176aa..1f1758f481 100644 --- a/CHOLMOD/Cholesky/t_cholmod_rowfac.c +++ b/CHOLMOD/Cholesky/t_cholmod_rowfac.c @@ -94,7 +94,7 @@ static int TEMPLATE (cholmod_rowfac) packed = A->packed ; sorted = A->sorted ; - use_dbound = (Common->dbound > 0) ; + use_dbound = IS_GT_ZERO (Common->dbound) ; /* get the current factors L (and D for LDL'); allocate space if needed */ is_ll = L->is_ll ; @@ -157,8 +157,7 @@ static int TEMPLATE (cholmod_rowfac) * zomplex. Xwork [i] == 0 must hold. */ Wz = Wx + n ; /* size n for zomplex case only */ mark = Common->mark ; - size_t wsize = (L->xtype == CHOLMOD_REAL ? 1:2) * n ; - ASSERT (Common->xworkbytes >= wsize * sizeof (Real)) ; + ASSERT ((Int) Common->xworksize >= (L->xtype == CHOLMOD_REAL ? 1:2)*n) ; /* ---------------------------------------------------------------------- */ /* compute LDL' or LL' factorization by rows */ @@ -180,7 +179,7 @@ static int TEMPLATE (cholmod_rowfac) /* column k of L is currently empty */ ASSERT (Lnz [k] == 1) ; - ASSERT (CHOLMOD(dump_work) (TRUE, TRUE, wsize, Common)) ; + ASSERT (CHOLMOD(dump_work) (TRUE, TRUE, 2*n, Common)) ; top = n ; /* Stack is empty */ Flag [k] = mark ; /* do not include diagonal entry in Stack */ @@ -263,7 +262,7 @@ static int TEMPLATE (cholmod_rowfac) * Flag [Stack [top..n-1]] is equal to mark, but no longer needed */ /* mark = CHOLMOD(clear_flag) (Common) ; */ - CLEAR_FLAG (Common) ; + CHOLMOD_CLEAR_FLAG (Common) ; mark = Common->mark ; /* ------------------------------------------------------------------ */ @@ -316,7 +315,7 @@ static int TEMPLATE (cholmod_rowfac) /* di = Lx [p] ; the diagonal entry L or D(i,i), which is real */ ASSIGN_REAL (di,0, Lx,p) ; - if (i >= (Int) L->minor || (di [0] == 0)) + if (i >= (Int) L->minor || IS_ZERO (di [0])) { /* For the LL' factorization, L(i,i) is zero. For the LDL', * D(i,i) is zero. Skip column i of L, and set L(k,i) = 0. */ @@ -387,7 +386,7 @@ static int TEMPLATE (cholmod_rowfac) /* W [i] = 0 ; */ CLEAR (Wx,Wz,i) ; } - ASSERT (CHOLMOD(dump_work) (TRUE, TRUE, wsize, Common)) ; + ASSERT (CHOLMOD(dump_work) (TRUE, TRUE, n, Common)) ; return (FALSE) ; } Li = L->i ; /* L->i, L->x, L->z may have moved */ @@ -421,7 +420,7 @@ static int TEMPLATE (cholmod_rowfac) /* modify the diagonal to force LL' or LDL' to exist */ dk [0] = CHOLMOD(dbound) (is_ll ? fabs (dk [0]) : dk [0], Common) ; } - else if ((is_ll ? (dk [0] <= 0) : (dk [0] == 0)) + else if ((is_ll ? (IS_LE_ZERO (dk [0])) : (IS_ZERO (dk [0]))) #ifndef REAL || dk_imaginary #endif @@ -450,7 +449,7 @@ static int TEMPLATE (cholmod_rowfac) Common->rowfacfl = fl ; DEBUG (CHOLMOD(dump_factor) (L, "final cholmod_rowfac", Common)) ; - ASSERT (CHOLMOD(dump_work) (TRUE, TRUE, wsize, Common)) ; + ASSERT (CHOLMOD(dump_work) (TRUE, TRUE, n, Common)) ; return (TRUE) ; } #undef PATTERN diff --git a/CHOLMOD/Config/cholmod.h.in b/CHOLMOD/Config/cholmod.h.in index 8b2b4d7cfa..37c3212d9b 100644 --- a/CHOLMOD/Config/cholmod.h.in +++ b/CHOLMOD/Config/cholmod.h.in @@ -2,14 +2,14 @@ // CHOLMOD/Include/cholmod.h: include file for CHOLMOD //------------------------------------------------------------------------------ -// CHOLMOD/Include/cholmod.h. Copyright (C) 2005-2023, Timothy A. Davis. +// CHOLMOD/Include/cholmod.h. Copyright (C) 2005-2022, Timothy A. Davis. // All Rights Reserved. // Each Module of CHOLMOD has its own license, and a shared cholmod.h file. // CHOLMOD/Check: SPDX-License-Identifier: LGPL-2.1+ // CHOLMOD/Cholesky: SPDX-License-Identifier: LGPL-2.1+ -// CHOLMOD/Utility: SPDX-License-Identifier: LGPL-2.1+ +// CHOLMOD/Core: SPDX-License-Identifier: LGPL-2.1+ // CHOLMOD/Partition: SPDX-License-Identifier: LGPL-2.1+ // CHOLMOD/Demo: SPDX-License-Identifier: GPL-2.0+ @@ -19,195 +19,433 @@ // CHOLMOD/Modify: SPDX-License-Identifier: GPL-2.0+ // CHOLMOD/Supernodal: SPDX-License-Identifier: GPL-2.0+ // CHOLMOD/Tcov: SPDX-License-Identifier: GPL-2.0+ +// CHOLMOD/Valgrind: SPDX-License-Identifier: GPL-2.0+ //------------------------------------------------------------------------------ -// CHOLMOD consists of a set of Modules, each with their own license: either -// LGPL-2.1+ or GPL-2.0+. This cholmod.h file includes defintions of the -// CHOLMOD API for all Modules, and this cholmod.h file itself is provided to -// you with a permissive license (Apache-2.0). You are permitted to provide -// the hooks for an optional interface to CHOLMOD in a non-GPL/non-LGPL code, -// without requiring you to agree to the GPL/LGPL license of the Modules, as -// long as you don't use the *.c files in the relevant Modules. The Modules -// themselves can only be functional if their GPL or LGPL licenses are used. -// -// The Modify Module is co-authored by William W. Hager. -// -// Acknowledgements: this work was supported in part by the National Science -// Foundation (NFS CCR-0203270 and DMS-9803599), and a grant from Sandia -// National Laboratories (Dept. of Energy) which supported the development of -// CHOLMOD's Partition Module. -// ----------------------------------------------------------------------------- - -// Each routine in CHOLMOD has a consistent interface. -// -// Naming convention: -// ------------------ -// -// All routine names, data types, and CHOLMOD library files use the -// cholmod_ prefix. All macros and other #define's use the CHOLMOD -// prefix. -// -// Return value: -// ------------- -// -// Most CHOLMOD routines return an int (TRUE (1) if successful, or FALSE -// (0) otherwise. An int32_t, int64_t, double, or float return value -// is >= 0 if successful, or -1 otherwise. A size_t return value -// is > 0 if successful, or 0 otherwise. -// -// If a routine returns a pointer, it is a pointer to a newly allocated -// object or NULL if a failure occured, with one exception. cholmod_free -// always returns NULL. -// -// "Common" parameter: -// ------------------ -// -// The last parameter in all CHOLMOD routines is a pointer to the CHOLMOD -// "Common" object. This contains control parameters, statistics, and -// workspace used between calls to CHOLMOD. It is always an input/output -// parameter. -// -// Input, Output, and Input/Output parameters: -// ------------------------------------------- -// -// Input parameters are listed first. They are not modified by CHOLMOD. -// -// Input/output are listed next. They must be defined on input, and -// are modified on output. -// -// Output parameters are listed next. If they are pointers, they must -// point to allocated space on input, but their contents are not defined -// on input. -// -// Workspace parameters appear next. They are used in only two routines -// in the Supernodal module. -// -// The cholmod_common *Common parameter always appears as the last -// parameter. It is always an input/output parameter. + +/* CHOLMOD consists of a set of Modules, each with their own license: either + * LGPL-2.1+ or GPL-2.0+. This cholmod.h file includes defintions of the + * CHOLMOD API for all Modules, and this cholmod.h file itself is provided to + * you with a permissive license (Apache-2.0). You are permitted to provide + * the hooks for an optional interface to CHOLMOD in a non-GPL/non-LGPL code, + * without requiring you to agree to the GPL/LGPL license of the Modules, as + * long as you don't use the *.c files in the relevant Modules. The Modules + * themselves can only be functional if their GPL or LGPL licenses are used. + * + * Portions of CHOLMOD (the Core and Partition Modules) are copyrighted by the + * University of Florida. The Modify Module is co-authored by William W. + * Hager, Univ. of Florida. + * + * Acknowledgements: this work was supported in part by the National Science + * Foundation (NFS CCR-0203270 and DMS-9803599), and a grant from Sandia + * National Laboratories (Dept. of Energy) which supported the development of + * CHOLMOD's Partition Module. + * -------------------------------------------------------------------------- */ + +/* CHOLMOD include file, for inclusion user programs. + * + * The include files listed below include a short description of each user- + * callable routine. Each routine in CHOLMOD has a consistent interface. + * More details about the CHOLMOD data types is in the cholmod_core.h file. + * + * Naming convention: + * ------------------ + * + * All routine names, data types, and CHOLMOD library files use the + * cholmod_ prefix. All macros and other #define's use the CHOLMOD + * prefix. + * + * Return value: + * ------------- + * + * Most CHOLMOD routines return an int (TRUE (1) if successful, or FALSE + * (0) otherwise. An int32_t, int64_t, or double return value is >= 0 if + * successful, or -1 otherwise. A size_t return value is > 0 if + * successful, or 0 otherwise. + * + * If a routine returns a pointer, it is a pointer to a newly allocated + * object or NULL if a failure occured, with one exception. cholmod_free + * always returns NULL. + * + * "Common" parameter: + * ------------------ + * + * The last parameter in all CHOLMOD routines is a pointer to the CHOLMOD + * "Common" object. This contains control parameters, statistics, and + * workspace used between calls to CHOLMOD. It is always an input/output + * parameter. + * + * Input, Output, and Input/Output parameters: + * ------------------------------------------- + * + * Input parameters are listed first. They are not modified by CHOLMOD. + * + * Input/output are listed next. They must be defined on input, and + * are modified on output. + * + * Output parameters are listed next. If they are pointers, they must + * point to allocated space on input, but their contents are not defined + * on input. + * + * Workspace parameters appear next. They are used in only two routines + * in the Supernodal module. + * + * The cholmod_common *Common parameter always appears as the last + * parameter. It is always an input/output parameter. + */ #ifndef CHOLMOD_H #define CHOLMOD_H -//============================================================================== -// version control -//============================================================================== - #define CHOLMOD_DATE "@CHOLMOD_DATE@" #define CHOLMOD_MAIN_VERSION @CHOLMOD_VERSION_MAJOR@ #define CHOLMOD_SUB_VERSION @CHOLMOD_VERSION_MINOR@ #define CHOLMOD_SUBSUB_VERSION @CHOLMOD_VERSION_SUB@ -#define CHOLMOD_VER_CODE(main,sub) ((main) * 1000 + (sub)) -#define CHOLMOD_VERSION \ - CHOLMOD_VER_CODE(CHOLMOD_MAIN_VERSION,CHOLMOD_SUB_VERSION) -#define CHOLMOD_HAS_VERSION_FUNCTION +/* ========================================================================== */ +/* === Include/cholmod_io64 ================================================= */ +/* ========================================================================== */ -int cholmod_version // returns CHOLMOD_VERSION, defined above -( - // if version is not NULL, then cholmod_version returns its contents as: - // version [0] = CHOLMOD_MAIN_VERSION - // version [1] = CHOLMOD_SUB_VERSION - // version [2] = CHOLMOD_SUBSUB_VERSION - int version [3] -) ; -int cholmod_l_version (int version [3]) ; +/* assume large file support. If problems occur, compile with -DNLARGEFILE */ -//============================================================================== -// Large file support -//============================================================================== +/* Definitions required for large file I/O, which must come before any other + * #includes. These are not used if -DNLARGEFILE is defined at compile time. + * Large file support may not be portable across all platforms and compilers; + * if you encounter an error here, compile your code with -DNLARGEFILE. In + * particular, you must use -DNLARGEFILE for MATLAB 6.5 or earlier (which does + * not have the io64.h include file). + */ + +/* skip all of this if NLARGEFILE is defined at the compiler command line */ +#ifndef NLARGEFILE -// CHOLMOD assumes large file support. If problems occur, compile with -// -DNLARGEFILE +#if defined(MATLAB_MEX_FILE) || defined(MATHWORKS) -// Definitions required for large file I/O, which must come before any other -// #includes. These are not used if -DNLARGEFILE is defined at compile time. -// Large file support may not be portable across all platforms and compilers; -// if you encounter an error here, compile your code with -DNLARGEFILE. In -// particular, you must use -DNLARGEFILE for MATLAB 6.5 or earlier (which does -// not have the io64.h include file). +/* CHOLMOD is being compiled as a MATLAB mexFunction, or for use in MATLAB */ +#include "io64.h" + +#else + +/* CHOLMOD is being compiled in a stand-alone library */ +#undef _LARGEFILE64_SOURCE +#define _LARGEFILE64_SOURCE +#undef _FILE_OFFSET_BITS +#define _FILE_OFFSET_BITS 64 + +#endif -// skip all of this if NLARGEFILE is defined at the compiler command line -#ifndef NLARGEFILE - #if defined(MATLAB_MEX_FILE) || defined(MATHWORKS) - // CHOLMOD compiled as a MATLAB mexFunction, or for use in MATLAB - #include "io64.h" - #else - // CHOLMOD is being compiled in a stand-alone library - #undef _LARGEFILE64_SOURCE - #define _LARGEFILE64_SOURCE - #undef _FILE_OFFSET_BITS - #define _FILE_OFFSET_BITS 64 - #endif #endif -//============================================================================== -// SuiteSparse_config -//============================================================================== +/* ========================================================================== */ +/* === SuiteSparse_config.h ================================================= */ +/* ========================================================================== */ #include "SuiteSparse_config.h" -//============================================================================== -// CHOLMOD configuration -//============================================================================== - -// You do not have to edit any CHOLMOD files to compile and install CHOLMOD. -// However, if you do not use all of CHOLMOD's modules, you need to compile -// with the appropriate flag, or edit this file to add the appropriate #define. -// -// Compiler flags for CHOLMOD -// -// -DNCHECK do not include the Check module. -// -DNCHOLESKY do not include the Cholesky module. -// -DNPARTITION do not include the Partition module. -// -DNCAMD do not include the interfaces to CAMD, -// CCOLAMD, CSYMAND in Partition module. -// -DNMATRIXOPS do not include the MatrixOps module. -// -DNMODIFY do not include the Modify module. -// -DNSUPERNODAL do not include the Supernodal module. -// -// -DNPRINT do not print anything -// -// The Utility Module is always included in the CHOLMOD library. - -// Use the compiler flag, or uncomment the definition(s), if you want to use -// one or more non-default installation options: - -// #define NCHECK -// #define NCHOLESKY -// #define NCAMD -// #define NPARTITION -// #define NMATRIXOPS -// #define NMODIFY -// #define NSUPERNODAL -// #define NPRINT -// #define NGPL - -// The NGPL option disables the MatrixOps, Modify, and Supernodal modules. The -// existence of this #define here, and its use in these 3 modules, does not -// affect the license itself; see CHOLMOD/Doc/License.txt for your actual -// license. +/* ========================================================================== */ +/* === Include/cholmod_config.h ============================================= */ +/* ========================================================================== */ + +/* CHOLMOD configuration file, for inclusion in user programs. + * + * You do not have to edit any CHOLMOD files to compile and install CHOLMOD. + * However, if you do not use all of CHOLMOD's modules, you need to compile + * with the appropriate flag, or edit this file to add the appropriate #define. + * + * Compiler flags for CHOLMOD: + * + * -DNCHECK do not include the Check module. + * -DNCHOLESKY do not include the Cholesky module. + * -DNPARTITION do not include the Partition module. + * -DNCAMD do not include the interfaces to CAMD, + * CCOLAMD, CSYMAND in Partition module. + * -DNMATRIXOPS do not include the MatrixOps module. + * -DNMODIFY do not include the Modify module. + * -DNSUPERNODAL do not include the Supernodal module. + * + * -DNPRINT do not print anything + * + * The Core Module is always included in the CHOLMOD library. + */ + +/* Use the compiler flag, or uncomment the definition(s), if you want to use + * one or more non-default installation options: */ + +/* +#define NCHECK +#define NCHOLESKY +#define NCAMD +#define NPARTITION +#define NMATRIXOPS +#define NMODIFY +#define NSUPERNODAL +#define NPRINT +#define NGPL +*/ + +/* The NGPL option disables the MatrixOps, Modify, and Supernodal modules. The + existence of this #define here, and its use in these 3 modules, does not + affect the license itself; see CHOLMOD/Doc/License.txt for your actual + license. + */ #ifdef NGPL - #undef NMATRIXOPS - #define NMATRIXOPS - #undef NMODIFY - #define NMODIFY - #undef NSUPERNODAL - #define NSUPERNODAL +#undef NMATRIXOPS +#define NMATRIXOPS +#undef NMODIFY +#define NMODIFY +#undef NSUPERNODAL +#define NSUPERNODAL #endif -//============================================================================== -// CHOLMOD:Utility Module -//============================================================================== -// the CHOLMOD:Utility Module is always required -#if 1 +/* ========================================================================== */ +/* === Include/cholmod_core.h =============================================== */ +/* ========================================================================== */ -//------------------------------------------------------------------------------ -// CUDA BLAS -//------------------------------------------------------------------------------ +/* CHOLMOD Core module: basic CHOLMOD objects and routines. + * Required by all CHOLMOD modules. Requires no other module or package. + * + * The CHOLMOD modules are: + * + * Core basic data structures and definitions + * Check check/print the 5 CHOLMOD objects, & 3 types of integer vectors + * Cholesky sparse Cholesky factorization + * Modify sparse Cholesky update/downdate/row-add/row-delete + * MatrixOps sparse matrix functions (add, multiply, norm, ...) + * Supernodal supernodal sparse Cholesky factorization + * Partition graph-partitioning based orderings + * + * The CHOLMOD objects: + * -------------------- + * + * cholmod_common parameters, statistics, and workspace + * cholmod_sparse a sparse matrix in compressed column form + * cholmod_factor an LL' or LDL' factorization + * cholmod_dense a dense matrix + * cholmod_triplet a sparse matrix in "triplet" form + * + * The Core module described here defines the CHOLMOD data structures, and + * basic operations on them. To create and solve a sparse linear system Ax=b, + * the user must create A and b, populate them with values, and then pass them + * to the routines in the CHOLMOD Cholesky module. There are two primary + * methods for creating A: (1) allocate space for a column-oriented sparse + * matrix and fill it with pattern and values, or (2) create a triplet form + * matrix and convert it to a sparse matrix. The latter option is simpler. + * + * The matrices b and x are typically dense matrices, but can also be sparse. + * You can allocate and free them as dense matrices with the + * cholmod_allocate_dense and cholmod_free_dense routines. + * + * The cholmod_factor object contains the symbolic and numeric LL' or LDL' + * factorization of sparse symmetric matrix. The matrix must be positive + * definite for an LL' factorization. It need only be symmetric and have well- + * conditioned leading submatrices for it to have an LDL' factorization + * (CHOLMOD does not pivot for numerical stability). It is typically created + * with the cholmod_factorize routine in the Cholesky module, but can also + * be initialized to L=D=I in the Core module and then modified by the Modify + * module. It must be freed with cholmod_free_factor, defined below. + * + * The Core routines for each object are described below. Each list is split + * into two parts: the primary routines and secondary routines. + * + * ============================================================================ + * === cholmod_common ========================================================= + * ============================================================================ + * + * The Common object contains control parameters, statistics, and + * You must call cholmod_start before calling any other CHOLMOD routine, and + * must call cholmod_finish as your last call to CHOLMOD, with two exceptions: + * you may call cholmod_print_common and cholmod_check_common in the Check + * module after calling cholmod_finish. + * + * cholmod_start first call to CHOLMOD + * cholmod_finish last call to CHOLMOD + * ----------------------------- + * cholmod_defaults restore default parameters + * cholmod_maxrank maximum rank for update/downdate + * cholmod_allocate_work allocate workspace in Common + * cholmod_free_work free workspace in Common + * cholmod_clear_flag clear Flag workspace in Common + * cholmod_error called when CHOLMOD encounters an error + * cholmod_dbound for internal use in CHOLMOD only + * cholmod_hypot compute sqrt (x*x + y*y) accurately + * cholmod_divcomplex complex division, c = a/b + * + * ============================================================================ + * === cholmod_sparse ========================================================= + * ============================================================================ + * + * A sparse matrix is held in compressed column form. In the basic type + * ("packed", which corresponds to a MATLAB sparse matrix), an n-by-n matrix + * with nz entries is held in three arrays: p of size n+1, i of size nz, and x + * of size nz. Row indices of column j are held in i [p [j] ... p [j+1]-1] and + * in the same locations in x. There may be no duplicate entries in a column. + * Row indices in each column may be sorted or unsorted (CHOLMOD keeps track). + * A->stype determines the storage mode: 0 if both upper/lower parts are stored, + * -1 if A is symmetric and just tril(A) is stored, +1 if symmetric and triu(A) + * is stored. + * + * cholmod_allocate_sparse allocate a sparse matrix + * cholmod_free_sparse free a sparse matrix + * ----------------------------- + * cholmod_reallocate_sparse change the size (# entries) of sparse matrix + * cholmod_nnz number of nonzeros in a sparse matrix + * cholmod_speye sparse identity matrix + * cholmod_spzeros sparse zero matrix + * cholmod_transpose transpose a sparse matrix + * cholmod_ptranspose transpose/permute a sparse matrix + * cholmod_transpose_unsym transpose/permute an unsymmetric sparse matrix + * cholmod_transpose_sym transpose/permute a symmetric sparse matrix + * cholmod_sort sort row indices in each column of sparse matrix + * cholmod_band C = tril (triu (A,k1), k2) + * cholmod_band_inplace A = tril (triu (A,k1), k2) + * cholmod_aat C = A*A' + * cholmod_copy_sparse C = A, create an exact copy of a sparse matrix + * cholmod_copy C = A, with possible change of stype + * cholmod_add C = alpha*A + beta*B + * cholmod_sparse_xtype change the xtype of a sparse matrix + * + * ============================================================================ + * === cholmod_factor ========================================================= + * ============================================================================ + * + * The data structure for an LL' or LDL' factorization is too complex to + * describe in one sentence. This object can hold the symbolic analysis alone, + * or in combination with a "simplicial" (similar to a sparse matrix) or + * "supernodal" form of the numerical factorization. Only the routine to free + * a factor is primary, since a factor object is created by the factorization + * routine (cholmod_factorize). It must be freed with cholmod_free_factor. + * + * cholmod_free_factor free a factor + * ----------------------------- + * cholmod_allocate_factor allocate a factor (LL' or LDL') + * cholmod_reallocate_factor change the # entries in a factor + * cholmod_change_factor change the type of factor (e.g., LDL' to LL') + * cholmod_pack_factor pack the columns of a factor + * cholmod_reallocate_column resize a single column of a factor + * cholmod_factor_to_sparse create a sparse matrix copy of a factor + * cholmod_copy_factor create a copy of a factor + * cholmod_factor_xtype change the xtype of a factor + * + * Note that there is no cholmod_sparse_to_factor routine to create a factor + * as a copy of a sparse matrix. It could be done, after a fashion, but a + * lower triangular sparse matrix would not necessarily have a chordal graph, + * which would break the many CHOLMOD routines that rely on this property. + * + * ============================================================================ + * === cholmod_dense ========================================================== + * ============================================================================ + * + * The solve routines and some of the MatrixOps and Modify routines use dense + * matrices as inputs. These are held in column-major order. With a leading + * dimension of d, the entry in row i and column j is held in x [i+j*d]. + * + * cholmod_allocate_dense allocate a dense matrix + * cholmod_free_dense free a dense matrix + * ----------------------------- + * cholmod_zeros allocate a dense matrix of all zeros + * cholmod_ones allocate a dense matrix of all ones + * cholmod_eye allocate a dense identity matrix + * cholmod_sparse_to_dense create a dense matrix copy of a sparse matrix + * cholmod_dense_to_sparse create a sparse matrix copy of a dense matrix + * cholmod_copy_dense create a copy of a dense matrix + * cholmod_copy_dense2 copy a dense matrix (pre-allocated) + * cholmod_dense_xtype change the xtype of a dense matrix + * cholmod_ensure_dense ensure a dense matrix has a given size and type + * + * ============================================================================ + * === cholmod_triplet ======================================================== + * ============================================================================ + * + * A sparse matrix held in triplet form is the simplest one for a user to + * create. It consists of a list of nz entries in arbitrary order, held in + * three arrays: i, j, and x, each of length nk. The kth entry is in row i[k], + * column j[k], with value x[k]. There may be duplicate values; if A(i,j) + * appears more than once, its value is the sum of the entries with those row + * and column indices. + * + * cholmod_allocate_triplet allocate a triplet matrix + * cholmod_triplet_to_sparse create a sparse matrix copy of a triplet matrix + * cholmod_free_triplet free a triplet matrix + * ----------------------------- + * cholmod_reallocate_triplet change the # of entries in a triplet matrix + * cholmod_sparse_to_triplet create a triplet matrix copy of a sparse matrix + * cholmod_copy_triplet create a copy of a triplet matrix + * cholmod_triplet_xtype change the xtype of a triplet matrix + * + * ============================================================================ + * === memory management ====================================================== + * ============================================================================ + * + * cholmod_malloc malloc wrapper + * cholmod_calloc calloc wrapper + * cholmod_free free wrapper + * cholmod_realloc realloc wrapper + * cholmod_realloc_multiple realloc wrapper for multiple objects + * + * ============================================================================ + * === Core CHOLMOD prototypes ================================================ + * ============================================================================ + * + * All CHOLMOD routines (in all modules) use the following protocol for return + * values, with one exception: + * + * int TRUE (1) if successful, or FALSE (0) otherwise. + * (exception: cholmod_divcomplex) + * int32_t a value >= 0 if successful, or -1 otherwise. + * int64_t a value >= 0 if successful, or -1 otherwise. + * double a value >= 0 if successful, or -1 otherwise. + * size_t a value > 0 if successful, or 0 otherwise. + * void * a non-NULL pointer to newly allocated memory if + * successful, or NULL otherwise. + * cholmod_sparse * a non-NULL pointer to a newly allocated matrix + * if successful, or NULL otherwise. + * cholmod_factor * a non-NULL pointer to a newly allocated factor + * if successful, or NULL otherwise. + * cholmod_triplet * a non-NULL pointer to a newly allocated triplet + * matrix if successful, or NULL otherwise. + * cholmod_dense * a non-NULL pointer to a newly allocated triplet + * matrix if successful, or NULL otherwise. + * + * The last parameter to all routines is always a pointer to the CHOLMOD + * Common object. + * + * TRUE and FALSE are not defined here, since they may conflict with the user + * program. A routine that described here returning TRUE or FALSE returns 1 + * or 0, respectively. Any TRUE/FALSE parameter is true if nonzero, false if + * zero. + */ + +/* ========================================================================== */ +/* === CHOLMOD version ====================================================== */ +/* ========================================================================== */ + +/* All versions of CHOLMOD will include the following definitions. + * As an example, to test if the version you are using is 1.3 or later: + * + * if (CHOLMOD_VERSION >= CHOLMOD_VER_CODE (1,3)) ... + * + * This also works during compile-time: + * + * #if CHOLMOD_VERSION >= CHOLMOD_VER_CODE (1,3) + * printf ("This is version 1.3 or later\n") ; + * #else + * printf ("This is version is earlier than 1.3\n") ; + * #endif + */ + +#define CHOLMOD_HAS_VERSION_FUNCTION +#define CHOLMOD_VER_CODE(main,sub) ((main) * 1000 + (sub)) +#define CHOLMOD_VERSION \ + CHOLMOD_VER_CODE(CHOLMOD_MAIN_VERSION,CHOLMOD_SUB_VERSION) + + +/* ========================================================================== */ +/* === CUDA BLAS for the GPU ================================================ */ +/* ========================================================================== */ -// Define buffering parameters for GPU processing +/* Define buffering parameters for GPU processing */ #ifndef SUITESPARSE_GPU_EXTERN_ON #ifdef SUITESPARSE_CUDA #include @@ -218,520 +456,724 @@ int cholmod_l_version (int version [3]) ; #define CHOLMOD_HOST_SUPERNODE_BUFFERS 8 #define CHOLMOD_DEVICE_STREAMS 2 -//------------------------------------------------------------------------------ -// CHOLMOD objects -//------------------------------------------------------------------------------ +/* ========================================================================== */ +/* === CHOLMOD objects ====================================================== */ +/* ========================================================================== */ + +/* Each CHOLMOD object has its own type code. */ -// CHOLMOD object enums #define CHOLMOD_COMMON 0 #define CHOLMOD_SPARSE 1 #define CHOLMOD_FACTOR 2 #define CHOLMOD_DENSE 3 #define CHOLMOD_TRIPLET 4 -//------------------------------------------------------------------------------ -// CHOLMOD Common object -//------------------------------------------------------------------------------ +/* ========================================================================== */ +/* === CHOLMOD Common ======================================================= */ +/* ========================================================================== */ + +/* itype defines the types of integer used: */ +#define CHOLMOD_INT 0 /* all integer arrays are int32_t */ +#define CHOLMOD_INTLONG 1 /* most are int32_t, some are int64_t */ +#define CHOLMOD_LONG 2 /* all integer arrays are int64_t */ + +/* The itype of all parameters for all CHOLMOD routines must match. + * FUTURE WORK: CHOLMOD_INTLONG is not yet supported. + */ + +/* dtype defines what the numerical type is (double or float): */ +#define CHOLMOD_DOUBLE 0 /* all numerical values are double */ +#define CHOLMOD_SINGLE 1 /* all numerical values are float */ + +/* The dtype of all parameters for all CHOLMOD routines must match. + * + * Scalar floating-point values are always passed as double arrays of size 2 + * (for the real and imaginary parts). They are typecast to float as needed. + * FUTURE WORK: the float case is not supported yet. + */ -// itype: integer sizes -// The itype is held in the Common object and must match the method used. -#define CHOLMOD_INT 0 /* int32, for cholmod_* methods (no _l_) */ -#define CHOLMOD_LONG 2 /* int64, for cholmod_l_* methods */ - -// dtype: floating point sizes (double or float) -// The dtype of all parameters for all CHOLMOD routines must match. -// NOTE: CHOLMOD_SINGLE is still under development. -#define CHOLMOD_DOUBLE 0 /* matrix or factorization is double precision */ -#define CHOLMOD_SINGLE 4 /* matrix or factorization is single precision */ - -// xtype: pattern, real, complex, or zomplex -#define CHOLMOD_PATTERN 0 /* no numerical values */ -#define CHOLMOD_REAL 1 /* real (double or single), not complex */ -#define CHOLMOD_COMPLEX 2 /* complex (double or single), interleaved */ -#define CHOLMOD_ZOMPLEX 3 /* complex (double or single), with real and imag */ - /* parts held in different arrays */ - -// xdtype is (xtype + dtype), which combines the two type parameters into -// a single number handling all 8 cases: -// -// (0) CHOLMOD_DOUBLE + CHOLMOD_PATTERN a pattern-only matrix -// (1) CHOLMOD_DOUBLE + CHOLMOD_REAL a double real matrix -// (2) CHOLMOD_DOUBLE + CHOLMOD_COMPLEX a double complex matrix -// (3) CHOLMOD_DOUBLE + CHOLMOD_ZOMPLEX a double zomplex matrix -// (4) CHOLMOD_SINGLE + CHOLMOD_PATTERN a pattern-only matrix -// (5) CHOLMOD_SINGLE + CHOLMOD_REAL a float real matrix -// (6) CHOLMOD_SINGLE + CHOLMOD_COMPLEX a float complex matrix -// (7) CHOLMOD_SINGLE + CHOLMOD_ZOMPLEX a float zomplex matrix - -// max # of ordering methods in Common -#define CHOLMOD_MAXMETHODS 9 - -// Common->status for error handling: 0 is ok, negative is a fatal error, -// and positive is a warning -#define CHOLMOD_OK (0) -#define CHOLMOD_NOT_INSTALLED (-1) /* module not installed */ -#define CHOLMOD_OUT_OF_MEMORY (-2) /* malloc, calloc, or realloc failed */ -#define CHOLMOD_TOO_LARGE (-3) /* integer overflow */ -#define CHOLMOD_INVALID (-4) /* input invalid */ -#define CHOLMOD_GPU_PROBLEM (-5) /* CUDA error */ -#define CHOLMOD_NOT_POSDEF (1) /* matrix not positive definite */ -#define CHOLMOD_DSMALL (2) /* diagonal entry very small */ - -// ordering method -#define CHOLMOD_NATURAL 0 /* no preordering */ -#define CHOLMOD_GIVEN 1 /* user-provided permutation */ -#define CHOLMOD_AMD 2 /* AMD: approximate minimum degree */ -#define CHOLMOD_METIS 3 /* METIS: mested dissection */ -#define CHOLMOD_NESDIS 4 /* CHOLMOD's nested dissection */ -#define CHOLMOD_COLAMD 5 /* AMD for A, COLAMD for AA' or A'A */ -#define CHOLMOD_POSTORDERED 6 /* natural then postordered */ - -// supernodal strategy -#define CHOLMOD_SIMPLICIAL 0 /* always use simplicial method */ -#define CHOLMOD_AUTO 1 /* auto select simplicial vs supernodal */ -#define CHOLMOD_SUPERNODAL 2 /* always use supernoda method */ +/* xtype defines the kind of numerical values used: */ +#define CHOLMOD_PATTERN 0 /* pattern only, no numerical values */ +#define CHOLMOD_REAL 1 /* a real matrix */ +#define CHOLMOD_COMPLEX 2 /* a complex matrix (ANSI C99 compatible) */ +#define CHOLMOD_ZOMPLEX 3 /* a complex matrix (MATLAB compatible) */ +/* The xtype of all parameters for all CHOLMOD routines must match. + * + * CHOLMOD_PATTERN: x and z are ignored. + * CHOLMOD_DOUBLE: x is non-null of size nzmax, z is ignored. + * CHOLMOD_COMPLEX: x is non-null of size 2*nzmax doubles, z is ignored. + * CHOLMOD_ZOMPLEX: x and z are non-null of size nzmax + * + * In the real case, z is ignored. The kth entry in the matrix is x [k]. + * There are two methods for the complex case. In the ANSI C99-compatible + * CHOLMOD_COMPLEX case, the real and imaginary parts of the kth entry + * are in x [2*k] and x [2*k+1], respectively. z is ignored. In the + * MATLAB-compatible CHOLMOD_ZOMPLEX case, the real and imaginary + * parts of the kth entry are in x [k] and z [k]. + * + * Scalar floating-point values are always passed as double arrays of size 2 + * (real and imaginary parts). The imaginary part of a scalar is ignored if + * the routine operates on a real matrix. + * + * These Modules support complex and zomplex matrices, with a few exceptions: + * + * Check all routines + * Cholesky all routines + * Core all except cholmod_aat, add, band, copy + * Demo all routines + * Partition all routines + * Supernodal all routines support any real, complex, or zomplex input. + * There will never be a supernodal zomplex L; a complex + * supernodal L is created if A is zomplex. + * Tcov all routines + * Valgrind all routines + * + * These Modules provide partial support for complex and zomplex matrices: + * + * MATLAB all routines support real and zomplex only, not complex, + * with the exception of ldlupdate, which supports + * real matrices only. This is a minor constraint since + * MATLAB's matrices are all real or zomplex. + * MatrixOps only norm_dense, norm_sparse, and sdmult support complex + * and zomplex + * + * These Modules do not support complex and zomplex matrices at all: + * + * Modify all routines support real matrices only + */ + +/* Definitions for cholmod_common: */ +#define CHOLMOD_MAXMETHODS 9 /* maximum number of different methods that */ + /* cholmod_analyze can try. Must be >= 9. */ + +/* Common->status values. zero means success, negative means a fatal error, + * positive is a warning. */ +#define CHOLMOD_OK 0 /* success */ +#define CHOLMOD_NOT_INSTALLED (-1) /* failure: method not installed */ +#define CHOLMOD_OUT_OF_MEMORY (-2) /* failure: out of memory */ +#define CHOLMOD_TOO_LARGE (-3) /* failure: integer overflow occured */ +#define CHOLMOD_INVALID (-4) /* failure: invalid input */ +#define CHOLMOD_GPU_PROBLEM (-5) /* failure: GPU fatal error */ +#define CHOLMOD_NOT_POSDEF (1) /* warning: matrix not pos. def. */ +#define CHOLMOD_DSMALL (2) /* warning: D for LDL' or diag(L) or */ + /* LL' has tiny absolute value */ + +/* ordering method (also used for L->ordering) */ +#define CHOLMOD_NATURAL 0 /* use natural ordering */ +#define CHOLMOD_GIVEN 1 /* use given permutation */ +#define CHOLMOD_AMD 2 /* use minimum degree (AMD) */ +#define CHOLMOD_METIS 3 /* use METIS' nested dissection */ +#define CHOLMOD_NESDIS 4 /* use CHOLMOD's version of nested dissection:*/ + /* node bisector applied recursively, followed + * by constrained minimum degree (CSYMAMD or + * CCOLAMD) */ +#define CHOLMOD_COLAMD 5 /* use AMD for A, COLAMD for A*A' */ + +/* POSTORDERED is not a method, but a result of natural ordering followed by a + * weighted postorder. It is used for L->ordering, not method [ ].ordering. */ +#define CHOLMOD_POSTORDERED 6 /* natural ordering, postordered. */ + +/* supernodal strategy (for Common->supernodal) */ +#define CHOLMOD_SIMPLICIAL 0 /* always do simplicial */ +#define CHOLMOD_AUTO 1 /* select simpl/super depending on matrix */ +#define CHOLMOD_SUPERNODAL 2 /* always do supernodal */ + +/* make it easy for C++ programs to include CHOLMOD */ #ifdef __cplusplus extern "C" { #endif typedef struct cholmod_common_struct { + /* ---------------------------------------------------------------------- */ + /* parameters for symbolic/numeric factorization and update/downdate */ + /* ---------------------------------------------------------------------- */ + + double dbound ; /* Smallest absolute value of diagonal entries of D + * for LDL' factorization and update/downdate/rowadd/ + * rowdel, or the diagonal of L for an LL' factorization. + * Entries in the range 0 to dbound are replaced with dbound. + * Entries in the range -dbound to 0 are replaced with -dbound. No + * changes are made to the diagonal if dbound <= 0. Default: zero */ + + double grow0 ; /* For a simplicial factorization, L->i and L->x can + * grow if necessary. grow0 is the factor by which + * it grows. For the initial space, L is of size MAX (1,grow0) times + * the required space. If L runs out of space, the new size of L is + * MAX(1.2,grow0) times the new required space. If you do not plan on + * modifying the LDL' factorization in the Modify module, set grow0 to + * zero (or set grow2 to 0, see below). Default: 1.2 */ + + double grow1 ; + + size_t grow2 ; /* For a simplicial factorization, each column j of L + * is initialized with space equal to + * grow1*L->ColCount[j] + grow2. If grow0 < 1, grow1 < 1, or grow2 == 0, + * then the space allocated is exactly equal to L->ColCount[j]. If the + * column j runs out of space, it increases to grow1*need + grow2 in + * size, where need is the total # of nonzeros in that column. If you do + * not plan on modifying the factorization in the Modify module, set + * grow2 to zero. Default: grow1 = 1.2, grow2 = 5. */ + + size_t maxrank ; /* rank of maximum update/downdate. Valid values: + * 2, 4, or 8. A value < 2 is set to 2, and a + * value > 8 is set to 8. It is then rounded up to the next highest + * power of 2, if not already a power of 2. Workspace (Xwork, below) of + * size nrow-by-maxrank double's is allocated for the update/downdate. + * If an update/downdate of rank-k is requested, with k > maxrank, + * it is done in steps of maxrank. Default: 8, which is fastest. + * Memory usage can be reduced by setting maxrank to 2 or 4. + */ + + double supernodal_switch ; /* supernodal vs simplicial factorization */ + int supernodal ; /* If Common->supernodal <= CHOLMOD_SIMPLICIAL + * (0) then cholmod_analyze performs a + * simplicial analysis. If >= CHOLMOD_SUPERNODAL (2), then a supernodal + * analysis is performed. If == CHOLMOD_AUTO (1) and + * flop/nnz(L) < Common->supernodal_switch, then a simplicial analysis + * is done. A supernodal analysis done otherwise. + * Default: CHOLMOD_AUTO. Default supernodal_switch = 40 */ + + int final_asis ; /* If TRUE, then ignore the other final_* parameters + * (except for final_pack). + * The factor is left as-is when done. Default: TRUE.*/ + + int final_super ; /* If TRUE, leave a factor in supernodal form when + * supernodal factorization is finished. If FALSE, + * then convert to a simplicial factor when done. + * Default: TRUE */ + + int final_ll ; /* If TRUE, leave factor in LL' form when done. + * Otherwise, leave in LDL' form. Default: FALSE */ + + int final_pack ; /* If TRUE, pack the columns when done. If TRUE, and + * cholmod_factorize is called with a symbolic L, L is + * allocated with exactly the space required, using L->ColCount. If you + * plan on modifying the factorization, set Common->final_pack to FALSE, + * and each column will be given a little extra slack space for future + * growth in fill-in due to updates. Default: TRUE */ + + int final_monotonic ; /* If TRUE, ensure columns are monotonic when done. + * Default: TRUE */ + + int final_resymbol ;/* if cholmod_factorize performed a supernodal + * factorization, final_resymbol is true, and + * final_super is FALSE (convert a simplicial numeric factorization), + * then numerically zero entries that resulted from relaxed supernodal + * amalgamation are removed. This does not remove entries that are zero + * due to exact numeric cancellation, since doing so would break the + * update/downdate rowadd/rowdel routines. Default: FALSE. */ + + /* supernodal relaxed amalgamation parameters: */ + double zrelax [3] ; + size_t nrelax [3] ; + + /* Let ns be the total number of columns in two adjacent supernodes. + * Let z be the fraction of zero entries in the two supernodes if they + * are merged (z includes zero entries from prior amalgamations). The + * two supernodes are merged if: + * (ns <= nrelax [0]) || (no new zero entries added) || + * (ns <= nrelax [1] && z < zrelax [0]) || + * (ns <= nrelax [2] && z < zrelax [1]) || (z < zrelax [2]) + * + * Default parameters result in the following rule: + * (ns <= 4) || (no new zero entries added) || + * (ns <= 16 && z < 0.8) || (ns <= 48 && z < 0.1) || (z < 0.05) + */ + + int prefer_zomplex ; /* X = cholmod_solve (sys, L, B, Common) computes + * x=A\b or solves a related system. If L and B are + * both real, then X is real. Otherwise, X is returned as + * CHOLMOD_COMPLEX if Common->prefer_zomplex is FALSE, or + * CHOLMOD_ZOMPLEX if Common->prefer_zomplex is TRUE. This parameter + * is needed because there is no supernodal zomplex L. Suppose the + * caller wants all complex matrices to be stored in zomplex form + * (MATLAB, for example). A supernodal L is returned in complex form + * if A is zomplex. B can be real, and thus X = cholmod_solve (L,B) + * should return X as zomplex. This cannot be inferred from the input + * arguments L and B. Default: FALSE, since all data types are + * supported in CHOLMOD_COMPLEX form and since this is the native type + * of LAPACK and the BLAS. Note that the MATLAB/cholmod.c mexFunction + * sets this parameter to TRUE, since MATLAB matrices are in + * CHOLMOD_ZOMPLEX form. + */ + + int prefer_upper ; /* cholmod_analyze and cholmod_factorize work + * fastest when a symmetric matrix is stored in + * upper triangular form when a fill-reducing ordering is used. In + * MATLAB, this corresponds to how x=A\b works. When the matrix is + * ordered as-is, they work fastest when a symmetric matrix is in lower + * triangular form. In MATLAB, R=chol(A) does the opposite. This + * parameter affects only how cholmod_read returns a symmetric matrix. + * If TRUE (the default case), a symmetric matrix is always returned in + * upper-triangular form (A->stype = 1). */ + + int quick_return_if_not_posdef ; /* if TRUE, the supernodal numeric + * factorization will return quickly if + * the matrix is not positive definite. Default: FALSE. */ + + int prefer_binary ; /* cholmod_read_triplet converts a symmetric + * pattern-only matrix into a real matrix. If + * prefer_binary is FALSE, the diagonal entries are set to 1 + the degree + * of the row/column, and off-diagonal entries are set to -1 (resulting + * in a positive definite matrix if the diagonal is zero-free). Most + * symmetric patterns are the pattern a positive definite matrix. If + * this parameter is TRUE, then the matrix is returned with a 1 in each + * entry, instead. Default: FALSE. Added in v1.3. */ + + /* ---------------------------------------------------------------------- */ + /* printing and error handling options */ + /* ---------------------------------------------------------------------- */ + + int print ; /* print level. Default: 3 */ + int precise ; /* if TRUE, print 16 digits. Otherwise print 5 */ + + /* CHOLMOD print_function replaced with SuiteSparse_config print_func */ + + int try_catch ; /* if TRUE, then ignore errors; CHOLMOD is in the middle + * of a try/catch block. No error message is printed + * and the Common->error_handler function is not called. */ + + void (*error_handler) (int status, const char *file, + int line, const char *message) ; + + /* Common->error_handler is the user's error handling routine. If not + * NULL, this routine is called if an error occurs in CHOLMOD. status + * can be CHOLMOD_OK (0), negative for a fatal error, and positive for + * a warning. file is a string containing the name of the source code + * file where the error occured, and line is the line number in that + * file. message is a string describing the error in more detail. */ + + /* ---------------------------------------------------------------------- */ + /* ordering options */ + /* ---------------------------------------------------------------------- */ + + /* The cholmod_analyze routine can try many different orderings and select + * the best one. It can also try one ordering method multiple times, with + * different parameter settings. The default is to use three orderings, + * the user's permutation (if provided), AMD which is the fastest ordering + * and generally gives good fill-in, and METIS. CHOLMOD's nested dissection + * (METIS with a constrained AMD) usually gives a better ordering than METIS + * alone (by about 5% to 10%) but it takes more time. + * + * If you know the method that is best for your matrix, set Common->nmethods + * to 1 and set Common->method [0] to the set of parameters for that method. + * If you set it to 1 and do not provide a permutation, then only AMD will + * be called. + * + * If METIS is not available, the default # of methods tried is 2 (the user + * permutation, if any, and AMD). + * + * To try other methods, set Common->nmethods to the number of methods you + * want to try. The suite of default methods and their parameters is + * described in the cholmod_defaults routine, and summarized here: + * + * Common->method [i]: + * i = 0: user-provided ordering (cholmod_analyze_p only) + * i = 1: AMD (for both A and A*A') + * i = 2: METIS + * i = 3: CHOLMOD's nested dissection (NESDIS), default parameters + * i = 4: natural + * i = 5: NESDIS with nd_small = 20000 + * i = 6: NESDIS with nd_small = 4, no constrained minimum degree + * i = 7: NESDIS with no dense node removal + * i = 8: AMD for A, COLAMD for A*A' + * + * You can modify the suite of methods you wish to try by modifying + * Common.method [...] after calling cholmod_start or cholmod_defaults. + * + * For example, to use AMD, followed by a weighted postordering: + * + * Common->nmethods = 1 ; + * Common->method [0].ordering = CHOLMOD_AMD ; + * Common->postorder = TRUE ; + * + * To use the natural ordering (with no postordering): + * + * Common->nmethods = 1 ; + * Common->method [0].ordering = CHOLMOD_NATURAL ; + * Common->postorder = FALSE ; + * + * If you are going to factorize hundreds or more matrices with the same + * nonzero pattern, you may wish to spend a great deal of time finding a + * good permutation. In this case, try setting Common->nmethods to 9. + * The time spent in cholmod_analysis will be very high, but you need to + * call it only once. + * + * cholmod_analyze sets Common->current to a value between 0 and nmethods-1. + * Each ordering method uses the set of options defined by this parameter. + */ + + int nmethods ; /* The number of ordering methods to try. Default: 0. + * nmethods = 0 is a special case. cholmod_analyze + * will try the user-provided ordering (if given) and AMD. Let fl and + * lnz be the flop count and nonzeros in L from AMD's ordering. Let + * anz be the number of nonzeros in the upper or lower triangular part + * of the symmetric matrix A. If fl/lnz < 500 or lnz/anz < 5, then this + * is a good ordering, and METIS is not attempted. Otherwise, METIS is + * tried. The best ordering found is used. If nmethods > 0, the + * methods used are given in the method[ ] array, below. The first + * three methods in the default suite of orderings is (1) use the given + * permutation (if provided), (2) use AMD, and (3) use METIS. Maximum + * allowed value is CHOLMOD_MAXMETHODS. */ + + int current ; /* The current method being tried. Default: 0. Valid + * range is 0 to nmethods-1. */ + + int selected ; /* The best method found. */ + + /* The suite of ordering methods and parameters: */ - //-------------------------------------------------------------------------- - // primary parameters for factorization and update/downdate - //-------------------------------------------------------------------------- - - double dbound ; // Bounds the diagonal entries of D for LDL' - // factorization and update/downdate/rowadd. Entries outside this - // bound are replaced with dbound. Default: 0. - // dbound is used for double precision factorization only. - // See sbound for single precision factorization. - - double grow0 ; // default: 1.2 - double grow1 ; // default: 1.2 - size_t grow2 ; // default: 5 - // Initial space for simplicial factorization is max(grow0,1) times the - // required space. If space is exhausted, L is grown by - // max(grow0,1.2) times the required space. grow1 and grow2 control - // how each column of L can grow in an update/downdate; if space runs - // out, then grow1*(required space) + grow2 is allocated. - - size_t maxrank ; // maximum rank for update/downdate. Valid values are - // 2, 4, and 8. Default is 8. If a larger update/downdate is done, - // it is done in steps of maxrank. - - double supernodal_switch ; // default: 40 - int supernodal ; // default: CHOLMOD_AUTO. - // Controls supernodal vs simplicial factorization. If - // Common->supernodal is CHOLMOD_SIMPLICIAL, a simplicial factorization - // is always done; if CHOLMOD_SUPERNODAL, a supernodal factorization is - // always done. If CHOLMOD_AUTO, then a simplicial factorization is - // down if flops/nnz(L) < Common->supernodal_switch. - - int final_asis ; // if true, other final_* parameters are ignored, - // except for final_pack and the factors are left as-is when done. - // Default: true. - - int final_super ; // if true, leave factor in supernodal form. - // if false, convert to simplicial. Default: true. - - int final_ll ; // if true, simplicial factors are converted to LL', - // otherwise left as LDL. Default: false. - - int final_pack ; // if true, the factorize are allocated with exactly - // the space required. Set this to false if you expect future - // updates/downdates (giving a little extra space for future growth), - // Default: true. - - int final_monotonic ; // if true, columns are sorted when done, by - // ascending row index. Default: true. - - int final_resymbol ; // if true, a supernodal factorization converted - // to simplicial is reanalyzed, to remove zeros added for relaxed - // amalgamation. Default: false. - - double zrelax [3] ; size_t nrelax [3] ; - // The zrelax and nrelax parameters control relaxed supernodal - // amalgamation, If ns is the # of columns in two adjacent supernodes, - // and z is the fraction of zeros in the two supernodes if merged, then - // the two supernodes are merged if any of the 5 following condition - // are true: - // - // no new zero entries added if the two supernodes are merged - // (ns <= nrelax [0]) - // (ns <= nrelax [1] && z < zrelax [0]) - // (ns <= nrelax [2] && z < zrelax [1]) - // (z < zrelax [2]) - // - // With the defaults, the rules become: - // - // no new zero entries added if the two supernodes are merged - // (ns <= 4) - // (ns <= 16 && z < 0.8) - // (ns <= 48 && z < 0.1) - // (z < 0.05) - - int prefer_zomplex ; // if true, and a complex system is solved, - // X is returned as zomplex (with two arrays, one for the real part - // and one for the imaginary part). If false, then X is returned as - // a single array with interleaved real and imaginary parts. - // Default: false. - - int prefer_upper ; // if true, then a preference is given for holding - // a symmetric matrix by just its upper triangular form. This gives - // the best performance by the CHOLMOD analysis and factorization - // methods. Only used by cholmod_read. Default: true. - - int quick_return_if_not_posdef ; // if true, a supernodal factorization - // returns immediately if it finds the matrix is not positive definite. - // If false, the failed supernode is refactorized, up to but not - // including the failed column (required by MATLAB). - - int prefer_binary ; // if true, cholmod_read_triplet converts a symmetric - // pattern-only matrix to a real matrix with all values set to 1. - // if false, diagonal entries A(k,k) are set to one plus the # of - // entries in row/column k, and off-diagonals are set to -1. - // Default: false. - - int print ; // print level. Default is 3. - int precise ; // if true, print 16 digits, otherwise 5. Default: false. - - int try_catch ; // if true, ignore errors (CHOLMOD is assumed to be inside - // a try/catch block. No error messages are printed and the - // error_handler function is not called. Default: false. - - void (*error_handler) (int status, const char *file, int line, - const char *message) ; - // User error handling routine; default is NULL. - // This function is called if an error occurs, with parameters: - // status: the Common->status result. - // file: filename where the error occurred. - // line: line number where the error occurred. - // message: a string that describes the error. - - //-------------------------------------------------------------------------- - // ordering options - //-------------------------------------------------------------------------- - - // CHOLMOD can try many ordering options and then pick the best result it - // finds. The default is to use one or two orderings: the user's - // permutation (if given), and AMD. - - // Common->nmethods is the number of methods to try. If the - // Common->method array is left unmodified, the methods are: - - // (0) given (skipped if no user permutation) - // (1) amd - // (2) metis - // (3) nesdis with defaults (CHOLMOD's nested dissection, based on METIS) - // (4) natural - // (5) nesdis: stop at subgraphs of 20000 nodes - // (6) nesdis: stop at subgraphs of 4 nodes, do not use CAMD - // (7) nesdis: no pruning on of dense rows/cols - // (8) colamd - - // To use all 9 of the above methods, set Common->nmethods to 9. The - // analysis will take a long time, but that might be worth it if the - // ordering will be reused many many times. - - // Common->nmethods and Common->methods can be revised to use a different - // set of orderings. For example, to use just a single method - // (AMD with a weighted postordering): - // - // Common->nmethods = 1 ; - // Common->method [0].ordering = CHOLMOD_AMD ; - // Common->postorder = TRUE ; - // - // - - int nmethods ; // Number of methods to try, default is 0. - // The value of 0 is a special case, and tells CHOLMOD to use the user - // permutation (if not NULL) and then AMD. Next, if fl is lnz are the - // flop counts and number of nonzeros in L as found by AMD, then the - // this ordering is used if fl/lnz < 500 or lnz/anz < 5, where anz is - // the number of entries in A. If this condition fails, METIS is tried - // as well. - // - // Otherwise, if Common->nmethods > 0, then the methods defined by - // Common->method [0 ... Common->nmethods-1] are used. - - int current ; // The current method being tried in the analysis. - int selected ; // The selected method: Common->method [Common->selected] - - // The Common->method parameter is an array of structs that defines up - // to 9 methods: struct cholmod_method_struct { + /* statistics for this method */ + double lnz ; /* nnz(L) excl. zeros from supernodal amalgamation, + * for a "pure" L */ + + double fl ; /* flop count for a "pure", real simplicial LL' + * factorization, with no extra work due to + * amalgamation. Subtract n to get the LDL' flop count. Multiply + * by about 4 if the matrix is complex or zomplex. */ + + /* ordering method parameters */ + double prune_dense ;/* dense row/col control for AMD, SYMAMD, CSYMAMD, + * and NESDIS (cholmod_nested_dissection). For a + * symmetric n-by-n matrix, rows/columns with more than + * MAX (16, prune_dense * sqrt (n)) entries are removed prior to + * ordering. They appear at the end of the re-ordered matrix. + * + * If prune_dense < 0, only completely dense rows/cols are removed. + * + * This paramater is also the dense column control for COLAMD and + * CCOLAMD. For an m-by-n matrix, columns with more than + * MAX (16, prune_dense * sqrt (MIN (m,n))) entries are removed prior + * to ordering. They appear at the end of the re-ordered matrix. + * CHOLMOD factorizes A*A', so it calls COLAMD and CCOLAMD with A', + * not A. Thus, this parameter affects the dense *row* control for + * CHOLMOD's matrix, and the dense *column* control for COLAMD and + * CCOLAMD. + * + * Removing dense rows and columns improves the run-time of the + * ordering methods. It has some impact on ordering quality + * (usually minimal, sometimes good, sometimes bad). + * + * Default: 10. */ + + double prune_dense2 ;/* dense row control for COLAMD and CCOLAMD. + * Rows with more than MAX (16, dense2 * sqrt (n)) + * for an m-by-n matrix are removed prior to ordering. CHOLMOD's + * matrix is transposed before ordering it with COLAMD or CCOLAMD, + * so this controls the dense *columns* of CHOLMOD's matrix, and + * the dense *rows* of COLAMD's or CCOLAMD's matrix. + * + * If prune_dense2 < 0, only completely dense rows/cols are removed. + * + * Default: -1. Note that this is not the default for COLAMD and + * CCOLAMD. -1 is best for Cholesky. 10 is best for LU. */ + + double nd_oksep ; /* in NESDIS, when a node separator is computed, it + * discarded if nsep >= nd_oksep*n, where nsep is + * the number of nodes in the separator, and n is the size of the + * graph being cut. Valid range is 0 to 1. If 1 or greater, the + * separator is discarded if it consists of the entire graph. + * Default: 1 */ + + double other_1 [4] ; /* future expansion */ + + size_t nd_small ; /* do not partition graphs with fewer nodes than + * nd_small, in NESDIS. Default: 200 (same as + * METIS) */ + + size_t other_2 [4] ; /* future expansion */ + + int aggressive ; /* Aggresive absorption in AMD, COLAMD, SYMAMD, + * CCOLAMD, and CSYMAMD. Default: TRUE */ + + int order_for_lu ; /* CCOLAMD can be optimized to produce an ordering + * for LU or Cholesky factorization. CHOLMOD only + * performs a Cholesky factorization. However, you may wish to use + * CHOLMOD as an interface for CCOLAMD but use it for your own LU + * factorization. In this case, order_for_lu should be set to FALSE. + * When factorizing in CHOLMOD itself, you should *** NEVER *** set + * this parameter FALSE. Default: TRUE. */ + + int nd_compress ; /* If TRUE, compress the graph and subgraphs before + * partitioning them in NESDIS. Default: TRUE */ + + int nd_camd ; /* If 1, follow the nested dissection ordering + * with a constrained minimum degree ordering that + * respects the partitioning just found (using CAMD). If 2, use + * CSYMAMD instead. If you set nd_small very small, you may not need + * this ordering, and can save time by setting it to zero (no + * constrained minimum degree ordering). Default: 1. */ + + int nd_components ; /* The nested dissection ordering finds a node + * separator that splits the graph into two parts, + * which may be unconnected. If nd_components is TRUE, each of + * these connected components is split independently. If FALSE, + * each part is split as a whole, even if it consists of more than + * one connected component. Default: FALSE */ + + /* fill-reducing ordering to use */ + int ordering ; + + size_t other_3 [4] ; /* future expansion */ + + } method [CHOLMOD_MAXMETHODS + 1] ; + + int postorder ; /* If TRUE, cholmod_analyze follows the ordering with a + * weighted postorder of the elimination tree. Improves + * supernode amalgamation. Does not affect fundamental nnz(L) and + * flop count. Default: TRUE. */ + + int default_nesdis ; /* Default: FALSE. If FALSE, then the default + * ordering strategy (when Common->nmethods == 0) + * is to try the given ordering (if present), AMD, and then METIS if AMD + * reports high fill-in. If Common->default_nesdis is TRUE then NESDIS + * is used instead in the default strategy. */ + + /* ---------------------------------------------------------------------- */ + /* memory management, complex divide, and hypot function pointers moved */ + /* ---------------------------------------------------------------------- */ + + /* Function pointers moved from here (in CHOLMOD 2.2.0) to + SuiteSparse_config.[ch]. See CHOLMOD/Include/cholmod_back.h + for a set of macros that can be #include'd or copied into your + application to define these function pointers on any version of CHOLMOD. + */ + + /* ---------------------------------------------------------------------- */ + /* METIS workarounds */ + /* ---------------------------------------------------------------------- */ + + /* These workarounds were put into place for METIS 4.0.1. They are safe + to use with METIS 5.1.0, but they might not longer be necessary. */ + + double metis_memory ; /* This is a parameter for CHOLMOD's interface to + * METIS, not a parameter to METIS itself. METIS + * uses an amount of memory that is difficult to estimate precisely + * beforehand. If it runs out of memory, it terminates your program. + * All routines in CHOLMOD except for CHOLMOD's interface to METIS + * return an error status and safely return to your program if they run + * out of memory. To mitigate this problem, the CHOLMOD interface + * can allocate a single block of memory equal in size to an empirical + * upper bound of METIS's memory usage times the Common->metis_memory + * parameter, and then immediately free it. It then calls METIS. If + * this pre-allocation fails, it is possible that METIS will fail as + * well, and so CHOLMOD returns with an out-of-memory condition without + * calling METIS. + * + * METIS_NodeND (used in the CHOLMOD_METIS ordering option) with its + * default parameter settings typically uses about (4*nz+40n+4096) + * times sizeof(int) memory, where nz is equal to the number of entries + * in A for the symmetric case or AA' if an unsymmetric matrix is + * being ordered (where nz includes both the upper and lower parts + * of A or AA'). The observed "upper bound" (with 2 exceptions), + * measured in an instrumented copy of METIS 4.0.1 on thousands of + * matrices, is (10*nz+50*n+4096) * sizeof(int). Two large matrices + * exceeded this bound, one by almost a factor of 2 (Gupta/gupta2). + * + * If your program is terminated by METIS, try setting metis_memory to + * 2.0, or even higher if needed. By default, CHOLMOD assumes that METIS + * does not have this problem (so that CHOLMOD will work correctly when + * this issue is fixed in METIS). Thus, the default value is zero. + * This work-around is not guaranteed anyway. + * + * If a matrix exceeds this predicted memory usage, AMD is attempted + * instead. It, too, may run out of memory, but if it does so it will + * not terminate your program. + */ + + double metis_dswitch ; /* METIS_NodeND in METIS 4.0.1 gives a seg */ + size_t metis_nswitch ; /* fault with one matrix of order n = 3005 and + * nz = 6,036,025. This is a very dense graph. + * The workaround is to use AMD instead of METIS for matrices of dimension + * greater than Common->metis_nswitch (default 3000) or more and with + * density of Common->metis_dswitch (default 0.66) or more. + * cholmod_nested_dissection has no problems with the same matrix, even + * though it uses METIS_ComputeVertexSeparator on this matrix. If this + * seg fault does not affect you, set metis_nswitch to zero or less, + * and CHOLMOD will not switch to AMD based just on the density of the + * matrix (it will still switch to AMD if the metis_memory parameter + * causes the switch). + */ + + /* ---------------------------------------------------------------------- */ + /* workspace */ + /* ---------------------------------------------------------------------- */ + + /* CHOLMOD has several routines that take less time than the size of + * workspace they require. Allocating and initializing the workspace would + * dominate the run time, unless workspace is allocated and initialized + * just once. CHOLMOD allocates this space when needed, and holds it here + * between calls to CHOLMOD. cholmod_start sets these pointers to NULL + * (which is why it must be the first routine called in CHOLMOD). + * cholmod_finish frees the workspace (which is why it must be the last + * call to CHOLMOD). + */ + + size_t nrow ; /* size of Flag and Head */ + int64_t mark ; /* mark value for Flag array */ + size_t iworksize ; /* size of Iwork. Upper bound: 6*nrow+ncol */ + size_t xworksize ; /* size of Xwork, in bytes. + * maxrank*nrow*sizeof(double) for update/downdate. + * 2*nrow*sizeof(double) otherwise */ + + /* initialized workspace: contents needed between calls to CHOLMOD */ + void *Flag ; /* size nrow, an integer array. Kept cleared between + * calls to cholmod rouines (Flag [i] < mark) */ + + void *Head ; /* size nrow+1, an integer array. Kept cleared between + * calls to cholmod routines (Head [i] = EMPTY) */ + + void *Xwork ; /* a double array. Its size varies. It is nrow for + * most routines (cholmod_rowfac, cholmod_add, + * cholmod_aat, cholmod_norm, cholmod_ssmult) for the real case, twice + * that when the input matrices are complex or zomplex. It is of size + * 2*nrow for cholmod_rowadd and cholmod_rowdel. For cholmod_updown, + * its size is maxrank*nrow where maxrank is 2, 4, or 8. Kept cleared + * between calls to cholmod (set to zero). */ + + /* uninitialized workspace, contents not needed between calls to CHOLMOD */ + void *Iwork ; /* size iworksize, 2*nrow+ncol for most routines, + * up to 6*nrow+ncol for cholmod_analyze. */ + + int itype ; /* If CHOLMOD_LONG, Flag, Head, and Iwork are + * int64_t. Otherwise all three are int. */ + + int dtype ; /* double or float */ + + /* Common->itype and Common->dtype are used to define the types of all + * sparse matrices, triplet matrices, dense matrices, and factors + * created using this Common struct. The itypes and dtypes of all + * parameters to all CHOLMOD routines must match. */ + + int no_workspace_reallocate ; /* this is an internal flag, used as a + * precaution by cholmod_analyze. It is normally false. If true, + * cholmod_allocate_work is not allowed to reallocate any workspace; + * they must use the existing workspace in Common (Iwork, Flag, Head, + * and Xwork). Added for CHOLMOD v1.1 */ + + /* ---------------------------------------------------------------------- */ + /* statistics */ + /* ---------------------------------------------------------------------- */ + + /* fl and lnz are set only in cholmod_analyze and cholmod_rowcolcounts, + * in the Cholesky modudle. modfl is set only in the Modify module. */ + + int status ; /* error code */ + double fl ; /* LL' flop count from most recent analysis */ + double lnz ; /* fundamental nz in L */ + double anz ; /* nonzeros in tril(A) if A is symmetric/lower, + * triu(A) if symmetric/upper, or tril(A*A') if + * unsymmetric, in last call to cholmod_analyze. */ + double modfl ; /* flop count from most recent update/downdate/ + * rowadd/rowdel (excluding flops to modify the + * solution to Lx=b, if computed) */ + size_t malloc_count ; /* # of objects malloc'ed minus the # free'd*/ + size_t memory_usage ; /* peak memory usage in bytes */ + size_t memory_inuse ; /* current memory usage in bytes */ + + double nrealloc_col ; /* # of column reallocations */ + double nrealloc_factor ;/* # of factor reallocations due to col. reallocs */ + double ndbounds_hit ; /* # of times diagonal modified by dbound */ + + double rowfacfl ; /* # of flops in last call to cholmod_rowfac */ + double aatfl ; /* # of flops to compute A(:,f)*A(:,f)' */ + + int called_nd ; /* TRUE if the last call to + * cholmod_analyze called NESDIS or METIS. */ + int blas_ok ; /* FALSE if SUITESPARSE_BLAS_INT overflow; + TRUE otherwise */ + + /* ---------------------------------------------------------------------- */ + /* SuiteSparseQR control parameters: */ + /* ---------------------------------------------------------------------- */ + + double SPQR_grain ; /* task size is >= max (total flops / grain) */ + double SPQR_small ; /* task size is >= small */ + int SPQR_shrink ; /* controls stack realloc method */ + int SPQR_nthreads ; /* number of TBB threads, 0 = auto */ + + /* ---------------------------------------------------------------------- */ + /* SuiteSparseQR statistics */ + /* ---------------------------------------------------------------------- */ + + /* was other1 [0:3] */ + double SPQR_flopcount ; /* flop count for SPQR */ + double SPQR_analyze_time ; /* analysis time in seconds for SPQR */ + double SPQR_factorize_time ; /* factorize time in seconds for SPQR */ + double SPQR_solve_time ; /* backsolve time in seconds */ + + /* was SPQR_xstat [0:3] */ + double SPQR_flopcount_bound ; /* upper bound on flop count */ + double SPQR_tol_used ; /* tolerance used */ + double SPQR_norm_E_fro ; /* Frobenius norm of dropped entries */ + + /* was SPQR_istat [0:9] */ + int64_t SPQR_istat [10] ; + + /* ---------------------------------------------------------------------- */ + /* GPU configuration and statistics */ + /* ---------------------------------------------------------------------- */ + + /* useGPU: 1 if gpu-acceleration is requested */ + /* 0 if gpu-acceleration is prohibited */ + /* -1 if gpu-acceleration is undefined in which case the */ + /* environment CHOLMOD_USE_GPU will be queried and used. */ + /* useGPU=-1 is only used by CHOLMOD and treated as 0 by SPQR */ + int useGPU; + + /* for CHOLMOD: */ + size_t maxGpuMemBytes; + double maxGpuMemFraction; + + /* for SPQR: */ + size_t gpuMemorySize; /* Amount of memory in bytes on the GPU */ + double gpuKernelTime; /* Time taken by GPU kernels */ + int64_t gpuFlops; /* Number of flops performed by the GPU */ + int gpuNumKernelLaunches; /* Number of GPU kernel launches */ + + /* If not using the GPU, these items are not used, but they should be + present so that the CHOLMOD Common has the same size whether the GPU + is used or not. This way, all packages will agree on the size of + the CHOLMOD Common, regardless of whether or not they are compiled + with the GPU libraries or not */ - //---------------------------------------------------------------------- - // statistics from the ordering - //---------------------------------------------------------------------- - - double lnz ; // number of nonzeros in L - double fl ; // Cholesky flop count for this ordering (each - // multiply and each add counted once (doesn't count complex - // flops). - - //---------------------------------------------------------------------- - // ordering parameters: - //---------------------------------------------------------------------- - - double prune_dense ; // dense row/col control. Default: 10. - // Rows/cols with more than max (prune_dense*sqrt(n),16) are - // removed prior to orderingm and placed last. If negative, - // only completely dense rows/cols are removed. Removing these - // rows/cols with many entries can speed up the ordering, but - // removing too many can reduce the ordering quality. - // - // For AMD, SYMAMD, and CSYMAMD, this is the only dense row/col - // parameter. For COLAMD and CCOLAMD, this parameter controls - // how dense columns are handled. - - double prune_dense2 ; // dense row control for COLAMD and CCOLAMD. - // Default -1. When computing the Cholesky factorization of AA' - // rows with more than max(prune_dense2*sqrt(n),16) entries - // are removed prior to ordering. If negative, only completely - // dense rows are removed. - - double nd_oksep ; // for CHOLMOD's nesdis method. Default 1. - // A node separator with nsep nodes is discarded if - // nsep >= nd_oksep*n. - - double other_1 [4] ; // unused, for future expansion - - size_t nd_small ; // for CHOLMOD's nesdis method. Default 200. - // Subgraphs with fewer than nd_small nodes are not partitioned. - - double other_2 [4] ; // unused, for future expansion - - int aggressive ; // if true, AMD, COLAMD, SYMAMD, CCOLAMD, and - // CSYMAMD perform aggresive absorption. Default: true - - int order_for_lu ; // Default: false. If the CHOLMOD analysis/ - // ordering methods are used as an ordering method for an LU - // factorization, then set this to true. For use in a Cholesky - // factorization by CHOLMOD itself, never set this to true. - - int nd_compress ; // if true, then the graph and subgraphs are - // compressed before partitioning them in CHOLMOD's nesdis - // method. Default: true. - - int nd_camd ; // if 1, then CHOLMOD's nesdis is followed by - // CAMD. If 2: followed by CSYMAMD. If nd_small is very small, - // then use 0, which skips CAMD or CSYMAMD. Default: 1. - - int nd_components ; // CHOLMOD's nesdis can partition a graph and then - // find that the subgraphs are unconnected. If true, each of these - // components is partitioned separately. If false, the whole - // subgraph is partitioned. Default: false. - - int ordering ; // ordering method to use - - size_t other_3 [4] ; // unused, for future expansion - - } - method [CHOLMOD_MAXMETHODS + 1] ; - - int postorder ; // if true, CHOLMOD performs a weighted postordering - // after its fill-reducing ordering, which improves supernodal - // amalgamation. Has no effect on flop count or nnz(L). - // Default: true. - - int default_nesdis ; // If false, then the default ordering strategy - // when Common->nmethods is zero is to try the user's permutation - // if given, then AMD, and then METIS if the AMD ordering results in - // a lot of fill-in. If true, then nesdis is used instead of METIS. - // Default: false. - - //-------------------------------------------------------------------------- - // METIS workarounds - //-------------------------------------------------------------------------- - - // These workarounds were put into place for METIS 4.0.1. They are safe - // to use with METIS 5.1.0, but they might not longer be necessary. - - double metis_memory ; // default: 0. If METIS terminates your - // program when it runs out of memory, try 2, or higher. - double metis_dswitch ; // default: 0.66 - size_t metis_nswitch ; // default: 3000 - // If a matrix has n > metis_nswitch and a density (nnz(A)/n^2) > - // metis_dswitch, then METIS is not used. - - //-------------------------------------------------------------------------- - // workspace - //-------------------------------------------------------------------------- - - // This workspace is kept in the CHOLMOD Common object. cholmod_start - // sets these arrays to NULL, and cholmod_finish frees them. - - size_t nrow ; // Flag has size nrow, Head has size nrow+1 - int64_t mark ; // Flag is cleared if Flag [0..nrow-1] < mark. - size_t iworksize ; // size of Iwork, in Ints (int32 or int64). - // This is at most 6*nrow + ncol. - size_t xworkbytes ; // size of Xwork, in bytes. for update/downdate: - // maxrank*nrow*sizeof(double or float), 2*nrow*sizeof(double or float) - // otherwise. NOTE: in CHOLMOD v4 and earlier, xworkwise was in terms - // of # of doubles, not # of bytes. - - void *Flag ; // size nrow. If this is "cleared" then - // Flag [i] < mark for all i = 0:nrow-1. Flag is kept cleared between - // calls to CHOLMOD. - - void *Head ; // size nrow+1. If Head [i] = EMPTY (-1) then that - // entry is "cleared". Head is kept cleared between calls to CHOLMOD. - - void *Xwork ; // a double or float array. It has size nrow for most - // routines, or 2*nrow if complex matrices are being handled. - // It has size 2*nrow for cholmod_rowadd/rowdel, and maxrank*nrow for - // cholmod_updown, where maxrank is 2, 4, or 8. Xwork is kept all - // zero between calls to CHOLMOD. - - void *Iwork ; // size iworksize integers (int32's or int64's). - // Uninitialized integer workspace, of size at most 6*nrow+ncol. - - int itype ; // cholmod_start (for int32's) sets this to CHOLMOD_INT, - // and cholmod_l_start sets this to CHOLMOD_LONG. It defines the - // integer sizes for th Flag, Head, and Iwork arrays, and also - // defines the integers for all objects created by CHOLMOD. - // The itype of the Common object must match the function name - // and all objects passed to it. - - int other_5 ; // unused: for future expansion - - int no_workspace_reallocate ; // an internal flag, usually false. - // This is set true to disable any reallocation of the workspace - // in the Common object. - - //-------------------------------------------------------------------------- - // statistics - //-------------------------------------------------------------------------- - - int status ; // status code (0: ok, negative: error, pos: warning - double fl ; // flop count from last analysis - double lnz ; // nnz(L) from last analysis - double anz ; // in last analysis: nnz(tril(A)) or nnz(triu(A)) if A - // symmetric, or tril(A*A') if A is unsymmetric. - double modfl ; // flop count from last update/downdate/rowadd/rowdel, - // not included the flops to revise the solution to Lx=b, - // if that was performed. - - size_t malloc_count ; // # of malloc'd objects not yet freed - size_t memory_usage ; // peak memory usage in bytes - size_t memory_inuse ; // current memory usage in bytes - - double nrealloc_col ; // # of column reallocations - double nrealloc_factor ;// # of factor reallocations due to col. reallocs - double ndbounds_hit ; // # of times diagonal modified by dbound - - double rowfacfl ; // flop count of cholmod_rowfac - double aatfl ; // flop count to compute A(:,f)*A(:,f)' - - int called_nd ; // true if last analysis used nesdis or METIS. - int blas_ok ; // true if no integer overflow has occured when trying to - // call the BLAS. The typical BLAS library uses 32-bit integers for - // its input parameters, even on a 64-bit platform. CHOLMOD uses int64 - // in its cholmod_l_* methods, and these must be typecast to the BLAS - // integer. If integer overflow occurs, this is set false. - - //-------------------------------------------------------------------------- - // SuiteSparseQR control parameters and statistics - //-------------------------------------------------------------------------- - - // SPQR uses the CHOLMOD Common object for its control and statistics. - // These parameters are not used by CHOLMOD itself. - - // control parameters: - double SPQR_grain ; // task size is >= max (total flops / grain) - double SPQR_small ; // task size is >= small - int SPQR_shrink ; // controls stack realloc method - int SPQR_nthreads ; // number of TBB threads, 0 = auto - - // statistics: - double SPQR_flopcount ; // flop count for SPQR - double SPQR_analyze_time ; // analysis time in seconds for SPQR - double SPQR_factorize_time ; // factorize time in seconds for SPQR - double SPQR_solve_time ; // backsolve time in seconds - double SPQR_flopcount_bound ; // upper bound on flop count - double SPQR_tol_used ; // tolerance used - double SPQR_norm_E_fro ; // Frobenius norm of dropped entries - - //-------------------------------------------------------------------------- - // Revised for CHOLMOD v5.0 - //-------------------------------------------------------------------------- - - // was size 10 in CHOLMOD v4.2; reduced to 8 in CHOLMOD v5: - int64_t SPQR_istat [8] ; // other statistics - - //-------------------------------------------------------------------------- - // Added for CHOLMOD v5.0 - //-------------------------------------------------------------------------- - - // These terms have been added to the CHOLMOD Common struct for v5.0, and - // on most systems they will total 16 bytes. The preceding term, - // SPQR_istat, was reduced by 16 bytes, since those last 2 entries were - // unused in CHOLMOD v4.2. As a result, the Common struct in v5.0 has the - // same size as v4.0, and all entries would normally be in the same offset, - // as well. This mitigates any changes between v4.0 and v5.0, and may make - // it easier to upgrade from v4 to v5. - - double nsbounds_hit ; // # of times diagonal modified by sbound. This - // ought to be int64_t, but ndbounds_hit was double in v4 - // (see above), so nsbounds_hit is made the same type for - // consistency. - float sbound ; // Same as dbound, but for single precision factorization. - float other_6 ; // for future expansion - - //-------------------------------------------------------------------------- - // GPU configuration and statistics - //-------------------------------------------------------------------------- - - int useGPU ; // 1 if GPU is requested for CHOLMOD - // 0 if GPU is not requested for CHOLMOD - // -1 if the use of the GPU is in CHOLMOD controled by the - // CHOLMOD_USE_GPU environment variable. - - size_t maxGpuMemBytes ; // GPU control for CHOLMOD - double maxGpuMemFraction ; // GPU control for CHOLMOD - - // for SPQR: - size_t gpuMemorySize ; // Amount of memory in bytes on the GPU - double gpuKernelTime ; // Time taken by GPU kernels - int64_t gpuFlops ; // Number of flops performed by the GPU - int gpuNumKernelLaunches ; // Number of GPU kernel launches - - #ifdef SUITESPARSE_CUDA - // these three types are pointers defined by CUDA: - #define CHOLMOD_CUBLAS_HANDLE cublasHandle_t - #define CHOLMOD_CUDASTREAM cudaStream_t - #define CHOLMOD_CUDAEVENT cudaEvent_t - #else - // they are (void *) if CUDA is not in use: - #define CHOLMOD_CUBLAS_HANDLE void * - #define CHOLMOD_CUDASTREAM void * - #define CHOLMOD_CUDAEVENT void * - #endif +#ifdef SUITESPARSE_CUDA + /* in CUDA, these three types are pointers */ + #define CHOLMOD_CUBLAS_HANDLE cublasHandle_t + #define CHOLMOD_CUDASTREAM cudaStream_t + #define CHOLMOD_CUDAEVENT cudaEvent_t +#else + /* ... so make them void * pointers if the GPU is not being used */ + #define CHOLMOD_CUBLAS_HANDLE void * + #define CHOLMOD_CUDASTREAM void * + #define CHOLMOD_CUDAEVENT void * +#endif CHOLMOD_CUBLAS_HANDLE cublasHandle ; - // a set of streams for general use - CHOLMOD_CUDASTREAM gpuStream [CHOLMOD_HOST_SUPERNODE_BUFFERS] ; + /* a set of streams for general use */ + CHOLMOD_CUDASTREAM gpuStream[CHOLMOD_HOST_SUPERNODE_BUFFERS]; + + CHOLMOD_CUDAEVENT cublasEventPotrf [3] ; + CHOLMOD_CUDAEVENT updateCKernelsComplete; + CHOLMOD_CUDAEVENT updateCBuffersFree[CHOLMOD_HOST_SUPERNODE_BUFFERS]; - CHOLMOD_CUDAEVENT cublasEventPotrf [3] ; - CHOLMOD_CUDAEVENT updateCKernelsComplete ; - CHOLMOD_CUDAEVENT updateCBuffersFree [CHOLMOD_HOST_SUPERNODE_BUFFERS] ; + void *dev_mempool; /* pointer to single allocation of device memory */ + size_t dev_mempool_size; - void *dev_mempool ; // pointer to single allocation of device memory - size_t dev_mempool_size ; + void *host_pinned_mempool; /* pointer to single allocation of pinned mem */ + size_t host_pinned_mempool_size; - void *host_pinned_mempool ; // pointer to single alloc of pinned mem - size_t host_pinned_mempool_size ; + size_t devBuffSize; + int ibuffer; - size_t devBuffSize ; - int ibuffer ; - double syrkStart ; // time syrk started + double syrkStart ; /* time syrk started */ - // run times of the different parts of CHOLMOD (GPU and CPU): + /* run times of the different parts of CHOLMOD (GPU and CPU) */ double cholmod_cpu_gemm_time ; double cholmod_cpu_syrk_time ; double cholmod_cpu_trsm_time ; @@ -743,7 +1185,7 @@ typedef struct cholmod_common_struct double cholmod_assemble_time ; double cholmod_assemble_time2 ; - // number of times the BLAS are called on the CPU and the GPU: + /* number of times the BLAS are called on the CPU and the GPU */ size_t cholmod_cpu_gemm_calls ; size_t cholmod_cpu_syrk_calls ; size_t cholmod_cpu_trsm_calls ; @@ -753,16 +1195,15 @@ typedef struct cholmod_common_struct size_t cholmod_gpu_trsm_calls ; size_t cholmod_gpu_potrf_calls ; - double chunk ; // chunksize for computing # of OpenMP threads to use. - // Given nwork work to do, # of threads is - // max (1, min (floor (work / chunk), nthreads_max)) - - int nthreads_max ; // max # of OpenMP threads to use in CHOLMOD. - // Defaults to SUITESPARSE_OPENMP_MAX_THREADS. + double chunk ; // chunksize for computing # of threads to use. + // Given nwork work to do, # of threads is + // max (1, min (floor (work / chunk), nthreads_max)) + int nthreads_max ; // max # of threads to use in CHOLMOD. Defaults to + // SUITESPARSE_OPENMP_MAX_THREADS. } cholmod_common ; -// size_t BLAS statistcs in Common: +/* size_t BLAS statistcs in Common: */ #define CHOLMOD_CPU_GEMM_CALLS cholmod_cpu_gemm_calls #define CHOLMOD_CPU_SYRK_CALLS cholmod_cpu_syrk_calls #define CHOLMOD_CPU_TRSM_CALLS cholmod_cpu_trsm_calls @@ -772,7 +1213,7 @@ typedef struct cholmod_common_struct #define CHOLMOD_GPU_TRSM_CALLS cholmod_gpu_trsm_calls #define CHOLMOD_GPU_POTRF_CALLS cholmod_gpu_potrf_calls -// double BLAS statistics in Common: +/* double BLAS statistics in Common: */ #define CHOLMOD_CPU_GEMM_TIME cholmod_cpu_gemm_time #define CHOLMOD_CPU_SYRK_TIME cholmod_cpu_syrk_time #define CHOLMOD_CPU_TRSM_TIME cholmod_cpu_trsm_time @@ -784,1138 +1225,1422 @@ typedef struct cholmod_common_struct #define CHOLMOD_ASSEMBLE_TIME cholmod_assemble_time #define CHOLMOD_ASSEMBLE_TIME2 cholmod_assemble_time2 -// for supernodal analysis: +/* for supernodal analysis */ #define CHOLMOD_ANALYZE_FOR_SPQR 0 #define CHOLMOD_ANALYZE_FOR_CHOLESKY 1 #define CHOLMOD_ANALYZE_FOR_SPQRGPU 2 -//------------------------------------------------------------------------------ -// cholmod_start: first call to CHOLMOD -//------------------------------------------------------------------------------ +/* -------------------------------------------------------------------------- */ +/* cholmod_start: first call to CHOLMOD */ +/* -------------------------------------------------------------------------- */ + +int cholmod_start +( + cholmod_common *Common +) ; -int cholmod_start (cholmod_common *Common) ; int cholmod_l_start (cholmod_common *) ; -//------------------------------------------------------------------------------ -// cholmod_finish: last call to CHOLMOD -//------------------------------------------------------------------------------ +/* -------------------------------------------------------------------------- */ +/* cholmod_finish: last call to CHOLMOD */ +/* -------------------------------------------------------------------------- */ + +int cholmod_finish +( + cholmod_common *Common +) ; -int cholmod_finish (cholmod_common *Common) ; int cholmod_l_finish (cholmod_common *) ; -//------------------------------------------------------------------------------ -// cholmod_defaults: set default parameters -//------------------------------------------------------------------------------ +/* -------------------------------------------------------------------------- */ +/* cholmod_defaults: restore default parameters */ +/* -------------------------------------------------------------------------- */ + +int cholmod_defaults +( + cholmod_common *Common +) ; -int cholmod_defaults (cholmod_common *Common) ; int cholmod_l_defaults (cholmod_common *) ; -//------------------------------------------------------------------------------ -// cholmod_maxrank: return valid maximum rank for update/downdate -//------------------------------------------------------------------------------ +/* -------------------------------------------------------------------------- */ +/* cholmod_maxrank: return valid maximum rank for update/downdate */ +/* -------------------------------------------------------------------------- */ -size_t cholmod_maxrank // return validated Common->maxrank +size_t cholmod_maxrank /* returns validated value of Common->maxrank */ ( - size_t n, // # of rows of L and A + /* ---- input ---- */ + size_t n, /* A and L will have n rows */ + /* --------------- */ cholmod_common *Common ) ; -size_t cholmod_l_maxrank (size_t, cholmod_common *) ; -//------------------------------------------------------------------------------ -// cholmod_allocate_work: allocate workspace in Common -//------------------------------------------------------------------------------ +size_t cholmod_l_maxrank (size_t, cholmod_common *) ; -// This method always allocates Xwork as double, for backward compatibility -// with CHOLMOD v4 and earlier. See cholmod_alloc_work for CHOLMOD v5. +/* -------------------------------------------------------------------------- */ +/* cholmod_allocate_work: allocate workspace in Common */ +/* -------------------------------------------------------------------------- */ int cholmod_allocate_work ( - size_t nrow, // size of Common->Flag (nrow int32's) - // and Common->Head (nrow+1 int32's) - size_t iworksize, // size of Common->Iwork (# of int32's) - size_t xworksize, // size of Common->Xwork (# of double's) + /* ---- input ---- */ + size_t nrow, /* size: Common->Flag (nrow), Common->Head (nrow+1) */ + size_t iworksize, /* size of Common->Iwork */ + size_t xworksize, /* size of Common->Xwork */ + /* --------------- */ cholmod_common *Common ) ; -int cholmod_l_allocate_work (size_t, size_t, size_t, cholmod_common *) ; -//------------------------------------------------------------------------------ -// cholmod_alloc_work: allocate workspace in Common -//------------------------------------------------------------------------------ +int cholmod_l_allocate_work (size_t, size_t, size_t, cholmod_common *) ; -// Added for CHOLMOD v5: allocates Xwork as either double or single. +/* -------------------------------------------------------------------------- */ +/* cholmod_free_work: free workspace in Common */ +/* -------------------------------------------------------------------------- */ -int cholmod_alloc_work +int cholmod_free_work ( - size_t nrow, // size of Common->Flag (nrow int32's) - // and Common->Head (nrow+1 int32's) - size_t iworksize, // size of Common->Iwork (# of int32's) - size_t xworksize, // size of Common->Xwork (# of entries) - int dtype, // CHOLMOD_DOUBLE or CHOLMOD_SINGLE cholmod_common *Common ) ; -int cholmod_l_alloc_work (size_t, size_t, size_t, int, cholmod_common *) ; -//------------------------------------------------------------------------------ -// cholmod_free_work: free workspace in Common -//------------------------------------------------------------------------------ - -int cholmod_free_work (cholmod_common *Common) ; int cholmod_l_free_work (cholmod_common *) ; -//------------------------------------------------------------------------------ -// cholmod_clear_flag: clear Flag workspace in Common -//------------------------------------------------------------------------------ +/* -------------------------------------------------------------------------- */ +/* cholmod_clear_flag: clear Flag workspace in Common */ +/* -------------------------------------------------------------------------- */ -// This macro is deprecated; do not use it: -#define CHOLMOD_CLEAR_FLAG(Common) \ -{ \ - Common->mark++ ; \ - if (Common->mark <= 0 || Common->mark >= INT32_MAX) \ - { \ - Common->mark = EMPTY ; \ - CHOLMOD (clear_flag) (Common) ; \ - } \ +/* use a macro for speed */ +#define CHOLMOD_CLEAR_FLAG(Common) \ +{ \ + Common->mark++ ; \ + if (Common->mark <= 0) \ + { \ + Common->mark = EMPTY ; \ + CHOLMOD (clear_flag) (Common) ; \ + } \ } -int64_t cholmod_clear_flag (cholmod_common *Common) ; +int64_t cholmod_clear_flag +( + cholmod_common *Common +) ; + int64_t cholmod_l_clear_flag (cholmod_common *) ; -//------------------------------------------------------------------------------ -// cholmod_error: called when CHOLMOD encounters an error -//------------------------------------------------------------------------------ +/* -------------------------------------------------------------------------- */ +/* cholmod_error: called when CHOLMOD encounters an error */ +/* -------------------------------------------------------------------------- */ int cholmod_error ( - int status, // Common->status - const char *file, // source file where error occurred - int line, // line number where error occurred - const char *message, // error message to print + /* ---- input ---- */ + int status, /* error status */ + const char *file, /* name of source code file where error occured */ + int line, /* line number in source code file where error occured*/ + const char *message,/* error message */ + /* --------------- */ cholmod_common *Common ) ; + int cholmod_l_error (int, const char *, int, const char *, cholmod_common *) ; -//------------------------------------------------------------------------------ -// cholmod_dbound and cholmod_sbound: for internal use in CHOLMOD only -//------------------------------------------------------------------------------ +/* -------------------------------------------------------------------------- */ +/* cholmod_dbound: for internal use in CHOLMOD only */ +/* -------------------------------------------------------------------------- */ -// These were once documented functions but no are no longer meant to be used -// by the user application. They remain here for backward compatibility. +double cholmod_dbound /* returns modified diagonal entry of D or L */ +( + /* ---- input ---- */ + double dj, /* diagonal entry of D for LDL' or L for LL' */ + /* --------------- */ + cholmod_common *Common +) ; -double cholmod_dbound (double, cholmod_common *) ; double cholmod_l_dbound (double, cholmod_common *) ; -float cholmod_sbound (float, cholmod_common *) ; -float cholmod_l_sbound (float, cholmod_common *) ; -//------------------------------------------------------------------------------ -// cholmod_hypot: compute sqrt (x*x + y*y) accurately -//------------------------------------------------------------------------------ +/* -------------------------------------------------------------------------- */ +/* cholmod_hypot: compute sqrt (x*x + y*y) accurately */ +/* -------------------------------------------------------------------------- */ + +double cholmod_hypot +( + /* ---- input ---- */ + double x, double y +) ; -double cholmod_hypot (double x, double y) ; double cholmod_l_hypot (double, double) ; -//------------------------------------------------------------------------------ -// cholmod_divcomplex: complex division, c = a/b -//------------------------------------------------------------------------------ +/* -------------------------------------------------------------------------- */ +/* cholmod_divcomplex: complex division, c = a/b */ +/* -------------------------------------------------------------------------- */ -int cholmod_divcomplex // return 1 if divide-by-zero, 0 if OK +int cholmod_divcomplex /* return 1 if divide-by-zero, 0 otherise */ ( - double ar, double ai, // a (real, imaginary) - double br, double bi, // b (real, imaginary) - double *cr, double *ci // c (real, imaginary) + /* ---- input ---- */ + double ar, double ai, /* real and imaginary parts of a */ + double br, double bi, /* real and imaginary parts of b */ + /* ---- output --- */ + double *cr, double *ci /* real and imaginary parts of c */ ) ; + int cholmod_l_divcomplex (double, double, double, double, double *, double *) ; -//============================================================================== -// cholmod_sparse: a sparse matrix in compressed-column (CSC) form -//============================================================================== + +/* ========================================================================== */ +/* === Core/cholmod_sparse ================================================== */ +/* ========================================================================== */ + +/* A sparse matrix stored in compressed-column form. */ typedef struct cholmod_sparse_struct { - size_t nrow ; // # of rows of the matrix - size_t ncol ; // # of colums of the matrix - size_t nzmax ; // max # of entries that can be held in the matrix - - // int32_t or int64_t arrays: - void *p ; // A->p [0..ncol], column "pointers" of the CSC matrix - void *i ; // A->i [0..nzmax-1], the row indices - - // for unpacked matrices only: - void *nz ; // A->nz [0..ncol-1], is the # of nonzeros in each col. - // This is NULL for a "packed" matrix (conventional CSC). - // For a packed matrix, the jth column is held in A->i and A->x in - // postions A->p [j] to A->p [j+1]-1, with no gaps between columns. - // For an "unpacked" matrix, there can be gaps between columns, so - // the jth columns appears in positions A-p [j] to - // A->p [j] + A->nz [j] - 1. - - // double or float arrays: - void *x ; // size nzmax or 2*nzmax, or NULL - void *z ; // size nzmax, or NULL - - int stype ; // A->stype defines what parts of the matrix is held: - // 0: the matrix is unsymmetric with both lower and upper parts stored. - // >0: the matrix is square and symmetric, with just the upper - // triangular part stored. - // <0: the matrix is square and symmetric, with just the lower - // triangular part stored. - - int itype ; // A->itype defines the integers used for A->p, A->i, and A->nz. - // if CHOLMOD_INT, these arrays are all of type int32_t. - // if CHOLMOD_LONG, these arrays are all of type int64_t. - int xtype ; // pattern, real, complex, or zomplex - int dtype ; // x and z are double or single - int sorted ; // true if columns are sorted, false otherwise - int packed ; // true if packed (A->nz ignored), false if unpacked + size_t nrow ; /* the matrix is nrow-by-ncol */ + size_t ncol ; + size_t nzmax ; /* maximum number of entries in the matrix */ + + /* pointers to int32_t or int64_t: */ + void *p ; /* p [0..ncol], the column pointers */ + void *i ; /* i [0..nzmax-1], the row indices */ + + /* for unpacked matrices only: */ + void *nz ; /* nz [0..ncol-1], the # of nonzeros in each col. In + * packed form, the nonzero pattern of column j is in + * A->i [A->p [j] ... A->p [j+1]-1]. In unpacked form, column j is in + * A->i [A->p [j] ... A->p [j]+A->nz[j]-1] instead. In both cases, the + * numerical values (if present) are in the corresponding locations in + * the array x (or z if A->xtype is CHOLMOD_ZOMPLEX). */ + + /* pointers to double or float: */ + void *x ; /* size nzmax or 2*nzmax, if present */ + void *z ; /* size nzmax, if present */ + + int stype ; /* Describes what parts of the matrix are considered: + * + * 0: matrix is "unsymmetric": use both upper and lower triangular parts + * (the matrix may actually be symmetric in pattern and value, but + * both parts are explicitly stored and used). May be square or + * rectangular. + * >0: matrix is square and symmetric, use upper triangular part. + * Entries in the lower triangular part are ignored. + * <0: matrix is square and symmetric, use lower triangular part. + * Entries in the upper triangular part are ignored. + * + * Note that stype>0 and stype<0 are different for cholmod_sparse and + * cholmod_triplet. See the cholmod_triplet data structure for more + * details. + */ + + int itype ; /* CHOLMOD_INT: p, i, and nz are int32_t. + * CHOLMOD_INTLONG: p is int64_t, + * i and nz are int32_t. + * CHOLMOD_LONG: p, i, and nz are int64_t */ + + int xtype ; /* pattern, real, complex, or zomplex */ + int dtype ; /* x and z are double or float */ + int sorted ; /* TRUE if columns are sorted, FALSE otherwise */ + int packed ; /* TRUE if packed (nz ignored), FALSE if unpacked + * (nz is required) */ } cholmod_sparse ; -//------------------------------------------------------------------------------ -// cholmod_allocate_sparse: allocate a sparse matrix -//------------------------------------------------------------------------------ +typedef struct cholmod_descendant_score_t +{ + double score ; + int64_t d ; +} +descendantScore ; + +/* For sorting descendant supernodes with qsort */ +int cholmod_score_comp (struct cholmod_descendant_score_t *i, + struct cholmod_descendant_score_t *j) ; + +int cholmod_l_score_comp (struct cholmod_descendant_score_t *i, + struct cholmod_descendant_score_t *j) ; + +/* -------------------------------------------------------------------------- */ +/* cholmod_allocate_sparse: allocate a sparse matrix */ +/* -------------------------------------------------------------------------- */ cholmod_sparse *cholmod_allocate_sparse ( - size_t nrow, // # of rows - size_t ncol, // # of columns - size_t nzmax, // max # of entries the matrix can hold - int sorted, // true if columns are sorted - int packed, // true if A is be packed (A->nz NULL), false if unpacked - int stype, // the stype of the matrix (unsym, tril, or triu) - int xdtype, // xtype + dtype of the matrix: - // (CHOLMOD_DOUBLE, _SINGLE) + - // (CHOLMOD_PATTERN, _REAL, _COMPLEX, or _ZOMPLEX) + /* ---- input ---- */ + size_t nrow, /* # of rows of A */ + size_t ncol, /* # of columns of A */ + size_t nzmax, /* max # of nonzeros of A */ + int sorted, /* TRUE if columns of A sorted, FALSE otherwise */ + int packed, /* TRUE if A will be packed, FALSE otherwise */ + int stype, /* stype of A */ + int xtype, /* CHOLMOD_PATTERN, _REAL, _COMPLEX, or _ZOMPLEX */ + /* --------------- */ cholmod_common *Common ) ; + cholmod_sparse *cholmod_l_allocate_sparse (size_t, size_t, size_t, int, int, int, int, cholmod_common *) ; -//------------------------------------------------------------------------------ -// cholmod_free_sparse: free a sparse matrix -//------------------------------------------------------------------------------ +/* -------------------------------------------------------------------------- */ +/* cholmod_free_sparse: free a sparse matrix */ +/* -------------------------------------------------------------------------- */ int cholmod_free_sparse ( - cholmod_sparse **A, // handle of sparse matrix to free + /* ---- in/out --- */ + cholmod_sparse **A, /* matrix to deallocate, NULL on output */ + /* --------------- */ cholmod_common *Common ) ; + int cholmod_l_free_sparse (cholmod_sparse **, cholmod_common *) ; -//------------------------------------------------------------------------------ -// cholmod_reallocate_sparse: change max # of entries in a sparse matrix -//------------------------------------------------------------------------------ +/* -------------------------------------------------------------------------- */ +/* cholmod_reallocate_sparse: change the size (# entries) of sparse matrix */ +/* -------------------------------------------------------------------------- */ int cholmod_reallocate_sparse ( - size_t nznew, // new max # of nonzeros the sparse matrix can hold - cholmod_sparse *A, // sparse matrix to reallocate + /* ---- input ---- */ + size_t nznew, /* new # of entries in A */ + /* ---- in/out --- */ + cholmod_sparse *A, /* matrix to reallocate */ + /* --------------- */ cholmod_common *Common ) ; -int cholmod_l_reallocate_sparse (size_t, cholmod_sparse *, cholmod_common *) ; -//------------------------------------------------------------------------------ -// cholmod_nnz: # of entries in a sparse matrix -//------------------------------------------------------------------------------ +int cholmod_l_reallocate_sparse ( size_t, cholmod_sparse *, cholmod_common *) ; -int64_t cholmod_nnz // return # of entries in the sparse matrix +/* -------------------------------------------------------------------------- */ +/* cholmod_nnz: return number of nonzeros in a sparse matrix */ +/* -------------------------------------------------------------------------- */ + +int64_t cholmod_nnz ( - cholmod_sparse *A, // sparse matrix to query + /* ---- input ---- */ + cholmod_sparse *A, + /* --------------- */ cholmod_common *Common ) ; + int64_t cholmod_l_nnz (cholmod_sparse *, cholmod_common *) ; -//------------------------------------------------------------------------------ -// cholmod_speye: sparse identity matrix (possibly rectangular) -//------------------------------------------------------------------------------ +/* -------------------------------------------------------------------------- */ +/* cholmod_speye: sparse identity matrix */ +/* -------------------------------------------------------------------------- */ cholmod_sparse *cholmod_speye ( - size_t nrow, // # of rows - size_t ncol, // # of columns - int xdtype, // xtype + dtype of the matrix: - // (CHOLMOD_DOUBLE, _SINGLE) + - // (CHOLMOD_PATTERN, _REAL, _COMPLEX, or _ZOMPLEX) + /* ---- input ---- */ + size_t nrow, /* # of rows of A */ + size_t ncol, /* # of columns of A */ + int xtype, /* CHOLMOD_PATTERN, _REAL, _COMPLEX, or _ZOMPLEX */ + /* --------------- */ cholmod_common *Common ) ; -cholmod_sparse *cholmod_l_speye (size_t, size_t, int, cholmod_common *) ; -//------------------------------------------------------------------------------ -// cholmod_spzeros: sparse matrix with no entries -//------------------------------------------------------------------------------ +cholmod_sparse *cholmod_l_speye (size_t, size_t, int, cholmod_common *) ; -// Identical to cholmod_allocate_sparse, with packed = true, sorted = true, -// and stype = 0. +/* -------------------------------------------------------------------------- */ +/* cholmod_spzeros: sparse zero matrix */ +/* -------------------------------------------------------------------------- */ -cholmod_sparse *cholmod_spzeros // return a sparse matrix with no entries +cholmod_sparse *cholmod_spzeros ( - size_t nrow, // # of rows - size_t ncol, // # of columns - size_t nzmax, // max # of entries the matrix can hold - int xdtype, // xtype + dtype of the matrix: - // (CHOLMOD_DOUBLE, _SINGLE) + - // (CHOLMOD_PATTERN, _REAL, _COMPLEX, or _ZOMPLEX) + /* ---- input ---- */ + size_t nrow, /* # of rows of A */ + size_t ncol, /* # of columns of A */ + size_t nzmax, /* max # of nonzeros of A */ + int xtype, /* CHOLMOD_PATTERN, _REAL, _COMPLEX, or _ZOMPLEX */ + /* --------------- */ cholmod_common *Common ) ; + cholmod_sparse *cholmod_l_spzeros (size_t, size_t, size_t, int, cholmod_common *) ; -//------------------------------------------------------------------------------ -// cholmod_transpose: transpose a sparse matrix -//------------------------------------------------------------------------------ +/* -------------------------------------------------------------------------- */ +/* cholmod_transpose: transpose a sparse matrix */ +/* -------------------------------------------------------------------------- */ -cholmod_sparse *cholmod_transpose // return new sparse matrix C +/* Return A' or A.' The "values" parameter is 0, 1, or 2 to denote the pattern + * transpose, the array transpose (A.'), and the complex conjugate transpose + * (A'). + */ + +cholmod_sparse *cholmod_transpose ( - cholmod_sparse *A, // input matrix - int mode, // 2: numerical (conj), 1: numerical (non-conj.), - // <= 0: pattern (with diag) + /* ---- input ---- */ + cholmod_sparse *A, /* matrix to transpose */ + int values, /* 0: pattern, 1: array transpose, 2: conj. transpose */ + /* --------------- */ cholmod_common *Common ) ; + cholmod_sparse *cholmod_l_transpose (cholmod_sparse *, int, cholmod_common *) ; -//------------------------------------------------------------------------------ -// cholmod_transpose_unsym: transpose an unsymmetric sparse matrix -//------------------------------------------------------------------------------ +/* -------------------------------------------------------------------------- */ +/* cholmod_transpose_unsym: transpose an unsymmetric sparse matrix */ +/* -------------------------------------------------------------------------- */ -// Compute C = A', A (:,f)', or A (p,f)', where A is unsymmetric and C is -// already allocated. See cholmod_transpose for a routine with a simpler -// interface. +/* Compute F = A', A (:,f)', or A (p,f)', where A is unsymmetric and F is + * already allocated. See cholmod_transpose for a simpler routine. */ int cholmod_transpose_unsym ( - cholmod_sparse *A, // input matrix - int mode, // 2: numerical (conj), 1: numerical (non-conj.), - // <= 0: pattern (with diag) - int32_t *Perm, // permutation for C=A(p,f)', or NULL - int32_t *fset, // a list of column indices in range 0:A->ncol-1 - size_t fsize, // # of entries in fset - cholmod_sparse *C, // output matrix, must be allocated on input + /* ---- input ---- */ + cholmod_sparse *A, /* matrix to transpose */ + int values, /* 0: pattern, 1: array transpose, 2: conj. transpose */ + int32_t *Perm, /* size nrow, if present (can be NULL) */ + int32_t *fset, /* subset of 0:(A->ncol)-1 */ + size_t fsize, /* size of fset */ + /* ---- output --- */ + cholmod_sparse *F, /* F = A', A(:,f)', or A(p,f)' */ + /* --------------- */ cholmod_common *Common ) ; -int cholmod_l_transpose_unsym (cholmod_sparse *, int, int64_t *, int64_t *, - size_t, cholmod_sparse *, cholmod_common *) ; -//------------------------------------------------------------------------------ -// cholmod_transpose_sym: symmetric permuted transpose -//------------------------------------------------------------------------------ +int cholmod_l_transpose_unsym (cholmod_sparse *, int, int64_t *, + int64_t *, size_t, cholmod_sparse *, cholmod_common *) ; + +/* -------------------------------------------------------------------------- */ +/* cholmod_transpose_sym: transpose a symmetric sparse matrix */ +/* -------------------------------------------------------------------------- */ -// C = A' or C = A(p,p)' where A and C are both symmetric and C is already -// allocated. See cholmod_transpose or cholmod_ptranspose for a routine with -// a simpler interface. +/* Compute F = A' or A (p,p)', where A is symmetric and F is already allocated. + * See cholmod_transpose for a simpler routine. */ int cholmod_transpose_sym ( - cholmod_sparse *A, // input matrix - int mode, // 2: numerical (conj), 1: numerical (non-conj.), - // <= 0: pattern (with diag) - int32_t *Perm, // permutation for C=A(p,p)', or NULL - cholmod_sparse *C, // output matrix, must be allocated on input + /* ---- input ---- */ + cholmod_sparse *A, /* matrix to transpose */ + int values, /* 0: pattern, 1: array transpose, 2: conj. transpose */ + int32_t *Perm, /* size nrow, if present (can be NULL) */ + /* ---- output --- */ + cholmod_sparse *F, /* F = A' or A(p,p)' */ + /* --------------- */ cholmod_common *Common ) ; -int cholmod_l_transpose_sym (cholmod_sparse *, int, int64_t *, cholmod_sparse *, - cholmod_common *) ; -//------------------------------------------------------------------------------ -// cholmod_ptranspose: C = A', A(:,f)', A(p,p)', or A(p,f)' -//------------------------------------------------------------------------------ +int cholmod_l_transpose_sym (cholmod_sparse *, int, int64_t *, + cholmod_sparse *, cholmod_common *) ; -cholmod_sparse *cholmod_ptranspose // return new sparse matrix C +/* -------------------------------------------------------------------------- */ +/* cholmod_ptranspose: transpose a sparse matrix */ +/* -------------------------------------------------------------------------- */ + +/* Return A' or A(p,p)' if A is symmetric. Return A', A(:,f)', or A(p,f)' if + * A is unsymmetric. */ + +cholmod_sparse *cholmod_ptranspose ( - cholmod_sparse *A, // input matrix - int mode, // 2: numerical (conj), 1: numerical (non-conj.), - // <= 0: pattern (with diag) - int32_t *Perm, // permutation for C=A(p,f)', or NULL - int32_t *fset, // a list of column indices in range 0:A->ncol-1 - size_t fsize, // # of entries in fset + /* ---- input ---- */ + cholmod_sparse *A, /* matrix to transpose */ + int values, /* 0: pattern, 1: array transpose, 2: conj. transpose */ + int32_t *Perm, /* if non-NULL, F = A(p,f) or A(p,p) */ + int32_t *fset, /* subset of 0:(A->ncol)-1 */ + size_t fsize, /* size of fset */ + /* --------------- */ cholmod_common *Common ) ; + cholmod_sparse *cholmod_l_ptranspose (cholmod_sparse *, int, int64_t *, int64_t *, size_t, cholmod_common *) ; -//------------------------------------------------------------------------------ -// cholmod_sort: sort the indices of a sparse matrix -//------------------------------------------------------------------------------ +/* -------------------------------------------------------------------------- */ +/* cholmod_sort: sort row indices in each column of sparse matrix */ +/* -------------------------------------------------------------------------- */ int cholmod_sort ( - cholmod_sparse *A, // input/output matrix to sort + /* ---- in/out --- */ + cholmod_sparse *A, /* matrix to sort */ + /* --------------- */ cholmod_common *Common ) ; + int cholmod_l_sort (cholmod_sparse *, cholmod_common *) ; -//------------------------------------------------------------------------------ -// cholmod_band_nnz: # of entries within a band of a sparse matrix -//------------------------------------------------------------------------------ +/* -------------------------------------------------------------------------- */ +/* cholmod_band: C = tril (triu (A,k1), k2) */ +/* -------------------------------------------------------------------------- */ -int64_t cholmod_band_nnz // return # of entries in a band (-1 if error) +cholmod_sparse *cholmod_band ( - cholmod_sparse *A, // matrix to examine - int64_t k1, // count entries in k1:k2 diagonals - int64_t k2, - bool ignore_diag, // if true, exclude any diagonal entries + /* ---- input ---- */ + cholmod_sparse *A, /* matrix to extract band matrix from */ + int64_t k1, /* ignore entries below the k1-st diagonal */ + int64_t k2, /* ignore entries above the k2-nd diagonal */ + int mode, /* >0: numerical, 0: pattern, <0: pattern (no diag) */ + /* --------------- */ cholmod_common *Common ) ; -int64_t cholmod_l_band_nnz (cholmod_sparse *, int64_t, int64_t, bool, - cholmod_common *) ; -//------------------------------------------------------------------------------ -// cholmod_band: C = tril (triu (A,k1), k2) -//------------------------------------------------------------------------------ - -cholmod_sparse *cholmod_band // return a new matrix C -( - cholmod_sparse *A, // input matrix - int64_t k1, // count entries in k1:k2 diagonals - int64_t k2, - int mode, // >0: numerical, 0: pattern, <0: pattern (no diag) - cholmod_common *Common -) ; -cholmod_sparse *cholmod_l_band (cholmod_sparse *, int64_t, int64_t, int, - cholmod_common *) ; +cholmod_sparse *cholmod_l_band (cholmod_sparse *, int64_t, + int64_t, int, cholmod_common *) ; -//------------------------------------------------------------------------------ -// cholmod_band_inplace: A = tril (triu (A,k1), k2) */ -//------------------------------------------------------------------------------ +/* -------------------------------------------------------------------------- */ +/* cholmod_band_inplace: A = tril (triu (A,k1), k2) */ +/* -------------------------------------------------------------------------- */ int cholmod_band_inplace ( - int64_t k1, // count entries in k1:k2 diagonals - int64_t k2, - int mode, // >0: numerical, 0: pattern, <0: pattern (no diag) - cholmod_sparse *A, // input/output matrix + /* ---- input ---- */ + int64_t k1, /* ignore entries below the k1-st diagonal */ + int64_t k2, /* ignore entries above the k2-nd diagonal */ + int mode, /* >0: numerical, 0: pattern, <0: pattern (no diag) */ + /* ---- in/out --- */ + cholmod_sparse *A, /* matrix from which entries not in band are removed */ + /* --------------- */ cholmod_common *Common ) ; -int cholmod_l_band_inplace (int64_t, int64_t, int, cholmod_sparse *, - cholmod_common *) ; -//------------------------------------------------------------------------------ -// cholmod_aat: C = A*A' or A(:,f)*A(:,f)' -//------------------------------------------------------------------------------ +int cholmod_l_band_inplace (int64_t, int64_t, int, + cholmod_sparse *, cholmod_common *) ; -cholmod_sparse *cholmod_aat // return sparse matrix C +/* -------------------------------------------------------------------------- */ +/* cholmod_aat: C = A*A' or A(:,f)*A(:,f)' */ +/* -------------------------------------------------------------------------- */ + +cholmod_sparse *cholmod_aat ( - cholmod_sparse *A, // input matrix - int32_t *fset, // a list of column indices in range 0:A->ncol-1 - size_t fsize, // # of entries in fset - int mode, // 2: numerical (conj), 1: numerical (non-conj.), - // 0: pattern (with diag), -1: pattern (remove diag), - // -2: pattern (remove diag; add ~50% extra space in C) + /* ---- input ---- */ + cholmod_sparse *A, /* input matrix; C=A*A' is constructed */ + int32_t *fset, /* subset of 0:(A->ncol)-1 */ + size_t fsize, /* size of fset */ + int mode, /* >0: numerical, 0: pattern, <0: pattern (no diag), + * -2: pattern only, no diagonal, add 50%+n extra + * space to C */ + /* --------------- */ cholmod_common *Common ) ; -cholmod_sparse *cholmod_l_aat (cholmod_sparse *, int64_t *, size_t, int, - cholmod_common *) ; -//------------------------------------------------------------------------------ -// cholmod_copy_sparse: C = A, create an exact copy of a sparse matrix -//------------------------------------------------------------------------------ +cholmod_sparse *cholmod_l_aat (cholmod_sparse *, int64_t *, size_t, + int, cholmod_common *) ; -// Creates an exact copy of a sparse matrix. For making a copy with a change -// of stype and/or copying the pattern of a numerical matrix, see cholmod_copy. -// For changing the xtype and/or dtype, see cholmod_sparse_xtype. +/* -------------------------------------------------------------------------- */ +/* cholmod_copy_sparse: C = A, create an exact copy of a sparse matrix */ +/* -------------------------------------------------------------------------- */ -cholmod_sparse *cholmod_copy_sparse // return new sparse matrix +cholmod_sparse *cholmod_copy_sparse ( - cholmod_sparse *A, // sparse matrix to copy + /* ---- input ---- */ + cholmod_sparse *A, /* matrix to copy */ + /* --------------- */ cholmod_common *Common ) ; + cholmod_sparse *cholmod_l_copy_sparse (cholmod_sparse *, cholmod_common *) ; -//------------------------------------------------------------------------------ -// cholmod_copy: C = A, with possible change of stype -//------------------------------------------------------------------------------ +/* -------------------------------------------------------------------------- */ +/* cholmod_copy: C = A, with possible change of stype */ +/* -------------------------------------------------------------------------- */ -cholmod_sparse *cholmod_copy // return new sparse matrix +cholmod_sparse *cholmod_copy ( - cholmod_sparse *A, // input matrix, not modified - int stype, // stype of C - int mode, // 2: numerical (conj), 1: numerical (non-conj.), - // 0: pattern (with diag), -1: pattern (remove diag), - // -2: pattern (remove diag; add ~50% extra space in C) + /* ---- input ---- */ + cholmod_sparse *A, /* matrix to copy */ + int stype, /* requested stype of C */ + int mode, /* >0: numerical, 0: pattern, <0: pattern (no diag) */ + /* --------------- */ cholmod_common *Common ) ; + cholmod_sparse *cholmod_l_copy (cholmod_sparse *, int, int, cholmod_common *) ; -//------------------------------------------------------------------------------ -// cholmod_add: C = alpha*A + beta*B -//------------------------------------------------------------------------------ +/* -------------------------------------------------------------------------- */ +/* cholmod_add: C = alpha*A + beta*B */ +/* -------------------------------------------------------------------------- */ -cholmod_sparse *cholmod_add // return C = alpha*A + beta*B +cholmod_sparse *cholmod_add ( - cholmod_sparse *A, // input matrix - cholmod_sparse *B, // input matrix - double alpha [2], // scale factor for A (two entires used if complex) - double beta [2], // scale factor for A (two entires used if complex) - int values, // if TRUE compute the numerical values of C - int sorted, // ignored; C is now always returned as sorted + /* ---- input ---- */ + cholmod_sparse *A, /* matrix to add */ + cholmod_sparse *B, /* matrix to add */ + double alpha [2], /* scale factor for A */ + double beta [2], /* scale factor for B */ + int values, /* if TRUE compute the numerical values of C */ + int sorted, /* if TRUE, sort columns of C */ + /* --------------- */ cholmod_common *Common ) ; + cholmod_sparse *cholmod_l_add (cholmod_sparse *, cholmod_sparse *, double *, double *, int, int, cholmod_common *) ; -//------------------------------------------------------------------------------ -// cholmod_sparse_xtype: change the xtype and/or dtype of a sparse matrix -//------------------------------------------------------------------------------ +/* -------------------------------------------------------------------------- */ +/* cholmod_sparse_xtype: change the xtype of a sparse matrix */ +/* -------------------------------------------------------------------------- */ int cholmod_sparse_xtype ( - int to_xdtype, // requested xtype and dtype - cholmod_sparse *A, // sparse matrix to change + /* ---- input ---- */ + int to_xtype, /* requested xtype (pattern, real, complex, zomplex) */ + /* ---- in/out --- */ + cholmod_sparse *A, /* sparse matrix to change */ + /* --------------- */ cholmod_common *Common ) ; + int cholmod_l_sparse_xtype (int, cholmod_sparse *, cholmod_common *) ; -//============================================================================== -// cholmod_factor: symbolic or numeric factorization (simplicial or supernodal) -//============================================================================== + +/* ========================================================================== */ +/* === Core/cholmod_factor ================================================== */ +/* ========================================================================== */ + +/* A symbolic and numeric factorization, either simplicial or supernodal. + * In all cases, the row indices in the columns of L are kept sorted. */ typedef struct cholmod_factor_struct { - size_t n ; // L is n-by-n - - size_t minor ; // If the factorization failed because of numerical issues - // (the matrix being factorized is found to be singular or not positive - // definte), then L->minor is the column at which it failed. L->minor - // = n means the factorization was successful. - - //-------------------------------------------------------------------------- - // symbolic ordering and analysis - //-------------------------------------------------------------------------- - - void *Perm ; // int32/int64, size n, fill-reducing ordering - void *ColCount ;// int32/int64, size n, # entries in each column of L - void *IPerm ; // int32/int64, size n, created by cholmod_solve2; - // containing the inverse of L->Perm - - //-------------------------------------------------------------------------- - // simplicial factorization (not supernodal) - //-------------------------------------------------------------------------- - - size_t nzmax ; // # of entries that L->i, L->x, and L->z can hold - - void *p ; // int32/int64, size n+1, column pointers - void *i ; // int32/int64, size nzmax, row indices - void *x ; // float/double, size nzmax or 2*nzmax, numerical values - void *z ; // float/double, size nzmax or empty, imaginary values - void *nz ; // int32/int64, size ncol, # of entries in each column - - // The row indices of L(:,j) are held in - // L->i [L->p [j] ... L->p [j] + L->nz [j] - 1]. - - // The numeical values of L(:,j) are held in the same positions in L->x - // (and L->z if L is zomplex) - - // L->next and L->prev hold a link list of columns of L, that tracks the - // order they appear in the arrays L->i, L->x, and L->z. The head and tail - // of the list is n+1 and n, respectively. - - void *next ; // int32/int64, size n+2 - void *prev ; // int32/int64, size n+2 - - //-------------------------------------------------------------------------- - // supernodal factorization (not simplicial) - //-------------------------------------------------------------------------- - - // L->x is shared with the simplicial structure above. L->z is not used - // for the supernodal case since a supernodal factor cannot be zomplex. - - size_t nsuper ; // # of supernodes - size_t ssize ; // # of integers in L->s - size_t xsize ; // # of entries in L->x - size_t maxcsize ; // size of largest update matrix - size_t maxesize ; // max # of rows in supernodes, excl. triangular part - - // the following are int32/int64 and are size nsuper+1: - void *super ; // first column in each supernode - void *pi ; // index into L->s for integer part of a supernode - void *px ; // index into L->x for numeric part of a supernode - - void *s ; // int32/int64, ssize, integer part of supernodes - - //-------------------------------------------------------------------------- - // type of the factorization - //-------------------------------------------------------------------------- - - int ordering ; // the fill-reducing method used (CHOLMOD_NATURAL, - // CHOLMOD_GIVEN, CHOLMOD_AMD, CHOLMOD_METIS, CHOLMOD_NESDIS, - // CHOLMOD_COLAMD, or CHOLMOD_POSTORDERED). - - int is_ll ; // true: an LL' factorization; false: LDL' instead - int is_super ; // true: supernodal; false: simplicial - int is_monotonic ; // true: columns appear in order 0 to n-1 in L, for a - // simplicial factorization only - - // Two boolean values above (is_ll, is_super) and L->xtype (pattern or - // otherwise, define eight types of factorizations, but only 6 are used: - - // If L->xtype is CHOLMOD_PATTERN, then L is a symbolic factor: - // - // simplicial LDL': (is_ll false, is_super false). Nothing is present - // except Perm and ColCount. - // - // simplicial LL': (is_ll true, is_super false). Identical to the - // simplicial LDL', except for the is_ll flag. - // - // supernodal LL': (is_ll true, is_super true). A supernodal symbolic - // factorization. The simplicial symbolic information is present - // (Perm and ColCount), as is all of the supernodal factorization - // except for the numerical values (x and z). - // - // If L->xtype is CHOLMOD_REAL, CHOLMOD_COMPLEX, or CHOLMOD_ZOMPLEX, - // then L is a numeric factor: - // - // - // simplicial LDL': (is_ll false, is_super false). Stored in compressed - // column form, using the simplicial components above (nzmax, p, i, - // x, z, nz, next, and prev). The unit diagonal of L is not stored, - // and D is stored in its place. There are no supernodes. - // - // simplicial LL': (is_ll true, is_super false). Uses the same storage - // scheme as the simplicial LDL', except that D does not appear. - // The first entry of each column of L is the diagonal entry of - // that column of L. - // - // supernodal LL': (is_ll true, is_super true). A supernodal factor, - // using the supernodal components described above (nsuper, ssize, - // xsize, maxcsize, maxesize, super, pi, px, s, x, and z). - // A supernodal factorization is never zomplex. - - int itype ; // integer type for L->Perm, L->ColCount, L->p, L->i, L->nz, - // L->next, L->prev, L->super, L->pi, L->px, and L->s. - // These are all int32 if L->itype is CHOLMOD_INT, or all int64 - // if L->itype is CHOLMOD_LONG. - - int xtype ; // pattern, real, complex, or zomplex - int dtype ; // x and z are double or single - - int useGPU; // if true, symbolic factorization allows for use of the GPU + /* ---------------------------------------------------------------------- */ + /* for both simplicial and supernodal factorizations */ + /* ---------------------------------------------------------------------- */ + + size_t n ; /* L is n-by-n */ + + size_t minor ; /* If the factorization failed, L->minor is the column + * at which it failed (in the range 0 to n-1). A value + * of n means the factorization was successful or + * the matrix has not yet been factorized. */ + + /* ---------------------------------------------------------------------- */ + /* symbolic ordering and analysis */ + /* ---------------------------------------------------------------------- */ + + void *Perm ; /* size n, permutation used */ + void *ColCount ; /* size n, column counts for simplicial L */ + + void *IPerm ; /* size n, inverse permutation. Only created by + * cholmod_solve2 if Bset is used. */ + + /* ---------------------------------------------------------------------- */ + /* simplicial factorization */ + /* ---------------------------------------------------------------------- */ + + size_t nzmax ; /* size of i and x */ + + void *p ; /* p [0..ncol], the column pointers */ + void *i ; /* i [0..nzmax-1], the row indices */ + void *x ; /* x [0..nzmax-1], the numerical values */ + void *z ; + void *nz ; /* nz [0..ncol-1], the # of nonzeros in each column. + * i [p [j] ... p [j]+nz[j]-1] contains the row indices, + * and the numerical values are in the same locatins + * in x. The value of i [p [k]] is always k. */ + + void *next ; /* size ncol+2. next [j] is the next column in i/x */ + void *prev ; /* size ncol+2. prev [j] is the prior column in i/x. + * head of the list is ncol+1, and the tail is ncol. */ + + /* ---------------------------------------------------------------------- */ + /* supernodal factorization */ + /* ---------------------------------------------------------------------- */ + + /* Note that L->x is shared with the simplicial data structure. L->x has + * size L->nzmax for a simplicial factor, and size L->xsize for a supernodal + * factor. */ + + size_t nsuper ; /* number of supernodes */ + size_t ssize ; /* size of s, integer part of supernodes */ + size_t xsize ; /* size of x, real part of supernodes */ + size_t maxcsize ; /* size of largest update matrix */ + size_t maxesize ; /* max # of rows in supernodes, excl. triangular part */ + + void *super ; /* size nsuper+1, first col in each supernode */ + void *pi ; /* size nsuper+1, pointers to integer patterns */ + void *px ; /* size nsuper+1, pointers to real parts */ + void *s ; /* size ssize, integer part of supernodes */ + + /* ---------------------------------------------------------------------- */ + /* factorization type */ + /* ---------------------------------------------------------------------- */ + + int ordering ; /* ordering method used */ + + int is_ll ; /* TRUE if LL', FALSE if LDL' */ + int is_super ; /* TRUE if supernodal, FALSE if simplicial */ + int is_monotonic ; /* TRUE if columns of L appear in order 0..n-1. + * Only applicable to simplicial numeric types. */ + + /* There are 8 types of factor objects that cholmod_factor can represent + * (only 6 are used): + * + * Numeric types (xtype is not CHOLMOD_PATTERN) + * -------------------------------------------- + * + * simplicial LDL': (is_ll FALSE, is_super FALSE). Stored in compressed + * column form, using the simplicial components above (nzmax, p, i, + * x, z, nz, next, and prev). The unit diagonal of L is not stored, + * and D is stored in its place. There are no supernodes. + * + * simplicial LL': (is_ll TRUE, is_super FALSE). Uses the same storage + * scheme as the simplicial LDL', except that D does not appear. + * The first entry of each column of L is the diagonal entry of + * that column of L. + * + * supernodal LDL': (is_ll FALSE, is_super TRUE). Not used. + * FUTURE WORK: add support for supernodal LDL' + * + * supernodal LL': (is_ll TRUE, is_super TRUE). A supernodal factor, + * using the supernodal components described above (nsuper, ssize, + * xsize, maxcsize, maxesize, super, pi, px, s, x, and z). + * + * + * Symbolic types (xtype is CHOLMOD_PATTERN) + * ----------------------------------------- + * + * simplicial LDL': (is_ll FALSE, is_super FALSE). Nothing is present + * except Perm and ColCount. + * + * simplicial LL': (is_ll TRUE, is_super FALSE). Identical to the + * simplicial LDL', except for the is_ll flag. + * + * supernodal LDL': (is_ll FALSE, is_super TRUE). Not used. + * FUTURE WORK: add support for supernodal LDL' + * + * supernodal LL': (is_ll TRUE, is_super TRUE). A supernodal symbolic + * factorization. The simplicial symbolic information is present + * (Perm and ColCount), as is all of the supernodal factorization + * except for the numerical values (x and z). + */ + + int itype ; /* The integer arrays are Perm, ColCount, p, i, nz, + * next, prev, super, pi, px, and s. If itype is + * CHOLMOD_INT, all of these are int arrays. + * CHOLMOD_INTLONG: p, pi, px are int64_t, others int. + * CHOLMOD_LONG: all integer arrays are int64_t. */ + int xtype ; /* pattern, real, complex, or zomplex */ + int dtype ; /* x and z double or float */ + + int useGPU; /* Indicates the symbolic factorization supports + * GPU acceleration */ } cholmod_factor ; -//------------------------------------------------------------------------------ -// cholmod_allocate_factor: allocate a numerical factor -//------------------------------------------------------------------------------ -// L is returned as double precision +/* -------------------------------------------------------------------------- */ +/* cholmod_allocate_factor: allocate a factor (symbolic LL' or LDL') */ +/* -------------------------------------------------------------------------- */ -cholmod_factor *cholmod_allocate_factor // return the new factor L +cholmod_factor *cholmod_allocate_factor ( - size_t n, // L is factorization of an n-by-n matrix + /* ---- input ---- */ + size_t n, /* L is n-by-n */ + /* --------------- */ cholmod_common *Common ) ; -cholmod_factor *cholmod_l_allocate_factor (size_t, cholmod_common *) ; - -//------------------------------------------------------------------------------ -// cholmod_alloc_factor: allocate a numerical factor (double or single) -//------------------------------------------------------------------------------ -cholmod_factor *cholmod_alloc_factor // return the new factor L -( - size_t n, // L is factorization of an n-by-n matrix - int dtype, // CHOLMOD_SINGLE or CHOLMOD_DOUBLE - cholmod_common *Common -) ; -cholmod_factor *cholmod_l_alloc_factor (size_t, int, cholmod_common *) ; +cholmod_factor *cholmod_l_allocate_factor (size_t, cholmod_common *) ; -//------------------------------------------------------------------------------ -// cholmod_free_factor: free a factor -//------------------------------------------------------------------------------ +/* -------------------------------------------------------------------------- */ +/* cholmod_free_factor: free a factor */ +/* -------------------------------------------------------------------------- */ int cholmod_free_factor ( - cholmod_factor **L, // handle of sparse factorization to free + /* ---- in/out --- */ + cholmod_factor **L, /* factor to free, NULL on output */ + /* --------------- */ cholmod_common *Common ) ; + int cholmod_l_free_factor (cholmod_factor **, cholmod_common *) ; -//------------------------------------------------------------------------------ -// cholmod_reallocate_factor: change the # entries in a factor -//------------------------------------------------------------------------------ +/* -------------------------------------------------------------------------- */ +/* cholmod_reallocate_factor: change the # entries in a factor */ +/* -------------------------------------------------------------------------- */ int cholmod_reallocate_factor ( - size_t nznew, // new max # of nonzeros the factor matrix can hold - cholmod_factor *L, // factor to reallocate + /* ---- input ---- */ + size_t nznew, /* new # of entries in L */ + /* ---- in/out --- */ + cholmod_factor *L, /* factor to modify */ + /* --------------- */ cholmod_common *Common ) ; + int cholmod_l_reallocate_factor (size_t, cholmod_factor *, cholmod_common *) ; -//------------------------------------------------------------------------------ -// cholmod_change_factor: change the type of factor (e.g., LDL' to LL') -//------------------------------------------------------------------------------ +/* -------------------------------------------------------------------------- */ +/* cholmod_change_factor: change the type of factor (e.g., LDL' to LL') */ +/* -------------------------------------------------------------------------- */ int cholmod_change_factor ( - int to_xtype, // CHOLMOD_PATTERN, _REAL, _COMPLEX, or _ZOMPLEX - int to_ll, // if true: convert to LL'; else to LDL' - int to_super, // if true: convert to supernodal; else to simplicial - int to_packed, // if true: pack simplicial columns' else: do not pack - int to_monotonic, // if true, put simplicial columns in order - cholmod_factor *L, // factor to change. + /* ---- input ---- */ + int to_xtype, /* to CHOLMOD_PATTERN, _REAL, _COMPLEX, _ZOMPLEX */ + int to_ll, /* TRUE: convert to LL', FALSE: LDL' */ + int to_super, /* TRUE: convert to supernodal, FALSE: simplicial */ + int to_packed, /* TRUE: pack simplicial columns, FALSE: do not pack */ + int to_monotonic, /* TRUE: put simplicial columns in order, FALSE: not */ + /* ---- in/out --- */ + cholmod_factor *L, /* factor to modify */ + /* --------------- */ cholmod_common *Common ) ; -int cholmod_l_change_factor (int, int, int, int, int, cholmod_factor *, + +int cholmod_l_change_factor ( int, int, int, int, int, cholmod_factor *, cholmod_common *) ; -//------------------------------------------------------------------------------ -// cholmod_pack_factor: pack a factor -//------------------------------------------------------------------------------ +/* -------------------------------------------------------------------------- */ +/* cholmod_pack_factor: pack the columns of a factor */ +/* -------------------------------------------------------------------------- */ -// Removes all slack space from all columns in a factor. +/* Pack the columns of a simplicial factor. Unlike cholmod_change_factor, + * it can pack the columns of a factor even if they are not stored in their + * natural order (non-monotonic). */ int cholmod_pack_factor ( - cholmod_factor *L, // factor to pack + /* ---- in/out --- */ + cholmod_factor *L, /* factor to modify */ + /* --------------- */ cholmod_common *Common ) ; + int cholmod_l_pack_factor (cholmod_factor *, cholmod_common *) ; -//------------------------------------------------------------------------------ -// cholmod_reallocate_column: reallocate a single column L(:,j) -//------------------------------------------------------------------------------ +/* -------------------------------------------------------------------------- */ +/* cholmod_reallocate_column: resize a single column of a factor */ +/* -------------------------------------------------------------------------- */ int cholmod_reallocate_column ( - size_t j, // reallocate L(:,j) - size_t need, // space in L(:,j) for this # of entries - cholmod_factor *L, // L factor modified, L(:,j) resized + /* ---- input ---- */ + size_t j, /* the column to reallocate */ + size_t need, /* required size of column j */ + /* ---- in/out --- */ + cholmod_factor *L, /* factor to modify */ + /* --------------- */ cholmod_common *Common ) ; + int cholmod_l_reallocate_column (size_t, size_t, cholmod_factor *, cholmod_common *) ; -//------------------------------------------------------------------------------ -// cholmod_factor_to_sparse: create a sparse matrix copy of a factor -//------------------------------------------------------------------------------ +/* -------------------------------------------------------------------------- */ +/* cholmod_factor_to_sparse: create a sparse matrix copy of a factor */ +/* -------------------------------------------------------------------------- */ + +/* Only operates on numeric factors, not symbolic ones */ -cholmod_sparse *cholmod_factor_to_sparse // return a new sparse matrix +cholmod_sparse *cholmod_factor_to_sparse ( - cholmod_factor *L, // input: factor to convert; output: L is converted - // to a simplicial symbolic factor + /* ---- in/out --- */ + cholmod_factor *L, /* factor to copy, converted to symbolic on output */ + /* --------------- */ cholmod_common *Common ) ; + cholmod_sparse *cholmod_l_factor_to_sparse (cholmod_factor *, - cholmod_common *) ; + cholmod_common *) ; -//------------------------------------------------------------------------------ -// cholmod_copy_factor: create a copy of a factor -//------------------------------------------------------------------------------ +/* -------------------------------------------------------------------------- */ +/* cholmod_copy_factor: create a copy of a factor */ +/* -------------------------------------------------------------------------- */ -cholmod_factor *cholmod_copy_factor // return a copy of the factor +cholmod_factor *cholmod_copy_factor ( - cholmod_factor *L, // factor to copy (not modified) + /* ---- input ---- */ + cholmod_factor *L, /* factor to copy */ + /* --------------- */ cholmod_common *Common ) ; + cholmod_factor *cholmod_l_copy_factor (cholmod_factor *, cholmod_common *) ; -//------------------------------------------------------------------------------ -// cholmod_factor_xtype: change the xtype and/or dtype of a factor -//------------------------------------------------------------------------------ +/* -------------------------------------------------------------------------- */ +/* cholmod_factor_xtype: change the xtype of a factor */ +/* -------------------------------------------------------------------------- */ int cholmod_factor_xtype ( - int to_xdtype, // requested xtype and dtype - cholmod_factor *L, // factor to change + /* ---- input ---- */ + int to_xtype, /* requested xtype (real, complex, or zomplex) */ + /* ---- in/out --- */ + cholmod_factor *L, /* factor to change */ + /* --------------- */ cholmod_common *Common ) ; + int cholmod_l_factor_xtype (int, cholmod_factor *, cholmod_common *) ; -//============================================================================== -// cholmod_dense: a dense matrix, held by column -//============================================================================== + +/* ========================================================================== */ +/* === Core/cholmod_dense =================================================== */ +/* ========================================================================== */ + +/* A dense matrix in column-oriented form. It has no itype since it contains + * no integers. Entry in row i and column j is located in x [i+j*d]. + */ typedef struct cholmod_dense_struct { - size_t nrow ; // the matrix is nrow-by-ncol + size_t nrow ; /* the matrix is nrow-by-ncol */ size_t ncol ; - size_t nzmax ; // maximum number of entries in the matrix - size_t d ; // leading dimension (d >= nrow must hold) - void *x ; // size nzmax or 2*nzmax, if present - void *z ; // size nzmax, if present - int xtype ; // pattern, real, complex, or zomplex - int dtype ; // x and z double or single + size_t nzmax ; /* maximum number of entries in the matrix */ + size_t d ; /* leading dimension (d >= nrow must hold) */ + void *x ; /* size nzmax or 2*nzmax, if present */ + void *z ; /* size nzmax, if present */ + int xtype ; /* pattern, real, complex, or zomplex */ + int dtype ; /* x and z double or float */ } cholmod_dense ; -//------------------------------------------------------------------------------ -// cholmod_allocate_dense: allocate a dense matrix (contents not initialized) -//------------------------------------------------------------------------------ +/* -------------------------------------------------------------------------- */ +/* cholmod_allocate_dense: allocate a dense matrix (contents uninitialized) */ +/* -------------------------------------------------------------------------- */ cholmod_dense *cholmod_allocate_dense ( - size_t nrow, // # of rows - size_t ncol, // # of columns - size_t d, // leading dimension - int xdtype, // xtype + dtype of the matrix: - // (CHOLMOD_DOUBLE, _SINGLE) + - // (CHOLMOD_REAL, _COMPLEX, or _ZOMPLEX) + /* ---- input ---- */ + size_t nrow, /* # of rows of matrix */ + size_t ncol, /* # of columns of matrix */ + size_t d, /* leading dimension */ + int xtype, /* CHOLMOD_REAL, _COMPLEX, or _ZOMPLEX */ + /* --------------- */ cholmod_common *Common ) ; + cholmod_dense *cholmod_l_allocate_dense (size_t, size_t, size_t, int, cholmod_common *) ; -//------------------------------------------------------------------------------ -// cholmod_zeros: allocate a dense matrix and set it to zero -//------------------------------------------------------------------------------ +/* -------------------------------------------------------------------------- */ +/* cholmod_zeros: allocate a dense matrix and set it to zero */ +/* -------------------------------------------------------------------------- */ cholmod_dense *cholmod_zeros ( - size_t nrow, // # of rows - size_t ncol, // # of columns - int xdtype, // xtype + dtype of the matrix: - // (CHOLMOD_DOUBLE, _SINGLE) + - // (CHOLMOD_REAL, _COMPLEX, or _ZOMPLEX) + /* ---- input ---- */ + size_t nrow, /* # of rows of matrix */ + size_t ncol, /* # of columns of matrix */ + int xtype, /* CHOLMOD_REAL, _COMPLEX, or _ZOMPLEX */ + /* --------------- */ cholmod_common *Common ) ; + cholmod_dense *cholmod_l_zeros (size_t, size_t, int, cholmod_common *) ; -//------------------------------------------------------------------------------ -// cholmod_ones: allocate a dense matrix of all 1's -//------------------------------------------------------------------------------ +/* -------------------------------------------------------------------------- */ +/* cholmod_ones: allocate a dense matrix and set it to all ones */ +/* -------------------------------------------------------------------------- */ cholmod_dense *cholmod_ones ( - size_t nrow, // # of rows - size_t ncol, // # of columns - int xdtype, // xtype + dtype of the matrix: - // (CHOLMOD_DOUBLE, _SINGLE) + - // (_REAL, _COMPLEX, or _ZOMPLEX) + /* ---- input ---- */ + size_t nrow, /* # of rows of matrix */ + size_t ncol, /* # of columns of matrix */ + int xtype, /* CHOLMOD_REAL, _COMPLEX, or _ZOMPLEX */ + /* --------------- */ cholmod_common *Common ) ; + cholmod_dense *cholmod_l_ones (size_t, size_t, int, cholmod_common *) ; -//------------------------------------------------------------------------------ -// cholmod_eye: allocate a dense identity matrix -//------------------------------------------------------------------------------ +/* -------------------------------------------------------------------------- */ +/* cholmod_eye: allocate a dense matrix and set it to the identity matrix */ +/* -------------------------------------------------------------------------- */ -cholmod_dense *cholmod_eye // return a dense identity matrix +cholmod_dense *cholmod_eye ( - size_t nrow, // # of rows - size_t ncol, // # of columns - int xdtype, // xtype + dtype of the matrix: - // (CHOLMOD_DOUBLE, _SINGLE) + - // (_REAL, _COMPLEX, or _ZOMPLEX) + /* ---- input ---- */ + size_t nrow, /* # of rows of matrix */ + size_t ncol, /* # of columns of matrix */ + int xtype, /* CHOLMOD_REAL, _COMPLEX, or _ZOMPLEX */ + /* --------------- */ cholmod_common *Common ) ; + cholmod_dense *cholmod_l_eye (size_t, size_t, int, cholmod_common *) ; -//------------------------------------------------------------------------------ -// cholmod_free_dense: free a dense matrix -//------------------------------------------------------------------------------ +/* -------------------------------------------------------------------------- */ +/* cholmod_free_dense: free a dense matrix */ +/* -------------------------------------------------------------------------- */ int cholmod_free_dense ( - cholmod_dense **X, // handle of dense matrix to free + /* ---- in/out --- */ + cholmod_dense **X, /* dense matrix to deallocate, NULL on output */ + /* --------------- */ cholmod_common *Common ) ; + int cholmod_l_free_dense (cholmod_dense **, cholmod_common *) ; -//------------------------------------------------------------------------------ -// cholmod_ensure_dense: ensure a dense matrix has a given size and type -//------------------------------------------------------------------------------ +/* -------------------------------------------------------------------------- */ +/* cholmod_ensure_dense: ensure a dense matrix has a given size and type */ +/* -------------------------------------------------------------------------- */ cholmod_dense *cholmod_ensure_dense ( - cholmod_dense **X, // matrix to resize as needed (*X may be NULL) - size_t nrow, // # of rows - size_t ncol, // # of columns - size_t d, // leading dimension - int xdtype, // xtype + dtype of the matrix: - // (CHOLMOD_DOUBLE, _SINGLE) + - // (CHOLMOD_REAL, _COMPLEX, or _ZOMPLEX) + /* ---- input/output ---- */ + cholmod_dense **XHandle, /* matrix handle to check */ + /* ---- input ---- */ + size_t nrow, /* # of rows of matrix */ + size_t ncol, /* # of columns of matrix */ + size_t d, /* leading dimension */ + int xtype, /* CHOLMOD_REAL, _COMPLEX, or _ZOMPLEX */ + /* --------------- */ cholmod_common *Common ) ; -cholmod_dense *cholmod_l_ensure_dense (cholmod_dense **, size_t, size_t, - size_t, int, cholmod_common *) ; - -//------------------------------------------------------------------------------ -// cholmod_sparse_to_dense: create a dense matrix copy of a sparse matrix -//------------------------------------------------------------------------------ -cholmod_dense *cholmod_sparse_to_dense // return a dense matrix -( - cholmod_sparse *A, // input matrix - cholmod_common *Common -) ; -cholmod_dense *cholmod_l_sparse_to_dense (cholmod_sparse *, cholmod_common *) ; +cholmod_dense *cholmod_l_ensure_dense (cholmod_dense **, size_t, size_t, size_t, + int, cholmod_common *) ; -//------------------------------------------------------------------------------ -// cholmod_dense_nnz: count # of nonzeros in a dense matrix -//------------------------------------------------------------------------------ +/* -------------------------------------------------------------------------- */ +/* cholmod_sparse_to_dense: create a dense matrix copy of a sparse matrix */ +/* -------------------------------------------------------------------------- */ -int64_t cholmod_dense_nnz // return # of entries in the dense matrix +cholmod_dense *cholmod_sparse_to_dense ( - cholmod_dense *X, // input matrix + /* ---- input ---- */ + cholmod_sparse *A, /* matrix to copy */ + /* --------------- */ cholmod_common *Common ) ; -int64_t cholmod_l_dense_nnz (cholmod_dense *, cholmod_common *) ; -//------------------------------------------------------------------------------ -// cholmod_dense_to_sparse: create a sparse matrix copy of a dense matrix -//------------------------------------------------------------------------------ +cholmod_dense *cholmod_l_sparse_to_dense (cholmod_sparse *, + cholmod_common *) ; + +/* -------------------------------------------------------------------------- */ +/* cholmod_dense_to_sparse: create a sparse matrix copy of a dense matrix */ +/* -------------------------------------------------------------------------- */ -cholmod_sparse *cholmod_dense_to_sparse // return a sparse matrix C +cholmod_sparse *cholmod_dense_to_sparse ( - cholmod_dense *X, // input matrix - int values, // if true, copy the values; if false, C is pattern + /* ---- input ---- */ + cholmod_dense *X, /* matrix to copy */ + int values, /* TRUE if values to be copied, FALSE otherwise */ + /* --------------- */ cholmod_common *Common ) ; + cholmod_sparse *cholmod_l_dense_to_sparse (cholmod_dense *, int, cholmod_common *) ; -//------------------------------------------------------------------------------ -// cholmod_copy_dense: create a copy of a dense matrix -//------------------------------------------------------------------------------ +/* -------------------------------------------------------------------------- */ +/* cholmod_copy_dense: create a copy of a dense matrix */ +/* -------------------------------------------------------------------------- */ -cholmod_dense *cholmod_copy_dense // returns new dense matrix +cholmod_dense *cholmod_copy_dense ( - cholmod_dense *X, // input dense matrix + /* ---- input ---- */ + cholmod_dense *X, /* matrix to copy */ + /* --------------- */ cholmod_common *Common ) ; + cholmod_dense *cholmod_l_copy_dense (cholmod_dense *, cholmod_common *) ; -//------------------------------------------------------------------------------ -// cholmod_copy_dense2: copy a dense matrix (pre-allocated) -//------------------------------------------------------------------------------ +/* -------------------------------------------------------------------------- */ +/* cholmod_copy_dense2: copy a dense matrix (pre-allocated) */ +/* -------------------------------------------------------------------------- */ int cholmod_copy_dense2 ( - cholmod_dense *X, // input dense matrix - cholmod_dense *Y, // output dense matrix (already allocated on input) + /* ---- input ---- */ + cholmod_dense *X, /* matrix to copy */ + /* ---- output --- */ + cholmod_dense *Y, /* copy of matrix X */ + /* --------------- */ cholmod_common *Common ) ; + int cholmod_l_copy_dense2 (cholmod_dense *, cholmod_dense *, cholmod_common *) ; -//------------------------------------------------------------------------------ -// cholmod_dense_xtype: change the xtype and/or dtype of a dense matrix -//------------------------------------------------------------------------------ +/* -------------------------------------------------------------------------- */ +/* cholmod_dense_xtype: change the xtype of a dense matrix */ +/* -------------------------------------------------------------------------- */ int cholmod_dense_xtype ( - int to_xdtype, // requested xtype and dtype - cholmod_dense *X, // dense matrix to change + /* ---- input ---- */ + int to_xtype, /* requested xtype (real, complex,or zomplex) */ + /* ---- in/out --- */ + cholmod_dense *X, /* dense matrix to change */ + /* --------------- */ cholmod_common *Common ) ; + int cholmod_l_dense_xtype (int, cholmod_dense *, cholmod_common *) ; -//============================================================================= -// cholmod_triplet: a sparse matrix in triplet form -//============================================================================= + +/* ========================================================================== */ +/* === Core/cholmod_triplet ================================================= */ +/* ========================================================================== */ + +/* A sparse matrix stored in triplet form. */ typedef struct cholmod_triplet_struct { - size_t nrow ; // # of rows of the matrix - size_t ncol ; // # of colums of the matrix - size_t nzmax ; // max # of entries that can be held in the matrix - size_t nnz ; // current # of entries can be held in the matrix - - // int32 or int64 arrays (depending on T->itype) - void *i ; // i [0..nzmax-1], the row indices - void *j ; // j [0..nzmax-1], the column indices - - // double or float arrays: - void *x ; // size nzmax or 2*nzmax, or NULL - void *z ; // size nzmax, or NULL - - int stype ; // T->stype defines what parts of the matrix is held: - // 0: the matrix is unsymmetric with both lower and upper parts stored. - // >0: the matrix is square and symmetric, where entries in the lower - // triangular part are transposed and placed in the upper - // triangular part of A if T is converted into a sparse matrix A. - // <0: the matrix is square and symmetric, where entries in the upper - // triangular part are transposed and placed in the lower - // triangular part of A if T is converted into a sparse matrix A. - // - // Note that A->stype (for a sparse matrix) and T->stype (for a - // triplet matrix) are handled differently. In a triplet matrix T, - // no entry is ever ignored. For a sparse matrix A, if A->stype < 0 - // or A->stype > 0, then entries not in the correct triangular part - // are ignored. - - int itype ; // T->itype defines the integers used for T->i and T->j. - // if CHOLMOD_INT, these arrays are all of type int32_t. - // if CHOLMOD_LONG, these arrays are all of type int64_t. - int xtype ; // pattern, real, complex, or zomplex - int dtype ; // x and z are double or single + size_t nrow ; /* the matrix is nrow-by-ncol */ + size_t ncol ; + size_t nzmax ; /* maximum number of entries in the matrix */ + size_t nnz ; /* number of nonzeros in the matrix */ + + void *i ; /* i [0..nzmax-1], the row indices */ + void *j ; /* j [0..nzmax-1], the column indices */ + void *x ; /* size nzmax or 2*nzmax, if present */ + void *z ; /* size nzmax, if present */ + + int stype ; /* Describes what parts of the matrix are considered: + * + * 0: matrix is "unsymmetric": use both upper and lower triangular parts + * (the matrix may actually be symmetric in pattern and value, but + * both parts are explicitly stored and used). May be square or + * rectangular. + * >0: matrix is square and symmetric. Entries in the lower triangular + * part are transposed and added to the upper triangular part when + * the matrix is converted to cholmod_sparse form. + * <0: matrix is square and symmetric. Entries in the upper triangular + * part are transposed and added to the lower triangular part when + * the matrix is converted to cholmod_sparse form. + * + * Note that stype>0 and stype<0 are different for cholmod_sparse and + * cholmod_triplet. The reason is simple. You can permute a symmetric + * triplet matrix by simply replacing a row and column index with their + * new row and column indices, via an inverse permutation. Suppose + * P = L->Perm is your permutation, and Pinv is an array of size n. + * Suppose a symmetric matrix A is represent by a triplet matrix T, with + * entries only in the upper triangular part. Then the following code: + * + * Ti = T->i ; + * Tj = T->j ; + * for (k = 0 ; k < n ; k++) Pinv [P [k]] = k ; + * for (k = 0 ; k < nz ; k++) Ti [k] = Pinv [Ti [k]] ; + * for (k = 0 ; k < nz ; k++) Tj [k] = Pinv [Tj [k]] ; + * + * creates the triplet form of C=P*A*P'. However, if T initially + * contains just the upper triangular entries (T->stype = 1), after + * permutation it has entries in both the upper and lower triangular + * parts. These entries should be transposed when constructing the + * cholmod_sparse form of A, which is what cholmod_triplet_to_sparse + * does. Thus: + * + * C = cholmod_triplet_to_sparse (T, 0, &Common) ; + * + * will return the matrix C = P*A*P'. + * + * Since the triplet matrix T is so simple to generate, it's quite easy + * to remove entries that you do not want, prior to converting T to the + * cholmod_sparse form. So if you include these entries in T, CHOLMOD + * assumes that there must be a reason (such as the one above). Thus, + * no entry in a triplet matrix is ever ignored. + */ + + int itype ; /* CHOLMOD_LONG: i and j are int64_t. Otherwise int */ + int xtype ; /* pattern, real, complex, or zomplex */ + int dtype ; /* x and z are double or float */ } cholmod_triplet ; -//------------------------------------------------------------------------------ -// cholmod_allocate_triplet: allocate a triplet matrix -//------------------------------------------------------------------------------ +/* -------------------------------------------------------------------------- */ +/* cholmod_allocate_triplet: allocate a triplet matrix */ +/* -------------------------------------------------------------------------- */ -cholmod_triplet *cholmod_allocate_triplet // return triplet matrix T +cholmod_triplet *cholmod_allocate_triplet ( - size_t nrow, // # of rows - size_t ncol, // # of columns - size_t nzmax, // max # of entries the matrix can hold - int stype, // the stype of the matrix (unsym, tril, or triu) - int xdtype, // xtype + dtype of the matrix: - // (CHOLMOD_DOUBLE, _SINGLE) + - // (CHOLMOD_PATTERN, _REAL, _COMPLEX, or _ZOMPLEX) + /* ---- input ---- */ + size_t nrow, /* # of rows of T */ + size_t ncol, /* # of columns of T */ + size_t nzmax, /* max # of nonzeros of T */ + int stype, /* stype of T */ + int xtype, /* CHOLMOD_PATTERN, _REAL, _COMPLEX, or _ZOMPLEX */ + /* --------------- */ cholmod_common *Common ) ; + cholmod_triplet *cholmod_l_allocate_triplet (size_t, size_t, size_t, int, int, cholmod_common *) ; -//------------------------------------------------------------------------------ -// cholmod_free_triplet: free a triplet matrix -//------------------------------------------------------------------------------ +/* -------------------------------------------------------------------------- */ +/* cholmod_free_triplet: free a triplet matrix */ +/* -------------------------------------------------------------------------- */ int cholmod_free_triplet ( - cholmod_triplet **T, // handle of triplet matrix to free + /* ---- in/out --- */ + cholmod_triplet **T, /* triplet matrix to deallocate, NULL on output */ + /* --------------- */ cholmod_common *Common ) ; + int cholmod_l_free_triplet (cholmod_triplet **, cholmod_common *) ; -//------------------------------------------------------------------------------ -// cholmod_reallocate_triplet: change max # of entries in a triplet matrix -//------------------------------------------------------------------------------ +/* -------------------------------------------------------------------------- */ +/* cholmod_reallocate_triplet: change the # of entries in a triplet matrix */ +/* -------------------------------------------------------------------------- */ int cholmod_reallocate_triplet ( - size_t nznew, // new max # of nonzeros the triplet matrix can hold - cholmod_triplet *T, // triplet matrix to reallocate + /* ---- input ---- */ + size_t nznew, /* new # of entries in T */ + /* ---- in/out --- */ + cholmod_triplet *T, /* triplet matrix to modify */ + /* --------------- */ cholmod_common *Common ) ; + int cholmod_l_reallocate_triplet (size_t, cholmod_triplet *, cholmod_common *) ; -//------------------------------------------------------------------------------ -// cholmod_sparse_to_triplet: create a triplet matrix copy of a sparse matrix -//------------------------------------------------------------------------------ +/* -------------------------------------------------------------------------- */ +/* cholmod_sparse_to_triplet: create a triplet matrix copy of a sparse matrix*/ +/* -------------------------------------------------------------------------- */ cholmod_triplet *cholmod_sparse_to_triplet ( - cholmod_sparse *A, // matrix to copy into triplet form T + /* ---- input ---- */ + cholmod_sparse *A, /* matrix to copy */ + /* --------------- */ cholmod_common *Common ) ; + cholmod_triplet *cholmod_l_sparse_to_triplet (cholmod_sparse *, cholmod_common *) ; -//------------------------------------------------------------------------------ -// cholmod_triplet_to_sparse: create a sparse matrix from of triplet matrix -//------------------------------------------------------------------------------ +/* -------------------------------------------------------------------------- */ +/* cholmod_triplet_to_sparse: create a sparse matrix copy of a triplet matrix*/ +/* -------------------------------------------------------------------------- */ -cholmod_sparse *cholmod_triplet_to_sparse // return sparse matrix A +cholmod_sparse *cholmod_triplet_to_sparse ( - cholmod_triplet *T, // input triplet matrix - size_t nzmax, // allocate space for max(nzmax,nnz(A)) entries + /* ---- input ---- */ + cholmod_triplet *T, /* matrix to copy */ + size_t nzmax, /* allocate at least this much space in output matrix */ + /* --------------- */ cholmod_common *Common ) ; + cholmod_sparse *cholmod_l_triplet_to_sparse (cholmod_triplet *, size_t, cholmod_common *) ; -//------------------------------------------------------------------------------ -// cholmod_copy_triplet: copy a triplet matrix -//------------------------------------------------------------------------------ +/* -------------------------------------------------------------------------- */ +/* cholmod_copy_triplet: create a copy of a triplet matrix */ +/* -------------------------------------------------------------------------- */ -cholmod_triplet *cholmod_copy_triplet // return new triplet matrix +cholmod_triplet *cholmod_copy_triplet ( - cholmod_triplet *T, // triplet matrix to copy + /* ---- input ---- */ + cholmod_triplet *T, /* matrix to copy */ + /* --------------- */ cholmod_common *Common ) ; + cholmod_triplet *cholmod_l_copy_triplet (cholmod_triplet *, cholmod_common *) ; -//------------------------------------------------------------------------------ -// cholmod_triplet_xtype: change the xtype and/or dtype of a triplet matrix -//------------------------------------------------------------------------------ +/* -------------------------------------------------------------------------- */ +/* cholmod_triplet_xtype: change the xtype of a triplet matrix */ +/* -------------------------------------------------------------------------- */ int cholmod_triplet_xtype ( - int to_xdtype, // requested xtype and dtype - cholmod_triplet *T, // triplet matrix to change + /* ---- input ---- */ + int to_xtype, /* requested xtype (pattern, real, complex,or zomplex)*/ + /* ---- in/out --- */ + cholmod_triplet *T, /* triplet matrix to change */ + /* --------------- */ cholmod_common *Common ) ; + int cholmod_l_triplet_xtype (int, cholmod_triplet *, cholmod_common *) ; -//============================================================================== -// memory allocation -//============================================================================== -// These methods act like malloc/calloc/realloc/free, with some differences. -// They are simple wrappers around the memory management functions in -// SuiteSparse_config. cholmod_malloc and cholmod_calloc have the same -// signature, unlike malloc and calloc. If cholmod_free is given a NULL -// pointer, it safely does nothing. cholmod_free must be passed the size of -// the object being freed, but that is just to keep track of memory usage -// statistics. cholmod_realloc does not return NULL if it fails; instead, it -// returns the pointer to the unmodified block of memory. +/* ========================================================================== */ +/* === Core/cholmod_memory ================================================== */ +/* ========================================================================== */ + +/* The user may make use of these, just like malloc and free. You can even + * malloc an object and safely free it with cholmod_free, and visa versa + * (except that the memory usage statistics will be corrupted). These routines + * do differ from malloc and free. If cholmod_free is given a NULL pointer, + * for example, it does nothing (unlike the ANSI free). cholmod_realloc does + * not return NULL if given a non-NULL pointer and a nonzero size, even if it + * fails (it returns the original pointer and sets an error code in + * Common->status instead). + * + * CHOLMOD keeps track of the amount of memory it has allocated, and so the + * cholmod_free routine also takes the size of the object being freed. This + * is only used for statistics. If you, the user of CHOLMOD, pass the wrong + * size, the only consequence is that the memory usage statistics will be + * corrupted. + */ -void *cholmod_malloc // return pointer to newly allocated memory +void *cholmod_malloc /* returns pointer to the newly malloc'd block */ ( - size_t n, // number of items - size_t size, // size of each item + /* ---- input ---- */ + size_t n, /* number of items */ + size_t size, /* size of each item */ + /* --------------- */ cholmod_common *Common ) ; + void *cholmod_l_malloc (size_t, size_t, cholmod_common *) ; -void *cholmod_calloc // return pointer to newly allocated memory +void *cholmod_calloc /* returns pointer to the newly calloc'd block */ ( - size_t n, // number of items - size_t size, // size of each item + /* ---- input ---- */ + size_t n, /* number of items */ + size_t size, /* size of each item */ + /* --------------- */ cholmod_common *Common ) ; + void *cholmod_l_calloc (size_t, size_t, cholmod_common *) ; -void *cholmod_free // returns NULL to simplify its usage +void *cholmod_free /* always returns NULL */ ( - size_t n, // number of items - size_t size, // size of each item - void *p, // memory to free + /* ---- input ---- */ + size_t n, /* number of items */ + size_t size, /* size of each item */ + /* ---- in/out --- */ + void *p, /* block of memory to free */ + /* --------------- */ cholmod_common *Common ) ; + void *cholmod_l_free (size_t, size_t, void *, cholmod_common *) ; -void *cholmod_realloc // return newly reallocated block of memory +void *cholmod_realloc /* returns pointer to reallocated block */ ( - size_t nnew, // # of items in newly reallocate memory - size_t size, // size of each item - void *p, // pointer to memory to reallocate (may be NULL) - size_t *n, // # of items in p on input; nnew on output if success + /* ---- input ---- */ + size_t nnew, /* requested # of items in reallocated block */ + size_t size, /* size of each item */ + /* ---- in/out --- */ + void *p, /* block of memory to realloc */ + size_t *n, /* current size on input, nnew on output if successful*/ + /* --------------- */ cholmod_common *Common ) ; + void *cholmod_l_realloc (size_t, size_t, void *, size_t *, cholmod_common *) ; -int cholmod_realloc_multiple // returns true if successful, false otherwise +int cholmod_realloc_multiple ( - size_t nnew, // # of items in newly reallocate memory - int nint, // 0: do not allocate I or J, 1: just I, 2: both I and J - int xdtype, // xtype + dtype of the matrix: - // (CHOLMOD_DOUBLE, _SINGLE) + - // (CHOLMOD_PATTERN, _REAL, _COMPLEX, or _ZOMPLEX) - // input/output: - void **I, // integer block of memory (int32_t or int64_t) - void **J, // integer block of memory (int32_t or int64_t) - void **X, // real or complex, double or single, block - void **Z, // zomplex only: double or single block - size_t *n, // current size of I, J, X, and/or Z blocks on input, - // changed to nnew on output, if successful + /* ---- input ---- */ + size_t nnew, /* requested # of items in reallocated blocks */ + int nint, /* number of int32_t/int64_t blocks */ + int xtype, /* CHOLMOD_PATTERN, _REAL, _COMPLEX, or _ZOMPLEX */ + /* ---- in/out --- */ + void **Iblock, /* int32_t or int64_t block */ + void **Jblock, /* int32_t or int64_t block */ + void **Xblock, /* complex, double, or float block */ + void **Zblock, /* zomplex case only: double or float block */ + size_t *n, /* current size of the I,J,X,Z blocks on input, + * nnew on output if successful */ + /* --------------- */ cholmod_common *Common ) ; + int cholmod_l_realloc_multiple (size_t, int, int, void **, void **, void **, void **, size_t *, cholmod_common *) ; -//============================================================================== -// numerical comparisons -//============================================================================== +/* ========================================================================== */ +/* === version control ====================================================== */ +/* ========================================================================== */ + +int cholmod_version /* returns CHOLMOD_VERSION */ +( + /* output, contents not defined on input. Not used if NULL. + version [0] = CHOLMOD_MAIN_VERSION + version [1] = CHOLMOD_SUB_VERSION + version [2] = CHOLMOD_SUBSUB_VERSION + */ + int version [3] +) ; + +int cholmod_l_version (int version [3]) ; + +/* Versions prior to 2.1.1 do not have the above function. The following + code fragment will work with any version of CHOLMOD: + #ifdef CHOLMOD_HAS_VERSION_FUNCTION + v = cholmod_version (NULL) ; + #else + v = CHOLMOD_VERSION ; + #endif +*/ + +/* ========================================================================== */ +/* === symmetry types ======================================================= */ +/* ========================================================================== */ + +#define CHOLMOD_MM_RECTANGULAR 1 +#define CHOLMOD_MM_UNSYMMETRIC 2 +#define CHOLMOD_MM_SYMMETRIC 3 +#define CHOLMOD_MM_HERMITIAN 4 +#define CHOLMOD_MM_SKEW_SYMMETRIC 5 +#define CHOLMOD_MM_SYMMETRIC_POSDIAG 6 +#define CHOLMOD_MM_HERMITIAN_POSDIAG 7 + +/* ========================================================================== */ +/* === Numerical relop macros =============================================== */ +/* ========================================================================== */ -// These macros were different on Windows for older versions of CHOLMOD. -// They are no longer needed but are kept for backward compatibility. +/* These macros correctly handle the NaN case. + * + * CHOLMOD_IS_NAN(x): + * True if x is NaN. False otherwise. The commonly-existing isnan(x) + * function could be used, but it's not in Kernighan & Ritchie 2nd edition + * (ANSI C89). It may appear in , but I'm not certain about + * portability. The expression x != x is true if and only if x is NaN, + * according to the IEEE 754 floating-point standard. + * + * CHOLMOD_IS_ZERO(x): + * True if x is zero. False if x is nonzero, NaN, or +/- Inf. + * This is (x == 0) if the compiler is IEEE 754 compliant. + * + * CHOLMOD_IS_NONZERO(x): + * True if x is nonzero, NaN, or +/- Inf. False if x zero. + * This is (x != 0) if the compiler is IEEE 754 compliant. + * + * CHOLMOD_IS_LT_ZERO(x): + * True if x is < zero or -Inf. False if x is >= 0, NaN, or +Inf. + * This is (x < 0) if the compiler is IEEE 754 compliant. + * + * CHOLMOD_IS_GT_ZERO(x): + * True if x is > zero or +Inf. False if x is <= 0, NaN, or -Inf. + * This is (x > 0) if the compiler is IEEE 754 compliant. + * + * CHOLMOD_IS_LE_ZERO(x): + * True if x is <= zero or -Inf. False if x is > 0, NaN, or +Inf. + * This is (x <= 0) if the compiler is IEEE 754 compliant. + */ -#define CHOLMOD_IS_NAN(x) isnan (x) -#define CHOLMOD_IS_ZERO(x) ((x) == 0.) -#define CHOLMOD_IS_NONZERO(x) ((x) != 0.) -#define CHOLMOD_IS_LT_ZERO(x) ((x) < 0.) -#define CHOLMOD_IS_GT_ZERO(x) ((x) > 0.) -#define CHOLMOD_IS_LE_ZERO(x) ((x) <= 0.) +#ifdef CHOLMOD_WINDOWS + +/* Yes, this is exceedingly ugly. Blame Microsoft, which hopelessly */ +/* violates the IEEE 754 floating-point standard in a bizarre way. */ +/* If you're using an IEEE 754-compliant compiler, then x != x is true */ +/* iff x is NaN. For Microsoft, (x < x) is true iff x is NaN. */ +/* So either way, this macro safely detects a NaN. */ +#define CHOLMOD_IS_NAN(x) (((x) != (x)) || (((x) < (x)))) +#define CHOLMOD_IS_ZERO(x) (((x) == 0.) && !CHOLMOD_IS_NAN(x)) +#define CHOLMOD_IS_NONZERO(x) (((x) != 0.) || CHOLMOD_IS_NAN(x)) +#define CHOLMOD_IS_LT_ZERO(x) (((x) < 0.) && !CHOLMOD_IS_NAN(x)) +#define CHOLMOD_IS_GT_ZERO(x) (((x) > 0.) && !CHOLMOD_IS_NAN(x)) +#define CHOLMOD_IS_LE_ZERO(x) (((x) <= 0.) && !CHOLMOD_IS_NAN(x)) + +#else + +/* These all work properly, according to the IEEE 754 standard ... except on */ +/* a PC with windows. Works fine in Linux on the same PC... */ +#define CHOLMOD_IS_NAN(x) ((x) != (x)) +#define CHOLMOD_IS_ZERO(x) ((x) == 0.) +#define CHOLMOD_IS_NONZERO(x) ((x) != 0.) +#define CHOLMOD_IS_LT_ZERO(x) ((x) < 0.) +#define CHOLMOD_IS_GT_ZERO(x) ((x) > 0.) +#define CHOLMOD_IS_LE_ZERO(x) ((x) <= 0.) #endif -//============================================================================== -// CHOLMOD:Check Module -//============================================================================== -#ifndef NCHECK -/* Routines that check and print the 5 basic data types in CHOLMOD, and 3 kinds + +/* ========================================================================== */ +/* === Include/cholmod_check.h ============================================== */ +/* ========================================================================== */ + +/* CHOLMOD Check module. + * + * Routines that check and print the 5 basic data types in CHOLMOD, and 3 kinds * of integer vectors (subset, perm, and parent), and read in matrices from a * file: * @@ -1959,13 +2684,15 @@ int cholmod_l_realloc_multiple (size_t, int, int, void **, void **, void **, * cholmod_print_common and cholmod_check_common are the only two routines that * you may call after calling cholmod_finish. * - * Requires the Utility module. Not required by any CHOLMOD module, except when + * Requires the Core module. Not required by any CHOLMOD module, except when * debugging is enabled (in which case all modules require the Check module). * * See cholmod_read.c for a description of the file formats supported by the * cholmod_read_* routines. */ +#ifndef NCHECK + /* -------------------------------------------------------------------------- */ /* cholmod_check_common: check the Common object */ /* -------------------------------------------------------------------------- */ @@ -2112,8 +2839,7 @@ int cholmod_print_triplet cholmod_common *Common ) ; -int cholmod_l_print_triplet (cholmod_triplet *, const char *, - cholmod_common *) ; +int cholmod_l_print_triplet (cholmod_triplet *, const char *, cholmod_common *); /* -------------------------------------------------------------------------- */ /* cholmod_check_subset: check a subset */ @@ -2256,7 +2982,7 @@ cholmod_dense *cholmod_read_dense cholmod_common *Common ) ; -cholmod_dense *cholmod_l_read_dense (FILE *, cholmod_common *) ; +cholmod_dense *cholmod_l_read_dense (FILE *, cholmod_common *) ; /* -------------------------------------------------------------------------- */ /* cholmod_read_matrix: read a sparse or dense matrix from a file */ @@ -2292,7 +3018,7 @@ void *cholmod_l_read_matrix (FILE *, int, int *, cholmod_common *) ; /* cholmod_write_sparse: write a sparse matrix to a file */ /* -------------------------------------------------------------------------- */ -int cholmod_write_sparse // returns the same result as cholmod_symmetry +int cholmod_write_sparse ( /* ---- input ---- */ FILE *f, /* file to write to, must already be open */ @@ -2322,21 +3048,25 @@ int cholmod_write_dense int cholmod_l_write_dense (FILE *, cholmod_dense *, const char *, cholmod_common *) ; - #endif -//============================================================================== -// CHOLMOD:Cholesky Module -//============================================================================== -#ifndef NCHOLESKY -/* Sparse Cholesky routines: analysis, factorization, and solve. + + + +/* ========================================================================== */ +/* === Include/cholmod_cholesky.h =========================================== */ +/* ========================================================================== */ + +/* CHOLMOD Cholesky module. + * + * Sparse Cholesky routines: analysis, factorization, and solve. * * The primary routines are all that a user requires to order, analyze, and * factorize a sparse symmetric positive definite matrix A (or A*A'), and * to solve Ax=b (or A*A'x=b). The primary routines rely on the secondary - * routines, the CHOLMOD Utility module, and the AMD and COLAMD packages. They + * routines, the CHOLMOD Core module, and the AMD and COLAMD packages. They * make optional use of the CHOLMOD Supernodal and Partition modules, the * METIS package, and the CCOLAMD package. * @@ -2367,11 +3097,13 @@ int cholmod_l_write_dense (FILE *, cholmod_dense *, const char *, * cholmod_resymbol_noperm recompute the symbolic pattern of L, no L->Perm * cholmod_postorder postorder a tree * - * Requires the Utility module, and two packages: AMD and COLAMD. + * Requires the Core module, and two packages: AMD and COLAMD. * Optionally uses the Supernodal and Partition modules. * Required by the Partition module. */ +#ifndef NCHOLESKY + /* -------------------------------------------------------------------------- */ /* cholmod_analyze: order and analyze (simplicial or supernodal) */ /* -------------------------------------------------------------------------- */ @@ -2379,7 +3111,7 @@ int cholmod_l_write_dense (FILE *, cholmod_dense *, const char *, /* Orders and analyzes A, AA', PAP', or PAA'P' and returns a symbolic factor * that can later be passed to cholmod_factorize. */ -cholmod_factor *cholmod_analyze // order and analyze +cholmod_factor *cholmod_analyze ( /* ---- input ---- */ cholmod_sparse *A, /* matrix to order and analyze */ @@ -2442,7 +3174,7 @@ cholmod_factor *cholmod_l_analyze_p2 (int, cholmod_sparse *, int64_t *, * routine a second time with another matrix. A must have the same nonzero * pattern as that passed to cholmod_analyze. */ -int cholmod_factorize // simplicial or superodal Cholesky factorization +int cholmod_factorize ( /* ---- input ---- */ cholmod_sparse *A, /* matrix to factorize */ @@ -2818,7 +3550,7 @@ int cholmod_l_row_lsubtree (cholmod_sparse *, int64_t *, size_t, * first permutes A according to L->Perm. A can be upper/lower/unsymmetric, * in contrast to cholmod_resymbol_noperm (which can be lower or unsym). */ -int cholmod_resymbol // recompute symbolic pattern of L +int cholmod_resymbol ( /* ---- input ---- */ cholmod_sparse *A, /* matrix to analyze */ @@ -2887,18 +3619,19 @@ int32_t cholmod_postorder /* return # of nodes postordered */ cholmod_common *Common ) ; -int64_t cholmod_l_postorder (int64_t *, size_t, int64_t *, int64_t *, - cholmod_common *) ; +int64_t cholmod_l_postorder (int64_t *, size_t, + int64_t *, int64_t *, cholmod_common *) ; #endif -//============================================================================== -// CHOLMOD:MatrixOps Module -//============================================================================== -#ifndef NMATRIXOPS +/* ========================================================================== */ +/* === Include/cholmod_matrixops.h ========================================== */ +/* ========================================================================== */ -/* Basic operations on sparse and dense matrices. +/* CHOLMOD MatrixOps module. + * + * Basic operations on sparse and dense matrices. * * cholmod_drop A = entries in A with abs. value >= tol * cholmod_norm_dense s = norm (X), 1-norm, inf-norm, or 2-norm @@ -2914,9 +3647,11 @@ int64_t cholmod_l_postorder (int64_t *, size_t, int64_t *, int64_t *, * X, Y: dense matrices (cholmod_dense) * s: scalar or vector * - * Requires the Utility module. Not required by any other CHOLMOD module. + * Requires the Core module. Not required by any other CHOLMOD module. */ +#ifndef NMATRIXOPS + /* -------------------------------------------------------------------------- */ /* cholmod_drop: drop entries with small absolute value */ /* -------------------------------------------------------------------------- */ @@ -3072,7 +3807,8 @@ cholmod_sparse *cholmod_submatrix ) ; cholmod_sparse *cholmod_l_submatrix (cholmod_sparse *, int64_t *, - int64_t, int64_t *, int64_t, int, int, cholmod_common *) ; + int64_t, int64_t *, int64_t, int, int, + cholmod_common *) ; /* -------------------------------------------------------------------------- */ /* cholmod_vertcat: C = [A ; B] */ @@ -3095,15 +3831,6 @@ cholmod_sparse *cholmod_l_vertcat (cholmod_sparse *, cholmod_sparse *, int, /* cholmod_symmetry: determine if a sparse matrix is symmetric */ /* -------------------------------------------------------------------------- */ -// returns one of the following: -#define CHOLMOD_MM_RECTANGULAR 1 -#define CHOLMOD_MM_UNSYMMETRIC 2 -#define CHOLMOD_MM_SYMMETRIC 3 -#define CHOLMOD_MM_HERMITIAN 4 -#define CHOLMOD_MM_SKEW_SYMMETRIC 5 -#define CHOLMOD_MM_SYMMETRIC_POSDIAG 6 -#define CHOLMOD_MM_HERMITIAN_POSDIAG 7 - int cholmod_symmetry ( /* ---- input ---- */ @@ -3118,16 +3845,18 @@ int cholmod_symmetry cholmod_common *Common ) ; -int cholmod_l_symmetry (cholmod_sparse *, int, int64_t *, int64_t *, int64_t *, - int64_t *, cholmod_common *) ; +int cholmod_l_symmetry (cholmod_sparse *, int, int64_t *, + int64_t *, int64_t *, int64_t *, + cholmod_common *) ; #endif -//============================================================================== -// CHOLMOD:Modify Module -//============================================================================== -#ifndef NMODIFY + + +/* ========================================================================== */ +/* === Include/cholmod_modify.h ============================================= */ +/* ========================================================================== */ /* ----------------------------------------------------------------------------- * CHOLMOD/Include/cholmod_modify.h. @@ -3135,11 +3864,13 @@ int cholmod_l_symmetry (cholmod_sparse *, int, int64_t *, int64_t *, int64_t *, * http://www.suitesparse.com * -------------------------------------------------------------------------- */ -/* Sparse Cholesky modification routines: update / downdate / rowadd / rowdel. +/* CHOLMOD Modify module. + * + * Sparse Cholesky modification routines: update / downdate / rowadd / rowdel. * Can also modify a corresponding solution to Lx=b when L is modified. This * module is most useful when applied on a Cholesky factorization computed by * the Cholesky module, but it does not actually require the Cholesky module. - * The Utility module can create an identity Cholesky factorization (LDL' where + * The Core module can create an identity Cholesky factorization (LDL' where * L=D=I) that can then by modified by these routines. * * Primary routines: @@ -3161,9 +3892,12 @@ int cholmod_l_symmetry (cholmod_sparse *, int, int64_t *, int64_t *, int64_t *, * cholmod_rowdel_solve delete a row, and downdate Lx=b * cholmod_rowdel_mark delete a row, and downdate solution to partial Lx=b * - * Requires the Utility module. Not required by any other CHOLMOD module. + * Requires the Core module. Not required by any other CHOLMOD module. */ + +#ifndef NMODIFY + /* -------------------------------------------------------------------------- */ /* cholmod_updown: multiple rank update/downdate */ /* -------------------------------------------------------------------------- */ @@ -3172,7 +3906,7 @@ int cholmod_l_symmetry (cholmod_sparse *, int, int64_t *, int64_t *, int64_t *, * (a downdate). The factor object L need not be an LDL' factorization; it * is converted to one if it isn't. */ -int cholmod_updown // update/downdate +int cholmod_updown ( /* ---- input ---- */ int update, /* TRUE for update, FALSE for downdate */ @@ -3182,8 +3916,9 @@ int cholmod_updown // update/downdate /* --------------- */ cholmod_common *Common ) ; -int cholmod_l_updown (int, cholmod_sparse *, cholmod_factor *, cholmod_common *) ; +int cholmod_l_updown (int, cholmod_sparse *, cholmod_factor *, + cholmod_common *) ; /* -------------------------------------------------------------------------- */ /* cholmod_updown_solve: update/downdate, and modify solution to Lx=b */ @@ -3295,7 +4030,7 @@ int cholmod_l_updown_mask2 (int, cholmod_sparse *, int64_t *, * computed as the factorization of the kth row/column of the matrix to * factorize, which is provided as a single n-by-1 sparse matrix R. */ -int cholmod_rowadd // add a row to an LDL' factorization +int cholmod_rowadd ( /* ---- input ---- */ size_t k, /* row/column index to add */ @@ -3373,7 +4108,7 @@ int cholmod_l_rowadd_mark (size_t, cholmod_sparse *, double *, * a little more time. */ -int cholmod_rowdel // delete a rw from an LDL' factorization +int cholmod_rowdel ( /* ---- input ---- */ size_t k, /* row/column index to delete */ @@ -3442,11 +4177,11 @@ int cholmod_l_rowdel_mark (size_t, cholmod_sparse *, double *, #endif -//============================================================================== -// CHOLMOD:Partition Module (CAMD, CCOLAMD, and CSYMAMD) -//============================================================================== -#ifndef NCAMD + +/* ========================================================================== */ +/* === Include/cholmod_camd.h =============================================== */ +/* ========================================================================== */ /* CHOLMOD Partition module, interface to CAMD, CCOLAMD, and CSYMAMD * @@ -3460,10 +4195,12 @@ int cholmod_l_rowdel_mark (size_t, cholmod_sparse *, double *, * cholmod_csymamd interface to CSYMAMD ordering * cholmod_camd interface to CAMD ordering * - * Requires the Utility and Cholesky modules, and two packages: CAMD, + * Requires the Core and Cholesky modules, and two packages: CAMD, * and CCOLAMD. Used by functions in the Partition Module. */ +#ifndef NCAMD + /* -------------------------------------------------------------------------- */ /* cholmod_ccolamd */ /* -------------------------------------------------------------------------- */ @@ -3534,13 +4271,9 @@ int cholmod_l_camd (cholmod_sparse *, int64_t *, size_t, #endif -//============================================================================== -// CHOLMOD:Partition Module (graph partition methods) -//============================================================================== - -// These routines still exist if CHOLMOD is compiled with -DNPARTITION, -// but they return Common->status = CHOLMOD_NOT_INSTALLED in that case. -#if 1 +/* ========================================================================== */ +/* === Include/cholmod_partition.h ========================================== */ +/* ========================================================================== */ /* ----------------------------------------------------------------------------- * CHOLMOD/Include/cholmod_partition.h. @@ -3560,7 +4293,7 @@ int cholmod_l_camd (cholmod_sparse *, int64_t *, size_t, * cholmod_bisect graph partitioner (currently based on METIS) * cholmod_metis_bisector direct interface to METIS_ComputeVertexSeparator * - * Requires the Utility and Cholesky modules, and three packages: METIS, CAMD, + * Requires the Core and Cholesky modules, and three packages: METIS, CAMD, * and CCOLAMD. Optionally used by the Cholesky module. * * Note that METIS does not have a version that uses int64_t integers. If you @@ -3571,6 +4304,9 @@ int cholmod_l_camd (cholmod_sparse *, int64_t *, size_t, * idxtype. */ +// These routines still exist if CHOLMOD is compiled with -DNPARTITION, +// but they return Common->status = CHOLMOD_NOT_INSTALLED. + /* -------------------------------------------------------------------------- */ /* cholmod_nested_dissection */ /* -------------------------------------------------------------------------- */ @@ -3598,8 +4334,9 @@ int64_t cholmod_nested_dissection /* returns # of components */ cholmod_common *Common ) ; -int64_t cholmod_l_nested_dissection (cholmod_sparse *, int64_t *, size_t, - int64_t *, int64_t *, int64_t *, cholmod_common *) ; +int64_t cholmod_l_nested_dissection (cholmod_sparse *, + int64_t *, size_t, int64_t *, int64_t *, + int64_t *, cholmod_common *) ; /* -------------------------------------------------------------------------- */ /* cholmod_metis */ @@ -3620,8 +4357,8 @@ int cholmod_metis cholmod_common *Common ) ; -int cholmod_l_metis (cholmod_sparse *, int64_t *, size_t, int, int64_t *, - cholmod_common *) ; +int cholmod_l_metis (cholmod_sparse *, int64_t *, size_t, int, + int64_t *, cholmod_common *) ; /* -------------------------------------------------------------------------- */ /* cholmod_bisect */ @@ -3644,8 +4381,8 @@ int64_t cholmod_bisect /* returns # of nodes in separator */ cholmod_common *Common ) ; -int64_t cholmod_l_bisect (cholmod_sparse *, int64_t *, size_t, int, int64_t *, - cholmod_common *) ; +int64_t cholmod_l_bisect (cholmod_sparse *, int64_t *, + size_t, int, int64_t *, cholmod_common *) ; /* -------------------------------------------------------------------------- */ /* cholmod_metis_bisector */ @@ -3659,7 +4396,7 @@ int64_t cholmod_metis_bisector /* returns separator size */ /* ---- input ---- */ cholmod_sparse *A, /* matrix to bisect */ int32_t *Anw, /* size A->nrow, node weights, can be NULL, */ - /* which means the graph is unweighted. */ + /* which means the graph is unweighted. */ int32_t *Aew, /* size nz, edge weights (silently ignored). */ /* This option was available with METIS 4, but not */ /* in METIS 5. This argument is now unused, but */ @@ -3671,8 +4408,9 @@ int64_t cholmod_metis_bisector /* returns separator size */ cholmod_common *Common ) ; -int64_t cholmod_l_metis_bisector (cholmod_sparse *, int64_t *, int64_t *, - int64_t *, cholmod_common *) ; +int64_t cholmod_l_metis_bisector (cholmod_sparse *, + int64_t *, int64_t *, int64_t *, + cholmod_common *) ; /* -------------------------------------------------------------------------- */ /* cholmod_collapse_septree */ @@ -3694,18 +4432,16 @@ int64_t cholmod_collapse_septree cholmod_common *Common ) ; -int64_t cholmod_l_collapse_septree (size_t, size_t, double, size_t, int64_t *, - int64_t *, cholmod_common *) ; - -#endif - -//============================================================================== -// CHOLMOD:Supernodal Module -//============================================================================== +int64_t cholmod_l_collapse_septree (size_t, size_t, double, size_t, + int64_t *, int64_t *, cholmod_common *) ; -#ifndef NSUPERNODAL +/* ========================================================================== */ +/* === Include/cholmod_supernodal.h ========================================= */ +/* ========================================================================== */ -/* Supernodal analysis, factorization, and solve. The simplest way to use +/* CHOLMOD Supernodal module. + * + * Supernodal analysis, factorization, and solve. The simplest way to use * these routines is via the Cholesky module. It does not provide any * fill-reducing orderings, but does accept the orderings computed by the * Cholesky module. It does not require the Cholesky module itself, however. @@ -3732,10 +4468,12 @@ int64_t cholmod_l_collapse_septree (size_t, size_t, double, size_t, int64_t *, * ---------------- * dpotrf LAPACK: A=chol(tril(A)) * - * Requires the Utility module, and two external packages: LAPACK and the BLAS. + * Requires the Core module, and two external packages: LAPACK and the BLAS. * Optionally used by the Cholesky module. */ +#ifndef NSUPERNODAL + /* -------------------------------------------------------------------------- */ /* cholmod_super_symbolic */ /* -------------------------------------------------------------------------- */ @@ -3758,8 +4496,8 @@ int cholmod_super_symbolic cholmod_common *Common ) ; -int cholmod_l_super_symbolic (cholmod_sparse *, cholmod_sparse *, int64_t *, - cholmod_factor *, cholmod_common *) ; +int cholmod_l_super_symbolic (cholmod_sparse *, cholmod_sparse *, + int64_t *, cholmod_factor *, cholmod_common *) ; /* -------------------------------------------------------------------------- */ /* cholmod_super_symbolic2 */ @@ -3862,37 +4600,19 @@ int cholmod_l_super_ltsolve (cholmod_factor *, cholmod_dense *, cholmod_dense *, } #endif -//============================================================================== -// CHOLMOD:SupernodalGPU Module -//============================================================================== - -//------------------------------------------------------------------------------ -// cholmod_score_comp: for sorting descendant supernodes with qsort -//------------------------------------------------------------------------------ - -#ifdef __cplusplus -extern "C" { -#endif - -typedef struct cholmod_descendant_score_t -{ - double score ; - int64_t d ; -} -descendantScore ; -int cholmod_score_comp (struct cholmod_descendant_score_t *i, - struct cholmod_descendant_score_t *j) ; -int cholmod_l_score_comp (struct cholmod_descendant_score_t *i, - struct cholmod_descendant_score_t *j) ; +/* ========================================================================== */ +/* === Include/cholmod_gpu.h ================================================ */ +/* ========================================================================== */ -#ifdef __cplusplus -} -#endif +/* ----------------------------------------------------------------------------- + * CHOLMOD/Include/cholmod_gpu.h. + * Copyright (C) 2014, Timothy A. Davis + * http://www.suitesparse.com + * -------------------------------------------------------------------------- */ -//------------------------------------------------------------------------------ -// remainder of SupernodalGPU Module -//------------------------------------------------------------------------------ +/* CHOLMOD GPU module + */ #ifdef SUITESPARSE_CUDA @@ -3915,10 +4635,11 @@ int cholmod_l_score_comp (struct cholmod_descendant_score_t *i, #define CHOLMOD_POTRF_LIMIT 512 /* required cols for POTRF & TRSM on GPU */ /* # of host supernodes to perform before checking for free pinned buffers */ -#define CHOLMOD_GPU_SKIP 3 +#define CHOLMOD_GPU_SKIP 3 #define CHOLMOD_HANDLE_CUDA_ERROR(e,s) {if (e) {ERROR(CHOLMOD_GPU_PROBLEM,s);}} +/* make it easy for C++ programs to include CHOLMOD */ #ifdef __cplusplus extern "C" { #endif @@ -3948,7 +4669,7 @@ int cholmod_l_gpu_memorysize /* GPU memory size available, 1 if no GPU */ size_t *available_mem, cholmod_common *Common ) ; - + int cholmod_gpu_probe ( cholmod_common *Common ) ; int cholmod_l_gpu_probe ( cholmod_common *Common ) ; @@ -3968,4 +4689,3 @@ int cholmod_l_gpu_allocate ( cholmod_common *Common ) ; #endif #endif - diff --git a/CHOLMOD/Core/cholmod_aat.c b/CHOLMOD/Core/cholmod_aat.c new file mode 100644 index 0000000000..d1c21f7600 --- /dev/null +++ b/CHOLMOD/Core/cholmod_aat.c @@ -0,0 +1,298 @@ +//------------------------------------------------------------------------------ +// CHOLMOD/Core/cholmod_aat: compute A*A' or A(:,f)*A(:,f)' +//------------------------------------------------------------------------------ + +// CHOLMOD/Core Module. Copyright (C) 2005-2022, University of Florida. +// All Rights Reserved. Author: Timothy A. Davis +// SPDX-License-Identifier: LGPL-2.1+ + +//------------------------------------------------------------------------------ + +/* C = A*A' or C = A(:,f)*A(:,f)' + * + * A can be packed or unpacked, sorted or unsorted, but must be stored with + * both upper and lower parts (A->stype of zero). C is returned as packed, + * C->stype of zero (both upper and lower parts present), and unsorted. See + * cholmod_ssmult in the MatrixOps Module for a more general matrix-matrix + * multiply. + * + * You can trivially convert C into a symmetric upper/lower matrix by + * changing C->stype = 1 or -1 after calling this routine. + * + * workspace: + * Flag (A->nrow), + * Iwork (max (A->nrow, A->ncol)) if fset present, + * Iwork (A->nrow) if no fset, + * W (A->nrow) if mode > 0, + * allocates temporary copy for A'. + * + * A can be pattern or real. Complex or zomplex cases are supported only + * if the mode is <= 0 (in which case the numerical values are ignored). + */ + +#include "cholmod_internal.h" + +cholmod_sparse *CHOLMOD(aat) +( + /* ---- input ---- */ + cholmod_sparse *A, /* input matrix; C=A*A' is constructed */ + Int *fset, /* subset of 0:(A->ncol)-1 */ + size_t fsize, /* size of fset */ + int mode, /* >0: numerical, 0: pattern, <0: pattern (no diag) + * -2: pattern only, no diagonal, add 50% + n extra + * space to C */ + /* --------------- */ + cholmod_common *Common +) +{ + double fjt ; + double *Ax, *Fx, *Cx, *W ; + Int *Ap, *Anz, *Ai, *Fp, *Fi, *Cp, *Ci, *Flag ; + cholmod_sparse *C, *F ; + Int packed, j, i, pa, paend, pf, pfend, n, mark, cnz, t, p, values, diag, + extra ; + + /* ---------------------------------------------------------------------- */ + /* check inputs */ + /* ---------------------------------------------------------------------- */ + + RETURN_IF_NULL_COMMON (NULL) ; + RETURN_IF_NULL (A, NULL) ; + values = (mode > 0) && (A->xtype != CHOLMOD_PATTERN) ; + RETURN_IF_XTYPE_INVALID (A, CHOLMOD_PATTERN, + values ? CHOLMOD_REAL : CHOLMOD_ZOMPLEX, NULL) ; + if (A->stype) + { + ERROR (CHOLMOD_INVALID, "matrix cannot be symmetric") ; + return (NULL) ; + } + Common->status = CHOLMOD_OK ; + + /* ---------------------------------------------------------------------- */ + /* allocate workspace */ + /* ---------------------------------------------------------------------- */ + + diag = (mode >= 0) ; + n = A->nrow ; + CHOLMOD(allocate_work) (n, MAX (A->ncol, A->nrow), values ? n : 0, Common) ; + if (Common->status < CHOLMOD_OK) + { + return (NULL) ; /* out of memory */ + } + ASSERT (CHOLMOD(dump_work) (TRUE, TRUE, values ? n : 0, Common)) ; + + /* ---------------------------------------------------------------------- */ + /* get inputs */ + /* ---------------------------------------------------------------------- */ + + ASSERT (CHOLMOD(dump_sparse) (A, "A", Common) >= 0) ; + + /* get the A matrix */ + Ap = A->p ; + Anz = A->nz ; + Ai = A->i ; + Ax = A->x ; + packed = A->packed ; + + /* get workspace */ + W = Common->Xwork ; /* size n, unused if values is FALSE */ + Flag = Common->Flag ; /* size n, Flag [0..n-1] < mark on input*/ + + /* ---------------------------------------------------------------------- */ + /* F = A' or A(:,f)' */ + /* ---------------------------------------------------------------------- */ + + /* workspace: Iwork (nrow if no fset; MAX (nrow,ncol) if fset)*/ + F = CHOLMOD(ptranspose) (A, values, NULL, fset, fsize, Common) ; + if (Common->status < CHOLMOD_OK) + { + return (NULL) ; /* out of memory */ + } + + Fp = F->p ; + Fi = F->i ; + Fx = F->x ; + + /* ---------------------------------------------------------------------- */ + /* count the number of entries in the result C */ + /* ---------------------------------------------------------------------- */ + + cnz = 0 ; + for (j = 0 ; j < n ; j++) + { + /* clear the Flag array */ + /* mark = CHOLMOD(clear_flag) (Common) ; */ + CHOLMOD_CLEAR_FLAG (Common) ; + mark = Common->mark ; + + /* exclude the diagonal, if requested */ + if (!diag) + { + Flag [j] = mark ; + } + + /* for each nonzero F(t,j) in column j, do: */ + pfend = Fp [j+1] ; + for (pf = Fp [j] ; pf < pfend ; pf++) + { + /* F(t,j) is nonzero */ + t = Fi [pf] ; + + /* add the nonzero pattern of A(:,t) to the pattern of C(:,j) */ + pa = Ap [t] ; + paend = (packed) ? (Ap [t+1]) : (pa + Anz [t]) ; + for ( ; pa < paend ; pa++) + { + i = Ai [pa] ; + if (Flag [i] != mark) + { + Flag [i] = mark ; + cnz++ ; + } + } + } + if (cnz < 0) + { + break ; /* integer overflow case */ + } + } + + extra = (mode == -2) ? (cnz/2 + n) : 0 ; + + mark = CHOLMOD(clear_flag) (Common) ; + + /* ---------------------------------------------------------------------- */ + /* check for integer overflow */ + /* ---------------------------------------------------------------------- */ + + if (cnz < 0 || (cnz + extra) < 0) + { + ERROR (CHOLMOD_TOO_LARGE, "problem too large") ; + CHOLMOD(clear_flag) (Common) ; + CHOLMOD(free_sparse) (&F, Common) ; + return (NULL) ; /* problem too large */ + } + + /* ---------------------------------------------------------------------- */ + /* allocate C */ + /* ---------------------------------------------------------------------- */ + + C = CHOLMOD(allocate_sparse) (n, n, cnz + extra, FALSE, TRUE, 0, + values ? A->xtype : CHOLMOD_PATTERN, Common) ; + if (Common->status < CHOLMOD_OK) + { + CHOLMOD(free_sparse) (&F, Common) ; + return (NULL) ; /* out of memory */ + } + + Cp = C->p ; + Ci = C->i ; + Cx = C->x ; + + /* ---------------------------------------------------------------------- */ + /* C = A*A' */ + /* ---------------------------------------------------------------------- */ + + cnz = 0 ; + + if (values) + { + + /* pattern and values */ + for (j = 0 ; j < n ; j++) + { + /* clear the Flag array */ + mark = CHOLMOD(clear_flag) (Common) ; + + /* start column j of C */ + Cp [j] = cnz ; + + /* for each nonzero F(t,j) in column j, do: */ + pfend = Fp [j+1] ; + for (pf = Fp [j] ; pf < pfend ; pf++) + { + /* F(t,j) is nonzero */ + t = Fi [pf] ; + fjt = Fx [pf] ; + + /* add the nonzero pattern of A(:,t) to the pattern of C(:,j) + * and scatter the values into W */ + pa = Ap [t] ; + paend = (packed) ? (Ap [t+1]) : (pa + Anz [t]) ; + for ( ; pa < paend ; pa++) + { + i = Ai [pa] ; + if (Flag [i] != mark) + { + Flag [i] = mark ; + Ci [cnz++] = i ; + } + W [i] += Ax [pa] * fjt ; + } + } + + /* gather the values into C(:,j) */ + for (p = Cp [j] ; p < cnz ; p++) + { + i = Ci [p] ; + Cx [p] = W [i] ; + W [i] = 0 ; + } + } + + } + else + { + + /* pattern only */ + for (j = 0 ; j < n ; j++) + { + /* clear the Flag array */ + mark = CHOLMOD(clear_flag) (Common) ; + + /* exclude the diagonal, if requested */ + if (!diag) + { + Flag [j] = mark ; + } + + /* start column j of C */ + Cp [j] = cnz ; + + /* for each nonzero F(t,j) in column j, do: */ + pfend = Fp [j+1] ; + for (pf = Fp [j] ; pf < pfend ; pf++) + { + /* F(t,j) is nonzero */ + t = Fi [pf] ; + + /* add the nonzero pattern of A(:,t) to the pattern of C(:,j) */ + pa = Ap [t] ; + paend = (packed) ? (Ap [t+1]) : (pa + Anz [t]) ; + for ( ; pa < paend ; pa++) + { + i = Ai [pa] ; + if (Flag [i] != mark) + { + Flag [i] = mark ; + Ci [cnz++] = i ; + } + } + } + } + } + + Cp [n] = cnz ; + ASSERT (IMPLIES (mode != -2, MAX (1,cnz) == C->nzmax)) ; + + /* ---------------------------------------------------------------------- */ + /* clear workspace and free temporary matrices and return result */ + /* ---------------------------------------------------------------------- */ + + CHOLMOD(free_sparse) (&F, Common) ; + CHOLMOD(clear_flag) (Common) ; + ASSERT (CHOLMOD(dump_work) (TRUE, TRUE, values ? n : 0, Common)) ; + DEBUG (i = CHOLMOD(dump_sparse) (C, "aat", Common)) ; + ASSERT (IMPLIES (mode < 0, i == 0)) ; + return (C) ; +} diff --git a/CHOLMOD/Core/cholmod_add.c b/CHOLMOD/Core/cholmod_add.c new file mode 100644 index 0000000000..371b981e0e --- /dev/null +++ b/CHOLMOD/Core/cholmod_add.c @@ -0,0 +1,278 @@ +//------------------------------------------------------------------------------ +// CHOLMOD/Core/cholmod_add: compute alpha*A + beta*B +//------------------------------------------------------------------------------ + +// CHOLMOD/Core Module. Copyright (C) 2005-2022, University of Florida. +// All Rights Reserved. Author: Timothy A. Davis +// SPDX-License-Identifier: LGPL-2.1+ + +//------------------------------------------------------------------------------ + +/* C = alpha*A + beta*B, or spones(A+B). Result is packed, with sorted or + * unsorted columns. This routine is much faster and takes less memory if C + * is allowed to have unsorted columns. + * + * If A and B are both symmetric (in upper form) then C is the same. Likewise, + * if A and B are both symmetric (in lower form) then C is the same. + * Otherwise, C is unsymmetric. A and B must have the same dimension. + * + * workspace: Flag (nrow), W (nrow) if values, Iwork (max (nrow,ncol)). + * allocates temporary copies for A and B if they are symmetric. + * allocates temporary copy of C if it is to be returned sorted. + * + * A and B can have an xtype of pattern or real. Complex or zomplex cases + * are supported only if the "values" input parameter is FALSE. + */ + +#include "cholmod_internal.h" + +cholmod_sparse *CHOLMOD(add) +( + /* ---- input ---- */ + cholmod_sparse *A, /* matrix to add */ + cholmod_sparse *B, /* matrix to add */ + double alpha [2], /* scale factor for A */ + double beta [2], /* scale factor for B */ + int values, /* if TRUE compute the numerical values of C */ + int sorted, /* if TRUE, sort columns of C */ + /* --------------- */ + cholmod_common *Common +) +{ + double *Ax, *Bx, *Cx, *W ; + Int apacked, up, lo, nrow, ncol, bpacked, nzmax, pa, paend, pb, pbend, i, + j, p, mark, nz ; + Int *Ap, *Ai, *Anz, *Bp, *Bi, *Bnz, *Flag, *Cp, *Ci ; + cholmod_sparse *A2, *B2, *C ; + + /* ---------------------------------------------------------------------- */ + /* check inputs */ + /* ---------------------------------------------------------------------- */ + + RETURN_IF_NULL_COMMON (NULL) ; + RETURN_IF_NULL (A, NULL) ; + RETURN_IF_NULL (B, NULL) ; + values = values && + (A->xtype != CHOLMOD_PATTERN) && (B->xtype != CHOLMOD_PATTERN) ; + RETURN_IF_XTYPE_INVALID (A, CHOLMOD_PATTERN, + values ? CHOLMOD_REAL : CHOLMOD_ZOMPLEX, NULL) ; + RETURN_IF_XTYPE_INVALID (B, CHOLMOD_PATTERN, + values ? CHOLMOD_REAL : CHOLMOD_ZOMPLEX, NULL) ; + if (A->nrow != B->nrow || A->ncol != B->ncol) + { + /* A and B must have the same dimensions */ + ERROR (CHOLMOD_INVALID, "A and B dimesions do not match") ; + return (NULL) ; + } + /* A and B must have the same numerical type if values is TRUE (both must + * be CHOLMOD_REAL, this is implicitly checked above) */ + + Common->status = CHOLMOD_OK ; + + /* ---------------------------------------------------------------------- */ + /* allocate workspace */ + /* ---------------------------------------------------------------------- */ + + nrow = A->nrow ; + ncol = A->ncol ; + CHOLMOD(allocate_work) (nrow, MAX (nrow,ncol), values ? nrow : 0, Common) ; + if (Common->status < CHOLMOD_OK) + { + return (NULL) ; /* out of memory */ + } + + /* ---------------------------------------------------------------------- */ + /* get inputs */ + /* ---------------------------------------------------------------------- */ + + if (nrow <= 1) + { + /* C will be implicitly sorted, so no need to sort it here */ + sorted = FALSE ; + } + + /* convert A or B to unsymmetric, if necessary */ + A2 = NULL ; + B2 = NULL ; + + if (A->stype != B->stype) + { + if (A->stype) + { + /* workspace: Iwork (max (nrow,ncol)) */ + A2 = CHOLMOD(copy) (A, 0, values, Common) ; + if (Common->status < CHOLMOD_OK) + { + return (NULL) ; /* out of memory */ + } + A = A2 ; + } + if (B->stype) + { + /* workspace: Iwork (max (nrow,ncol)) */ + B2 = CHOLMOD(copy) (B, 0, values, Common) ; + if (Common->status < CHOLMOD_OK) + { + CHOLMOD(free_sparse) (&A2, Common) ; + return (NULL) ; /* out of memory */ + } + B = B2 ; + } + } + + /* get the A matrix */ + ASSERT (A->stype == B->stype) ; + up = (A->stype > 0) ; + lo = (A->stype < 0) ; + + Ap = A->p ; + Anz = A->nz ; + Ai = A->i ; + Ax = A->x ; + apacked = A->packed ; + + /* get the B matrix */ + Bp = B->p ; + Bnz = B->nz ; + Bi = B->i ; + Bx = B->x ; + bpacked = B->packed ; + + /* get workspace */ + W = Common->Xwork ; /* size nrow, used if values is TRUE */ + Flag = Common->Flag ; /* size nrow, Flag [0..nrow-1] < mark on input */ + + /* ---------------------------------------------------------------------- */ + /* allocate the result C */ + /* ---------------------------------------------------------------------- */ + + /* If integer overflow occurs, nzmax < 0 and the allocate fails properly + * (likewise in most other matrix manipulation routines). */ + + nzmax = CHOLMOD(nnz) (A, Common) + CHOLMOD(nnz) (B, Common) ; + + C = CHOLMOD(allocate_sparse) (nrow, ncol, nzmax, FALSE, TRUE, + SIGN (A->stype), values ? A->xtype : CHOLMOD_PATTERN, Common) ; + if (Common->status < CHOLMOD_OK) + { + CHOLMOD(free_sparse) (&A2, Common) ; + CHOLMOD(free_sparse) (&B2, Common) ; + return (NULL) ; /* out of memory */ + } + + Cp = C->p ; + Ci = C->i ; + Cx = C->x ; + + /* ---------------------------------------------------------------------- */ + /* compute C = alpha*A + beta*B */ + /* ---------------------------------------------------------------------- */ + + nz = 0 ; + for (j = 0 ; j < ncol ; j++) + { + Cp [j] = nz ; + + /* clear the Flag array */ + /* mark = CHOLMOD(clear_flag) (Common) ; */ + CHOLMOD_CLEAR_FLAG (Common) ; + mark = Common->mark ; + + /* scatter B into W */ + pb = Bp [j] ; + pbend = (bpacked) ? (Bp [j+1]) : (pb + Bnz [j]) ; + for (p = pb ; p < pbend ; p++) + { + i = Bi [p] ; + if ((up && i > j) || (lo && i < j)) + { + continue ; + } + Flag [i] = mark ; + if (values) + { + W [i] = beta [0] * Bx [p] ; + } + } + + /* add A and gather from W into C(:,j) */ + pa = Ap [j] ; + paend = (apacked) ? (Ap [j+1]) : (pa + Anz [j]) ; + for (p = pa ; p < paend ; p++) + { + i = Ai [p] ; + if ((up && i > j) || (lo && i < j)) + { + continue ; + } + Flag [i] = EMPTY ; + Ci [nz] = i ; + if (values) + { + Cx [nz] = W [i] + alpha [0] * Ax [p] ; + W [i] = 0 ; + } + nz++ ; + } + + /* gather remaining entries into C(:,j), using pattern of B */ + for (p = pb ; p < pbend ; p++) + { + i = Bi [p] ; + if ((up && i > j) || (lo && i < j)) + { + continue ; + } + if (Flag [i] == mark) + { + Ci [nz] = i ; + if (values) + { + Cx [nz] = W [i] ; + W [i] = 0 ; + } + nz++ ; + } + } + } + + Cp [ncol] = nz ; + + /* ---------------------------------------------------------------------- */ + /* reduce C in size and free temporary matrices */ + /* ---------------------------------------------------------------------- */ + + ASSERT (MAX (1,nz) <= C->nzmax) ; + CHOLMOD(reallocate_sparse) (nz, C, Common) ; + ASSERT (Common->status >= CHOLMOD_OK) ; + + /* clear the Flag array */ + mark = CHOLMOD(clear_flag) (Common) ; + + CHOLMOD(free_sparse) (&A2, Common) ; + CHOLMOD(free_sparse) (&B2, Common) ; + + /* ---------------------------------------------------------------------- */ + /* sort C, if requested */ + /* ---------------------------------------------------------------------- */ + + if (sorted) + { + /* workspace: Iwork (max (nrow,ncol)) */ + if (!CHOLMOD(sort) (C, Common)) + { + CHOLMOD(free_sparse) (&C, Common) ; + if (Common->status < CHOLMOD_OK) + { + return (NULL) ; /* out of memory */ + } + } + } + + /* ---------------------------------------------------------------------- */ + /* return result */ + /* ---------------------------------------------------------------------- */ + + ASSERT (CHOLMOD(dump_sparse) (C, "add", Common) >= 0) ; + return (C) ; +} diff --git a/CHOLMOD/Core/cholmod_band.c b/CHOLMOD/Core/cholmod_band.c new file mode 100644 index 0000000000..ebc5bc7c7b --- /dev/null +++ b/CHOLMOD/Core/cholmod_band.c @@ -0,0 +1,370 @@ +//------------------------------------------------------------------------------ +// CHOLMOD/Core/cholmod_band: extract entries within a band +//------------------------------------------------------------------------------ + +// CHOLMOD/Core Module. Copyright (C) 2005-2022, University of Florida. +// All Rights Reserved. Author: Timothy A. Davis +// SPDX-License-Identifier: LGPL-2.1+ + +//------------------------------------------------------------------------------ + +/* C = tril (triu (A,k1), k2) + * + * C is a matrix consisting of the diagonals of A from k1 to k2. + * + * k=0 is the main diagonal of A, k=1 is the superdiagonal, k=-1 is the + * subdiagonal, and so on. If A is m-by-n, then: + * + * k1=-m C = tril (A,k2) + * k2=n C = triu (A,k1) + * k1=0 and k2=0 C = diag(A), except C is a matrix, not a vector + * + * Values of k1 and k2 less than -m are treated as -m, and values greater + * than n are treated as n. + * + * A can be of any symmetry (upper, lower, or unsymmetric); C is returned in + * the same form, and packed. If A->stype > 0, entries in the lower + * triangular part of A are ignored, and the opposite is true if + * A->stype < 0. If A has sorted columns, then so does C. + * C has the same size as A. + * + * If inplace is TRUE, then the matrix A is modified in place. + * Only packed matrices can be converted in place. + * + * C can be returned as a numerical valued matrix (if A has numerical values + * and mode > 0), as a pattern-only (mode == 0), or as a pattern-only but with + * the diagonal entries removed (mode < 0). + * + * workspace: none + * + * A can have an xtype of pattern or real. Complex and zomplex cases supported + * only if mode <= 0 (in which case the numerical values are ignored). + */ + +#include "cholmod_internal.h" + +static cholmod_sparse *band /* returns C, or NULL if failure */ +( + /* ---- input or in/out if inplace is TRUE --- */ + cholmod_sparse *A, + /* ---- input ---- */ + int64_t k1, /* ignore entries below the k1-st diagonal */ + int64_t k2, /* ignore entries above the k2-nd diagonal */ + int mode, /* >0: numerical, 0: pattern, <0: pattern (no diagonal) */ + int inplace, /* if TRUE, then convert A in place */ + /* --------------- */ + cholmod_common *Common +) +{ + double *Ax, *Cx ; + Int packed, nz, j, p, pend, i, ncol, nrow, jlo, jhi, ilo, ihi, sorted, + values, diag ; + Int *Ap, *Anz, *Ai, *Cp, *Ci ; + cholmod_sparse *C ; + + /* ---------------------------------------------------------------------- */ + /* check inputs */ + /* ---------------------------------------------------------------------- */ + + RETURN_IF_NULL_COMMON (NULL) ; + RETURN_IF_NULL (A, NULL) ; + values = (mode > 0) && (A->xtype != CHOLMOD_PATTERN) ; + RETURN_IF_XTYPE_INVALID (A, CHOLMOD_PATTERN, + values ? CHOLMOD_REAL : CHOLMOD_ZOMPLEX, NULL) ; + packed = A->packed ; + diag = (mode >= 0) ; + if (inplace && !packed) + { + /* cannot operate on an unpacked matrix in place */ + ERROR (CHOLMOD_INVALID, "cannot operate on unpacked matrix in-place") ; + return (NULL) ; + } + Common->status = CHOLMOD_OK ; + + /* ---------------------------------------------------------------------- */ + /* get inputs */ + /* ---------------------------------------------------------------------- */ + + + PRINT1 (("k1 %ld k2 %ld\n", k1, k2)) ; + Ap = A->p ; + Anz = A->nz ; + Ai = A->i ; + Ax = A->x ; + sorted = A->sorted ; + + + if (A->stype > 0) + { + /* ignore any entries in strictly lower triangular part of A */ + k1 = MAX (k1, 0) ; + } + if (A->stype < 0) + { + /* ignore any entries in strictly upper triangular part of A */ + k2 = MIN (k2, 0) ; + } + ncol = A->ncol ; + nrow = A->nrow ; + + /* ensure k1 and k2 are in the range -nrow to +ncol to + * avoid possible integer overflow if k1 and k2 are huge */ + k1 = MAX (-nrow, k1) ; + k1 = MIN (k1, ncol) ; + k2 = MAX (-nrow, k2) ; + k2 = MIN (k2, ncol) ; + + /* consider columns jlo to jhi. columns outside this range are empty */ + jlo = MAX (k1, 0) ; + jhi = MIN (k2+nrow, ncol) ; + + if (k1 > k2) + { + /* nothing to do */ + jlo = ncol ; + jhi = ncol ; + } + + /* ---------------------------------------------------------------------- */ + /* allocate C, or operate on A in place */ + /* ---------------------------------------------------------------------- */ + + if (inplace) + { + /* convert A in place */ + C = A ; + } + else + { + /* count the number of entries in the result C */ + nz = 0 ; + if (sorted) + { + for (j = jlo ; j < jhi ; j++) + { + ilo = j-k2 ; + ihi = j-k1 ; + p = Ap [j] ; + pend = (packed) ? (Ap [j+1]) : (p + Anz [j]) ; + for ( ; p < pend ; p++) + { + i = Ai [p] ; + if (i > ihi) + { + break ; + } + if (i >= ilo && (diag || i != j)) + { + nz++ ; + } + } + } + } + else + { + for (j = jlo ; j < jhi ; j++) + { + ilo = j-k2 ; + ihi = j-k1 ; + p = Ap [j] ; + pend = (packed) ? (Ap [j+1]) : (p + Anz [j]) ; + for ( ; p < pend ; p++) + { + i = Ai [p] ; + if (i >= ilo && i <= ihi && (diag || i != j)) + { + nz++ ; + } + } + } + } + /* allocate C; A will not be modified. C is sorted if A is sorted */ + C = CHOLMOD(allocate_sparse) (A->nrow, ncol, nz, sorted, TRUE, + A->stype, values ? A->xtype : CHOLMOD_PATTERN, Common) ; + if (Common->status < CHOLMOD_OK) + { + return (NULL) ; /* out of memory */ + } + } + + Cp = C->p ; + Ci = C->i ; + Cx = C->x ; + + /* ---------------------------------------------------------------------- */ + /* construct C */ + /* ---------------------------------------------------------------------- */ + + /* columns 0 to jlo-1 are empty */ + for (j = 0 ; j < jlo ; j++) + { + Cp [j] = 0 ; + } + + nz = 0 ; + if (sorted) + { + if (values) + { + /* pattern and values */ + ASSERT (diag) ; + for (j = jlo ; j < jhi ; j++) + { + ilo = j-k2 ; + ihi = j-k1 ; + p = Ap [j] ; + pend = (packed) ? (Ap [j+1]) : (p + Anz [j]) ; + Cp [j] = nz ; + for ( ; p < pend ; p++) + { + i = Ai [p] ; + if (i > ihi) + { + break ; + } + if (i >= ilo) + { + Ci [nz] = i ; + Cx [nz] = Ax [p] ; + nz++ ; + } + } + } + } + else + { + /* pattern only, perhaps with no diagonal */ + for (j = jlo ; j < jhi ; j++) + { + ilo = j-k2 ; + ihi = j-k1 ; + p = Ap [j] ; + pend = (packed) ? (Ap [j+1]) : (p + Anz [j]) ; + Cp [j] = nz ; + for ( ; p < pend ; p++) + { + i = Ai [p] ; + if (i > ihi) + { + break ; + } + if (i >= ilo && (diag || i != j)) + { + Ci [nz++] = i ; + } + } + } + } + } + else + { + if (values) + { + /* pattern and values */ + ASSERT (diag) ; + for (j = jlo ; j < jhi ; j++) + { + ilo = j-k2 ; + ihi = j-k1 ; + p = Ap [j] ; + pend = (packed) ? (Ap [j+1]) : (p + Anz [j]) ; + Cp [j] = nz ; + for ( ; p < pend ; p++) + { + i = Ai [p] ; + if (i >= ilo && i <= ihi) + { + Ci [nz] = i ; + Cx [nz] = Ax [p] ; + nz++ ; + } + } + } + } + else + { + /* pattern only, perhaps with no diagonal */ + for (j = jlo ; j < jhi ; j++) + { + ilo = j-k2 ; + ihi = j-k1 ; + p = Ap [j] ; + pend = (packed) ? (Ap [j+1]) : (p + Anz [j]) ; + Cp [j] = nz ; + for ( ; p < pend ; p++) + { + i = Ai [p] ; + if (i >= ilo && i <= ihi && (diag || i != j)) + { + Ci [nz++] = i ; + } + } + } + } + } + + /* columns jhi to ncol-1 are empty */ + for (j = jhi ; j <= ncol ; j++) + { + Cp [j] = nz ; + } + + /* ---------------------------------------------------------------------- */ + /* reduce A in size if done in place */ + /* ---------------------------------------------------------------------- */ + + if (inplace) + { + /* free the unused parts of A, and reduce A->i and A->x in size */ + ASSERT (MAX (1,nz) <= A->nzmax) ; + CHOLMOD(reallocate_sparse) (nz, A, Common) ; + ASSERT (Common->status >= CHOLMOD_OK) ; + } + + /* ---------------------------------------------------------------------- */ + /* return the result C */ + /* ---------------------------------------------------------------------- */ + + DEBUG (i = CHOLMOD(dump_sparse) (C, "band", Common)) ; + ASSERT (IMPLIES (mode < 0, i == 0)) ; + return (C) ; +} + + +/* ========================================================================== */ +/* === cholmod_band ========================================================= */ +/* ========================================================================== */ + +cholmod_sparse *CHOLMOD(band) +( + /* ---- input ---- */ + cholmod_sparse *A, /* matrix to extract band matrix from */ + int64_t k1, /* ignore entries below the k1-st diagonal */ + int64_t k2, /* ignore entries above the k2-nd diagonal */ + int mode, /* >0: numerical, 0: pattern, <0: pattern (no diag) */ + /* --------------- */ + cholmod_common *Common +) +{ + return (band (A, k1, k2, mode, FALSE, Common)) ; +} + + +/* ========================================================================== */ +/* === cholmod_band_inplace ================================================= */ +/* ========================================================================== */ + +int CHOLMOD(band_inplace) +( + /* ---- input ---- */ + int64_t k1, /* ignore entries below the k1-st diagonal */ + int64_t k2, /* ignore entries above the k2-nd diagonal */ + int mode, /* >0: numerical, 0: pattern, <0: pattern (no diag) */ + /* ---- in/out --- */ + cholmod_sparse *A, /* matrix from which entries not in band are removed */ + /* --------------- */ + cholmod_common *Common +) +{ + return (band (A, k1, k2, mode, TRUE, Common) != NULL) ; +} diff --git a/CHOLMOD/Core/cholmod_change_factor.c b/CHOLMOD/Core/cholmod_change_factor.c new file mode 100644 index 0000000000..223a71b24d --- /dev/null +++ b/CHOLMOD/Core/cholmod_change_factor.c @@ -0,0 +1,1223 @@ +//------------------------------------------------------------------------------ +// CHOLMOD/Core/cholmod_change_factor: change format of a Cholesky factorization +//------------------------------------------------------------------------------ + +// CHOLMOD/Core Module. Copyright (C) 2005-2022, University of Florida. +// All Rights Reserved. Author: Timothy A. Davis +// SPDX-License-Identifier: LGPL-2.1+ + +//------------------------------------------------------------------------------ + +/* Change the numeric/symbolic, LL/LDL, simplicial/super, packed/unpacked, + * monotonic/non-monotonic status of a cholmod_factor object. + * + * There are four basic classes of factor types: + * + * (1) simplicial symbolic: Consists of two size-n arrays: the fill-reducing + * permutation (L->Perm) and the nonzero count for each column of L + * (L->ColCount). All other factor types also include this information. + * L->ColCount may be exact (obtained from the analysis routines), or + * it may be a guess. During factorization, and certainly after update/ + * downdate, the columns of L can have a different number of nonzeros. + * L->ColCount is used to allocate space. L->ColCount is exact for the + * supernodal factorizations. The nonzero pattern of L is not kept. + * + * (2) simplicial numeric: These represent L in a compressed column form. The + * variants of this type are: + * + * LDL': L is unit diagonal. Row indices in column j are located in + * L->i [L->p [j] ... L->p [j] + L->nz [j]], and corresponding numeric + * values are in the same locations in L->x. The total number of + * entries is the sum of L->nz [j]. The unit diagonal is not stored; + * D is stored on the diagonal of L instead. L->p may or may not be + * monotonic. The order of storage of the columns in L->i and L->x is + * given by a doubly-linked list (L->prev and L->next). L->p is of + * size n+1, but only the first n entries are used (it is used if L + * is converted to a sparse matrix via cholmod_factor_to_sparse). + * + * For the complex case, L->x is stored interleaved with real/imag + * parts, and is of size 2*lnz*sizeof(double). For the zomplex case, + * L->x is of size lnz*sizeof(double) and holds the real part; L->z + * is the same size and holds the imaginary part. + * + * LL': This is identical to the LDL' form, except that the non-unit + * diagonal of L is stored as the first entry in each column of L. + * + * (3) supernodal symbolic: A representation of the nonzero pattern of the + * supernodes for a supernodal factorization. There are L->nsuper + * supernodes. Columns L->super [k] to L->super [k+1]-1 are in the kth + * supernode. The row indices for the kth supernode are in + * L->s [L->pi [k] ... L->pi [k+1]-1]. The numerical values are not + * allocated (L->x), but when they are they will be located in + * L->x [L->px [k] ... L->px [k+1]-1], and the L->px array is defined + * in this factor type. + * + * For the complex case, L->x is stored interleaved with real/imag parts, + * and is of size 2*L->xsize*sizeof(double). The zomplex supernodal case + * is not supported, since it is not compatible with LAPACK and the BLAS. + * + * (4) supernodal numeric: Always an LL' factorization. L is non-unit + * diagonal. L->x contains the numerical values of the supernodes, as + * described above for the supernodal symbolic factor. + * For the complex case, L->x is stored interleaved, and is of size + * 2*L->xsize*sizeof(double). The zomplex supernodal case is not + * supported, since it is not compatible with LAPACK and the BLAS. + * + * FUTURE WORK: support a supernodal LDL' factor. + * + * + * In all cases, the row indices in each column (L->i for simplicial L and + * L->s for supernodal L) are kept sorted from low indices to high indices. + * This means the diagonal of L (or D for LDL' factors) is always kept as the + * first entry in each column. + * + * The cholmod_change_factor routine can do almost all possible conversions. + * It cannot do the following conversions: + * + * (1) Simplicial numeric types cannot be converted to a supernodal + * symbolic type. This would simultaneously deallocate the + * simplicial pattern and numeric values and reallocate uninitialized + * space for the supernodal pattern. This isn't useful for the user, + * and not needed by CHOLMOD's own routines either. + * + * (2) Only a symbolic factor (simplicial to supernodal) can be converted + * to a supernodal numeric factor. + * + * Some conversions are meant only to be used internally by other CHOLMOD + * routines, and should not be performed by the end user. They allocate space + * whose contents are undefined: + * + * (1) converting from simplicial symbolic to supernodal symbolic. + * (2) converting any factor to supernodal numeric. + * + * workspace: no conversion routine uses workspace in Common. No temporary + * workspace is allocated. + * + * Supports all xtypes, except that there is no supernodal zomplex L. + * + * The to_xtype parameter is used only when converting from symbolic to numeric + * or numeric to symbolic. It cannot be used to convert a numeric xtype (real, + * complex, or zomplex) to a different numeric xtype. For that conversion, + * use cholmod_factor_xtype instead. + */ + +#include "cholmod_internal.h" + +static void natural_list (cholmod_factor *L) ; + +/* ========================================================================== */ +/* === TEMPLATE ============================================================= */ +/* ========================================================================== */ + +#define REAL +#include "t_cholmod_change_factor.c" +#define COMPLEX +#include "t_cholmod_change_factor.c" +#define ZOMPLEX +#include "t_cholmod_change_factor.c" + + +/* ========================================================================== */ +/* === L_is_packed ========================================================== */ +/* ========================================================================== */ + +/* Return TRUE if the columns of L are packed, FALSE otherwise. For debugging + * only. */ + +#ifndef NDEBUG +static int L_is_packed (cholmod_factor *L, cholmod_common *Common) +{ + Int j ; + Int *Lnz = L->nz ; + Int *Lp = L->p ; + Int n = L->n ; + + if (L->xtype == CHOLMOD_PATTERN || L->is_super) + { + return (TRUE) ; + } + + if (Lnz == NULL || Lp == NULL) + { + return (TRUE) ; + } + + for (j = 0 ; j < n ; j++) + { + PRINT3 (("j: "ID" Lnz "ID" Lp[j+1] "ID" Lp[j] "ID"\n", j, Lnz [j], + Lp [j+1], Lp [j])) ; + if (Lnz [j] != (Lp [j+1] - Lp [j])) + { + PRINT2 (("L is not packed\n")) ; + return (FALSE) ; + } + } + return (TRUE) ; +} +#endif + + +/* ========================================================================== */ +/* === natural_list ========================================================= */ +/* ========================================================================== */ + +/* Create a naturally-ordered doubly-linked list of columns. */ + +static void natural_list (cholmod_factor *L) +{ + Int head, tail, n, j ; + Int *Lnext, *Lprev ; + Lnext = L->next ; + Lprev = L->prev ; + ASSERT (Lprev != NULL && Lnext != NULL) ; + n = L->n ; + head = n+1 ; + tail = n ; + Lnext [head] = 0 ; + Lprev [head] = EMPTY ; + Lnext [tail] = EMPTY ; + Lprev [tail] = n-1 ; + for (j = 0 ; j < n ; j++) + { + Lnext [j] = j+1 ; + Lprev [j] = j-1 ; + } + Lprev [0] = head ; + L->is_monotonic = TRUE ; +} + + +/* ========================================================================== */ +/* === allocate_simplicial_numeric ========================================== */ +/* ========================================================================== */ + +/* Allocate O(n) arrays for simplicial numeric factorization. Initializes + * the link lists only. Does not allocate the L->i, L->x, or L->z arrays. */ + +static int allocate_simplicial_numeric +( + cholmod_factor *L, + cholmod_common *Common +) +{ + Int n ; + Int *Lp, *Lnz, *Lprev, *Lnext ; + size_t n1, n2 ; + + PRINT1 (("Allocate simplicial\n")) ; + + ASSERT (L->xtype == CHOLMOD_PATTERN || L->is_super) ; + ASSERT (L->p == NULL) ; + ASSERT (L->nz == NULL) ; + ASSERT (L->prev == NULL) ; + ASSERT (L->next == NULL) ; + + n = L->n ; + + /* this cannot cause size_t overflow */ + n1 = ((size_t) n) + 1 ; + n2 = ((size_t) n) + 2 ; + + Lp = CHOLMOD(malloc) (n1, sizeof (Int), Common) ; + Lnz = CHOLMOD(malloc) (n, sizeof (Int), Common) ; + Lprev = CHOLMOD(malloc) (n2, sizeof (Int), Common) ; + Lnext = CHOLMOD(malloc) (n2, sizeof (Int), Common) ; + + if (Common->status < CHOLMOD_OK) + { + CHOLMOD(free) (n1, sizeof (Int), Lp, Common) ; + CHOLMOD(free) (n, sizeof (Int), Lnz, Common) ; + CHOLMOD(free) (n2, sizeof (Int), Lprev, Common) ; + CHOLMOD(free) (n2, sizeof (Int), Lnext, Common) ; + PRINT1 (("Allocate simplicial failed\n")) ; + return (FALSE) ; /* out of memory */ + } + + /* ============================================== commit the changes to L */ + + L->p = Lp ; + L->nz = Lnz ; + L->prev = Lprev ; + L->next = Lnext ; + /* initialize a doubly linked list for columns in natural order */ + natural_list (L) ; + PRINT1 (("Allocate simplicial done\n")) ; + return (TRUE) ; +} + + +/* ========================================================================== */ +/* === simplicial_symbolic_to_super_symbolic ================================ */ +/* ========================================================================== */ + +/* Convert a simplicial symbolic factor supernodal symbolic factor. Does not + * initialize the new space. */ + +static int simplicial_symbolic_to_super_symbolic +( + cholmod_factor *L, + cholmod_common *Common +) +{ + Int nsuper, xsize, ssize ; + Int *Lsuper, *Lpi, *Lpx, *Ls ; + size_t nsuper1 ; + + ASSERT (L->xtype == CHOLMOD_PATTERN && !(L->is_super)) ; + + xsize = L->xsize ; + ssize = L->ssize ; + nsuper = L->nsuper ; + nsuper1 = ((size_t) nsuper) + 1 ; + + PRINT1 (("simple sym to super sym: ssize "ID" xsize "ID" nsuper "ID"" + " status %d\n", ssize, xsize, nsuper, Common->status)) ; + + /* O(nsuper) arrays, where nsuper <= n */ + Lsuper = CHOLMOD(malloc) (nsuper1, sizeof (Int), Common) ; + Lpi = CHOLMOD(malloc) (nsuper1, sizeof (Int), Common) ; + Lpx = CHOLMOD(malloc) (nsuper1, sizeof (Int), Common) ; + + /* O(ssize) array, where ssize <= nnz(L), and usually much smaller */ + Ls = CHOLMOD(malloc) (ssize, sizeof (Int), Common) ; + + if (Common->status < CHOLMOD_OK) + { + CHOLMOD(free) (nsuper1, sizeof (Int), Lsuper, Common) ; + CHOLMOD(free) (nsuper1, sizeof (Int), Lpi, Common) ; + CHOLMOD(free) (nsuper1, sizeof (Int), Lpx, Common) ; + CHOLMOD(free) (ssize, sizeof (Int), Ls, Common) ; + return (FALSE) ; /* out of memory */ + } + + /* ============================================== commit the changes to L */ + + ASSERT (Lsuper != NULL && Lpi != NULL && Lpx != NULL && Ls != NULL) ; + + L->maxcsize = 0 ; + L->maxesize = 0 ; + + L->super = Lsuper ; + L->pi = Lpi ; + L->px = Lpx ; + L->s = Ls ; + Ls [0] = EMPTY ; /* supernodal pattern undefined */ + + L->is_super = TRUE ; + L->is_ll = TRUE ; /* supernodal LDL' not supported */ + L->xtype = CHOLMOD_PATTERN ; + L->dtype = DTYPE ; + L->minor = L->n ; + return (TRUE) ; +} + + +/* ========================================================================== */ +/* === any_to_simplicial_symbolic =========================================== */ +/* ========================================================================== */ + +/* Convert any factor L to a simplicial symbolic factor, leaving only L->Perm + * and L->ColCount. Cannot fail. Any of the components of L (except Perm and + * ColCount) may already be free'd. */ + +static void any_to_simplicial_symbolic +( + cholmod_factor *L, + int to_ll, + cholmod_common *Common +) +{ + Int n, lnz, xs, ss, s, e ; + size_t n1, n2 ; + + /* ============================================== commit the changes to L */ + + n = L->n ; + lnz = L->nzmax ; + s = L->nsuper + 1 ; + xs = (L->is_super) ? ((Int) (L->xsize)) : (lnz) ; + e = (L->xtype == CHOLMOD_COMPLEX ? 2 : 1) ; + ss = L->ssize ; + + /* this cannot cause size_t overflow */ + n1 = ((size_t) n) + 1 ; + n2 = ((size_t) n) + 2 ; + + /* free all but the symbolic analysis (Perm and ColCount) */ + L->p = CHOLMOD(free) (n1, sizeof (Int), L->p, Common) ; + L->i = CHOLMOD(free) (lnz, sizeof (Int), L->i, Common) ; + L->x = CHOLMOD(free) (xs, e*sizeof (double), L->x, Common) ; + L->z = CHOLMOD(free) (lnz, sizeof (double), L->z, Common) ; + L->nz = CHOLMOD(free) (n, sizeof (Int), L->nz, Common) ; + L->next = CHOLMOD(free) (n2, sizeof (Int), L->next, Common) ; + L->prev = CHOLMOD(free) (n2, sizeof (Int), L->prev, Common) ; + L->super = CHOLMOD(free) (s, sizeof (Int), L->super, Common) ; + L->pi = CHOLMOD(free) (s, sizeof (Int), L->pi, Common) ; + L->px = CHOLMOD(free) (s, sizeof (Int), L->px, Common) ; + L->s = CHOLMOD(free) (ss, sizeof (Int), L->s, Common) ; + L->nzmax = 0 ; + L->is_super = FALSE ; + L->xtype = CHOLMOD_PATTERN ; + L->dtype = DTYPE ; + L->minor = n ; + L->is_ll = to_ll ; +} + + +/* ========================================================================== */ +/* === ll_super_to_super_symbolic =========================================== */ +/* ========================================================================== */ + +/* Convert a numerical supernodal L to symbolic supernodal. Cannot fail. */ + +static void ll_super_to_super_symbolic +( + cholmod_factor *L, + cholmod_common *Common +) +{ + + /* ============================================== commit the changes to L */ + + /* free all but the supernodal numerical factor */ + ASSERT (L->xtype != CHOLMOD_PATTERN && L->is_super && L->is_ll) ; + DEBUG (CHOLMOD(dump_factor) (L, "start to super symbolic", Common)) ; + L->x = CHOLMOD(free) (L->xsize, + (L->xtype == CHOLMOD_COMPLEX ? 2 : 1) * sizeof (double), L->x, + Common) ; + L->xtype = CHOLMOD_PATTERN ; + L->dtype = DTYPE ; + L->minor = L->n ; + L->is_ll = TRUE ; /* supernodal LDL' not supported */ + DEBUG (CHOLMOD(dump_factor) (L, "done to super symbolic", Common)) ; +} + + +/* ========================================================================== */ +/* === simplicial_symbolic_to_simplicial_numeric ============================ */ +/* ========================================================================== */ + +/* Convert a simplicial symbolic L to a simplicial numeric L; allocate space + * for L using L->ColCount from symbolic analysis, and set L to identity. + * + * If packed < 0, then this routine is creating a copy of another factor + * (via cholmod_copy_factor). In this case, the space is not initialized. */ + +static void simplicial_symbolic_to_simplicial_numeric +( + cholmod_factor *L, + int to_ll, + int packed, + int to_xtype, + cholmod_common *Common +) +{ + double grow0, grow1, xlen, xlnz ; + double *Lx, *Lz ; + Int *Li, *Lp, *Lnz, *ColCount ; + Int n, grow, grow2, p, j, lnz, len, ok, e ; + + ASSERT (L->xtype == CHOLMOD_PATTERN && !(L->is_super)) ; + if (!allocate_simplicial_numeric (L, Common)) + { + PRINT1 (("out of memory, allocate simplicial numeric\n")) ; + return ; /* out of memory */ + } + ASSERT (L->ColCount != NULL && L->nz != NULL && L->p != NULL) ; + ASSERT (L->x == NULL && L->z == NULL && L->i == NULL) ; + + ColCount = L->ColCount ; + Lnz = L->nz ; + Lp = L->p ; + ok = TRUE ; + n = L->n ; + + if (packed < 0) + { + + /* ------------------------------------------------------------------ */ + /* used by cholmod_copy_factor to allocate a copy of a factor object */ + /* ------------------------------------------------------------------ */ + + lnz = L->nzmax ; + L->nzmax = 0 ; + + } + else if (packed) + { + + /* ------------------------------------------------------------------ */ + /* LDL' or LL' packed */ + /* ------------------------------------------------------------------ */ + + PRINT1 (("convert to packed LL' or LDL'\n")) ; + lnz = 0 ; + for (j = 0 ; ok && j < n ; j++) + { + /* ensure len is in the range 1 to n-j */ + len = ColCount [j] ; + len = MAX (1, len) ; + len = MIN (len, n-j) ; + lnz += len ; + ok = (lnz >= 0) ; + } + for (j = 0 ; j <= n ; j++) + { + Lp [j] = j ; + } + for (j = 0 ; j < n ; j++) + { + Lnz [j] = 1 ; + } + + } + else + { + + /* ------------------------------------------------------------------ */ + /* LDL' unpacked */ + /* ------------------------------------------------------------------ */ + + PRINT1 (("convert to unpacked\n")) ; + /* compute new lnzmax */ + /* if any parameter is NaN, grow is false */ + grow0 = Common->grow0 ; + grow1 = Common->grow1 ; + grow2 = Common->grow2 ; + grow0 = IS_NAN (grow0) ? 1 : grow0 ; + grow1 = IS_NAN (grow1) ? 1 : grow1 ; + /* fl.pt. compare, but no NaN's: */ + grow = (grow0 >= 1.0) && (grow1 >= 1.0) && (grow2 > 0) ; + PRINT1 (("init, grow1 %g grow2 "ID"\n", grow1, grow2)) ; + /* initialize Lp and Lnz for each column */ + lnz = 0 ; + for (j = 0 ; ok && j < n ; j++) + { + Lp [j] = lnz ; + Lnz [j] = 1 ; + + /* ensure len is in the range 1 to n-j */ + len = ColCount [j] ; + len = MAX (1, len) ; + len = MIN (len, n-j) ; + + /* compute len in double to avoid integer overflow */ + PRINT1 (("ColCount ["ID"] = "ID"\n", j, len)) ; + if (grow) + { + xlen = (double) len ; + xlen = grow1 * xlen + grow2 ; + xlen = MIN (xlen, n-j) ; + len = (Int) xlen ; + } + ASSERT (len >= 1 && len <= n-j) ; + lnz += len ; + ok = (lnz >= 0) ; + } + if (ok) + { + Lp [n] = lnz ; + if (grow) + { + /* add extra space */ + xlnz = (double) lnz ; + xlnz *= grow0 ; + xlnz = MIN (xlnz, (double) SIZE_MAX) ; + xlnz = MIN (xlnz, ((double) n * (double) n + (double) n) / 2) ; + lnz = (Int) xlnz ; + } + } + } + + lnz = MAX (1, lnz) ; + + if (!ok) + { + ERROR (CHOLMOD_TOO_LARGE, "problem too large") ; + } + + /* allocate L->i, L->x, and L->z */ + PRINT1 (("resizing from zero size to lnz "ID"\n", lnz)) ; + ASSERT (L->nzmax == 0) ; + e = (to_xtype == CHOLMOD_COMPLEX ? 2 : 1) ; + if (!ok || !CHOLMOD(realloc_multiple) (lnz, 1, to_xtype, &(L->i), NULL, + &(L->x), &(L->z), &(L->nzmax), Common)) + { + L->p = CHOLMOD(free) (n+1, sizeof (Int), L->p, Common) ; + L->nz = CHOLMOD(free) (n, sizeof (Int), L->nz, Common) ; + L->prev = CHOLMOD(free) (n+2, sizeof (Int), L->prev, Common) ; + L->next = CHOLMOD(free) (n+2, sizeof (Int), L->next, Common) ; + L->i = CHOLMOD(free) (lnz, sizeof (Int), L->i, Common) ; + L->x = CHOLMOD(free) (lnz, e*sizeof (double), L->x, Common) ; + L->z = CHOLMOD(free) (lnz, sizeof (double), L->z, Common) ; + PRINT1 (("cannot realloc simplicial numeric\n")) ; + return ; /* out of memory */ + } + + /* ============================================== commit the changes to L */ + + /* initialize L to be the identity matrix */ + L->xtype = to_xtype ; + L->dtype = DTYPE ; + L->minor = n ; + + Li = L->i ; + Lx = L->x ; + Lz = L->z ; + +#if 0 + if (lnz == 1) + { + /* the user won't expect to access this entry, but some CHOLMOD + * routines may. Set it to zero so that valgrind doesn't complain. */ + switch (to_xtype) + { + case CHOLMOD_REAL: + Lx [0] = 0 ; + break ; + + case CHOLMOD_COMPLEX: + Lx [0] = 0 ; + Lx [1] = 0 ; + break ; + + case CHOLMOD_ZOMPLEX: + Lx [0] = 0 ; + Lz [0] = 0 ; + break ; + } + } +#endif + + if (packed >= 0) + { + /* create the unit diagonal for either the LL' or LDL' case */ + + switch (L->xtype) + { + case CHOLMOD_REAL: + for (j = 0 ; j < n ; j++) + { + ASSERT (Lp [j] < Lp [j+1]) ; + p = Lp [j] ; + Li [p] = j ; + Lx [p] = 1 ; + } + break ; + + case CHOLMOD_COMPLEX: + for (j = 0 ; j < n ; j++) + { + ASSERT (Lp [j] < Lp [j+1]) ; + p = Lp [j] ; + Li [p] = j ; + Lx [2*p ] = 1 ; + Lx [2*p+1] = 0 ; + } + break ; + + case CHOLMOD_ZOMPLEX: + for (j = 0 ; j < n ; j++) + { + ASSERT (Lp [j] < Lp [j+1]) ; + p = Lp [j] ; + Li [p] = j ; + Lx [p] = 1 ; + Lz [p] = 0 ; + } + break ; + } + } + + L->is_ll = to_ll ; + + PRINT1 (("done convert simplicial symbolic to numeric\n")) ; +} + + +/* ========================================================================== */ +/* === change_simplicial_numeric ============================================ */ +/* ========================================================================== */ + +/* Change LL' to LDL', LDL' to LL', or leave as-is. + * + * If to_packed is TRUE, then the columns of L are packed and made monotonic + * (to_monotonic is ignored; it is implicitly TRUE). + * + * If to_monotonic is TRUE but to_packed is FALSE, the columns of L are made + * monotonic but not packed. + * + * If both to_packed and to_monotonic are FALSE, then the columns of L are + * left as-is, and the conversion is done in place. + * + * If L is already monotonic, or if it is to be left non-monotonic, then this + * conversion always succeeds. + * + * When converting an LDL' to LL' factorization, any column with a negative + * or zero diagonal entry is not modified so that conversion back to LDL' will + * succeed. This can result in a matrix L with a negative entry on the diagonal + * If the kth entry on the diagonal of D is negative, it and the kth column of + * L are left unchanged. A subsequent conversion back to an LDL' form will also + * leave the column unchanged, so the correct LDL' factorization will be + * restored. L->minor is set to the smallest k for which D (k,k) is negative. + */ + +static void change_simplicial_numeric +( + cholmod_factor *L, + int to_ll, + int to_packed, + int to_monotonic, + cholmod_common *Common +) +{ + double grow0, grow1, xlen, xlnz ; + void *newLi, *newLx, *newLz ; + double *Lx, *Lz ; + Int *Lp, *Li, *Lnz ; + Int make_monotonic, grow2, n, j, lnz, len, grow, ok, make_ll, make_ldl ; + size_t nzmax0 ; + + PRINT1 (("\n===Change simplicial numeric: %d %d %d\n", + to_ll, to_packed, to_monotonic)) ; + DEBUG (CHOLMOD(dump_factor) (L, "change simplicial numeric", Common)) ; + ASSERT (L->xtype != CHOLMOD_PATTERN && !(L->is_super)) ; + + make_monotonic = ((to_packed || to_monotonic) && !(L->is_monotonic)) ; + make_ll = (to_ll && !(L->is_ll)) ; + make_ldl = (!to_ll && L->is_ll) ; + + n = L->n ; + Lp = L->p ; + Li = L->i ; + Lx = L->x ; + Lz = L->z ; + Lnz = L->nz ; + + grow = FALSE ; + grow0 = Common->grow0 ; + grow1 = Common->grow1 ; + grow2 = Common->grow2 ; + grow0 = IS_NAN (grow0) ? 1 : grow0 ; + grow1 = IS_NAN (grow1) ? 1 : grow1 ; + ok = TRUE ; + newLi = NULL ; + newLx = NULL ; + newLz = NULL ; + lnz = 0 ; + + if (make_monotonic) + { + + /* ------------------------------------------------------------------ */ + /* Columns out of order, but will be reordered and optionally packed. */ + /* ------------------------------------------------------------------ */ + + PRINT1 (("L is non-monotonic\n")) ; + + /* compute new L->nzmax */ + if (!to_packed) + { + /* if any parameter is NaN, grow is false */ + /* fl.pt. comparisons below are false if any parameter is NaN */ + grow = (grow0 >= 1.0) && (grow1 >= 1.0) && (grow2 > 0) ; + } + for (j = 0 ; ok && j < n ; j++) + { + len = Lnz [j] ; + ASSERT (len >= 1 && len <= n-j) ; + + /* compute len in double to avoid integer overflow */ + if (grow) + { + xlen = (double) len ; + xlen = grow1 * xlen + grow2 ; + xlen = MIN (xlen, n-j) ; + len = (Int) xlen ; + } + ASSERT (len >= Lnz [j] && len <= n-j) ; + + PRINT2 (("j: "ID" Lnz[j] "ID" len "ID" p "ID"\n", + j, Lnz [j], len, lnz)) ; + + lnz += len ; + ok = (lnz >= 0) ; + } + + if (!ok) + { + ERROR (CHOLMOD_TOO_LARGE, "problem too large") ; + return ; + } + + if (grow) + { + xlnz = (double) lnz ; + xlnz *= grow0 ; + xlnz = MIN (xlnz, (double) SIZE_MAX) ; + xlnz = MIN (xlnz, ((double) n * (double) n + (double) n) / 2) ; + lnz = (Int) xlnz ; + } + + lnz = MAX (1, lnz) ; + PRINT1 (("final lnz "ID"\n", lnz)) ; + nzmax0 = 0 ; + + CHOLMOD(realloc_multiple) (lnz, 1, L->xtype, &newLi, NULL, + &newLx, &newLz, &nzmax0, Common) ; + + if (Common->status < CHOLMOD_OK) + { + return ; /* out of memory */ + } + } + + /* ============================================== commit the changes to L */ + + /* ---------------------------------------------------------------------- */ + /* convert the simplicial L, using template routine */ + /* ---------------------------------------------------------------------- */ + + switch (L->xtype) + { + + case CHOLMOD_REAL: + r_change_simplicial_numeric (L, to_ll, to_packed, + newLi, newLx, newLz, lnz, grow, grow1, grow2, + make_ll, make_monotonic, make_ldl, Common) ; + break ; + + case CHOLMOD_COMPLEX: + c_change_simplicial_numeric (L, to_ll, to_packed, + newLi, newLx, newLz, lnz, grow, grow1, grow2, + make_ll, make_monotonic, make_ldl, Common) ; + break ; + + case CHOLMOD_ZOMPLEX: + z_change_simplicial_numeric (L, to_ll, to_packed, + newLi, newLx, newLz, lnz, grow, grow1, grow2, + make_ll, make_monotonic, make_ldl, Common) ; + break ; + } + + DEBUG (CHOLMOD(dump_factor) (L, "L simplicial changed", Common)) ; +} + + +/* ========================================================================== */ +/* === ll_super_to_simplicial_numeric ======================================= */ +/* ========================================================================== */ + +/* Convert a supernodal numeric factorization to any simplicial numeric one. + * Leaves L->xtype unchanged (real or complex, not zomplex since there is + * no supernodal zomplex L). */ + +static void ll_super_to_simplicial_numeric +( + cholmod_factor *L, + int to_packed, + int to_ll, + cholmod_common *Common +) +{ + Int *Ls, *Lpi, *Lpx, *Super, *Li ; + Int n, lnz, s, nsuper, psi, psend, nsrow, nscol, k1, k2, erows ; + + DEBUG (CHOLMOD(dump_factor) (L, "start LL super to simplicial", Common)) ; + PRINT1 (("super -> simplicial (%d %d)\n", to_packed, to_ll)) ; + ASSERT (L->xtype != CHOLMOD_PATTERN && L->is_ll && L->is_super) ; + ASSERT (L->x != NULL && L->i == NULL) ; + + n = L->n ; + nsuper = L->nsuper ; + Lpi = L->pi ; + Lpx = L->px ; + Ls = L->s ; + Super = L->super ; + + /* Int overflow cannot occur since supernodal L already exists */ + + if (to_packed) + { + /* count the number of nonzeros in L. Each supernode is of the form + * + * l . . . For this example, nscol = 4 (# columns). nsrow = 9. + * l l . . The "." entries are allocated in the supernodal + * l l l . factor, but not used. They are not copied to the + * l l l l simplicial factor. Some "l" and "e" entries may be + * e e e e numerically zero and even symbolically zero if a + * e e e e tight simplicial factorization or resymbol were + * e e e e done, because of numerical cancellation and relaxed + * e e e e supernode amalgamation, respectively. + * e e e e + */ + lnz = 0 ; + for (s = 0 ; s < nsuper ; s++) + { + k1 = Super [s] ; + k2 = Super [s+1] ; + psi = Lpi [s] ; + psend = Lpi [s+1] ; + nsrow = psend - psi ; + nscol = k2 - k1 ; + ASSERT (nsrow >= nscol) ; + erows = nsrow - nscol ; + + /* lower triangular part, including the diagonal, + * counting the "l" terms in the figure above. */ + lnz += nscol * (nscol+1) / 2 ; + + /* rectangular part, below the diagonal block (the "e" terms) */ + lnz += nscol * erows ; + } + ASSERT (lnz <= (Int) (L->xsize)) ; + } + else + { + /* Li will be the same size as Lx */ + lnz = L->xsize ; + } + ASSERT (lnz >= 0) ; + PRINT1 (("simplicial lnz = "ID" to_packed: %d to_ll: %d L->xsize %g\n", + lnz, to_ll, to_packed, (double) L->xsize)) ; + + Li = CHOLMOD(malloc) (lnz, sizeof (Int), Common) ; + if (Common->status < CHOLMOD_OK) + { + return ; /* out of memory */ + } + + if (!allocate_simplicial_numeric (L, Common)) + { + CHOLMOD(free) (lnz, sizeof (Int), Li, Common) ; + return ; /* out of memory */ + } + + /* ============================================== commit the changes to L */ + + L->i = Li ; + L->nzmax = lnz ; + + /* ---------------------------------------------------------------------- */ + /* convert the supernodal L, using template routine */ + /* ---------------------------------------------------------------------- */ + + switch (L->xtype) + { + + case CHOLMOD_REAL: + r_ll_super_to_simplicial_numeric (L, to_packed, to_ll, Common) ; + break ; + + case CHOLMOD_COMPLEX: + c_ll_super_to_simplicial_numeric (L, to_packed, to_ll, Common) ; + break ; + } + + /* ---------------------------------------------------------------------- */ + /* free unused parts of L */ + /* ---------------------------------------------------------------------- */ + + L->super = CHOLMOD(free) (nsuper+1, sizeof (Int), L->super, Common) ; + L->pi = CHOLMOD(free) (nsuper+1, sizeof (Int), L->pi, Common) ; + L->px = CHOLMOD(free) (nsuper+1, sizeof (Int), L->px, Common) ; + L->s = CHOLMOD(free) (L->ssize, sizeof (Int), L->s, Common) ; + + L->ssize = 0 ; + L->xsize = 0 ; + L->nsuper = 0 ; + L->maxesize = 0 ; + L->maxcsize = 0 ; + + L->is_super = FALSE ; + + DEBUG (CHOLMOD(dump_factor) (L, "done LL super to simplicial", Common)) ; +} + + +/* ========================================================================== */ +/* === super_symbolic_to_ll_super =========================================== */ +/* ========================================================================== */ + +/* Convert a supernodal symbolic factorization to a supernodal numeric + * factorization by allocating L->x. Contents of L->x are undefined. + */ + +static int super_symbolic_to_ll_super +( + int to_xtype, + cholmod_factor *L, + cholmod_common *Common +) +{ + double *Lx ; + Int wentry = (to_xtype == CHOLMOD_REAL) ? 1 : 2 ; + PRINT1 (("convert super sym to num\n")) ; + ASSERT (L->xtype == CHOLMOD_PATTERN && L->is_super) ; + Lx = CHOLMOD(malloc) (L->xsize, wentry * sizeof (double), Common) ; + PRINT1 (("xsize %g\n", (double) L->xsize)) ; + if (Common->status < CHOLMOD_OK) + { + return (FALSE) ; /* out of memory */ + } + + /* ============================================== commit the changes to L */ + + if (L->xsize == 1) + { + /* the caller won't expect to access this entry, but some CHOLMOD + * routines may. Set it to zero so that valgrind doesn't complain. */ + switch (to_xtype) + { + case CHOLMOD_REAL: + Lx [0] = 0 ; + break ; + + case CHOLMOD_COMPLEX: + Lx [0] = 0 ; + Lx [1] = 0 ; + break ; + } + } + + L->x = Lx ; + L->xtype = to_xtype ; + L->dtype = DTYPE ; + L->minor = L->n ; + return (TRUE) ; +} + + +/* ========================================================================== */ +/* === cholmod_change_factor ================================================ */ +/* ========================================================================== */ + +/* Convert a factor L. Some conversions simply allocate uninitialized space + * that meant to be filled later. + * + * If the conversion fails, the factor is left in its original form, with one + * exception. Converting a supernodal symbolic factor to a simplicial numeric + * one (with L=D=I) may leave the factor in simplicial symbolic form. + * + * Memory allocated for each conversion is listed below. + */ + +int CHOLMOD(change_factor) +( + /* ---- input ---- */ + int to_xtype, /* convert to CHOLMOD_PATTERN, _REAL, _COMPLEX, or + * _ZOMPLEX */ + int to_ll, /* TRUE: convert to LL', FALSE: LDL' */ + int to_super, /* TRUE: convert to supernodal, FALSE: simplicial */ + int to_packed, /* TRUE: pack simplicial columns, FALSE: do not pack */ + int to_monotonic, /* TRUE: put simplicial columns in order, FALSE: not */ + /* ---- in/out --- */ + cholmod_factor *L, /* factor to modify */ + /* --------------- */ + cholmod_common *Common +) +{ + + /* ---------------------------------------------------------------------- */ + /* get inputs */ + /* ---------------------------------------------------------------------- */ + + RETURN_IF_NULL_COMMON (FALSE) ; + RETURN_IF_NULL (L, FALSE) ; + RETURN_IF_XTYPE_INVALID (L, CHOLMOD_PATTERN, CHOLMOD_ZOMPLEX, FALSE) ; + if (to_xtype < CHOLMOD_PATTERN || to_xtype > CHOLMOD_ZOMPLEX) + { + ERROR (CHOLMOD_INVALID, "xtype invalid") ; + return (FALSE) ; + } + Common->status = CHOLMOD_OK ; + + PRINT1 (("-----convert from (%d,%d,%d,%d,%d) to (%d,%d,%d,%d,%d)\n", + L->xtype, L->is_ll, L->is_super, L_is_packed (L, Common), L->is_monotonic, + to_xtype, to_ll, to_super, to_packed, to_monotonic)) ; + + /* ensure all parameters are TRUE/FALSE */ + to_ll = BOOLEAN (to_ll) ; + to_super = BOOLEAN (to_super) ; + + ASSERT (BOOLEAN (L->is_ll) == L->is_ll) ; + ASSERT (BOOLEAN (L->is_super) == L->is_super) ; + + if (to_super && to_xtype == CHOLMOD_ZOMPLEX) + { + ERROR (CHOLMOD_INVALID, "supernodal zomplex L not supported") ; + return (FALSE) ; + } + + /* ---------------------------------------------------------------------- */ + /* convert */ + /* ---------------------------------------------------------------------- */ + + if (to_xtype == CHOLMOD_PATTERN) + { + + /* ------------------------------------------------------------------ */ + /* convert to symbolic */ + /* ------------------------------------------------------------------ */ + + if (!to_super) + { + + /* -------------------------------------------------------------- */ + /* convert any factor into a simplicial symbolic factor */ + /* -------------------------------------------------------------- */ + + any_to_simplicial_symbolic (L, to_ll, Common) ; /* cannot fail */ + + } + else + { + + /* -------------------------------------------------------------- */ + /* convert to a supernodal symbolic factor */ + /* -------------------------------------------------------------- */ + + if (L->xtype != CHOLMOD_PATTERN && L->is_super) + { + /* convert from supernodal numeric to supernodal symbolic. + * this preserves symbolic pattern of L, discards numeric + * values */ + ll_super_to_super_symbolic (L, Common) ; /* cannot fail */ + } + else if (L->xtype == CHOLMOD_PATTERN && !(L->is_super)) + { + /* convert from simplicial symbolic to supernodal symbolic. + * contents of supernodal pattern are uninitialized. Not meant + * for the end user. */ + simplicial_symbolic_to_super_symbolic (L, Common) ; + } + else + { + /* cannot convert from simplicial numeric to supernodal + * symbolic */ + ERROR (CHOLMOD_INVALID, + "cannot convert L to supernodal symbolic") ; + } + } + + } + else + { + + /* ------------------------------------------------------------------ */ + /* convert to numeric */ + /* ------------------------------------------------------------------ */ + + if (to_super) + { + + /* -------------------------------------------------------------- */ + /* convert to supernodal numeric factor */ + /* -------------------------------------------------------------- */ + + if (L->xtype == CHOLMOD_PATTERN) + { + if (L->is_super) + { + /* Convert supernodal symbolic to supernodal numeric. + * Contents of supernodal numeric values are uninitialized. + * This is used by cholmod_super_numeric. Not meant for + * the end user. */ + super_symbolic_to_ll_super (to_xtype, L, Common) ; + } + else + { + /* Convert simplicial symbolic to supernodal numeric. + * Contents not defined. This is used by + * Core/cholmod_copy_factor only. Not meant for the end + * user. */ + if (!simplicial_symbolic_to_super_symbolic (L, Common)) + { + /* failure, convert back to simplicial symbolic */ + any_to_simplicial_symbolic (L, to_ll, Common) ; + } + else + { + /* conversion to super symbolic OK, allocate numeric + * part */ + super_symbolic_to_ll_super (to_xtype, L, Common) ; + } + } + } + else + { + /* nothing to do if L is already in supernodal numeric form */ + if (!(L->is_super)) + { + ERROR (CHOLMOD_INVALID, + "cannot convert simplicial L to supernodal") ; + } + /* FUTURE WORK: convert to/from supernodal LL' and LDL' */ + } + + } + else + { + + /* -------------------------------------------------------------- */ + /* convert any factor to simplicial numeric */ + /* -------------------------------------------------------------- */ + + if (L->xtype == CHOLMOD_PATTERN && !(L->is_super)) + { + + /* ---------------------------------------------------------- */ + /* convert simplicial symbolic to simplicial numeric (L=I,D=I)*/ + /* ---------------------------------------------------------- */ + + simplicial_symbolic_to_simplicial_numeric (L, to_ll, to_packed, + to_xtype, Common) ; + + } + else if (L->xtype != CHOLMOD_PATTERN && L->is_super) + { + + /* ---------------------------------------------------------- */ + /* convert a supernodal LL' to simplicial numeric */ + /* ---------------------------------------------------------- */ + + ll_super_to_simplicial_numeric (L, to_packed, to_ll, Common) ; + + } + else if (L->xtype == CHOLMOD_PATTERN && L->is_super) + { + + /* ---------------------------------------------------------- */ + /* convert a supernodal symbolic to simplicial numeric (L=D=I)*/ + /* ---------------------------------------------------------- */ + + any_to_simplicial_symbolic (L, to_ll, Common) ; + /* if the following fails, it leaves the factor in simplicial + * symbolic form */ + simplicial_symbolic_to_simplicial_numeric (L, to_ll, to_packed, + to_xtype, Common) ; + + } + else + { + + /* ---------------------------------------------------------- */ + /* change a simplicial numeric factor */ + /* ---------------------------------------------------------- */ + + /* change LL' to LDL', LDL' to LL', or leave as-is. pack the + * columns of L, or leave as-is. Ensure the columns are + * monotonic, or leave as-is. */ + + change_simplicial_numeric (L, to_ll, to_packed, to_monotonic, + Common) ; + } + } + } + + /* ---------------------------------------------------------------------- */ + /* return result */ + /* ---------------------------------------------------------------------- */ + + return (Common->status >= CHOLMOD_OK) ; +} diff --git a/CHOLMOD/Core/cholmod_common.c b/CHOLMOD/Core/cholmod_common.c new file mode 100644 index 0000000000..7bf3c3ccb5 --- /dev/null +++ b/CHOLMOD/Core/cholmod_common.c @@ -0,0 +1,755 @@ +//------------------------------------------------------------------------------ +// CHOLMOD/Core/cholmod_common: core methods for cholmod_common object +//------------------------------------------------------------------------------ + +// CHOLMOD/Core Module. Copyright (C) 2005-2022, University of Florida. +// All Rights Reserved. Author: Timothy A. Davis +// SPDX-License-Identifier: LGPL-2.1+ + +//------------------------------------------------------------------------------ + +/* Core utility routines for the cholmod_common object: + * + * Primary routines: + * ----------------- + * cholmod_start the first call to CHOLMOD + * cholmod_finish the last call to CHOLMOD + * + * Secondary routines: + * ------------------- + * cholmod_defaults restore (most) default control parameters + * cholmod_allocate_work allocate (or reallocate) workspace in Common + * cholmod_free_work free workspace in Common + * cholmod_clear_flag clear Common->Flag in workspace + * cholmod_maxrank column dimension of Common->Xwork workspace + * + * The Common object is unique. It cannot be allocated or deallocated by + * CHOLMOD, since it contains the definition of the memory management routines + * used (pointers to malloc, free, realloc, and calloc, or their equivalent). + * The Common object contains workspace that is used between calls to + * CHOLMOD routines. This workspace allocated by CHOLMOD as needed, by + * cholmod_allocate_work and cholmod_free_work. + */ + +#include "cholmod_internal.h" + +/* ========================================================================== */ +/* === cholmod_start ======================================================== */ +/* ========================================================================== */ + +/* Initialize Common default parameters and statistics. Sets workspace + * pointers to NULL. + * + * This routine must be called just once, prior to calling any other CHOLMOD + * routine. Do not call this routine after any other CHOLMOD routine (except + * cholmod_finish, to start a new CHOLMOD session), or a memory leak will + * occur. + * + * workspace: none + */ + +int CHOLMOD(start) +( + cholmod_common *Common +) +{ + int k ; + + if (Common == NULL) + { + return (FALSE) ; + } + + /* ---------------------------------------------------------------------- */ + /* user error handling routine */ + /* ---------------------------------------------------------------------- */ + + Common->error_handler = NULL ; + + /* ---------------------------------------------------------------------- */ + /* integer and numerical types */ + /* ---------------------------------------------------------------------- */ + + Common->itype = ITYPE ; + Common->dtype = DTYPE ; + + /* ---------------------------------------------------------------------- */ + /* default control parameters */ + /* ---------------------------------------------------------------------- */ + + CHOLMOD(defaults) (Common) ; + Common->try_catch = FALSE ; + + /* ---------------------------------------------------------------------- */ + /* memory management routines */ + /* ---------------------------------------------------------------------- */ + + /* moved to SuiteSparse_config */ + + /* ---------------------------------------------------------------------- */ + /* complex arithmetic routines */ + /* ---------------------------------------------------------------------- */ + + /* moved to SuiteSparse_config */ + + /* ---------------------------------------------------------------------- */ + /* print routine */ + /* ---------------------------------------------------------------------- */ + + /* moved to SuiteSparse_config */ + + /* ---------------------------------------------------------------------- */ + /* workspace */ + /* ---------------------------------------------------------------------- */ + + /* This code assumes the workspace held in Common is not initialized. If + * it is, then a memory leak will occur because the pointers are + * overwritten with NULL. */ + + Common->nrow = 0 ; + Common->mark = EMPTY ; + Common->xworksize = 0 ; + Common->iworksize = 0 ; + Common->Flag = NULL ; + Common->Head = NULL ; + Common->Iwork = NULL ; + Common->Xwork = NULL ; + Common->no_workspace_reallocate = FALSE ; + + /* ---------------------------------------------------------------------- */ + /* statistics */ + /* ---------------------------------------------------------------------- */ + + /* fl and lnz are computed in cholmod_analyze and cholmod_rowcolcounts */ + Common->fl = EMPTY ; + Common->lnz = EMPTY ; + + /* modfl is computed in cholmod_updown, cholmod_rowadd, and cholmod_rowdel*/ + Common->modfl = EMPTY ; + + /* all routines use status as their error-report code */ + Common->status = CHOLMOD_OK ; + + Common->malloc_count = 0 ; /* # calls to malloc minus # calls to free */ + Common->memory_usage = 0 ; /* peak memory usage (in bytes) */ + Common->memory_inuse = 0 ; /* current memory in use (in bytes) */ + + Common->nrealloc_col = 0 ; + Common->nrealloc_factor = 0 ; + Common->ndbounds_hit = 0 ; + Common->rowfacfl = 0 ; + Common->aatfl = EMPTY ; + + /* Common->called_nd is TRUE if cholmod_analyze called or NESDIS */ + Common->called_nd = FALSE ; + + Common->blas_ok = TRUE ; /* false if SUITESPARSE_BLAS_INT overflows */ + + /* ---------------------------------------------------------------------- */ + /* default SuiteSparseQR knobs and statististics */ + /* ---------------------------------------------------------------------- */ + + for (k = 0 ; k < 10 ; k++) Common->SPQR_istat [k] = 0 ; + + Common->SPQR_flopcount_bound = 0 ; /* upper bound on flop count */ + Common->SPQR_tol_used = 0 ; /* tolerance used */ + Common->SPQR_norm_E_fro = 0 ; /* Frobenius norm of dropped entries */ + + Common->SPQR_grain = 1 ; /* no Intel TBB multitasking, by default */ + Common->SPQR_small = 1e6 ; /* target min task size for TBB */ + Common->SPQR_shrink = 1 ; /* controls SPQR shrink realloc */ + Common->SPQR_nthreads = 0 ; /* 0: let TBB decide how many threads to use */ + + Common->SPQR_flopcount = 0 ; /* flop count for SPQR */ + Common->SPQR_analyze_time = 0 ; /* analysis time for SPQR */ + Common->SPQR_factorize_time = 0 ; /* factorize time for SPQR */ + Common->SPQR_solve_time = 0 ; /* backsolve time for SPQR */ + + /* ---------------------------------------------------------------------- */ + /* GPU initializations */ + /* ---------------------------------------------------------------------- */ + + /* these are destroyed by cholmod_gpu_deallocate and cholmod_gpu_end */ + Common->cublasHandle = NULL ; + Common->cublasEventPotrf [0] = NULL ; + Common->cublasEventPotrf [1] = NULL ; + Common->cublasEventPotrf [2] = NULL ; + for (k = 0 ; k < CHOLMOD_HOST_SUPERNODE_BUFFERS ; k++) + { + Common->gpuStream [k] = NULL ; + Common->updateCBuffersFree [k] = NULL ; + } + Common->updateCKernelsComplete = NULL; + + /* these are destroyed by cholmod_gpu_deallocate */ + Common->dev_mempool = NULL; + Common->dev_mempool_size = 0; + Common->host_pinned_mempool = NULL; + Common->host_pinned_mempool_size = 0; + + Common->syrkStart = 0 ; + + Common->cholmod_cpu_gemm_time = 0 ; + Common->cholmod_cpu_syrk_time = 0 ; + Common->cholmod_cpu_trsm_time = 0 ; + Common->cholmod_cpu_potrf_time = 0 ; + Common->cholmod_gpu_gemm_time = 0 ; + Common->cholmod_gpu_syrk_time = 0 ; + Common->cholmod_gpu_trsm_time = 0 ; + Common->cholmod_gpu_potrf_time = 0 ; + Common->cholmod_assemble_time = 0 ; + Common->cholmod_assemble_time2 = 0 ; + + Common->cholmod_cpu_gemm_calls = 0 ; + Common->cholmod_cpu_syrk_calls = 0 ; + Common->cholmod_cpu_trsm_calls = 0 ; + Common->cholmod_cpu_potrf_calls = 0 ; + + Common->cholmod_gpu_gemm_calls = 0 ; + Common->cholmod_gpu_syrk_calls = 0 ; + Common->cholmod_gpu_trsm_calls = 0 ; + Common->cholmod_gpu_potrf_calls = 0 ; + + Common->maxGpuMemBytes = 0; + Common->maxGpuMemFraction = 0.0; + + /* SPQR statistics and settings */ + Common->gpuMemorySize = 1 ; /* default: no GPU memory available */ + Common->gpuKernelTime = 0.0 ; + Common->gpuFlops = 0 ; + Common->gpuNumKernelLaunches = 0 ; + + // ------------------------------------------------------------------------- + // OpenMP initializations + // ------------------------------------------------------------------------- + + Common->chunk = 128000 ; + Common->nthreads_max = SUITESPARSE_OPENMP_MAX_THREADS ; + + // ------------------------------------------------------------------------- + // return result + // ------------------------------------------------------------------------- + + DEBUG_INIT ("cholmod start", Common) ; + + return (TRUE) ; +} + + +/* ========================================================================== */ +/* === cholmod_defaults ===================================================== */ +/* ========================================================================== */ + +/* Set Common default parameters, except for the function pointers. + * + * workspace: none + */ + +int CHOLMOD(defaults) +( + cholmod_common *Common +) +{ + Int i ; + + RETURN_IF_NULL_COMMON (FALSE) ; + + /* ---------------------------------------------------------------------- */ + /* default control parameters */ + /* ---------------------------------------------------------------------- */ + + Common->dbound = 0.0 ; + Common->grow0 = 1.2 ; + Common->grow1 = 1.2 ; + Common->grow2 = 5 ; + Common->maxrank = 8 ; + + Common->final_asis = TRUE ; + Common->final_super = TRUE ; + Common->final_ll = FALSE ; + Common->final_pack = TRUE ; + Common->final_monotonic = TRUE ; + Common->final_resymbol = FALSE ; + + /* use simplicial factorization if flop/nnz(L) < 40, supernodal otherwise */ + Common->supernodal = CHOLMOD_AUTO ; + Common->supernodal_switch = 40 ; + + Common->nrelax [0] = 4 ; + Common->nrelax [1] = 16 ; + Common->nrelax [2] = 48 ; + Common->zrelax [0] = 0.8 ; + Common->zrelax [1] = 0.1 ; + Common->zrelax [2] = 0.05 ; + + Common->prefer_zomplex = FALSE ; + Common->prefer_upper = TRUE ; + Common->prefer_binary = FALSE ; + Common->quick_return_if_not_posdef = FALSE ; + + /* METIS workarounds */ + Common->metis_memory = 0.0 ; /* > 0 for memory guard (2 is reasonable) */ + Common->metis_nswitch = 3000 ; + Common->metis_dswitch = 0.66 ; + + Common->print = 3 ; + Common->precise = FALSE ; + + /* ---------------------------------------------------------------------- */ + /* default ordering methods */ + /* ---------------------------------------------------------------------- */ + + /* Note that if the Partition module is not installed, the CHOLMOD_METIS + * and CHOLMOD_NESDIS methods will not be available. cholmod_analyze will + * report the CHOLMOD_NOT_INSTALLED error, and safely skip over them. + */ + +#if (CHOLMOD_MAXMETHODS < 9) +#error "CHOLMOD_MAXMETHODS must be 9 or more (defined in cholmod_core.h)." +#endif + + /* default strategy: try given, AMD, and then METIS if AMD reports high + * fill-in. NESDIS can be used instead, if Common->default_nesdis is TRUE. + */ + Common->nmethods = 0 ; /* use default strategy */ + Common->default_nesdis = FALSE ; /* use METIS in default strategy */ + + Common->current = 0 ; /* current method being tried */ + Common->selected = 0 ; /* the best method selected */ + + /* first, fill each method with default parameters */ + for (i = 0 ; i <= CHOLMOD_MAXMETHODS ; i++) + { + /* CHOLMOD's default method is AMD for A or AA' */ + Common->method [i].ordering = CHOLMOD_AMD ; + + /* CHOLMOD nested dissection and minimum degree parameter */ + Common->method [i].prune_dense = 10.0 ; /* dense row/col control */ + + /* min degree parameters (AMD, COLAMD, SYMAMD, CAMD, CCOLAMD, CSYMAMD)*/ + Common->method [i].prune_dense2 = -1 ; /* COLAMD dense row control */ + Common->method [i].aggressive = TRUE ; /* aggressive absorption */ + Common->method [i].order_for_lu = FALSE ;/* order for Cholesky not LU */ + + /* CHOLMOD's nested dissection (METIS + constrained AMD) */ + Common->method [i].nd_small = 200 ; /* small graphs aren't cut */ + Common->method [i].nd_compress = TRUE ; /* compress graph & subgraphs */ + Common->method [i].nd_camd = 1 ; /* use CAMD */ + Common->method [i].nd_components = FALSE ; /* lump connected comp. */ + Common->method [i].nd_oksep = 1.0 ; /* sep ok if < oksep*n */ + + /* statistics for each method are not yet computed */ + Common->method [i].fl = EMPTY ; + Common->method [i].lnz = EMPTY ; + } + + Common->postorder = TRUE ; /* follow ordering with weighted postorder */ + + /* Next, define some methods. The first five use default parameters. */ + Common->method [0].ordering = CHOLMOD_GIVEN ; /* skip if UserPerm NULL */ + Common->method [1].ordering = CHOLMOD_AMD ; + Common->method [2].ordering = CHOLMOD_METIS ; + Common->method [3].ordering = CHOLMOD_NESDIS ; + Common->method [4].ordering = CHOLMOD_NATURAL ; + + /* CHOLMOD's nested dissection with large leaves of separator tree */ + Common->method [5].ordering = CHOLMOD_NESDIS ; + Common->method [5].nd_small = 20000 ; + + /* CHOLMOD's nested dissection with tiny leaves, and no AMD ordering */ + Common->method [6].ordering = CHOLMOD_NESDIS ; + Common->method [6].nd_small = 4 ; + Common->method [6].nd_camd = 0 ; /* no CSYMAMD or CAMD */ + + /* CHOLMOD's nested dissection with no dense node removal */ + Common->method [7].ordering = CHOLMOD_NESDIS ; + Common->method [7].prune_dense = -1. ; + + /* COLAMD for A*A', AMD for A */ + Common->method [8].ordering = CHOLMOD_COLAMD ; + + /* ---------------------------------------------------------------------- */ + /* GPU configuration and statistics */ + /* ---------------------------------------------------------------------- */ + +#ifdef DLONG + Common->useGPU = EMPTY ; +#else + /* GPU acceleration is not supported for int version of CHOLMOD */ + Common->useGPU = 0 ; +#endif + + return (TRUE) ; +} + + +/* ========================================================================== */ +/* === cholmod_finish ======================================================= */ +/* ========================================================================== */ + +/* The last call to CHOLMOD must be cholmod_finish. You may call this routine + * more than once, and can safely call any other CHOLMOD routine after calling + * it (including cholmod_start). + * + * The statistics and parameter settings in Common are preserved. The + * workspace in Common is freed. This routine is just another name for + * cholmod_free_work. + */ + +int CHOLMOD(finish) +( + cholmod_common *Common +) +{ + return (CHOLMOD(free_work) (Common)) ; +} + + +/* ========================================================================== */ +/* === cholmod_allocate_work ================================================ */ +/* ========================================================================== */ + +/* Allocate and initialize workspace for CHOLMOD routines, or increase the size + * of already-allocated workspace. If enough workspace is already allocated, + * then nothing happens. + * + * workspace: Flag (nrow), Head (nrow+1), Iwork (iworksize), Xwork (xworksize) + */ + +int CHOLMOD(allocate_work) +( + /* ---- input ---- */ + size_t nrow, /* # of rows in the matrix A */ + size_t iworksize, /* size of Iwork */ + size_t xworksize, /* size of Xwork */ + /* --------------- */ + cholmod_common *Common +) +{ + double *W ; + Int *Head ; + Int i ; + size_t nrow1 ; + int ok = TRUE ; + + /* ---------------------------------------------------------------------- */ + /* get inputs */ + /* ---------------------------------------------------------------------- */ + + RETURN_IF_NULL_COMMON (FALSE) ; + Common->status = CHOLMOD_OK ; + + /* ---------------------------------------------------------------------- */ + /* Allocate Flag (nrow) and Head (nrow+1) */ + /* ---------------------------------------------------------------------- */ + + nrow = MAX (1, nrow) ; + + /* nrow1 = nrow + 1 */ + nrow1 = CHOLMOD(add_size_t) (nrow, 1, &ok) ; + if (!ok) + { + /* nrow+1 causes size_t overflow ; problem is too large */ + Common->status = CHOLMOD_TOO_LARGE ; + CHOLMOD(free_work) (Common) ; + return (FALSE) ; + } + + if (nrow > Common->nrow) + { + + if (Common->no_workspace_reallocate) + { + /* CHOLMOD is not allowed to change the workspace here */ + Common->status = CHOLMOD_INVALID ; + return (FALSE) ; + } + + /* free the old workspace (if any) and allocate new space */ + Common->Flag = CHOLMOD(free) (Common->nrow, sizeof (Int), Common->Flag, + Common) ; + Common->Head = CHOLMOD(free) (Common->nrow+1,sizeof (Int), Common->Head, + Common) ; + Common->Flag = CHOLMOD(malloc) (nrow, sizeof (Int), Common) ; + Common->Head = CHOLMOD(malloc) (nrow1, sizeof (Int), Common) ; + + /* record the new size of Flag and Head */ + Common->nrow = nrow ; + + if (Common->status < CHOLMOD_OK) + { + CHOLMOD(free_work) (Common) ; + return (FALSE) ; + } + + /* initialize Flag and Head */ + Common->mark = EMPTY ; + CHOLMOD(clear_flag) (Common) ; + Head = Common->Head ; + for (i = 0 ; i <= (Int) (nrow) ; i++) + { + Head [i] = EMPTY ; + } + } + + /* ---------------------------------------------------------------------- */ + /* Allocate Iwork (iworksize) */ + /* ---------------------------------------------------------------------- */ + + iworksize = MAX (1, iworksize) ; + if (iworksize > Common->iworksize) + { + + if (Common->no_workspace_reallocate) + { + /* CHOLMOD is not allowed to change the workspace here */ + Common->status = CHOLMOD_INVALID ; + return (FALSE) ; + } + + /* free the old workspace (if any) and allocate new space. + * integer overflow safely detected in cholmod_malloc */ + CHOLMOD(free) (Common->iworksize, sizeof (Int), Common->Iwork, Common) ; + Common->Iwork = CHOLMOD(malloc) (iworksize, sizeof (Int), Common) ; + + /* record the new size of Iwork */ + Common->iworksize = iworksize ; + + if (Common->status < CHOLMOD_OK) + { + CHOLMOD(free_work) (Common) ; + return (FALSE) ; + } + + /* note that Iwork does not need to be initialized */ + } + + /* ---------------------------------------------------------------------- */ + /* Allocate Xwork (xworksize) and set it to ((double) 0.) */ + /* ---------------------------------------------------------------------- */ + + /* make sure xworksize is >= 1 */ + xworksize = MAX (1, xworksize) ; + if (xworksize > Common->xworksize) + { + + if (Common->no_workspace_reallocate) + { + /* CHOLMOD is not allowed to change the workspace here */ + Common->status = CHOLMOD_INVALID ; + return (FALSE) ; + } + + /* free the old workspace (if any) and allocate new space */ + CHOLMOD(free) (Common->xworksize, sizeof (double), Common->Xwork, + Common) ; + Common->Xwork = CHOLMOD(malloc) (xworksize, sizeof (double), Common) ; + + /* record the new size of Xwork */ + Common->xworksize = xworksize ; + + if (Common->status < CHOLMOD_OK) + { + CHOLMOD(free_work) (Common) ; + return (FALSE) ; + } + + /* initialize Xwork */ + W = Common->Xwork ; + for (i = 0 ; i < (Int) xworksize ; i++) + { + W [i] = 0. ; + } + } + + return (TRUE) ; +} + + +/* ========================================================================== */ +/* === cholmod_free_work ==================================================== */ +/* ========================================================================== */ + +/* Deallocate the CHOLMOD workspace. + * + * workspace: deallocates all workspace in Common + */ + +int CHOLMOD(free_work) +( + cholmod_common *Common +) +{ + RETURN_IF_NULL_COMMON (FALSE) ; + Common->Flag = CHOLMOD(free) (Common->nrow, sizeof (Int), + Common->Flag, Common) ; + Common->Head = CHOLMOD(free) (Common->nrow+1, sizeof (Int), + Common->Head, Common) ; + Common->Iwork = CHOLMOD(free) (Common->iworksize, sizeof (Int), + Common->Iwork, Common) ; + Common->Xwork = CHOLMOD(free) (Common->xworksize, sizeof (double), + Common->Xwork, Common) ; + Common->nrow = 0 ; + Common->iworksize = 0 ; + Common->xworksize = 0 ; + +#ifdef SUITESPARSE_CUDA + CHOLMOD(gpu_deallocate) (Common) ; +#endif + return (TRUE) ; +} + + +/* ========================================================================== */ +/* === cholmod_clear_flag =================================================== */ +/* ========================================================================== */ + +/* Increment mark to ensure Flag [0..nrow-1] < mark. If integer overflow + * occurs, or mark was initially negative, reset the entire array. This is + * not an error condition, but an intended function of the Flag workspace. + * + * workspace: Flag (nrow). Does not modify Flag if nrow is zero. + */ + +int64_t CHOLMOD(clear_flag) +( + cholmod_common *Common +) +{ + Int i, nrow, *Flag ; + + RETURN_IF_NULL_COMMON (-1) ; + + Common->mark++ ; + if (Common->mark <= 0) + { + nrow = Common->nrow ; + Flag = Common->Flag ; + PRINT2 (("reset Flag: nrow "ID"\n", nrow)) ; + PRINT2 (("reset Flag: mark %ld\n", Common->mark)) ; + for (i = 0 ; i < nrow ; i++) + { + Flag [i] = EMPTY ; + } + Common->mark = 0 ; + } + return (Common->mark) ; +} + + +/* ========================================================================== */ +/* ==== cholmod_maxrank ===================================================== */ +/* ========================================================================== */ + +/* Find a valid value of Common->maxrank. Returns 0 if error, or 2, 4, or 8 + * if successful. */ + +size_t CHOLMOD(maxrank) /* returns validated value of Common->maxrank */ +( + /* ---- input ---- */ + size_t n, /* A and L will have n rows */ + /* --------------- */ + cholmod_common *Common +) +{ + size_t maxrank ; + RETURN_IF_NULL_COMMON (0) ; + maxrank = Common->maxrank ; + if (n > 0) + { + /* Ensure maxrank*n*sizeof(double) does not result in integer overflow. + * If n is so large that 2*n*sizeof(double) results in integer overflow + * (n = 268,435,455 if an Int is 32 bits), then maxrank will be 0 or 1, + * but maxrank will be set to 2 below. 2*n will not result in integer + * overflow, and CHOLMOD will run out of memory or safely detect integer + * overflow elsewhere. + */ + maxrank = MIN (maxrank, SIZE_MAX / (n * sizeof (double))) ; + } + if (maxrank <= 2) + { + maxrank = 2 ; + } + else if (maxrank <= 4) + { + maxrank = 4 ; + } + else + { + maxrank = 8 ; + } + return (maxrank) ; +} + + +/* ========================================================================== */ +/* === cholmod_dbound ======================================================= */ +/* ========================================================================== */ + +/* Ensure the absolute value of a diagonal entry, D (j,j), is greater than + * Common->dbound. This routine is not meant for the user to call. It is used + * by the various LDL' factorization and update/downdate routines. The + * default value of Common->dbound is zero, and in that case this routine is not + * called at all. No change is made if D (j,j) is NaN. CHOLMOD does not call + * this routine if Common->dbound is NaN. + */ + +double CHOLMOD(dbound) /* returns modified diagonal entry of D */ +( + /* ---- input ---- */ + double dj, /* diagonal entry of D, for LDL' factorization */ + /* --------------- */ + cholmod_common *Common +) +{ + double dbound ; + RETURN_IF_NULL_COMMON (0) ; + if (!IS_NAN (dj)) + { + dbound = Common->dbound ; + if (dj < 0) + { + if (dj > -dbound) + { + dj = -dbound ; + Common->ndbounds_hit++ ; + if (Common->status == CHOLMOD_OK) + { + ERROR (CHOLMOD_DSMALL, "diagonal below threshold") ; + } + } + } + else + { + if (dj < dbound) + { + dj = dbound ; + Common->ndbounds_hit++ ; + if (Common->status == CHOLMOD_OK) + { + ERROR (CHOLMOD_DSMALL, "diagonal below threshold") ; + } + } + } + } + return (dj) ; +} + + +/* ========================================================================== */ +/* === scorecomp ============================================================ */ +/* ========================================================================== */ + +/* For sorting descendant supernodes with qsort */ +int CHOLMOD(score_comp) (struct cholmod_descendant_score_t *i, + struct cholmod_descendant_score_t *j) +{ + if ((*i).score < (*j).score) + { + return (1) ; + } + else + { + return (-1) ; + } +} diff --git a/CHOLMOD/Core/cholmod_complex.c b/CHOLMOD/Core/cholmod_complex.c new file mode 100644 index 0000000000..f2026a19db --- /dev/null +++ b/CHOLMOD/Core/cholmod_complex.c @@ -0,0 +1,487 @@ +//------------------------------------------------------------------------------ +// CHOLMOD/Core/cholmod_complex: complex functions +//------------------------------------------------------------------------------ + +// CHOLMOD/Core Module. Copyright (C) 2005-2022, University of Florida. +// All Rights Reserved. Author: Timothy A. Davis +// SPDX-License-Identifier: LGPL-2.1+ + +//------------------------------------------------------------------------------ + +/* If you convert a matrix that contains uninitialized data, valgrind will + * complain. This can occur in a factor L which has gaps (a partial + * factorization, or after updates that change the nonzero pattern), an + * unpacked sparse matrix, a dense matrix with leading dimension d > # of rows, + * or any matrix (dense, sparse, triplet, or factor) with more space allocated + * than is used. You can safely ignore any of these complaints by valgrind. */ + +#include "cholmod_internal.h" + +/* ========================================================================== */ +/* === cholmod_hypot ======================================================== */ +/* ========================================================================== */ + +double CHOLMOD(hypot) (double x, double y) +{ + return (SuiteSparse_config_hypot (x, y)) ; +} + + +/* ========================================================================== */ +/* === cholmod_divcomplex =================================================== */ +/* ========================================================================== */ + +/* c = a/b where c, a, and b are complex. The real and imaginary parts are + * passed as separate arguments to this routine. The NaN case is ignored + * for the double relop br >= bi. Returns 1 if the denominator is zero, + * 0 otherwise. Note that this return value is the single exception to the + * rule that all CHOLMOD routines that return int return TRUE if successful + * or FALSE otherise. + * + * This uses ACM Algo 116, by R. L. Smith, 1962, which tries to avoid + * underflow and overflow. + * + * c can be the same variable as a or b. + * + * Default value of the SuiteSparse_config divcomplex_func pointer is + * SuiteSparse_divcomplex, located in SuiteSparse_config.c. + */ + +int CHOLMOD(divcomplex) +( + double ar, double ai, /* real and imaginary parts of a */ + double br, double bi, /* real and imaginary parts of b */ + double *cr, double *ci /* real and imaginary parts of c */ +) +{ + return (SuiteSparse_config_divcomplex (ar, ai, br, bi, cr, ci)) ; +} + + +/* ========================================================================== */ +/* === change_complexity ==================================================== */ +/* ========================================================================== */ + +/* X and Z represent an array of size nz, with numeric xtype given by xtype_in. + * + * If xtype_in is: + * CHOLMOD_PATTERN: X and Z must be NULL. + * CHOLMOD_REAL: X is of size nz, Z must be NULL. + * CHOLMOD_COMPLEX: X is of size 2*nz, Z must be NULL. + * CHOLMOD_ZOMPLEX: X is of size nz, Z is of size nz. + * + * The array is changed into the numeric xtype given by xtype_out, with the + * same definitions of X and Z above. Note that the input conditions, above, + * are not checked. These are checked in the caller routine. + * + * Returns TRUE if successful, FALSE otherwise. X and Z are not modified if + * not successful. + */ + +static int change_complexity +( + /* ---- input ---- */ + Int nz, /* size of X and/or Z */ + int xtype_in, /* xtype of X and Z on input */ + int xtype_out, /* requested xtype of X and Z on output */ + int xtype1, /* xtype_out must be in the range [xtype1 .. xtype2] */ + int xtype2, + /* ---- in/out --- */ + void **XX, /* old X on input, new X on output */ + void **ZZ, /* old Z on input, new Z on output */ + /* --------------- */ + cholmod_common *Common +) +{ + double *Xold, *Zold, *Xnew, *Znew ; + Int k ; + size_t nz2 ; + + if (xtype_out < xtype1 || xtype_out > xtype2) + { + ERROR (CHOLMOD_INVALID, "invalid xtype") ; + return (FALSE) ; + } + + Common->status = CHOLMOD_OK ; + Xold = *XX ; + Zold = *ZZ ; + + switch (xtype_in) + { + + /* ------------------------------------------------------------------ */ + /* converting from pattern */ + /* ------------------------------------------------------------------ */ + + case CHOLMOD_PATTERN: + + switch (xtype_out) + { + + /* ---------------------------------------------------------- */ + /* pattern -> real */ + /* ---------------------------------------------------------- */ + + case CHOLMOD_REAL: + /* allocate X and set to all ones */ + Xnew = CHOLMOD(malloc) (nz, sizeof (double), Common) ; + if (Common->status < CHOLMOD_OK) + { + return (FALSE) ; + } + for (k = 0 ; k < nz ; k++) + { + Xnew [k] = 1 ; + } + *XX = Xnew ; + break ; + + /* ---------------------------------------------------------- */ + /* pattern -> complex */ + /* ---------------------------------------------------------- */ + + case CHOLMOD_COMPLEX: + /* allocate X and set to all ones */ + Xnew = CHOLMOD(malloc) (nz, 2*sizeof (double), Common) ; + if (Common->status < CHOLMOD_OK) + { + return (FALSE) ; + } + for (k = 0 ; k < nz ; k++) + { + Xnew [2*k ] = 1 ; + Xnew [2*k+1] = 0 ; + } + *XX = Xnew ; + break ; + + /* ---------------------------------------------------------- */ + /* pattern -> zomplex */ + /* ---------------------------------------------------------- */ + + case CHOLMOD_ZOMPLEX: + /* allocate X and Z and set to all ones */ + Xnew = CHOLMOD(malloc) (nz, sizeof (double), Common) ; + Znew = CHOLMOD(malloc) (nz, sizeof (double), Common) ; + if (Common->status < CHOLMOD_OK) + { + CHOLMOD(free) (nz, sizeof (double), Xnew, Common) ; + CHOLMOD(free) (nz, sizeof (double), Znew, Common) ; + return (FALSE) ; + } + for (k = 0 ; k < nz ; k++) + { + Xnew [k] = 1 ; + Znew [k] = 0 ; + } + *XX = Xnew ; + *ZZ = Znew ; + break ; + } + break ; + + /* ------------------------------------------------------------------ */ + /* converting from real */ + /* ------------------------------------------------------------------ */ + + case CHOLMOD_REAL: + + switch (xtype_out) + { + + /* ---------------------------------------------------------- */ + /* real -> pattern */ + /* ---------------------------------------------------------- */ + + case CHOLMOD_PATTERN: + /* free X */ + *XX = CHOLMOD(free) (nz, sizeof (double), *XX, Common) ; + break ; + + /* ---------------------------------------------------------- */ + /* real -> complex */ + /* ---------------------------------------------------------- */ + + case CHOLMOD_COMPLEX: + /* allocate a new X and copy the old X */ + Xnew = CHOLMOD(malloc) (nz, 2*sizeof (double), Common) ; + if (Common->status < CHOLMOD_OK) + { + return (FALSE) ; + } + for (k = 0 ; k < nz ; k++) + { + Xnew [2*k ] = Xold [k] ; + Xnew [2*k+1] = 0 ; + } + CHOLMOD(free) (nz, sizeof (double), *XX, Common) ; + *XX = Xnew ; + break ; + + /* ---------------------------------------------------------- */ + /* real -> zomplex */ + /* ---------------------------------------------------------- */ + + case CHOLMOD_ZOMPLEX: + /* allocate a new Z and set it to zero */ + Znew = CHOLMOD(malloc) (nz, sizeof (double), Common) ; + if (Common->status < CHOLMOD_OK) + { + return (FALSE) ; + } + for (k = 0 ; k < nz ; k++) + { + Znew [k] = 0 ; + } + *ZZ = Znew ; + break ; + } + break ; + + /* ------------------------------------------------------------------ */ + /* converting from complex */ + /* ------------------------------------------------------------------ */ + + case CHOLMOD_COMPLEX: + + switch (xtype_out) + { + + /* ---------------------------------------------------------- */ + /* complex -> pattern */ + /* ---------------------------------------------------------- */ + + case CHOLMOD_PATTERN: + /* free X */ + *XX = CHOLMOD(free) (nz, 2*sizeof (double), *XX, Common) ; + break ; + + /* ---------------------------------------------------------- */ + /* complex -> real */ + /* ---------------------------------------------------------- */ + + case CHOLMOD_REAL: + /* pack the real part of X, discarding the imaginary part */ + for (k = 0 ; k < nz ; k++) + { + Xold [k] = Xold [2*k] ; + } + /* shrink X in half (this cannot fail) */ + nz2 = 2*nz ; + *XX = CHOLMOD(realloc) (nz, sizeof (double), *XX, &nz2, + Common) ; + break ; + + /* ---------------------------------------------------------- */ + /* complex -> zomplex */ + /* ---------------------------------------------------------- */ + + case CHOLMOD_ZOMPLEX: + /* allocate X and Z and copy the old X into them */ + Xnew = CHOLMOD(malloc) (nz, sizeof (double), Common) ; + Znew = CHOLMOD(malloc) (nz, sizeof (double), Common) ; + if (Common->status < CHOLMOD_OK) + { + CHOLMOD(free) (nz, sizeof (double), Xnew, Common) ; + CHOLMOD(free) (nz, sizeof (double), Znew, Common) ; + return (FALSE) ; + } + for (k = 0 ; k < nz ; k++) + { + Xnew [k] = Xold [2*k ] ; + Znew [k] = Xold [2*k+1] ; + } + CHOLMOD(free) (nz, 2*sizeof (double), *XX, Common) ; + *XX = Xnew ; + *ZZ = Znew ; + break ; + } + break ; + + /* ------------------------------------------------------------------ */ + /* converting from zomplex */ + /* ------------------------------------------------------------------ */ + + case CHOLMOD_ZOMPLEX: + + switch (xtype_out) + { + + /* ---------------------------------------------------------- */ + /* zomplex -> pattern */ + /* ---------------------------------------------------------- */ + + case CHOLMOD_PATTERN: + /* free X and Z */ + *XX = CHOLMOD(free) (nz, sizeof (double), *XX, Common) ; + *ZZ = CHOLMOD(free) (nz, sizeof (double), *ZZ, Common) ; + break ; + + /* ---------------------------------------------------------- */ + /* zomplex -> real */ + /* ---------------------------------------------------------- */ + + case CHOLMOD_REAL: + /* free the imaginary part */ + *ZZ = CHOLMOD(free) (nz, sizeof (double), *ZZ, Common) ; + break ; + + /* ---------------------------------------------------------- */ + /* zomplex -> complex */ + /* ---------------------------------------------------------- */ + + case CHOLMOD_COMPLEX: + Xnew = CHOLMOD(malloc) (nz, 2*sizeof (double), Common) ; + if (Common->status < CHOLMOD_OK) + { + return (FALSE) ; + } + for (k = 0 ; k < nz ; k++) + { + Xnew [2*k ] = Xold [k] ; + Xnew [2*k+1] = Zold [k] ; + } + CHOLMOD(free) (nz, sizeof (double), *XX, Common) ; + CHOLMOD(free) (nz, sizeof (double), *ZZ, Common) ; + *XX = Xnew ; + *ZZ = NULL ; + break ; + + } + break ; + } + + return (TRUE) ; +} + + +/* ========================================================================== */ +/* === cholmod_sparse_xtype ================================================= */ +/* ========================================================================== */ + +/* Change the numeric xtype of a sparse matrix. Supports any type on input + * and output (pattern, real, complex, or zomplex). */ + +int CHOLMOD(sparse_xtype) +( + /* ---- input ---- */ + int to_xtype, /* requested xtype */ + /* ---- in/out --- */ + cholmod_sparse *A, /* sparse matrix to change */ + /* --------------- */ + cholmod_common *Common +) +{ + Int ok ; + RETURN_IF_NULL_COMMON (FALSE) ; + RETURN_IF_NULL (A, FALSE) ; + RETURN_IF_XTYPE_INVALID (A, CHOLMOD_PATTERN, CHOLMOD_ZOMPLEX, FALSE) ; + + ok = change_complexity (A->nzmax, A->xtype, to_xtype, + CHOLMOD_PATTERN, CHOLMOD_ZOMPLEX, &(A->x), &(A->z), Common) ; + if (ok) + { + A->xtype = to_xtype ; + } + return (ok) ; +} + + +/* ========================================================================== */ +/* === cholmod_triplet_xtype ================================================ */ +/* ========================================================================== */ + +/* Change the numeric xtype of a triplet matrix. Supports any type on input + * and output (pattern, real, complex, or zomplex). */ + +int CHOLMOD(triplet_xtype) +( + /* ---- input ---- */ + int to_xtype, /* requested xtype */ + /* ---- in/out --- */ + cholmod_triplet *T, /* triplet matrix to change */ + /* --------------- */ + cholmod_common *Common +) +{ + Int ok ; + RETURN_IF_NULL_COMMON (FALSE) ; + RETURN_IF_NULL (T, FALSE) ; + RETURN_IF_XTYPE_INVALID (T, CHOLMOD_PATTERN, CHOLMOD_ZOMPLEX, FALSE) ; + ok = change_complexity (T->nzmax, T->xtype, to_xtype, + CHOLMOD_PATTERN, CHOLMOD_ZOMPLEX, &(T->x), &(T->z), Common) ; + if (ok) + { + T->xtype = to_xtype ; + } + return (ok) ; +} + + +/* ========================================================================== */ +/* === cholmod_dense_xtype ================================================= */ +/* ========================================================================== */ + +/* Change the numeric xtype of a dense matrix. Supports real, complex or + * zomplex on input and output */ + +int CHOLMOD(dense_xtype) +( + /* ---- input ---- */ + int to_xtype, /* requested xtype */ + /* ---- in/out --- */ + cholmod_dense *X, /* dense matrix to change */ + /* --------------- */ + cholmod_common *Common +) +{ + Int ok ; + RETURN_IF_NULL_COMMON (FALSE) ; + RETURN_IF_NULL (X, FALSE) ; + RETURN_IF_XTYPE_INVALID (X, CHOLMOD_REAL, CHOLMOD_ZOMPLEX, FALSE) ; + ok = change_complexity (X->nzmax, X->xtype, to_xtype, + CHOLMOD_REAL, CHOLMOD_ZOMPLEX, &(X->x), &(X->z), Common) ; + if (ok) + { + X->xtype = to_xtype ; + } + return (ok) ; +} + + +/* ========================================================================== */ +/* === cholmod_factor_xtype ================================================= */ +/* ========================================================================== */ + +/* Change the numeric xtype of a factor. Supports real, complex or zomplex on + * input and output. Supernodal zomplex factors are not supported. */ + +int CHOLMOD(factor_xtype) +( + /* ---- input ---- */ + int to_xtype, /* requested xtype */ + /* ---- in/out --- */ + cholmod_factor *L, /* factor to change */ + /* --------------- */ + cholmod_common *Common +) +{ + Int ok ; + RETURN_IF_NULL_COMMON (FALSE) ; + RETURN_IF_NULL (L, FALSE) ; + RETURN_IF_XTYPE_INVALID (L, CHOLMOD_REAL, CHOLMOD_ZOMPLEX, FALSE) ; + if (L->is_super && + (L->xtype == CHOLMOD_ZOMPLEX || to_xtype == CHOLMOD_ZOMPLEX)) + { + ERROR (CHOLMOD_INVALID, "invalid xtype for supernodal L") ; + return (FALSE) ; + } + ok = change_complexity ((L->is_super ? L->xsize : L->nzmax), L->xtype, + to_xtype, CHOLMOD_REAL, CHOLMOD_ZOMPLEX, &(L->x), &(L->z), Common) ; + if (ok) + { + L->xtype = to_xtype ; + } + return (ok) ; +} diff --git a/CHOLMOD/Core/cholmod_copy.c b/CHOLMOD/Core/cholmod_copy.c new file mode 100644 index 0000000000..000e750af5 --- /dev/null +++ b/CHOLMOD/Core/cholmod_copy.c @@ -0,0 +1,402 @@ +//------------------------------------------------------------------------------ +// CHOLMOD/Core/cholmod_copy: copy a matrix +//------------------------------------------------------------------------------ + +// CHOLMOD/Core Module. Copyright (C) 2005-2022, University of Florida. +// All Rights Reserved. Author: Timothy A. Davis +// SPDX-License-Identifier: LGPL-2.1+ + +//------------------------------------------------------------------------------ + +/* C = A, which allocates C and copies A into C, with possible change of + * stype. The diagonal can optionally be removed. The numerical entries + * can optionally be copied. This routine differs from cholmod_copy_sparse, + * which makes an exact copy of a sparse matrix. + * + * A can be of any type (packed/unpacked, upper/lower/unsymmetric). C is + * packed and can be of any stype (upper/lower/unsymmetric), except that if + * A is rectangular C can only be unsymmetric. If the stype of A and C + * differ, then the appropriate conversion is made. + * + * Symmetry of A (A->stype): + * <0: lower: assume A is symmetric with just tril(A); the rest of A is ignored + * 0 unsym: assume A is unsymmetric; consider all entries in A + * >0 upper: assume A is symmetric with just triu(A); the rest of A is ignored + * + * Symmetry of C (stype parameter): + * <0 lower: return just tril(C) + * 0 unsym: return all of C + * >0 upper: return just triu(C) + * + * In MATLAB: Using cholmod_copy: + * ---------- ---------------------------- + * C = A ; A unsymmetric, C unsymmetric + * C = tril (A) ; A unsymmetric, C lower + * C = triu (A) ; A unsymmetric, C upper + * U = triu (A) ; L = tril (U',-1) ; C = L+U ; A upper, C unsymmetric + * C = triu (A)' ; A upper, C lower + * C = triu (A) ; A upper, C upper + * L = tril (A) ; U = triu (L',1) ; C = L+U ; A lower, C unsymmetric + * C = tril (A) ; A lower, C lower + * C = tril (A)' ; A lower, C upper + * + * workspace: Iwork (max (nrow,ncol)) + * + * A can have an xtype of pattern or real. Complex and zomplex cases only + * supported when mode <= 0 (in which case the numerical values are ignored). + */ + +#include "cholmod_internal.h" + +/* ========================================================================== */ +/* === copy_sym_to_unsym ==================================================== */ +/* ========================================================================== */ + +/* Construct an unsymmetric copy of a symmetric sparse matrix. This does the + * work for as C = cholmod_copy (A, 0, mode, Common) when A is symmetric. + * In this case, extra space can be added to C. + */ + +static cholmod_sparse *copy_sym_to_unsym +( + /* ---- input ---- */ + cholmod_sparse *A, /* matrix to copy */ + int mode, /* >0: numerical, 0: pattern, <0: pattern (no diag) + * -2: pattern only, no diagonal, add 50% + n extra + * space to C */ + /* --------------- */ + cholmod_common *Common +) +{ + double aij ; + double *Ax, *Cx ; + Int *Ap, *Ai, *Anz, *Cp, *Ci, *Wj, *Iwork ; + cholmod_sparse *C ; + Int nrow, ncol, nz, packed, j, p, pend, i, pc, up, lo, values, diag, + astype, extra ; + + /* ---------------------------------------------------------------------- */ + /* get inputs */ + /* ---------------------------------------------------------------------- */ + + nrow = A->nrow ; + ncol = A->ncol ; + Ap = A->p ; + Anz = A->nz ; + Ai = A->i ; + Ax = A->x ; + packed = A->packed ; + values = (mode > 0) && (A->xtype != CHOLMOD_PATTERN) ; + diag = (mode >= 0) ; + + astype = SIGN (A->stype) ; + up = (astype > 0) ; + lo = (astype < 0) ; + ASSERT (astype != 0) ; + + /* ---------------------------------------------------------------------- */ + /* create an unsymmetric copy of a symmetric matrix */ + /* ---------------------------------------------------------------------- */ + + Iwork = Common->Iwork ; + Wj = Iwork ; /* size ncol (i/i/l) */ + + /* In MATLAB notation, for converting a symmetric/upper matrix: + * U = triu (A) ; + * L = tril (U',-1) ; + * C = L + U ; + * + * For converting a symmetric/lower matrix to unsymmetric: + * L = tril (A) ; + * U = triu (L',1) ; + * C = L + U ; + */ + ASSERT (up || lo) ; + PRINT1 (("copy: convert symmetric to unsym\n")) ; + + /* count the number of entries in each column of C */ + for (j = 0 ; j < ncol ; j++) + { + Wj [j] = 0 ; + } + for (j = 0 ; j < ncol ; j++) + { + p = Ap [j] ; + pend = (packed) ? (Ap [j+1]) : (p + Anz [j]) ; + for ( ; p < pend ; p++) + { + i = Ai [p] ; + if (i == j) + { + /* the diagonal entry A(i,i) will appear just once + * (unless it is excluded with mode < 0) */ + if (diag) + { + Wj [j]++ ; + } + } + else if ((up && i < j) || (lo && i > j)) + { + /* upper case: A(i,j) is in the strictly upper part; + * A(j,i) will be added to the strictly lower part of C. + * lower case is the opposite. */ + Wj [j]++ ; + Wj [i]++ ; + } + } + } + nz = 0 ; + for (j = 0 ; j < ncol ; j++) + { + nz += Wj [j] ; + } + + extra = (mode == -2) ? (nz/2 + ncol) : 0 ; + + /* allocate C. C is sorted if and only if A is sorted */ + C = CHOLMOD(allocate_sparse) (nrow, ncol, nz + extra, A->sorted, TRUE, 0, + values ? A->xtype : CHOLMOD_PATTERN, Common) ; + if (Common->status < CHOLMOD_OK) + { + return (NULL) ; + } + + Cp = C->p ; + Ci = C->i ; + Cx = C->x ; + + /* construct the column pointers for C */ + p = 0 ; + for (j = 0 ; j < ncol ; j++) + { + Cp [j] = p ; + p += Wj [j] ; + } + Cp [ncol] = p ; + for (j = 0 ; j < ncol ; j++) + { + Wj [j] = Cp [j] ; + } + + /* construct C */ + if (values) + { + + /* pattern and values */ + ASSERT (diag) ; + for (j = 0 ; j < ncol ; j++) + { + p = Ap [j] ; + pend = (packed) ? (Ap [j+1]) : (p + Anz [j]) ; + for ( ; p < pend ; p++) + { + i = Ai [p] ; + aij = Ax [p] ; + if (i == j) + { + /* add diagonal entry A(i,i) to column i */ + pc = Wj [i]++ ; + Ci [pc] = i ; + Cx [pc] = aij ; + } + else if ((up && i < j) || (lo && i > j)) + { + /* add A(i,j) to column j */ + pc = Wj [j]++ ; + Ci [pc] = i ; + Cx [pc] = aij ; + /* add A(j,i) to column i */ + pc = Wj [i]++ ; + Ci [pc] = j ; + Cx [pc] = aij ; + } + } + } + + } + else + { + + /* pattern only, possibly excluding the diagonal */ + for (j = 0 ; j < ncol ; j++) + { + p = Ap [j] ; + pend = (packed) ? (Ap [j+1]) : (p + Anz [j]) ; + for ( ; p < pend ; p++) + { + i = Ai [p] ; + if (i == j) + { + /* add diagonal entry A(i,i) to column i + * (unless it is excluded with mode < 0) */ + if (diag) + { + Ci [Wj [i]++] = i ; + } + } + else if ((up && i < j) || (lo && i > j)) + { + /* add A(i,j) to column j */ + Ci [Wj [j]++] = i ; + /* add A(j,i) to column i */ + Ci [Wj [i]++] = j ; + } + } + } + } + + /* ---------------------------------------------------------------------- */ + /* return the result */ + /* ---------------------------------------------------------------------- */ + + DEBUG (i = CHOLMOD(dump_sparse) (C, "copy_sym_to_unsym", Common)) ; + PRINT1 (("mode %d nnzdiag "ID"\n", mode, i)) ; + ASSERT (IMPLIES (mode < 0, i == 0)) ; + return (C) ; +} + + +/* ========================================================================== */ +/* === cholmod_copy ========================================================= */ +/* ========================================================================== */ + +cholmod_sparse *CHOLMOD(copy) +( + /* ---- input ---- */ + cholmod_sparse *A, /* matrix to copy */ + int stype, /* requested stype of C */ + int mode, /* >0: numerical, 0: pattern, <0: pattern (no diag) */ + /* --------------- */ + cholmod_common *Common +) +{ + cholmod_sparse *C ; + Int nrow, ncol, up, lo, values, diag, astype ; + + /* ---------------------------------------------------------------------- */ + /* check inputs */ + /* ---------------------------------------------------------------------- */ + + RETURN_IF_NULL_COMMON (NULL) ; + RETURN_IF_NULL (A, NULL) ; + values = (mode > 0) && (A->xtype != CHOLMOD_PATTERN) ; + RETURN_IF_XTYPE_INVALID (A, CHOLMOD_PATTERN, + values ? CHOLMOD_REAL : CHOLMOD_ZOMPLEX, NULL) ; + nrow = A->nrow ; + ncol = A->ncol ; + if ((stype || A->stype) && nrow != ncol) + { + /* inputs invalid */ + ERROR (CHOLMOD_INVALID, "matrix invalid") ; + return (NULL) ; + } + Common->status = CHOLMOD_OK ; + + /* ---------------------------------------------------------------------- */ + /* allocate workspace */ + /* ---------------------------------------------------------------------- */ + + CHOLMOD(allocate_work) (0, MAX (nrow,ncol), 0, Common) ; + if (Common->status < CHOLMOD_OK) + { + /* out of memory */ + return (NULL) ; + } + + /* ---------------------------------------------------------------------- */ + /* get inputs */ + /* ---------------------------------------------------------------------- */ + + diag = (mode >= 0) ; + astype = SIGN (A->stype) ; + stype = SIGN (stype) ; + up = (astype > 0) ; + lo = (astype < 0) ; + + /* ---------------------------------------------------------------------- */ + /* copy the matrix */ + /* ---------------------------------------------------------------------- */ + + if (astype == stype) + { + + /* ------------------------------------------------------------------ */ + /* symmetry of A and C are the same */ + /* ------------------------------------------------------------------ */ + + /* copy A into C, keeping the same symmetry. If A is symmetric + * entries in the ignored part of A are not copied into C */ + C = CHOLMOD(band) (A, -nrow, ncol, mode, Common) ; + + } + else if (!astype) + { + + /* ------------------------------------------------------------------ */ + /* convert unsymmetric matrix A into a symmetric matrix C */ + /* ------------------------------------------------------------------ */ + + if (stype > 0) + { + /* C = triu (A) */ + C = CHOLMOD(band) (A, 0, ncol, mode, Common) ; + } + else + { + /* C = tril (A) */ + C = CHOLMOD(band) (A, -nrow, 0, mode, Common) ; + } + if (Common->status < CHOLMOD_OK) + { + /* out of memory */ + return (NULL) ; + } + C->stype = stype ; + + } + else if (astype == -stype) + { + + /* ------------------------------------------------------------------ */ + /* transpose a symmetric matrix */ + /* ------------------------------------------------------------------ */ + + /* converting upper to lower or lower to upper */ + /* workspace: Iwork (nrow) */ + C = CHOLMOD(transpose) (A, values, Common) ; + if (!diag) + { + /* remove diagonal, if requested */ + CHOLMOD(band_inplace) (-nrow, ncol, -1, C, Common) ; + } + + } + else + { + + /* ------------------------------------------------------------------ */ + /* create an unsymmetric copy of a symmetric matrix */ + /* ------------------------------------------------------------------ */ + + C = copy_sym_to_unsym (A, mode, Common) ; + } + + /* ---------------------------------------------------------------------- */ + /* return if error */ + /* ---------------------------------------------------------------------- */ + + if (Common->status < CHOLMOD_OK) + { + /* out of memory */ + return (NULL) ; + } + + /* ---------------------------------------------------------------------- */ + /* return the result */ + /* ---------------------------------------------------------------------- */ + + DEBUG (diag = CHOLMOD(dump_sparse) (C, "copy", Common)) ; + PRINT1 (("mode %d nnzdiag "ID"\n", mode, diag)) ; + ASSERT (IMPLIES (mode < 0, diag == 0)) ; + return (C) ; +} diff --git a/CHOLMOD/Core/cholmod_dense.c b/CHOLMOD/Core/cholmod_dense.c new file mode 100644 index 0000000000..9e80337fb8 --- /dev/null +++ b/CHOLMOD/Core/cholmod_dense.c @@ -0,0 +1,684 @@ +//------------------------------------------------------------------------------ +// CHOLMOD/Core/cholmod_dense: core methods for the cholmod_dense object +//------------------------------------------------------------------------------ + +// CHOLMOD/Core Module. Copyright (C) 2005-2022, University of Florida. +// All Rights Reserved. Author: Timothy A. Davis +// SPDX-License-Identifier: LGPL-2.1+ + +//------------------------------------------------------------------------------ + +/* Core utility routines for the cholmod_dense object: + * + * The solve routines and some of the MatrixOps and Modify routines use dense + * matrices as inputs. These are held in column-major order. With a leading + * dimension of d, the entry in row i and column j is held in x [i+j*d]. + * + * Primary routines: + * ----------------- + * cholmod_allocate_dense allocate a dense matrix + * cholmod_free_dense free a dense matrix + * + * Secondary routines: + * ------------------- + * cholmod_zeros allocate a dense matrix of all zeros + * cholmod_ones allocate a dense matrix of all ones + * cholmod_eye allocate a dense identity matrix + * cholmod_sparse_to_dense create a dense matrix copy of a sparse matrix + * cholmod_dense_to_sparse create a sparse matrix copy of a dense matrix + * cholmod_copy_dense create a copy of a dense matrix + * cholmod_copy_dense2 copy a dense matrix (pre-allocated) + * + * All routines in this file can handle the real, complex, and zomplex cases. + * Pattern-only dense matrices are not supported. cholmod_sparse_to_dense can + * take a pattern-only input sparse matrix, however, and cholmod_dense_to_sparse + * can generate a pattern-only output sparse matrix. + */ + +#include "cholmod_internal.h" + +/* ========================================================================== */ +/* === TEMPLATE ============================================================= */ +/* ========================================================================== */ + +#define PATTERN +#include "t_cholmod_dense.c" +#define REAL +#include "t_cholmod_dense.c" +#define COMPLEX +#include "t_cholmod_dense.c" +#define ZOMPLEX +#include "t_cholmod_dense.c" + +/* ========================================================================== */ +/* === cholmod_allocate_dense =============================================== */ +/* ========================================================================== */ + +/* Allocate a dense matrix with leading dimension d. The space is not + * initialized. + */ + +cholmod_dense *CHOLMOD(allocate_dense) +( + /* ---- input ---- */ + size_t nrow, /* # of rows of matrix */ + size_t ncol, /* # of columns of matrix */ + size_t d, /* leading dimension */ + int xtype, /* CHOLMOD_REAL, _COMPLEX, or _ZOMPLEX */ + /* --------------- */ + cholmod_common *Common +) +{ + cholmod_dense *X ; + size_t nzmax, nzmax0 ; + int ok = TRUE ; + + /* ---------------------------------------------------------------------- */ + /* get inputs */ + /* ---------------------------------------------------------------------- */ + + RETURN_IF_NULL_COMMON (NULL) ; + if (d < nrow) + { + ERROR (CHOLMOD_INVALID, "leading dimension invalid") ; + return (NULL) ; + } + if (xtype < CHOLMOD_REAL || xtype > CHOLMOD_ZOMPLEX) + { + ERROR (CHOLMOD_INVALID, "xtype invalid") ; + return (NULL) ; + } + + /* ensure the dimensions do not cause integer overflow */ + (void) CHOLMOD(add_size_t) (ncol, 2, &ok) ; + + /* nzmax = MAX (1, d*ncol) ; */ + nzmax = CHOLMOD(mult_size_t) (d, ncol, &ok) ; + nzmax = MAX (1, nzmax) ; + + if (!ok || (int64_t) nrow >= Int_max + || (int64_t) ncol >= Int_max + || (int64_t) nzmax >= Int_max) + { + ERROR (CHOLMOD_TOO_LARGE, "problem too large") ; + return (NULL) ; + } + Common->status = CHOLMOD_OK ; + + /* ---------------------------------------------------------------------- */ + /* allocate header */ + /* ---------------------------------------------------------------------- */ + + X = CHOLMOD(malloc) (sizeof (cholmod_dense), 1, Common) ; + if (Common->status < CHOLMOD_OK) + { + return (NULL) ; /* out of memory */ + } + + PRINT1 (("cholmod_allocate_dense %d-by-%d nzmax %d xtype %d\n", + nrow, ncol, nzmax, xtype)) ; + + X->nrow = nrow ; + X->ncol = ncol ; + X->nzmax = nzmax ; + X->xtype = xtype ; + X->dtype = DTYPE ; + X->x = NULL ; + X->z = NULL ; + X->d = d ; + + /* ---------------------------------------------------------------------- */ + /* allocate the matrix itself */ + /* ---------------------------------------------------------------------- */ + + nzmax0 = 0 ; + CHOLMOD(realloc_multiple) (nzmax, 0, xtype, NULL, NULL, &(X->x), &(X->z), + &nzmax0, Common) ; + + if (Common->status < CHOLMOD_OK) + { + CHOLMOD(free_dense) (&X, Common) ; + return (NULL) ; /* out of memory */ + } + + return (X) ; +} + + +/* ========================================================================== */ +/* === cholmod_zeros ======================================================== */ +/* ========================================================================== */ + +/* Allocate a dense matrix and set it to zero */ + +cholmod_dense *CHOLMOD(zeros) +( + /* ---- input ---- */ + size_t nrow, /* # of rows of matrix */ + size_t ncol, /* # of columns of matrix */ + int xtype, /* CHOLMOD_REAL, _COMPLEX, or _ZOMPLEX */ + /* --------------- */ + cholmod_common *Common +) +{ + cholmod_dense *X ; + double *Xx, *Xz ; + Int i, nz ; + + /* ---------------------------------------------------------------------- */ + /* allocate a dense matrix and set it to zero */ + /* ---------------------------------------------------------------------- */ + + RETURN_IF_NULL_COMMON (NULL) ; + X = CHOLMOD(allocate_dense) (nrow, ncol, nrow, xtype, Common) ; + if (Common->status < CHOLMOD_OK) + { + return (NULL) ; /* NULL Common, out of memory, or inputs invalid */ + } + + Xx = X->x ; + Xz = X->z ; + nz = MAX (1, X->nzmax) ; + + switch (xtype) + { + case CHOLMOD_REAL: + for (i = 0 ; i < nz ; i++) + { + Xx [i] = 0 ; + } + break ; + + case CHOLMOD_COMPLEX: + for (i = 0 ; i < 2*nz ; i++) + { + Xx [i] = 0 ; + } + break ; + + case CHOLMOD_ZOMPLEX: + for (i = 0 ; i < nz ; i++) + { + Xx [i] = 0 ; + } + for (i = 0 ; i < nz ; i++) + { + Xz [i] = 0 ; + } + break ; + } + + return (X) ; +} + + +/* ========================================================================== */ +/* === cholmod_ones ========================================================= */ +/* ========================================================================== */ + +/* Allocate a dense matrix and set it to zero */ + +cholmod_dense *CHOLMOD(ones) +( + /* ---- input ---- */ + size_t nrow, /* # of rows of matrix */ + size_t ncol, /* # of columns of matrix */ + int xtype, /* CHOLMOD_REAL, _COMPLEX, or _ZOMPLEX */ + /* --------------- */ + cholmod_common *Common +) +{ + cholmod_dense *X ; + double *Xx, *Xz ; + Int i, nz ; + + /* ---------------------------------------------------------------------- */ + /* allocate a dense matrix and set it to all ones */ + /* ---------------------------------------------------------------------- */ + + RETURN_IF_NULL_COMMON (NULL) ; + X = CHOLMOD(allocate_dense) (nrow, ncol, nrow, xtype, Common) ; + if (Common->status < CHOLMOD_OK) + { + return (NULL) ; /* NULL Common, out of memory, or inputs invalid */ + } + + Xx = X->x ; + Xz = X->z ; + nz = MAX (1, X->nzmax) ; + + switch (xtype) + { + case CHOLMOD_REAL: + for (i = 0 ; i < nz ; i++) + { + Xx [i] = 1 ; + } + break ; + + case CHOLMOD_COMPLEX: + for (i = 0 ; i < nz ; i++) + { + Xx [2*i ] = 1 ; + Xx [2*i+1] = 0 ; + } + break ; + + case CHOLMOD_ZOMPLEX: + for (i = 0 ; i < nz ; i++) + { + Xx [i] = 1 ; + } + for (i = 0 ; i < nz ; i++) + { + Xz [i] = 0 ; + } + break ; + } + + return (X) ; +} + + +/* ========================================================================== */ +/* === cholmod_eye ========================================================== */ +/* ========================================================================== */ + +/* Allocate a dense matrix and set it to the identity matrix */ + +cholmod_dense *CHOLMOD(eye) +( + /* ---- input ---- */ + size_t nrow, /* # of rows of matrix */ + size_t ncol, /* # of columns of matrix */ + int xtype, /* CHOLMOD_REAL, _COMPLEX, or _ZOMPLEX */ + /* --------------- */ + cholmod_common *Common +) +{ + cholmod_dense *X ; + double *Xx, *Xz ; + Int i, n, nz ; + + /* ---------------------------------------------------------------------- */ + /* allocate a dense matrix and set it to the identity matrix */ + /* ---------------------------------------------------------------------- */ + + RETURN_IF_NULL_COMMON (NULL) ; + X = CHOLMOD(zeros) (nrow, ncol, xtype, Common) ; + if (Common->status < CHOLMOD_OK) + { + return (NULL) ; /* NULL Common, out of memory, or inputs invalid */ + } + + nz = MAX (1, nrow*ncol) ; + Xx = X->x ; + Xz = X->z ; + + n = MIN (nrow, ncol) ; + + switch (xtype) + { + case CHOLMOD_REAL: + case CHOLMOD_ZOMPLEX: + for (i = 0 ; i < n ; i++) + { + Xx [i + i*nrow] = 1 ; + } + break ; + + case CHOLMOD_COMPLEX: + for (i = 0 ; i < n ; i++) + { + Xx [2 * (i + i*nrow)] = 1 ; + } + break ; + } + + return (X) ; +} + +/* ========================================================================== */ +/* === cholmod_free_dense =================================================== */ +/* ========================================================================== */ + +/* free a dense matrix + * + * workspace: none + */ + +int CHOLMOD(free_dense) +( + /* ---- in/out --- */ + cholmod_dense **XHandle, /* dense matrix to deallocate, NULL on output */ + /* --------------- */ + cholmod_common *Common +) +{ + cholmod_dense *X ; + + RETURN_IF_NULL_COMMON (FALSE) ; + + if (XHandle == NULL) + { + /* nothing to do */ + return (TRUE) ; + } + X = *XHandle ; + if (X == NULL) + { + /* nothing to do */ + return (TRUE) ; + } + + switch (X->xtype) + { + case CHOLMOD_REAL: + X->x = CHOLMOD(free) (X->nzmax, sizeof (double), X->x, Common) ; + break ; + + case CHOLMOD_COMPLEX: + X->x = CHOLMOD(free) (X->nzmax, 2*sizeof (double), X->x, Common) ; + break ; + + case CHOLMOD_ZOMPLEX: + X->x = CHOLMOD(free) (X->nzmax, sizeof (double), X->x, Common) ; + X->z = CHOLMOD(free) (X->nzmax, sizeof (double), X->z, Common) ; + break ; + } + + *XHandle = CHOLMOD(free) (1, sizeof (cholmod_dense), (*XHandle), Common) ; + return (TRUE) ; +} + +/* ========================================================================== */ +/* === cholmod_ensure_dense ================================================= */ +/* ========================================================================== */ + +/* Ensure that the input matrix has a certain size and type. If not, free + * the existing matrix and reallocate one of the right size and type. + * Returns a pointer to the cholmod_dense matrix, possibly reallocated. + * Also modifies the input matrix handle, XHandle, if necessary. + */ + +cholmod_dense *CHOLMOD(ensure_dense) +( + /* ---- input/output ---- */ + cholmod_dense **XHandle, /* matrix handle to check */ + /* ---- input ---- */ + size_t nrow, /* # of rows of matrix */ + size_t ncol, /* # of columns of matrix */ + size_t d, /* leading dimension */ + int xtype, /* CHOLMOD_REAL, _COMPLEX, or _ZOMPLEX */ + /* --------------- */ + cholmod_common *Common +) +{ + cholmod_dense *X ; + + RETURN_IF_NULL_COMMON (NULL) ; + if (XHandle == NULL) + { + ERROR (CHOLMOD_INVALID, "matrix invalid") ; + return (NULL) ; + } + + X = *XHandle ; + if (X == NULL || X->nrow != nrow || X->ncol != ncol + || X->d != d || X->xtype != xtype) + { + /* Matrix X is not allocated, or has the wrong size. Free it and + * reallocate it in the right size and shape. If an error occurs + * (out of memory or inputs nrow, etc invalid), then the error is + * set in cholmod_allocate_dense and X is returned as NULL. */ + CHOLMOD(free_dense) (XHandle, Common) ; + X = CHOLMOD(allocate_dense) (nrow, ncol, d, xtype, Common) ; + *XHandle = X ; + } + return (X) ; +} + + +/* ========================================================================== */ +/* === cholmod_sparse_to_dense ============================================== */ +/* ========================================================================== */ + +/* Convert a sparse matrix to a dense matrix. + * The output dense matrix has the same xtype as the input sparse matrix, + * except that a pattern-only sparse matrix A is converted into a real dense + * matrix X, with 1's and 0's. All xtypes are supported. + */ + +cholmod_dense *CHOLMOD(sparse_to_dense) +( + /* ---- input ---- */ + cholmod_sparse *A, /* matrix to copy */ + /* --------------- */ + cholmod_common *Common +) +{ + cholmod_dense *X = NULL ; + + /* ---------------------------------------------------------------------- */ + /* check inputs */ + /* ---------------------------------------------------------------------- */ + + RETURN_IF_NULL_COMMON (NULL) ; + RETURN_IF_NULL (A, NULL) ; + RETURN_IF_XTYPE_INVALID (A, CHOLMOD_PATTERN, CHOLMOD_ZOMPLEX, NULL) ; + if (A->stype && A->nrow != A->ncol) + { + ERROR (CHOLMOD_INVALID, "matrix invalid") ; + return (NULL) ; + } + Common->status = CHOLMOD_OK ; + ASSERT (CHOLMOD(dump_sparse) (A, "A", Common) >= 0) ; + + /* ---------------------------------------------------------------------- */ + /* convert the matrix, using template routine */ + /* ---------------------------------------------------------------------- */ + + switch (A->xtype) + { + case CHOLMOD_PATTERN: + X = p_cholmod_sparse_to_dense (A, Common) ; + break ; + + case CHOLMOD_REAL: + X = r_cholmod_sparse_to_dense (A, Common) ; + break ; + + case CHOLMOD_COMPLEX: + X = c_cholmod_sparse_to_dense (A, Common) ; + break ; + + case CHOLMOD_ZOMPLEX: + X = z_cholmod_sparse_to_dense (A, Common) ; + break ; + } + return (X) ; +} + + +/* ========================================================================== */ +/* === cholmod_dense_to_sparse ============================================== */ +/* ========================================================================== */ + +/* Convert a dense matrix to a sparse matrix, similar to the MATLAB statements: + * + * C = sparse (X) values = TRUE + * C = spones (sparse (X)) values = FALSE + * + * except that X must be double (it can be of many different types in MATLAB) + * + * The resulting sparse matrix C has the same numeric xtype as the input dense + * matrix X, unless "values" is FALSE (in which case C is real, where C(i,j)=1 + * if (i,j) is an entry in X. + */ + +cholmod_sparse *CHOLMOD(dense_to_sparse) +( + /* ---- input ---- */ + cholmod_dense *X, /* matrix to copy */ + int values, /* TRUE if values to be copied, FALSE otherwise */ + /* --------------- */ + cholmod_common *Common +) +{ + cholmod_sparse *C = NULL ; + + DEBUG (CHOLMOD(dump_dense) (X, "X", Common)) ; + + /* ---------------------------------------------------------------------- */ + /* check inputs */ + /* ---------------------------------------------------------------------- */ + + RETURN_IF_NULL_COMMON (NULL) ; + RETURN_IF_NULL (X, NULL) ; + RETURN_IF_XTYPE_INVALID (X, CHOLMOD_REAL, CHOLMOD_ZOMPLEX, NULL) ; + if (X->d < X->nrow) + { + ERROR (CHOLMOD_INVALID, "matrix invalid") ; + return (NULL) ; + } + Common->status = CHOLMOD_OK ; + + /* ---------------------------------------------------------------------- */ + /* convert the matrix, using template routine */ + /* ---------------------------------------------------------------------- */ + + switch (X->xtype) + { + case CHOLMOD_REAL: + C = r_cholmod_dense_to_sparse (X, values, Common) ; + break ; + + case CHOLMOD_COMPLEX: + C = c_cholmod_dense_to_sparse (X, values, Common) ; + break ; + + case CHOLMOD_ZOMPLEX: + C = z_cholmod_dense_to_sparse (X, values, Common) ; + break ; + } + return (C) ; +} + + +/* ========================================================================== */ +/* === cholmod_copy_dense2 ================================================== */ +/* ========================================================================== */ + +/* Y = X, where X and Y are both already allocated. The leading dimensions of + * X and Y may differ, but both must be >= the # of rows in X and Y. + * Entries in rows nrow to d-1 are not copied from X, since the space might not + * be initialized. Y->nzmax is unchanged. X->nzmax is typically + * (X->d)*(X->ncol), but a user might modify that condition outside of any + * CHOLMOD routine. + * + * The two dense matrices X and Y must have the same numeric xtype. + */ + +int CHOLMOD(copy_dense2) +( + /* ---- input ---- */ + cholmod_dense *X, /* matrix to copy */ + /* ---- output --- */ + cholmod_dense *Y, /* copy of matrix X */ + /* --------------- */ + cholmod_common *Common +) +{ + /* ---------------------------------------------------------------------- */ + /* check inputs */ + /* ---------------------------------------------------------------------- */ + + RETURN_IF_NULL_COMMON (FALSE) ; + RETURN_IF_NULL (X, FALSE) ; + RETURN_IF_NULL (Y, FALSE) ; + RETURN_IF_XTYPE_INVALID (X, CHOLMOD_REAL, CHOLMOD_ZOMPLEX, FALSE) ; + RETURN_IF_XTYPE_INVALID (Y, CHOLMOD_REAL, CHOLMOD_ZOMPLEX, FALSE) ; + if (X->nrow != Y->nrow || X->ncol != Y->ncol || X->xtype != Y->xtype) + { + ERROR (CHOLMOD_INVALID, "X and Y must have same dimensions and xtype") ; + return (FALSE) ; + } + if (X->d < X->nrow || Y->d < Y->nrow + || (X->d * X->ncol) > X->nzmax || (Y->d * Y->ncol) > Y->nzmax) + { + ERROR (CHOLMOD_INVALID, "X and/or Y invalid") ; + return (FALSE) ; + } + Common->status = CHOLMOD_OK ; + + /* ---------------------------------------------------------------------- */ + /* copy the matrix, using template routine */ + /* ---------------------------------------------------------------------- */ + + switch (X->xtype) + { + case CHOLMOD_REAL: + r_cholmod_copy_dense2 (X, Y) ; + break ; + + case CHOLMOD_COMPLEX: + c_cholmod_copy_dense2 (X, Y) ; + break ; + + case CHOLMOD_ZOMPLEX: + z_cholmod_copy_dense2 (X, Y) ; + break ; + } + return (TRUE) ; +} + + +/* ========================================================================== */ +/* === cholmod_copy_dense =================================================== */ +/* ========================================================================== */ + +/* Y = X, copy a dense matrix */ + +cholmod_dense *CHOLMOD(copy_dense) +( + /* ---- input ---- */ + cholmod_dense *X, /* matrix to copy */ + /* --------------- */ + cholmod_common *Common +) +{ + cholmod_dense *Y ; + + /* ---------------------------------------------------------------------- */ + /* check inputs */ + /* ---------------------------------------------------------------------- */ + + RETURN_IF_NULL_COMMON (NULL) ; + RETURN_IF_NULL (X, NULL) ; + RETURN_IF_XTYPE_INVALID (X, CHOLMOD_REAL, CHOLMOD_ZOMPLEX, NULL) ; + Common->status = CHOLMOD_OK ; + + /* ---------------------------------------------------------------------- */ + /* allocate result */ + /* ---------------------------------------------------------------------- */ + + Y = CHOLMOD(allocate_dense) (X->nrow, X->ncol, X->d, X->xtype, Common) ; + if (Common->status < CHOLMOD_OK) + { + return (NULL) ; /* out of memory or X invalid */ + } + + /* ---------------------------------------------------------------------- */ + /* Y = X */ + /* ---------------------------------------------------------------------- */ + + /* This cannot fail (X and Y are allocated, and have the same nrow, ncol + * d, and xtype) */ + CHOLMOD(copy_dense2) (X, Y, Common) ; + + /* ---------------------------------------------------------------------- */ + /* return result */ + /* ---------------------------------------------------------------------- */ + + return (Y) ; +} diff --git a/CHOLMOD/Core/cholmod_error.c b/CHOLMOD/Core/cholmod_error.c new file mode 100644 index 0000000000..c56e6852cb --- /dev/null +++ b/CHOLMOD/Core/cholmod_error.c @@ -0,0 +1,96 @@ +//------------------------------------------------------------------------------ +// CHOLMOD/Core/cholmod_error: error handling routine +//------------------------------------------------------------------------------ + +// CHOLMOD/Core Module. Copyright (C) 2005-2022, University of Florida. +// All Rights Reserved. Author: Timothy A. Davis +// SPDX-License-Identifier: LGPL-2.1+ + +//------------------------------------------------------------------------------ + +#include "cholmod_internal.h" + +/* ========================================================================== */ +/* ==== cholmod_error ======================================================= */ +/* ========================================================================== */ + +/* An error has occurred. Set the status, optionally print an error message, + * and call the user error-handling routine (if it exists). If + * Common->try_catch is TRUE, then CHOLMOD is inside a try/catch block. + * The status is set, but no message is printed and the user error handler + * is not called. This is not (yet) an error, since CHOLMOD may recover. + * + * In the current version, this try/catch mechanism is used internally only in + * cholmod_analyze, which tries multiple ordering methods and picks the best + * one. If one or more ordering method fails, it keeps going. Only one + * ordering needs to succeed for cholmod_analyze to succeed. + */ + +int CHOLMOD(error) +( + /* ---- input ---- */ + int status, /* error status */ + const char *file, /* name of source code file where error occured */ + int line, /* line number in source code file where error occured*/ + const char *message, /* error message */ + /* --------------- */ + cholmod_common *Common +) +{ + RETURN_IF_NULL_COMMON (FALSE) ; + + Common->status = status ; + + if (!(Common->try_catch)) + { + +#ifndef NPRINT + /* print a warning or error message */ + int (*printf_func) (const char *, ...) ; + printf_func = SuiteSparse_config_printf_func_get ( ) ; + if (printf_func != NULL) + { + if (status > 0 && Common->print > 1) + { + printf_func ("CHOLMOD warning:") ; + if (message != NULL) + { + printf_func (" %s.", message) ; + } + if (file != NULL) + { + printf_func (" file: %s", file) ; + printf_func (" line: %d", line) ; + } + printf_func ("\n") ; + fflush (stdout) ; + fflush (stderr) ; + } + else if (Common->print > 0) + { + printf_func ("CHOLMOD error:") ; + if (message != NULL) + { + printf_func (" %s.", message) ; + } + if (file != NULL) + { + printf_func (" file: %s", file) ; + printf_func (" line: %d", line) ; + } + printf_func ("\n") ; + fflush (stdout) ; + fflush (stderr) ; + } + } +#endif + + /* call the user error handler, if it exists */ + if (Common->error_handler != NULL) + { + Common->error_handler (status, file, line, message) ; + } + } + + return (TRUE) ; +} diff --git a/CHOLMOD/Core/cholmod_factor.c b/CHOLMOD/Core/cholmod_factor.c new file mode 100644 index 0000000000..f60c1ee001 --- /dev/null +++ b/CHOLMOD/Core/cholmod_factor.c @@ -0,0 +1,933 @@ +//------------------------------------------------------------------------------ +// CHOLMOD/Core/cholmod_factor: core methods for cholmod_factor object +//------------------------------------------------------------------------------ + +// CHOLMOD/Core Module. Copyright (C) 2005-2022, University of Florida. +// All Rights Reserved. Author: Timothy A. Davis +// SPDX-License-Identifier: LGPL-2.1+ + +//------------------------------------------------------------------------------ + +/* Core utility routines for the cholmod_factor object: + * + * The data structure for an LL' or LDL' factorization is too complex to + * describe in one sentence. This object can hold the symbolic analysis alone, + * or in combination with a "simplicial" (similar to a sparse matrix) or + * "supernodal" form of the numerical factorization. Only the routine to free + * a factor is primary, since a factor object is created by the factorization + * routine (cholmod_factorize). It must be freed with cholmod_free_factor. + * + * Primary routine: + * ---------------- + * cholmod_free_factor free a factor + * + * Secondary routines: + * ------------------- + * cholmod_allocate_factor allocate a symbolic factor (LL' or LDL') + * cholmod_reallocate_factor change the # entries in a factor + * cholmod_change_factor change the type of factor (e.g., LDL' to LL') + * cholmod_pack_factor pack the columns of a factor + * cholmod_reallocate_column resize a single column of a factor + * cholmod_factor_to_sparse create a sparse matrix copy of a factor + * cholmod_copy_factor create a copy of a factor + * + * Note that there is no cholmod_sparse_to_factor routine to create a factor + * as a copy of a sparse matrix. It could be done, after a fashion, but a + * lower triangular sparse matrix would not necessarily have a chordal graph, + * which would break the many CHOLMOD routines that rely on this property. + * + * The cholmod_factor_to_sparse routine is provided so that matrix operations + * in the MatrixOps module may be applied to L. Those operations operate on + * cholmod_sparse objects, and they are not guaranteed to maintain the chordal + * property of L. Such a modified L cannot be safely converted back to a + * cholmod_factor object. + */ + +#include "cholmod_internal.h" + +/* ========================================================================== */ +/* === cholmod_allocate_factor ============================================== */ +/* ========================================================================== */ + +/* Allocate a simplicial symbolic factor, with L->Perm and L->ColCount allocated + * and initialized to "empty" values (Perm [k] = k, and ColCount[k] = 1). + * The integer and numerical parts of L are not allocated. L->xtype is returned + * as CHOLMOD_PATTERN and L->is_super are returned as FALSE. L->is_ll is also + * returned FALSE, but this may be modified when the matrix is factorized. + * + * This is sufficient (but far from ideal) for input to cholmod_factorize, + * since the simplicial LL' or LDL' factorization (cholmod_rowfac) can + * reallocate the columns of L as needed. The primary purpose of this routine + * is to allocate space for a symbolic factorization, for the "expert" user to + * do his or her own symbolic analysis. The typical user should use + * cholmod_analyze instead of this routine. + * + * workspace: none + */ + +cholmod_factor *CHOLMOD(allocate_factor) +( + /* ---- input ---- */ + size_t n, /* L is n-by-n */ + /* --------------- */ + cholmod_common *Common +) +{ + Int j ; + Int *Perm, *ColCount ; + cholmod_factor *L ; + int ok = TRUE ; + + RETURN_IF_NULL_COMMON (FALSE) ; + Common->status = CHOLMOD_OK ; + + /* ensure the dimension does not cause integer overflow */ + (void) CHOLMOD(add_size_t) (n, 2, &ok) ; + if (!ok || (int64_t) n >= Int_max) + { + ERROR (CHOLMOD_TOO_LARGE, "problem too large") ; + return (NULL) ; + } + + L = CHOLMOD(malloc) (sizeof (cholmod_factor), 1, Common) ; + if (Common->status < CHOLMOD_OK) + { + return (NULL) ; /* out of memory */ + } + L->n = n ; + L->is_ll = FALSE ; + L->is_super = FALSE ; + L->is_monotonic = TRUE ; + L->itype = ITYPE ; + L->xtype = CHOLMOD_PATTERN ; + L->dtype = DTYPE ; + + /* allocate the purely symbolic part of L */ + L->ordering = CHOLMOD_NATURAL ; + L->Perm = CHOLMOD(malloc) (n, sizeof (Int), Common) ; + L->IPerm = NULL ; /* only created by cholmod_solve2 when needed */ + L->ColCount = CHOLMOD(malloc) (n, sizeof (Int), Common) ; + + /* simplicial part of L is empty */ + L->nzmax = 0 ; + L->p = NULL ; + L->i = NULL ; + L->x = NULL ; + L->z = NULL ; + L->nz = NULL ; + L->next = NULL ; + L->prev = NULL ; + + /* supernodal part of L is also empty */ + L->nsuper = 0 ; + L->ssize = 0 ; + L->xsize = 0 ; + L->maxesize = 0 ; + L->maxcsize = 0 ; + L->super = NULL ; + L->pi = NULL ; + L->px = NULL ; + L->s = NULL ; + L->useGPU = 0; + + /* L has not been factorized */ + L->minor = n ; + + if (Common->status < CHOLMOD_OK) + { + CHOLMOD(free_factor) (&L, Common) ; + return (NULL) ; /* out of memory */ + } + + /* initialize Perm and ColCount */ + Perm = L->Perm ; + for (j = 0 ; j < ((Int) n) ; j++) + { + Perm [j] = j ; + } + ColCount = L->ColCount ; + for (j = 0 ; j < ((Int) n) ; j++) + { + ColCount [j] = 1 ; + } + + return (L) ; +} + + +/* ========================================================================== */ +/* === cholmod_free_factor ================================================== */ +/* ========================================================================== */ + +/* Free a factor object. + * + * workspace: none + */ + +int CHOLMOD(free_factor) +( + /* ---- in/out --- */ + cholmod_factor **LHandle, /* factor to free, NULL on output */ + /* --------------- */ + cholmod_common *Common +) +{ + Int n, lnz, xs, ss, s ; + cholmod_factor *L ; + + RETURN_IF_NULL_COMMON (FALSE) ; + + if (LHandle == NULL) + { + /* nothing to do */ + return (TRUE) ; + } + L = *LHandle ; + if (L == NULL) + { + /* nothing to do */ + return (TRUE) ; + } + + n = L->n ; + lnz = L->nzmax ; + s = L->nsuper + 1 ; + xs = (L->is_super) ? ((Int) (L->xsize)) : (lnz) ; + ss = L->ssize ; + + /* symbolic part of L */ + CHOLMOD(free) (n, sizeof (Int), L->Perm, Common) ; + CHOLMOD(free) (n, sizeof (Int), L->IPerm, Common) ; + CHOLMOD(free) (n, sizeof (Int), L->ColCount, Common) ; + + /* simplicial form of L */ + CHOLMOD(free) (n+1, sizeof (Int), L->p, Common) ; + CHOLMOD(free) (lnz, sizeof (Int), L->i, Common) ; + CHOLMOD(free) (n, sizeof (Int), L->nz, Common) ; + CHOLMOD(free) (n+2, sizeof (Int), L->next, Common) ; + CHOLMOD(free) (n+2, sizeof (Int), L->prev, Common) ; + + /* supernodal form of L */ + CHOLMOD(free) (s, sizeof (Int), L->pi, Common) ; + CHOLMOD(free) (s, sizeof (Int), L->px, Common) ; + CHOLMOD(free) (s, sizeof (Int), L->super, Common) ; + CHOLMOD(free) (ss, sizeof (Int), L->s, Common) ; + + /* numerical values for both simplicial and supernodal L */ + if (L->xtype == CHOLMOD_REAL) + { + CHOLMOD(free) (xs, sizeof (double), L->x, Common) ; + } + else if (L->xtype == CHOLMOD_COMPLEX) + { + CHOLMOD(free) (xs, 2*sizeof (double), L->x, Common) ; + } + else if (L->xtype == CHOLMOD_ZOMPLEX) + { + CHOLMOD(free) (xs, sizeof (double), L->x, Common) ; + CHOLMOD(free) (xs, sizeof (double), L->z, Common) ; + } + + *LHandle = CHOLMOD(free) (1, sizeof (cholmod_factor), (*LHandle), Common) ; + return (TRUE) ; +} + + +/* ========================================================================== */ +/* === cholmod_reallocate_factor ============================================ */ +/* ========================================================================== */ + +/* Change the size of L->i and L->x, or allocate them if their current size + * is zero. L must be simplicial. + * + * workspace: none + */ + +int CHOLMOD(reallocate_factor) +( + /* ---- input ---- */ + size_t nznew, /* new # of entries in L */ + /* ---- in/out --- */ + cholmod_factor *L, /* factor to modify */ + /* --------------- */ + cholmod_common *Common +) +{ + /* ---------------------------------------------------------------------- */ + /* get inputs */ + /* ---------------------------------------------------------------------- */ + + RETURN_IF_NULL_COMMON (FALSE) ; + RETURN_IF_NULL (L, FALSE) ; + RETURN_IF_XTYPE_INVALID (L, CHOLMOD_REAL, CHOLMOD_ZOMPLEX, FALSE) ; + PRINT1 (("realloc factor: xtype %d\n", L->xtype)) ; + if (L->is_super) + { + /* L must be simplicial, and not symbolic */ + ERROR (CHOLMOD_INVALID, "L invalid") ; + return (FALSE) ; + } + Common->status = CHOLMOD_OK ; + PRINT1 (("realloc factor %g to %g\n", (double) L->nzmax, (double) nznew)) ; + + /* ---------------------------------------------------------------------- */ + /* resize (or allocate) the L->i and L->x components of the factor */ + /* ---------------------------------------------------------------------- */ + + CHOLMOD(realloc_multiple) (nznew, 1, L->xtype, &(L->i), NULL, + &(L->x), &(L->z), &(L->nzmax), Common) ; + return (Common->status == CHOLMOD_OK) ; +} + + +/* ========================================================================== */ +/* === cholmod_reallocate_column =========================================== */ +/* ========================================================================== */ + +/* Column j needs more space, reallocate it at the end of L->i and L->x. + * If the reallocation fails, the factor is converted to a simplicial + * symbolic factor (no pattern, just L->Perm and L->ColCount). + * + * workspace: none + */ + +int CHOLMOD(reallocate_column) +( + /* ---- input ---- */ + size_t j, /* the column to reallocate */ + size_t need, /* required size of column j */ + /* ---- in/out --- */ + cholmod_factor *L, /* factor to modify */ + /* --------------- */ + cholmod_common *Common +) +{ + double xneed ; + double *Lx, *Lz ; + Int *Lp, *Lprev, *Lnext, *Li, *Lnz ; + Int n, pold, pnew, len, k, tail ; + + /* ---------------------------------------------------------------------- */ + /* get inputs */ + /* ---------------------------------------------------------------------- */ + + RETURN_IF_NULL_COMMON (FALSE) ; + RETURN_IF_NULL (L, FALSE) ; + RETURN_IF_XTYPE_INVALID (L, CHOLMOD_REAL, CHOLMOD_ZOMPLEX, FALSE) ; + if (L->is_super) + { + ERROR (CHOLMOD_INVALID, "L must be simplicial") ; + return (FALSE) ; + } + n = L->n ; + if (j >= L->n || need == 0) + { + ERROR (CHOLMOD_INVALID, "j invalid") ; + return (FALSE) ; /* j out of range */ + } + Common->status = CHOLMOD_OK ; + + DEBUG (CHOLMOD(dump_factor) (L, "start colrealloc", Common)) ; + + /* ---------------------------------------------------------------------- */ + /* increase the size of L if needed */ + /* ---------------------------------------------------------------------- */ + + /* head = n+1 ; */ + tail = n ; + Lp = L->p ; + Lnz = L->nz ; + Lprev = L->prev ; + Lnext = L->next ; + + ASSERT (Lnz != NULL) ; + ASSERT (Lnext != NULL && Lprev != NULL) ; + PRINT1 (("col %g need %g\n", (double) j, (double) need)) ; + + /* column j cannot have more than n-j entries if all entries are present */ + need = MIN (need, n-j) ; + + /* compute need in double to avoid integer overflow */ + if (Common->grow1 >= 1.0) + { + xneed = (double) need ; + xneed = Common->grow1 * xneed + Common->grow2 ; + xneed = MIN (xneed, n-j) ; + need = (Int) xneed ; + } + PRINT1 (("really new need %g current %g\n", (double) need, + (double) (Lp [Lnext [j]] - Lp [j]))) ; + ASSERT (need >= 1 && need <= n-j) ; + + if (Lp [Lnext [j]] - Lp [j] >= (Int) need) + { + /* no need to reallocate the column, it's already big enough */ + PRINT1 (("colrealloc: quick return %g %g\n", + (double) (Lp [Lnext [j]] - Lp [j]), (double) need)) ; + return (TRUE) ; + + } + + if (Lp [tail] + need > L->nzmax) + { + /* use double to avoid integer overflow */ + xneed = (double) need ; + if (Common->grow0 < 1.2) /* fl. pt. compare, false if NaN */ + { + /* if grow0 is less than 1.2 or NaN, don't use it */ + xneed = 1.2 * (((double) L->nzmax) + xneed + 1) ; + } + else + { + xneed = Common->grow0 * (((double) L->nzmax) + xneed + 1) ; + } + if (xneed > (double) SIZE_MAX || + !CHOLMOD(reallocate_factor) ((Int) xneed, L, Common)) + { + /* out of memory, convert to simplicial symbolic */ + CHOLMOD(change_factor) (CHOLMOD_PATTERN, L->is_ll, FALSE, TRUE, + TRUE, L, Common) ; + ERROR (CHOLMOD_OUT_OF_MEMORY, "out of memory; L now symbolic") ; + return (FALSE) ; /* out of memory */ + } + PRINT1 (("\n=== GROW L from %g to %g\n", + (double) L->nzmax, (double) xneed)) ; + /* pack all columns so that each column has at most grow2 free space */ + CHOLMOD(pack_factor) (L, Common) ; + ASSERT (Common->status == CHOLMOD_OK) ; + Common->nrealloc_factor++ ; + } + + /* ---------------------------------------------------------------------- */ + /* reallocate the column */ + /* ---------------------------------------------------------------------- */ + + Common->nrealloc_col++ ; + + Li = L->i ; + Lx = L->x ; + Lz = L->z ; + + /* remove j from its current position in the list */ + Lnext [Lprev [j]] = Lnext [j] ; + Lprev [Lnext [j]] = Lprev [j] ; + + /* place j at the end of the list */ + Lnext [Lprev [tail]] = j ; + Lprev [j] = Lprev [tail] ; + Lnext [j] = n ; + Lprev [tail] = j ; + + /* L is no longer monotonic; columns are out-of-order */ + L->is_monotonic = FALSE ; + + /* allocate space for column j */ + pold = Lp [j] ; + pnew = Lp [tail] ; + Lp [j] = pnew ; + Lp [tail] += need ; + + /* copy column j to the new space */ + len = Lnz [j] ; + for (k = 0 ; k < len ; k++) + { + Li [pnew + k] = Li [pold + k] ; + } + + if (L->xtype == CHOLMOD_REAL) + { + for (k = 0 ; k < len ; k++) + { + Lx [pnew + k] = Lx [pold + k] ; + } + } + else if (L->xtype == CHOLMOD_COMPLEX) + { + for (k = 0 ; k < len ; k++) + { + Lx [2*(pnew + k) ] = Lx [2*(pold + k) ] ; + Lx [2*(pnew + k)+1] = Lx [2*(pold + k)+1] ; + } + } + else if (L->xtype == CHOLMOD_ZOMPLEX) + { + for (k = 0 ; k < len ; k++) + { + Lx [pnew + k] = Lx [pold + k] ; + Lz [pnew + k] = Lz [pold + k] ; + } + } + + DEBUG (CHOLMOD(dump_factor) (L, "colrealloc done", Common)) ; + + /* successful reallocation of column j of L */ + return (TRUE) ; +} + + +/* ========================================================================== */ +/* === cholmod_pack_factor ================================================== */ +/* ========================================================================== */ + +/* Pack the columns of a simplicial LDL' or LL' factor. This can be followed + * by a call to cholmod_reallocate_factor to reduce the size of L to the exact + * size required by the factor, if desired. Alternatively, you can leave the + * size of L->i and L->x the same, to allow space for future updates/rowadds. + * + * Each column is reduced in size so that it has at most Common->grow2 free + * space at the end of the column. + * + * Does nothing and returns silently if given any other type of factor. + * + * Does NOT force the columns of L to be monotonic. It thus differs from + * cholmod_change_factor (xtype, -, FALSE, TRUE, TRUE, L, Common), which + * packs the columns and ensures that they appear in monotonic order. + */ + +int CHOLMOD(pack_factor) +( + /* ---- in/out --- */ + cholmod_factor *L, /* factor to modify */ + /* --------------- */ + cholmod_common *Common +) +{ + double *Lx, *Lz ; + Int *Lp, *Li, *Lnz, *Lnext ; + Int pnew, j, k, pold, len, n, head, tail, grow2 ; + + /* ---------------------------------------------------------------------- */ + /* get inputs */ + /* ---------------------------------------------------------------------- */ + + RETURN_IF_NULL_COMMON (FALSE) ; + RETURN_IF_NULL (L, FALSE) ; + RETURN_IF_XTYPE_INVALID (L, CHOLMOD_PATTERN, CHOLMOD_ZOMPLEX, FALSE) ; + Common->status = CHOLMOD_OK ; + DEBUG (CHOLMOD(dump_factor) (L, "start pack", Common)) ; + PRINT1 (("PACK factor %d\n", L->is_super)) ; + + if (L->xtype == CHOLMOD_PATTERN || L->is_super) + { + /* nothing to do unless L is simplicial numeric */ + return (TRUE) ; + } + + /* ---------------------------------------------------------------------- */ + /* pack */ + /* ---------------------------------------------------------------------- */ + + grow2 = Common->grow2 ; + PRINT1 (("\nPACK grow2 "ID"\n", grow2)) ; + + pnew = 0 ; + n = L->n ; + Lp = L->p ; + Li = L->i ; + Lx = L->x ; + Lz = L->z ; + Lnz = L->nz ; + Lnext = L->next ; + + head = n+1 ; + tail = n ; + + for (j = Lnext [head] ; j != tail ; j = Lnext [j]) + { + /* pack column j */ + pold = Lp [j] ; + len = Lnz [j] ; + ASSERT (len > 0) ; + PRINT2 (("col "ID" pnew "ID" pold "ID"\n", j, pnew, pold)) ; + if (pnew < pold) + { + PRINT2 ((" pack this column\n")) ; + + for (k = 0 ; k < len ; k++) + { + Li [pnew + k] = Li [pold + k] ; + } + + if (L->xtype == CHOLMOD_REAL) + { + for (k = 0 ; k < len ; k++) + { + Lx [pnew + k] = Lx [pold + k] ; + } + } + else if (L->xtype == CHOLMOD_COMPLEX) + { + for (k = 0 ; k < len ; k++) + { + Lx [2*(pnew + k) ] = Lx [2*(pold + k) ] ; + Lx [2*(pnew + k)+1] = Lx [2*(pold + k)+1] ; + } + } + else if (L->xtype == CHOLMOD_ZOMPLEX) + { + for (k = 0 ; k < len ; k++) + { + Lx [pnew + k] = Lx [pold + k] ; + Lz [pnew + k] = Lz [pold + k] ; + } + } + + Lp [j] = pnew ; + } + len = MIN (len + grow2, n - j) ; + pnew = MIN (Lp [j] + len, Lp [Lnext [j]]) ; + } + PRINT2 (("final pnew = "ID"\n", pnew)) ; + return (TRUE) ; +} + + +/* ========================================================================== */ +/* === cholmod_factor_to_sparse ============================================= */ +/* ========================================================================== */ + +/* Constructs a column-oriented sparse matrix containing the pattern and values + * of a simplicial or supernodal numerical factor, and then converts the factor + * into a simplicial symbolic factor. If L is already packed, monotonic, + * and simplicial (which is the case when cholmod_factorize uses the simplicial + * Cholesky factorization algorithm) then this routine requires only O(1) + * memory and takes O(1) time. + * + * Only operates on numeric factors (real, complex, or zomplex). Does not + * change the numeric L->xtype (the resulting sparse matrix has the same xtype + * as L). If this routine fails, L is left unmodified. + */ + +cholmod_sparse *CHOLMOD(factor_to_sparse) +( + /* ---- in/out --- */ + cholmod_factor *L, /* factor to copy, converted to symbolic on output */ + /* --------------- */ + cholmod_common *Common +) +{ + cholmod_sparse *Lsparse ; + + /* ---------------------------------------------------------------------- */ + /* get inputs */ + /* ---------------------------------------------------------------------- */ + + RETURN_IF_NULL_COMMON (NULL) ; + RETURN_IF_NULL (L, NULL) ; + RETURN_IF_XTYPE_INVALID (L, CHOLMOD_REAL, CHOLMOD_ZOMPLEX, NULL) ; + Common->status = CHOLMOD_OK ; + DEBUG (CHOLMOD(dump_factor) (L, "start convert to matrix", Common)) ; + + /* ---------------------------------------------------------------------- */ + /* convert to packed, monotonic, simplicial, numeric */ + /* ---------------------------------------------------------------------- */ + + /* leave as LL or LDL' */ + if (!CHOLMOD(change_factor) (L->xtype, L->is_ll, FALSE, TRUE, TRUE, L, + Common)) + { + ERROR (CHOLMOD_INVALID, "cannot convert L") ; + return (NULL) ; + } + + /* ---------------------------------------------------------------------- */ + /* create Lsparse */ + /* ---------------------------------------------------------------------- */ + + /* allocate the header for Lsparse, the sparse matrix version of L */ + Lsparse = CHOLMOD(malloc) (sizeof (cholmod_sparse), 1, Common) ; + if (Common->status < CHOLMOD_OK) + { + return (NULL) ; /* out of memory */ + } + + /* transfer the contents from L to Lsparse */ + Lsparse->nrow = L->n ; + Lsparse->ncol = L->n ; + Lsparse->p = L->p ; + Lsparse->i = L->i ; + Lsparse->x = L->x ; + Lsparse->z = L->z ; + Lsparse->nz = NULL ; + Lsparse->stype = 0 ; + Lsparse->itype = L->itype ; + Lsparse->xtype = L->xtype ; + Lsparse->dtype = L->dtype ; + Lsparse->sorted = TRUE ; + Lsparse->packed = TRUE ; + Lsparse->nzmax = L->nzmax ; + ASSERT (CHOLMOD(dump_sparse) (Lsparse, "Lsparse", Common) >= 0) ; + + /* ---------------------------------------------------------------------- */ + /* convert L to symbolic, but do not free contents transfered to Lsparse */ + /* ---------------------------------------------------------------------- */ + + L->p = NULL ; + L->i = NULL ; + L->x = NULL ; + L->z = NULL ; + L->xtype = CHOLMOD_PATTERN ; + CHOLMOD(change_factor) (CHOLMOD_PATTERN, FALSE, FALSE, TRUE, TRUE, L, + Common) ; + + return (Lsparse) ; +} + + +/* ========================================================================== */ +/* === cholmod_copy_factor ================================================== */ +/* ========================================================================== */ + +/* Create an exact copy of a factor, with one exception: + * + * Entries in unused space are not copied (they might not be initialized, + * and copying them would cause program checkers such as purify and + * valgrind to complain). + * + * Note that a supernodal L cannot be zomplex. + */ + +cholmod_factor *CHOLMOD(copy_factor) +( + /* ---- input ---- */ + cholmod_factor *L, /* factor to copy */ + /* --------------- */ + cholmod_common *Common +) +{ + cholmod_factor *L2 ; + double *Lx, *L2x, *Lz, *L2z ; + Int *Perm, *ColCount, *Lp, *Li, *Lnz, *Lnext, *Lprev, *Lsuper, *Lpi, *Lpx, + *Ls, *Perm2, *ColCount2, *L2p, *L2i, *L2nz, *L2next, *L2prev, *L2super, + *L2pi, *L2px, *L2s ; + Int n, j, p, pend, s, xsize, ssize, nsuper ; + + /* ---------------------------------------------------------------------- */ + /* get inputs */ + /* ---------------------------------------------------------------------- */ + + RETURN_IF_NULL_COMMON (NULL) ; + RETURN_IF_NULL (L, NULL) ; + RETURN_IF_XTYPE_INVALID (L, CHOLMOD_PATTERN, CHOLMOD_ZOMPLEX, NULL) ; + Common->status = CHOLMOD_OK ; + DEBUG (CHOLMOD(dump_factor) (L, "start copy", Common)) ; + + n = L->n ; + + /* ---------------------------------------------------------------------- */ + /* allocate a simplicial symbolic factor */ + /* ---------------------------------------------------------------------- */ + + /* allocates L2->Perm and L2->ColCount */ + L2 = CHOLMOD(allocate_factor) (n, Common) ; + if (Common->status < CHOLMOD_OK) + { + return (NULL) ; /* out of memory */ + } + ASSERT (L2->xtype == CHOLMOD_PATTERN && !(L2->is_super)) ; + + Perm = L->Perm ; + ColCount = L->ColCount ; + Perm2 = L2->Perm ; + ColCount2 = L2->ColCount ; + L2->ordering = L->ordering ; + + for (j = 0 ; j < n ; j++) + { + Perm2 [j] = Perm [j] ; + } + for (j = 0 ; j < n ; j++) + { + ColCount2 [j] = ColCount [j] ; + } + L2->is_ll = L->is_ll ; + + /* ---------------------------------------------------------------------- */ + /* copy the rest of the factor */ + /* ---------------------------------------------------------------------- */ + + if (L->xtype != CHOLMOD_PATTERN && !(L->super)) + { + + /* ------------------------------------------------------------------ */ + /* allocate a simplicial numeric factor */ + /* ------------------------------------------------------------------ */ + + /* allocate L2->p, L2->nz, L2->prev, L2->next, L2->i, and L2->x. + * packed = -1 so that cholmod_change_factor allocates space of + * size L2->nzmax */ + L2->nzmax = L->nzmax ; + if (!CHOLMOD(change_factor) (L->xtype, L->is_ll, FALSE, -1, TRUE, + L2, Common)) + { + CHOLMOD(free_factor) (&L2, Common) ; + return (NULL) ; /* out of memory */ + } + ASSERT (MAX (1, L->nzmax) == L2->nzmax) ; + + /* ------------------------------------------------------------------ */ + /* copy the contents of a simplicial numeric factor */ + /* ------------------------------------------------------------------ */ + + Lp = L->p ; + Li = L->i ; + Lx = L->x ; + Lz = L->z ; + Lnz = L->nz ; + Lnext = L->next ; + Lprev = L->prev ; + + L2p = L2->p ; + L2i = L2->i ; + L2x = L2->x ; + L2z = L2->z ; + L2nz = L2->nz ; + L2next = L2->next ; + L2prev = L2->prev ; + L2->xtype = L->xtype ; + L2->dtype = L->dtype ; + + for (j = 0 ; j <= n ; j++) + { + L2p [j] = Lp [j] ; + } + + for (j = 0 ; j < n+2 ; j++) + { + L2prev [j] = Lprev [j] ; + } + + for (j = 0 ; j < n+2 ; j++) + { + L2next [j] = Lnext [j] ; + } + + for (j = 0 ; j < n ; j++) + { + L2nz [j] = Lnz [j] ; + } + + for (j = 0 ; j < n ; j++) + { + p = Lp [j] ; + pend = p + Lnz [j] ; + for ( ; p < pend ; p++) + { + L2i [p] = Li [p] ; + } + p = Lp [j] ; + + if (L->xtype == CHOLMOD_REAL) + { + for ( ; p < pend ; p++) + { + L2x [p] = Lx [p] ; + } + } + else if (L->xtype == CHOLMOD_COMPLEX) + { + for ( ; p < pend ; p++) + { + L2x [2*p ] = Lx [2*p ] ; + L2x [2*p+1] = Lx [2*p+1] ; + } + } + else if (L->xtype == CHOLMOD_ZOMPLEX) + { + for ( ; p < pend ; p++) + { + L2x [p] = Lx [p] ; + L2z [p] = Lz [p] ; + } + } + + } + + } + else if (L->is_super) + { + + /* ------------------------------------------------------------------ */ + /* copy a supernodal factor */ + /* ------------------------------------------------------------------ */ + + xsize = L->xsize ; + ssize = L->ssize ; + nsuper = L->nsuper ; + + L2->xsize = xsize ; + L2->ssize = ssize ; + L2->nsuper = nsuper ; + + /* allocate L2->super, L2->pi, L2->px, and L2->s. Allocate L2->x if + * L is numeric */ + if (!CHOLMOD(change_factor) (L->xtype, TRUE, TRUE, TRUE, TRUE, L2, + Common)) + { + CHOLMOD(free_factor) (&L2, Common) ; + return (NULL) ; /* out of memory */ + } + + ASSERT (L2->s != NULL) ; + + /* ------------------------------------------------------------------ */ + /* copy the contents of a supernodal factor */ + /* ------------------------------------------------------------------ */ + + Lsuper = L->super ; + Lpi = L->pi ; + Lpx = L->px ; + Ls = L->s ; + Lx = L->x ; + + L2super = L2->super ; + L2pi = L2->pi ; + L2px = L2->px ; + L2s = L2->s ; + L2x = L2->x ; + + L2->maxcsize = L->maxcsize ; + L2->maxesize = L->maxesize ; + + for (s = 0 ; s <= nsuper ; s++) + { + L2super [s] = Lsuper [s] ; + } + for (s = 0 ; s <= nsuper ; s++) + { + L2pi [s] = Lpi [s] ; + } + for (s = 0 ; s <= nsuper ; s++) + { + L2px [s] = Lpx [s] ; + } + + L2s [0] = 0 ; + for (p = 0 ; p < ssize ; p++) + { + L2s [p] = Ls [p] ; + } + + if (L->xtype == CHOLMOD_REAL) + { + for (p = 0 ; p < xsize ; p++) + { + L2x [p] = Lx [p] ; + } + } + else if (L->xtype == CHOLMOD_COMPLEX) + { + for (p = 0 ; p < 2*xsize ; p++) + { + L2x [p] = Lx [p] ; + } + } + } + + L2->minor = L->minor ; + L2->is_monotonic = L->is_monotonic ; + + DEBUG (CHOLMOD(dump_factor) (L2, "L2 got copied", Common)) ; + ASSERT (L2->xtype == L->xtype && L2->is_super == L->is_super) ; + return (L2) ; +} diff --git a/CHOLMOD/Utility/cholmod_l_aat.c b/CHOLMOD/Core/cholmod_l_aat.c similarity index 55% rename from CHOLMOD/Utility/cholmod_l_aat.c rename to CHOLMOD/Core/cholmod_l_aat.c index 153645fc66..d451497392 100644 --- a/CHOLMOD/Utility/cholmod_l_aat.c +++ b/CHOLMOD/Core/cholmod_l_aat.c @@ -1,13 +1,13 @@ //------------------------------------------------------------------------------ -// CHOLMOD/Utility/cholmod_l_aat: compute AA' or A(:,f)*A(:,f)' +// CHOLMOD/Core/cholmod_l_aat.c: int64_t version of cholmod_aat //------------------------------------------------------------------------------ -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. +// CHOLMOD/Core Module. Copyright (C) 2005-2022, University of Florida. +// All Rights Reserved. Author: Timothy A. Davis // SPDX-License-Identifier: LGPL-2.1+ //------------------------------------------------------------------------------ -#define CHOLMOD_INT64 -#include "t_cholmod_aat.c" +#define DLONG +#include "cholmod_aat.c" diff --git a/CHOLMOD/Utility/cholmod_l_add.c b/CHOLMOD/Core/cholmod_l_add.c similarity index 55% rename from CHOLMOD/Utility/cholmod_l_add.c rename to CHOLMOD/Core/cholmod_l_add.c index 7b2465ca9e..070a12ae9f 100644 --- a/CHOLMOD/Utility/cholmod_l_add.c +++ b/CHOLMOD/Core/cholmod_l_add.c @@ -1,13 +1,13 @@ //------------------------------------------------------------------------------ -// CHOLMOD/Utility/cholmod_l_add: C = alpha*A + beta*B +// CHOLMOD/Core/cholmod_l_add.c: int64_t version of cholmod_add //------------------------------------------------------------------------------ -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. +// CHOLMOD/Core Module. Copyright (C) 2005-2022, University of Florida. +// All Rights Reserved. Author: Timothy A. Davis // SPDX-License-Identifier: LGPL-2.1+ //------------------------------------------------------------------------------ -#define CHOLMOD_INT64 -#include "t_cholmod_add.c" +#define DLONG +#include "cholmod_add.c" diff --git a/CHOLMOD/Utility/cholmod_l_band.c b/CHOLMOD/Core/cholmod_l_band.c similarity index 55% rename from CHOLMOD/Utility/cholmod_l_band.c rename to CHOLMOD/Core/cholmod_l_band.c index 3a560b618a..49d4d8fa08 100644 --- a/CHOLMOD/Utility/cholmod_l_band.c +++ b/CHOLMOD/Core/cholmod_l_band.c @@ -1,13 +1,13 @@ //------------------------------------------------------------------------------ -// CHOLMOD/Utility/cholmod_l_band: extract the band of a sparse matrix +// CHOLMOD/Core/cholmod_l_band.c: int64_t version of cholmod_band //------------------------------------------------------------------------------ -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. +// CHOLMOD/Core Module. Copyright (C) 2005-2022, University of Florida. +// All Rights Reserved. Author: Timothy A. Davis // SPDX-License-Identifier: LGPL-2.1+ //------------------------------------------------------------------------------ -#define CHOLMOD_INT64 -#include "t_cholmod_band.c" +#define DLONG +#include "cholmod_band.c" diff --git a/CHOLMOD/Utility/cholmod_l_change_factor.c b/CHOLMOD/Core/cholmod_l_change_factor.c similarity index 52% rename from CHOLMOD/Utility/cholmod_l_change_factor.c rename to CHOLMOD/Core/cholmod_l_change_factor.c index f80779e70e..8750890347 100644 --- a/CHOLMOD/Utility/cholmod_l_change_factor.c +++ b/CHOLMOD/Core/cholmod_l_change_factor.c @@ -1,13 +1,14 @@ //------------------------------------------------------------------------------ -// CHOLMOD/Utility/cholmod_l_change_factor: change format of a factor object +// CHOLMOD/Core/cholmod_l_change_factor.c: +// int64_t version of cholmod_change_factor //------------------------------------------------------------------------------ -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. +// CHOLMOD/Core Module. Copyright (C) 2005-2022, University of Florida. +// All Rights Reserved. Author: Timothy A. Davis // SPDX-License-Identifier: LGPL-2.1+ //------------------------------------------------------------------------------ -#define CHOLMOD_INT64 -#include "t_cholmod_change_factor.c" +#define DLONG +#include "cholmod_change_factor.c" diff --git a/CHOLMOD/Utility/cholmod_add.c b/CHOLMOD/Core/cholmod_l_common.c similarity index 54% rename from CHOLMOD/Utility/cholmod_add.c rename to CHOLMOD/Core/cholmod_l_common.c index 02dff7359b..9a062f8703 100644 --- a/CHOLMOD/Utility/cholmod_add.c +++ b/CHOLMOD/Core/cholmod_l_common.c @@ -1,13 +1,13 @@ //------------------------------------------------------------------------------ -// CHOLMOD/Utility/cholmod_add: C = alpha*A + beta*B +// CHOLMOD/Core/cholmod_l_common.c: int64_t version of cholmod_common //------------------------------------------------------------------------------ -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. +// CHOLMOD/Core Module. Copyright (C) 2005-2022, University of Florida. +// All Rights Reserved. Author: Timothy A. Davis // SPDX-License-Identifier: LGPL-2.1+ //------------------------------------------------------------------------------ -#define CHOLMOD_INT32 -#include "t_cholmod_add.c" +#define DLONG +#include "cholmod_common.c" diff --git a/CHOLMOD/Core/cholmod_l_complex.c b/CHOLMOD/Core/cholmod_l_complex.c new file mode 100644 index 0000000000..8d93936a13 --- /dev/null +++ b/CHOLMOD/Core/cholmod_l_complex.c @@ -0,0 +1,13 @@ +//------------------------------------------------------------------------------ +// CHOLMOD/Core/cholmod_l_complex.c: int64_t version of cholmod_complex +//------------------------------------------------------------------------------ + +// CHOLMOD/Core Module. Copyright (C) 2005-2022, University of Florida. +// All Rights Reserved. Author: Timothy A. Davis +// SPDX-License-Identifier: LGPL-2.1+ + +//------------------------------------------------------------------------------ + +#define DLONG +#include "cholmod_complex.c" + diff --git a/CHOLMOD/Utility/cholmod_l_copy.c b/CHOLMOD/Core/cholmod_l_copy.c similarity index 55% rename from CHOLMOD/Utility/cholmod_l_copy.c rename to CHOLMOD/Core/cholmod_l_copy.c index aa9f687b9a..f47ceb8cdd 100644 --- a/CHOLMOD/Utility/cholmod_l_copy.c +++ b/CHOLMOD/Core/cholmod_l_copy.c @@ -1,13 +1,13 @@ //------------------------------------------------------------------------------ -// CHOLMOD/Utility/cholmod_l_copy: copy a sparse matrix (with change of stype) +// CHOLMOD/Core/cholmod_l_copy.c: int64_t version of cholmod_copy //------------------------------------------------------------------------------ -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. +// CHOLMOD/Core Module. Copyright (C) 2005-2022, University of Florida. +// All Rights Reserved. Author: Timothy A. Davis // SPDX-License-Identifier: LGPL-2.1+ //------------------------------------------------------------------------------ -#define CHOLMOD_INT64 -#include "t_cholmod_copy.c" +#define DLONG +#include "cholmod_copy.c" diff --git a/CHOLMOD/Utility/cholmod_aat.c b/CHOLMOD/Core/cholmod_l_dense.c similarity index 55% rename from CHOLMOD/Utility/cholmod_aat.c rename to CHOLMOD/Core/cholmod_l_dense.c index 7940938414..bc354d98ff 100644 --- a/CHOLMOD/Utility/cholmod_aat.c +++ b/CHOLMOD/Core/cholmod_l_dense.c @@ -1,13 +1,13 @@ //------------------------------------------------------------------------------ -// CHOLMOD/Utility/cholmod_aat: compute AA' or A(:,f)*A(:,f)' +// CHOLMOD/Core/cholmod_l_dense.c: int64_t version of cholmod_dense //------------------------------------------------------------------------------ -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. +// CHOLMOD/Core Module. Copyright (C) 2005-2022, University of Florida. +// All Rights Reserved. Author: Timothy A. Davis // SPDX-License-Identifier: LGPL-2.1+ //------------------------------------------------------------------------------ -#define CHOLMOD_INT32 -#include "t_cholmod_aat.c" +#define DLONG +#include "cholmod_dense.c" diff --git a/CHOLMOD/Utility/cholmod_l_error.c b/CHOLMOD/Core/cholmod_l_error.c similarity index 55% rename from CHOLMOD/Utility/cholmod_l_error.c rename to CHOLMOD/Core/cholmod_l_error.c index aff983ce6a..62090ca31a 100644 --- a/CHOLMOD/Utility/cholmod_l_error.c +++ b/CHOLMOD/Core/cholmod_l_error.c @@ -1,13 +1,13 @@ //------------------------------------------------------------------------------ -// CHOLMOD/Utility/cholmod_l_error: CHOLMOD error handling +// CHOLMOD/Core/cholmod_l_error.c: int64_t version of cholmod_error //------------------------------------------------------------------------------ -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. +// CHOLMOD/Core Module. Copyright (C) 2005-2022, University of Florida. +// All Rights Reserved. Author: Timothy A. Davis // SPDX-License-Identifier: LGPL-2.1+ //------------------------------------------------------------------------------ -#define CHOLMOD_INT64 -#include "t_cholmod_error.c" +#define DLONG +#include "cholmod_error.c" diff --git a/CHOLMOD/Utility/cholmod_alloc_factor.c b/CHOLMOD/Core/cholmod_l_factor.c similarity index 55% rename from CHOLMOD/Utility/cholmod_alloc_factor.c rename to CHOLMOD/Core/cholmod_l_factor.c index 0c9924f837..865555df95 100644 --- a/CHOLMOD/Utility/cholmod_alloc_factor.c +++ b/CHOLMOD/Core/cholmod_l_factor.c @@ -1,13 +1,13 @@ //------------------------------------------------------------------------------ -// CHOLMOD/Utility/cholmod_alloc_factor: allocate a simplicial factor +// CHOLMOD/Core/cholmod_l_factor.c: int64_t version of cholmod_factor //------------------------------------------------------------------------------ -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. +// CHOLMOD/Core Module. Copyright (C) 2005-2022, University of Florida. +// All Rights Reserved. Author: Timothy A. Davis // SPDX-License-Identifier: LGPL-2.1+ //------------------------------------------------------------------------------ -#define CHOLMOD_INT32 -#include "t_cholmod_alloc_factor.c" +#define DLONG +#include "cholmod_factor.c" diff --git a/CHOLMOD/Utility/cholmod_add_size_t.c b/CHOLMOD/Core/cholmod_l_memory.c similarity index 54% rename from CHOLMOD/Utility/cholmod_add_size_t.c rename to CHOLMOD/Core/cholmod_l_memory.c index 51400bc7b4..564303bad2 100644 --- a/CHOLMOD/Utility/cholmod_add_size_t.c +++ b/CHOLMOD/Core/cholmod_l_memory.c @@ -1,13 +1,13 @@ //------------------------------------------------------------------------------ -// CHOLMOD/Utility/cholmod_add_size_t: add two size_t values +// CHOLMOD/Core/cholmod_l_memory.c: int64_t version of cholmod_memory //------------------------------------------------------------------------------ -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. +// CHOLMOD/Core Module. Copyright (C) 2005-2022, University of Florida. +// All Rights Reserved. Author: Timothy A. Davis // SPDX-License-Identifier: LGPL-2.1+ //------------------------------------------------------------------------------ -#define CHOLMOD_INT32 -#include "t_cholmod_add_size_t.c" +#define DLONG +#include "cholmod_memory.c" diff --git a/CHOLMOD/Core/cholmod_l_sparse.c b/CHOLMOD/Core/cholmod_l_sparse.c new file mode 100644 index 0000000000..1bb2f27a44 --- /dev/null +++ b/CHOLMOD/Core/cholmod_l_sparse.c @@ -0,0 +1,13 @@ +//------------------------------------------------------------------------------ +// CHOLMOD/Core/cholmod_l_sparse.c: int64_t version of cholmod_sparse +//------------------------------------------------------------------------------ + +// CHOLMOD/Core Module. Copyright (C) 2005-2022, University of Florida. +// All Rights Reserved. Author: Timothy A. Davis +// SPDX-License-Identifier: LGPL-2.1+ + +//------------------------------------------------------------------------------ + +#define DLONG +#include "cholmod_sparse.c" + diff --git a/CHOLMOD/Utility/cholmod_l_transpose.c b/CHOLMOD/Core/cholmod_l_transpose.c similarity index 53% rename from CHOLMOD/Utility/cholmod_l_transpose.c rename to CHOLMOD/Core/cholmod_l_transpose.c index 1d409ad176..57fb11ed3e 100644 --- a/CHOLMOD/Utility/cholmod_l_transpose.c +++ b/CHOLMOD/Core/cholmod_l_transpose.c @@ -1,13 +1,13 @@ //------------------------------------------------------------------------------ -// CHOLMOD/Utility/cholmod_l_transpose: transpose a sparse matrix +// CHOLMOD/Core/cholmod_l_transpose.c: int64_t version of cholmod_transpose //------------------------------------------------------------------------------ -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. +// CHOLMOD/Core Module. Copyright (C) 2005-2022, University of Florida. +// All Rights Reserved. Author: Timothy A. Davis // SPDX-License-Identifier: LGPL-2.1+ //------------------------------------------------------------------------------ -#define CHOLMOD_INT64 -#include "t_cholmod_transpose.c" +#define DLONG +#include "cholmod_transpose.c" diff --git a/CHOLMOD/Utility/cholmod_sparse_to_triplet.c b/CHOLMOD/Core/cholmod_l_triplet.c similarity index 56% rename from CHOLMOD/Utility/cholmod_sparse_to_triplet.c rename to CHOLMOD/Core/cholmod_l_triplet.c index 73b103ba4f..3d46b1a6c9 100644 --- a/CHOLMOD/Utility/cholmod_sparse_to_triplet.c +++ b/CHOLMOD/Core/cholmod_l_triplet.c @@ -1,13 +1,13 @@ //------------------------------------------------------------------------------ -// CHOLMOD/Utility/cholmod_sparse_to_triplet: convert sparse to triplet +// CHOLMOD/Core/cholmod_l_triplet.c: int64_t version of cholmod_triplet //------------------------------------------------------------------------------ -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. +// CHOLMOD/Core Module. Copyright (C) 2005-2022, University of Florida. +// All Rights Reserved. Author: Timothy A. Davis // SPDX-License-Identifier: LGPL-2.1+ //------------------------------------------------------------------------------ -#define CHOLMOD_INT32 -#include "t_cholmod_sparse_to_triplet.c" +#define DLONG +#include "cholmod_triplet.c" diff --git a/CHOLMOD/Utility/cholmod_l_version.c b/CHOLMOD/Core/cholmod_l_version.c similarity index 54% rename from CHOLMOD/Utility/cholmod_l_version.c rename to CHOLMOD/Core/cholmod_l_version.c index 5c31ea984b..039e2abb82 100644 --- a/CHOLMOD/Utility/cholmod_l_version.c +++ b/CHOLMOD/Core/cholmod_l_version.c @@ -1,13 +1,13 @@ //------------------------------------------------------------------------------ -// CHOLMOD/Utility/cholmod_l_version: CHOLMOD version +// CHOLMOD/Core/cholmod_l_version.c: int64_t version of cholmod_version //------------------------------------------------------------------------------ -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. +// CHOLMOD/Core Module. Copyright (C) 2005-2022, University of Florida. +// All Rights Reserved. Author: Timothy A. Davis // SPDX-License-Identifier: LGPL-2.1+ //------------------------------------------------------------------------------ -#define CHOLMOD_INT64 -#include "t_cholmod_version.c" +#define DLONG +#include "cholmod_version.c" diff --git a/CHOLMOD/Core/cholmod_memory.c b/CHOLMOD/Core/cholmod_memory.c new file mode 100644 index 0000000000..bc1b25f202 --- /dev/null +++ b/CHOLMOD/Core/cholmod_memory.c @@ -0,0 +1,553 @@ +//------------------------------------------------------------------------------ +// CHOLMOD/Core/cholmod_memory: memory management routines +//------------------------------------------------------------------------------ + +// CHOLMOD/Core Module. Copyright (C) 2005-2022, University of Florida. +// All Rights Reserved. Author: Timothy A. Davis +// SPDX-License-Identifier: LGPL-2.1+ + +//------------------------------------------------------------------------------ + +/* Core memory management routines: + * + * Primary routines: + * ----------------- + * cholmod_malloc malloc wrapper + * cholmod_free free wrapper + * + * Secondary routines: + * ------------------- + * cholmod_calloc calloc wrapper + * cholmod_realloc realloc wrapper + * cholmod_realloc_multiple realloc wrapper for multiple objects + * + * The user may make use of these, just like malloc and free. You can even + * malloc an object and safely free it with cholmod_free, and visa versa + * (except that the memory usage statistics will be corrupted). These routines + * do differ from malloc and free. If cholmod_free is given a NULL pointer, + * for example, it does nothing (unlike the ANSI free). cholmod_realloc does + * not return NULL if given a non-NULL pointer and a nonzero size, even if it + * fails (it sets an error code in Common->status instead). + * + * CHOLMOD keeps track of the amount of memory it has allocated, and so the + * cholmod_free routine includes as a parameter the size of the object being + * freed. This is only used for memory usage statistics, which are very useful + * in finding memory leaks in your program. If you, the user of CHOLMOD, pass + * the wrong size, the only consequence is that the memory usage statistics + * will be invalid. This will causes assertions to fail if CHOLMOD is + * compiled with debugging enabled, but otherwise it will cause no errors. + * + * The cholmod_free_* routines for each CHOLMOD object keep track of the size + * of the blocks they free, so they do not require you to pass their sizes + * as a parameter. + * + * If a block of size zero is requested, these routines allocate a block of + * size one instead. + */ + +#include "cholmod_internal.h" + +/* ========================================================================== */ +/* === cholmod_add_size_t =================================================== */ +/* ========================================================================== */ + +/* Safely compute a+b, and check for integer overflow. If overflow occurs, + * return 0 and set OK to FALSE. Also return 0 if OK is FALSE on input. */ + +size_t CHOLMOD(add_size_t) (size_t a, size_t b, int *ok) +{ + size_t s = a + b ; + (*ok) = (*ok) && (s >= a) ; + return ((*ok) ? s : 0) ; +} + +/* ========================================================================== */ +/* === cholmod_mult_size_t ================================================== */ +/* ========================================================================== */ + +/* Safely compute a*k, where k should be small, and check for integer overflow. + * If overflow occurs, return 0 and set OK to FALSE. Also return 0 if OK is + * FALSE on input. */ + +size_t CHOLMOD(mult_size_t) (size_t a, size_t k, int *ok) +{ + size_t p = 0, s ; + while (*ok) + { + if (k % 2) + { + p = p + a ; + (*ok) = (*ok) && (p >= a) ; + } + k = k / 2 ; + if (!k) return (p) ; + s = a + a ; + (*ok) = (*ok) && (s >= a) ; + a = s ; + } + return (0) ; +} + + +/* ========================================================================== */ +/* === cholmod_malloc ======================================================= */ +/* ========================================================================== */ + +/* Wrapper around malloc routine. Allocates space of size MAX(1,n)*size, where + * size is normally a sizeof (...). + * + * This routine, cholmod_calloc, and cholmod_realloc do not set Common->status + * to CHOLMOD_OK on success, so that a sequence of cholmod_malloc's, _calloc's, + * or _realloc's can be used. If any of them fails, the Common->status will + * hold the most recent error status. + * + * Usage, for a pointer to int: + * + * p = cholmod_malloc (n, sizeof (int), Common) + * + * Uses a pointer to the malloc routine (or its equivalent) defined in Common. + */ + +void *CHOLMOD(malloc) /* returns pointer to the newly malloc'd block */ +( + /* ---- input ---- */ + size_t n, /* number of items */ + size_t size, /* size of each item */ + /* --------------- */ + cholmod_common *Common +) +{ + void *p ; + size_t s ; + /* + int ok = TRUE ; + */ + + RETURN_IF_NULL_COMMON (NULL) ; + if (size == 0) + { + ERROR (CHOLMOD_INVALID, "sizeof(item) must be > 0") ; + p = NULL ; + } + else if (n >= (SIZE_MAX / size) || (int64_t) n >= Int_max) + { + /* object is too big to allocate without causing integer overflow */ + ERROR (CHOLMOD_TOO_LARGE, "problem too large") ; + p = NULL ; + } + else + { + /* call malloc, or its equivalent */ + p = SuiteSparse_malloc (n, size) ; + + if (p == NULL) + { + /* failure: out of memory */ + ERROR (CHOLMOD_OUT_OF_MEMORY, "out of memory") ; + } + else + { + /* success: increment the count of objects allocated */ + Common->malloc_count++ ; + Common->memory_inuse += (n * size) ; + Common->memory_usage = + MAX (Common->memory_usage, Common->memory_inuse) ; + PRINTM (("cholmod_malloc %p %g cnt: %g inuse %g\n", + p, (double) n*size, (double) Common->malloc_count, + (double) Common->memory_inuse)) ; + } + } + return (p) ; +} + + +/* ========================================================================== */ +/* === cholmod_free ========================================================= */ +/* ========================================================================== */ + +/* Wrapper around free routine. Returns NULL, which can be assigned to the + * pointer being freed, as in: + * + * p = cholmod_free (n, sizeof (int), p, Common) ; + * + * In CHOLMOD, the syntax: + * + * cholmod_free (n, sizeof (int), p, Common) ; + * + * is used if p is a local pointer and the routine is returning shortly. + * Uses a pointer to the free routine (or its equivalent) defined in Common. + * Nothing is freed if the pointer is NULL. + */ + +void *CHOLMOD(free) /* always returns NULL */ +( + /* ---- input ---- */ + size_t n, /* number of items */ + size_t size, /* size of each item */ + /* ---- in/out --- */ + void *p, /* block of memory to free */ + /* --------------- */ + cholmod_common *Common +) +{ + RETURN_IF_NULL_COMMON (NULL) ; + if (p != NULL) + { + /* only free the object if the pointer is not NULL */ + /* call free, or its equivalent */ + SuiteSparse_free (p) ; + + Common->malloc_count-- ; + Common->memory_inuse -= (n * size) ; + PRINTM (("cholmod_free %p %g cnt: %g inuse %g\n", + p, (double) n*size, (double) Common->malloc_count, + (double) Common->memory_inuse)) ; + /* This assertion will fail if the user calls cholmod_malloc and + * cholmod_free with mismatched memory sizes. It shouldn't fail + * otherwise. */ + ASSERT (IMPLIES (Common->malloc_count == 0, Common->memory_inuse == 0)); + } + /* return NULL, and the caller should assign this to p. This avoids + * freeing the same pointer twice. */ + return (NULL) ; +} + + +/* ========================================================================== */ +/* === cholmod_calloc ======================================================= */ +/* ========================================================================== */ + +/* Wrapper around calloc routine. + * + * Uses a pointer to the calloc routine (or its equivalent) defined in Common. + * This routine is identical to malloc, except that it zeros the newly allocated + * block to zero. + */ + +void *CHOLMOD(calloc) /* returns pointer to the newly calloc'd block */ +( + /* ---- input ---- */ + size_t n, /* number of items */ + size_t size, /* size of each item */ + /* --------------- */ + cholmod_common *Common +) +{ + void *p ; + + RETURN_IF_NULL_COMMON (NULL) ; + if (size == 0) + { + ERROR (CHOLMOD_INVALID, "sizeof(item) must be > 0") ; + p = NULL ; + } + else if (n >= (SIZE_MAX / size) || (int64_t) n >= Int_max) + { + /* object is too big to allocate without causing integer overflow */ + ERROR (CHOLMOD_TOO_LARGE, "problem too large") ; + p = NULL ; + } + else + { + /* call calloc, or its equivalent */ + p = SuiteSparse_calloc (n, size) ; + + if (p == NULL) + { + /* failure: out of memory */ + ERROR (CHOLMOD_OUT_OF_MEMORY, "out of memory") ; + } + else + { + /* success: increment the count of objects allocated */ + Common->malloc_count++ ; + Common->memory_inuse += (n * size) ; + Common->memory_usage = + MAX (Common->memory_usage, Common->memory_inuse) ; + PRINTM (("cholmod_malloc %p %g cnt: %g inuse %g\n", + p, (double) n*size, (double) Common->malloc_count, + (double) Common->memory_inuse)) ; + } + } + return (p) ; +} + + +/* ========================================================================== */ +/* === cholmod_realloc ====================================================== */ +/* ========================================================================== */ + +/* Wrapper around realloc routine. Given a pointer p to a block of size + * (*n)*size memory, it changes the size of the block pointed to by p to be + * MAX(1,nnew)*size in size. It may return a pointer different than p. This + * should be used as (for a pointer to int): + * + * p = cholmod_realloc (nnew, sizeof (int), p, *n, Common) ; + * + * If p is NULL, this is the same as p = cholmod_malloc (...). + * A size of nnew=0 is treated as nnew=1. + * + * If the realloc fails, p is returned unchanged and Common->status is set + * to CHOLMOD_OUT_OF_MEMORY. If successful, Common->status is not modified, + * and p is returned (possibly changed) and pointing to a large block of memory. + * + * Uses a pointer to the realloc routine (or its equivalent) defined in Common. + */ + +void *CHOLMOD(realloc) /* returns pointer to reallocated block */ +( + /* ---- input ---- */ + size_t nnew, /* requested # of items in reallocated block */ + size_t size, /* size of each item */ + /* ---- in/out --- */ + void *p, /* block of memory to realloc */ + size_t *n, /* current size on input, nnew on output if successful*/ + /* --------------- */ + cholmod_common *Common +) +{ + size_t nold = (*n) ; + void *pnew ; + size_t s ; + int ok = TRUE ; + + RETURN_IF_NULL_COMMON (NULL) ; + if (size == 0) + { + ERROR (CHOLMOD_INVALID, "sizeof(item) must be > 0") ; + p = NULL ; + } + else if (p == NULL) + { + /* A fresh object is being allocated. */ + PRINT1 (("realloc fresh: %d %d\n", nnew, size)) ; + p = CHOLMOD(malloc) (nnew, size, Common) ; + *n = (p == NULL) ? 0 : nnew ; + } + else if (nold == nnew) + { + /* Nothing to do. Do not change p or n. */ + PRINT1 (("realloc nothing: %d %d\n", nnew, size)) ; + } + else if (nnew >= (SIZE_MAX / size) || (int64_t) nnew >= Int_max) + { + /* failure: nnew is too big. Do not change p or n. */ + ERROR (CHOLMOD_TOO_LARGE, "problem too large") ; + } + else + { + /* The object exists, and is changing to some other nonzero size. */ + /* call realloc, or its equivalent */ + PRINT1 (("realloc : %d to %d, %d\n", nold, nnew, size)) ; + pnew = SuiteSparse_realloc (nnew, nold, size, p, &ok) ; + if (ok) + { + /* success: return revised p and change the size of the block */ + PRINTM (("cholmod_free %p %g cnt: %g inuse %g\n" + "cholmod_malloc %p %g cnt: %g inuse %g\n", + p, (double) nold*size, (double) Common->malloc_count-1, + (double) (Common->memory_inuse - nold*size), + pnew, (double) nnew*size, (double) Common->malloc_count, + (double) (Common->memory_inuse + (nnew-nold)*size))) ; + p = pnew ; + *n = nnew ; + Common->memory_inuse += ((nnew-nold) * size) ; + } + else + { + /* Increasing the size of the block has failed. + * Do not change n. */ + ERROR (CHOLMOD_OUT_OF_MEMORY, "out of memory") ; + } + + Common->memory_usage = MAX (Common->memory_usage, Common->memory_inuse); + } + + return (p) ; +} + + +/* ========================================================================== */ +/* === cholmod_realloc_multiple ============================================= */ +/* ========================================================================== */ + +/* reallocate multiple blocks of memory, all of the same size (up to two integer + * and two real blocks). Either reallocations all succeed, or all are returned + * in the original size (they are freed if the original size is zero). The nnew + * blocks are of size 1 or more. + */ + +int CHOLMOD(realloc_multiple) +( + /* ---- input ---- */ + size_t nnew, /* requested # of items in reallocated blocks */ + int nint, /* number of int32_t/int64_t blocks */ + int xtype, /* CHOLMOD_PATTERN, _REAL, _COMPLEX, or _ZOMPLEX */ + /* ---- in/out --- */ + void **Iblock, /* int32_t or int64_t block */ + void **Jblock, /* int32_t or int64_t block */ + void **Xblock, /* complex or double block */ + void **Zblock, /* zomplex case only: double block */ + size_t *nold_p, /* current size of the I,J,X,Z blocks on input, + * nnew on output if successful */ + /* --------------- */ + cholmod_common *Common +) +{ + double *xx, *zz ; + size_t i, j, x, z, nold ; + + RETURN_IF_NULL_COMMON (FALSE) ; + + if (xtype < CHOLMOD_PATTERN || xtype > CHOLMOD_ZOMPLEX) + { + ERROR (CHOLMOD_INVALID, "invalid xtype") ; + return (FALSE) ; + } + + nold = *nold_p ; + + if (nint < 1 && xtype == CHOLMOD_PATTERN) + { + /* nothing to do */ + return (TRUE) ; + } + + i = nold ; + j = nold ; + x = nold ; + z = nold ; + + if (nint > 0) + { + *Iblock = CHOLMOD(realloc) (nnew, sizeof (Int), *Iblock, &i, Common) ; + } + if (nint > 1) + { + *Jblock = CHOLMOD(realloc) (nnew, sizeof (Int), *Jblock, &j, Common) ; + } + + switch (xtype) + { + case CHOLMOD_REAL: + *Xblock = CHOLMOD(realloc) (nnew, sizeof (double), *Xblock, &x, + Common) ; + break ; + + case CHOLMOD_COMPLEX: + *Xblock = CHOLMOD(realloc) (nnew, 2*sizeof (double), *Xblock, &x, + Common) ; + break ; + + case CHOLMOD_ZOMPLEX: + *Xblock = CHOLMOD(realloc) (nnew, sizeof (double), *Xblock, &x, + Common) ; + *Zblock = CHOLMOD(realloc) (nnew, sizeof (double), *Zblock, &z, + Common) ; + break ; + } + + if (Common->status < CHOLMOD_OK) + { + /* one or more realloc's failed. Resize all back down to nold. */ + + if (nold == 0) + { + + if (nint > 0) + { + *Iblock = CHOLMOD(free) (i, sizeof (Int), *Iblock, Common) ; + } + if (nint > 1) + { + *Jblock = CHOLMOD(free) (j, sizeof (Int), *Jblock, Common) ; + } + + switch (xtype) + { + case CHOLMOD_REAL: + *Xblock = CHOLMOD(free) (x, sizeof (double), *Xblock, + Common) ; + break ; + + case CHOLMOD_COMPLEX: + *Xblock = CHOLMOD(free) (x, 2*sizeof (double), *Xblock, + Common) ; + break ; + + case CHOLMOD_ZOMPLEX: + *Xblock = CHOLMOD(free) (x, sizeof (double), *Xblock, + Common) ; + *Zblock = CHOLMOD(free) (x, sizeof (double), *Zblock, + Common) ; + break ; + } + + } + else + { + if (nint > 0) + { + *Iblock = CHOLMOD(realloc) (nold, sizeof (Int), *Iblock, &i, + Common) ; + } + if (nint > 1) + { + *Jblock = CHOLMOD(realloc) (nold, sizeof (Int), *Jblock, &j, + Common) ; + } + + switch (xtype) + { + case CHOLMOD_REAL: + *Xblock = CHOLMOD(realloc) (nold, sizeof (double), + *Xblock, &x, Common) ; + break ; + + case CHOLMOD_COMPLEX: + *Xblock = CHOLMOD(realloc) (nold, 2*sizeof (double), + *Xblock, &x, Common) ; + break ; + + case CHOLMOD_ZOMPLEX: + *Xblock = CHOLMOD(realloc) (nold, sizeof (double), + *Xblock, &x, Common) ; + *Zblock = CHOLMOD(realloc) (nold, sizeof (double), + *Zblock, &z, Common) ; + break ; + } + + } + + return (FALSE) ; + } + + if (nold == 0) + { + /* New space was allocated. Clear the first entry so that valgrind + * doesn't complain about its access in change_complexity + * (Core/cholmod_complex.c). */ + xx = *Xblock ; + zz = *Zblock ; + switch (xtype) + { + case CHOLMOD_REAL: + xx [0] = 0 ; + break ; + + case CHOLMOD_COMPLEX: + xx [0] = 0 ; + xx [1] = 0 ; + break ; + + case CHOLMOD_ZOMPLEX: + xx [0] = 0 ; + zz [0] = 0 ; + break ; + } + } + + /* all realloc's succeeded, change size to reflect realloc'ed size. */ + *nold_p = nnew ; + return (TRUE) ; +} diff --git a/CHOLMOD/Core/cholmod_sparse.c b/CHOLMOD/Core/cholmod_sparse.c new file mode 100644 index 0000000000..6fa9b8ddb9 --- /dev/null +++ b/CHOLMOD/Core/cholmod_sparse.c @@ -0,0 +1,649 @@ +//------------------------------------------------------------------------------ +// CHOLMOD/Core/cholmod_sparse: core methods for the cholmod_sparse object +//------------------------------------------------------------------------------ + +// CHOLMOD/Core Module. Copyright (C) 2005-2022, University of Florida. +// All Rights Reserved. Author: Timothy A. Davis +// SPDX-License-Identifier: LGPL-2.1+ + +//------------------------------------------------------------------------------ + +/* Core utility routines for the cholmod_sparse object: + * + * A sparse matrix is held in compressed column form. In the basic type + * ("packed", which corresponds to a MATLAB sparse matrix), an n-by-n matrix + * with nz entries is held in three arrays: p of size n+1, i of size nz, and x + * of size nz. Row indices of column j are held in i [p [j] ... p [j+1]-1] and + * in the same locations in x. There may be no duplicate entries in a column. + * Row indices in each column may be sorted or unsorted (CHOLMOD keeps track). + * + * Primary routines: + * ----------------- + * cholmod_allocate_sparse allocate a sparse matrix + * cholmod_free_sparse free a sparse matrix + * + * Secondary routines: + * ------------------- + * cholmod_reallocate_sparse change the size (# entries) of sparse matrix + * cholmod_nnz number of nonzeros in a sparse matrix + * cholmod_speye sparse identity matrix + * cholmod_spzeros sparse zero matrix + * cholmod_copy_sparse create a copy of a sparse matrix + * + * All xtypes are supported (pattern, real, complex, and zomplex) + */ + +#include "cholmod_internal.h" + +/* ========================================================================== */ +/* === cholmod_allocate_sparse ============================================== */ +/* ========================================================================== */ + +/* Allocate space for a matrix. A->i and A->x are not initialized. A->p + * (and A->nz if A is not packed) are set to zero, so a matrix containing no + * entries (all zero) is returned. See also cholmod_spzeros. + * + * workspace: none + */ + +cholmod_sparse *CHOLMOD(allocate_sparse) +( + /* ---- input ---- */ + size_t nrow, /* # of rows of A */ + size_t ncol, /* # of columns of A */ + size_t nzmax, /* max # of nonzeros of A */ + int sorted, /* TRUE if columns of A sorted, FALSE otherwise */ + int packed, /* TRUE if A will be packed, FALSE otherwise */ + int stype, /* stype of A */ + int xtype, /* CHOLMOD_PATTERN, _REAL, _COMPLEX, or _ZOMPLEX */ + /* --------------- */ + cholmod_common *Common +) +{ + cholmod_sparse *A ; + Int *Ap, *Anz ; + size_t nzmax0 ; + Int j ; + int ok = TRUE ; + + /* ---------------------------------------------------------------------- */ + /* get inputs */ + /* ---------------------------------------------------------------------- */ + + RETURN_IF_NULL_COMMON (NULL) ; + if (stype != 0 && nrow != ncol) + { + ERROR (CHOLMOD_INVALID, "rectangular matrix with stype != 0 invalid") ; + return (NULL) ; + } + if (xtype < CHOLMOD_PATTERN || xtype > CHOLMOD_ZOMPLEX) + { + ERROR (CHOLMOD_INVALID, "xtype invalid") ; + return (NULL) ; + } + /* ensure the dimensions do not cause integer overflow */ + (void) CHOLMOD(add_size_t) (ncol, 2, &ok) ; + if (!ok || (int64_t) nrow >= Int_max + || (int64_t) ncol >= Int_max + || (int64_t) nzmax >= Int_max) + { + ERROR (CHOLMOD_TOO_LARGE, "problem too large") ; + return (NULL) ; + } + Common->status = CHOLMOD_OK ; + + /* ---------------------------------------------------------------------- */ + /* allocate header */ + /* ---------------------------------------------------------------------- */ + + A = CHOLMOD(malloc) (sizeof (cholmod_sparse), 1, Common) ; + if (Common->status < CHOLMOD_OK) + { + return (NULL) ; /* out of memory */ + } + PRINT1 (("cholmod_allocate_sparse %d-by-%d nzmax %d sorted %d packed %d" + " xtype %d\n", nrow, ncol, nzmax, sorted, packed, xtype)) ; + + nzmax = MAX (1, nzmax) ; + + A->nrow = nrow ; + A->ncol = ncol ; + A->nzmax = nzmax ; + A->packed = packed ; /* default is packed (A->nz not present) */ + A->stype = stype ; + A->itype = ITYPE ; + A->xtype = xtype ; + A->dtype = DTYPE ; + + A->nz = NULL ; + A->p = NULL ; + A->i = NULL ; + A->x = NULL ; + A->z = NULL ; + + /* A 1-by-m matrix always has sorted columns */ + A->sorted = (nrow <= 1) ? TRUE : sorted ; + + /* ---------------------------------------------------------------------- */ + /* allocate the matrix itself */ + /* ---------------------------------------------------------------------- */ + + /* allocate O(ncol) space */ + A->p = CHOLMOD(malloc) (((size_t) ncol)+1, sizeof (Int), Common) ; + if (!packed) + { + A->nz = CHOLMOD(malloc) (ncol, sizeof (Int), Common) ; + } + + /* allocate O(nz) space */ + nzmax0 = 0 ; + CHOLMOD(realloc_multiple) (nzmax, 1, xtype, &(A->i), NULL, &(A->x), &(A->z), + &nzmax0, Common) ; + + if (Common->status < CHOLMOD_OK) + { + CHOLMOD(free_sparse) (&A, Common) ; + return (NULL) ; /* out of memory */ + } + + /* ---------------------------------------------------------------------- */ + /* initialize A->p and A->nz so that A is an empty matrix */ + /* ---------------------------------------------------------------------- */ + + Ap = A->p ; + for (j = 0 ; j <= (Int) ncol ; j++) + { + Ap [j] = 0 ; + } + if (!packed) + { + Anz = A->nz ; + for (j = 0 ; j < (Int) ncol ; j++) + { + Anz [j] = 0 ; + } + } + return (A) ; +} + + +/* ========================================================================== */ +/* === cholmod_free_sparse ================================================== */ +/* ========================================================================== */ + +/* free a sparse matrix + * + * workspace: none + */ + +int CHOLMOD(free_sparse) +( + /* ---- in/out --- */ + cholmod_sparse **AHandle, /* matrix to deallocate, NULL on output */ + /* --------------- */ + cholmod_common *Common +) +{ + Int n, nz ; + cholmod_sparse *A ; + + RETURN_IF_NULL_COMMON (FALSE) ; + + if (AHandle == NULL) + { + /* nothing to do */ + return (TRUE) ; + } + A = *AHandle ; + if (A == NULL) + { + /* nothing to do */ + return (TRUE) ; + } + n = A->ncol ; + nz = A->nzmax ; + A->p = CHOLMOD(free) (n+1, sizeof (Int), A->p, Common) ; + A->i = CHOLMOD(free) (nz, sizeof (Int), A->i, Common) ; + A->nz = CHOLMOD(free) (n, sizeof (Int), A->nz, Common) ; + + switch (A->xtype) + { + case CHOLMOD_REAL: + A->x = CHOLMOD(free) (nz, sizeof (double), A->x, Common) ; + break ; + + case CHOLMOD_COMPLEX: + A->x = CHOLMOD(free) (nz, 2*sizeof (double), A->x, Common) ; + break ; + + case CHOLMOD_ZOMPLEX: + A->x = CHOLMOD(free) (nz, sizeof (double), A->x, Common) ; + A->z = CHOLMOD(free) (nz, sizeof (double), A->z, Common) ; + break ; + } + + *AHandle = CHOLMOD(free) (1, sizeof (cholmod_sparse), (*AHandle), Common) ; + return (TRUE) ; +} + + +/* ========================================================================== */ +/* === cholmod_reallocate_sparse ============================================ */ +/* ========================================================================== */ + +/* Change the size of A->i, A->x, and A->z, or allocate them if their current + * size is zero. A->x and A->z are not modified if A->xtype is CHOLMOD_PATTERN. + * A->z is not modified unless A->xtype is CHOLMOD_ZOMPLEX. + * + * workspace: none + */ + +int CHOLMOD(reallocate_sparse) +( + /* ---- input ---- */ + size_t nznew, /* new # of entries in A */ + /* ---- in/out --- */ + cholmod_sparse *A, /* matrix to reallocate */ + /* --------------- */ + cholmod_common *Common +) +{ + + /* ---------------------------------------------------------------------- */ + /* get inputs */ + /* ---------------------------------------------------------------------- */ + + RETURN_IF_NULL_COMMON (FALSE) ; + RETURN_IF_NULL (A, FALSE) ; + RETURN_IF_XTYPE_INVALID (A, CHOLMOD_PATTERN, CHOLMOD_ZOMPLEX, FALSE) ; + Common->status = CHOLMOD_OK ; + PRINT1 (("realloc matrix %d to %d, xtype: %d\n", + A->nzmax, nznew, A->xtype)) ; + + /* ---------------------------------------------------------------------- */ + /* resize the matrix */ + /* ---------------------------------------------------------------------- */ + + CHOLMOD(realloc_multiple) (MAX (1,nznew), 1, A->xtype, &(A->i), NULL, + &(A->x), &(A->z), &(A->nzmax), Common) ; + + return (Common->status == CHOLMOD_OK) ; +} + + +/* ========================================================================== */ +/* === cholmod_speye ======================================================== */ +/* ========================================================================== */ + +/* Return a sparse identity matrix. */ + +cholmod_sparse *CHOLMOD(speye) +( + /* ---- input ---- */ + size_t nrow, /* # of rows of A */ + size_t ncol, /* # of columns of A */ + int xtype, /* CHOLMOD_PATTERN, _REAL, _COMPLEX, or _ZOMPLEX */ + /* --------------- */ + cholmod_common *Common +) +{ + double *Ax, *Az ; + cholmod_sparse *A ; + Int *Ap, *Ai ; + Int j, n ; + + /* ---------------------------------------------------------------------- */ + /* get inputs */ + /* ---------------------------------------------------------------------- */ + + RETURN_IF_NULL_COMMON (NULL) ; + Common->status = CHOLMOD_OK ; + + /* ---------------------------------------------------------------------- */ + /* allocate the matrix */ + /* ---------------------------------------------------------------------- */ + + n = MIN (nrow, ncol) ; + A = CHOLMOD(allocate_sparse) (nrow, ncol, n, TRUE, TRUE, 0, xtype, + Common) ; + + if (Common->status < CHOLMOD_OK) + { + return (NULL) ; /* out of memory or inputs invalid */ + } + + /* ---------------------------------------------------------------------- */ + /* create the identity matrix */ + /* ---------------------------------------------------------------------- */ + + Ap = A->p ; + Ai = A->i ; + Ax = A->x ; + Az = A->z ; + + for (j = 0 ; j < n ; j++) + { + Ap [j] = j ; + } + for (j = n ; j <= ((Int) ncol) ; j++) + { + Ap [j] = n ; + } + for (j = 0 ; j < n ; j++) + { + Ai [j] = j ; + } + + switch (xtype) + { + case CHOLMOD_REAL: + for (j = 0 ; j < n ; j++) + { + Ax [j] = 1 ; + } + break ; + + case CHOLMOD_COMPLEX: + for (j = 0 ; j < n ; j++) + { + Ax [2*j ] = 1 ; + Ax [2*j+1] = 0 ; + } + break ; + + case CHOLMOD_ZOMPLEX: + for (j = 0 ; j < n ; j++) + { + Ax [j] = 1 ; + } + for (j = 0 ; j < n ; j++) + { + Az [j] = 0 ; + } + break ; + } + + return (A) ; +} + + +/* ========================================================================== */ +/* === cholmod_spzeros ====================================================== */ +/* ========================================================================== */ + +/* Return a sparse zero matrix. */ + +cholmod_sparse *CHOLMOD(spzeros) +( + /* ---- input ---- */ + size_t nrow, /* # of rows of A */ + size_t ncol, /* # of columns of A */ + size_t nzmax, /* max # of nonzeros of A */ + int xtype, /* CHOLMOD_PATTERN, _REAL, _COMPLEX, or _ZOMPLEX */ + /* --------------- */ + cholmod_common *Common +) +{ + + /* ---------------------------------------------------------------------- */ + /* get inputs */ + /* ---------------------------------------------------------------------- */ + + RETURN_IF_NULL_COMMON (NULL) ; + Common->status = CHOLMOD_OK ; + + /* ---------------------------------------------------------------------- */ + /* allocate the matrix */ + /* ---------------------------------------------------------------------- */ + + return (CHOLMOD(allocate_sparse) (nrow, ncol, nzmax, TRUE, TRUE, 0, xtype, + Common)) ; +} + + +/* ========================================================================== */ +/* === cholmod_nnz ========================================================== */ +/* ========================================================================== */ + +/* Return the number of entries in a sparse matrix. + * + * workspace: none + * integer overflow cannot occur, since the matrix is already allocated. + */ + +int64_t CHOLMOD(nnz) +( + /* ---- input ---- */ + cholmod_sparse *A, + /* --------------- */ + cholmod_common *Common +) +{ + Int *Ap, *Anz ; + size_t nz ; + Int j, ncol ; + + /* ---------------------------------------------------------------------- */ + /* get inputs */ + /* ---------------------------------------------------------------------- */ + + RETURN_IF_NULL_COMMON (EMPTY) ; + RETURN_IF_NULL (A, EMPTY) ; + RETURN_IF_XTYPE_INVALID (A, CHOLMOD_PATTERN, CHOLMOD_ZOMPLEX, EMPTY) ; + Common->status = CHOLMOD_OK ; + + /* ---------------------------------------------------------------------- */ + /* return nnz (A) */ + /* ---------------------------------------------------------------------- */ + + ncol = A->ncol ; + if (A->packed) + { + Ap = A->p ; + RETURN_IF_NULL (Ap, EMPTY) ; + nz = Ap [ncol] ; + } + else + { + Anz = A->nz ; + RETURN_IF_NULL (Anz, EMPTY) ; + nz = 0 ; + for (j = 0 ; j < ncol ; j++) + { + nz += MAX (0, Anz [j]) ; + } + } + return (nz) ; +} + + +/* ========================================================================== */ +/* === cholmod_copy_sparse ================================================== */ +/* ========================================================================== */ + +/* C = A. Create an exact copy of a sparse matrix, with one exception. + * Entries in unused space are not copied (they might not be initialized, + * and copying them would cause program checkers such as purify and + * valgrind to complain). The xtype of the resulting matrix C is the same as + * the xtype of the input matrix A. + * + * See also Core/cholmod_copy, which copies a matrix with possible changes + * in stype, presence of diagonal entries, pattern vs. numerical values, + * real and/or imaginary parts, and so on. + */ + +cholmod_sparse *CHOLMOD(copy_sparse) +( + /* ---- input ---- */ + cholmod_sparse *A, /* matrix to copy */ + /* --------------- */ + cholmod_common *Common +) +{ + double *Ax, *Cx, *Az, *Cz ; + Int *Ap, *Ai, *Anz, *Cp, *Ci, *Cnz ; + cholmod_sparse *C ; + Int p, pend, j, ncol, packed, nzmax, nz, xtype ; + + /* ---------------------------------------------------------------------- */ + /* check inputs */ + /* ---------------------------------------------------------------------- */ + + RETURN_IF_NULL_COMMON (NULL) ; + RETURN_IF_NULL (A, NULL) ; + RETURN_IF_XTYPE_INVALID (A, CHOLMOD_PATTERN, CHOLMOD_ZOMPLEX, NULL) ; + if (A->stype != 0 && A->nrow != A->ncol) + { + ERROR (CHOLMOD_INVALID, "rectangular matrix with stype != 0 invalid") ; + return (NULL) ; + } + Common->status = CHOLMOD_OK ; + ASSERT (CHOLMOD(dump_sparse) (A, "A original", Common) >= 0) ; + + /* ---------------------------------------------------------------------- */ + /* get inputs */ + /* ---------------------------------------------------------------------- */ + + ncol = A->ncol ; + nzmax = A->nzmax ; + packed = A->packed ; + Ap = A->p ; + Ai = A->i ; + Ax = A->x ; + Az = A->z ; + Anz = A->nz ; + xtype = A->xtype ; + + /* ---------------------------------------------------------------------- */ + /* allocate the copy */ + /* ---------------------------------------------------------------------- */ + + C = CHOLMOD(allocate_sparse) (A->nrow, A->ncol, A->nzmax, A->sorted, + A->packed, A->stype, A->xtype, Common) ; + + if (Common->status < CHOLMOD_OK) + { + return (NULL) ; /* out of memory */ + } + + Cp = C->p ; + Ci = C->i ; + Cx = C->x ; + Cz = C->z ; + Cnz = C->nz ; + + /* ---------------------------------------------------------------------- */ + /* copy the matrix */ + /* ---------------------------------------------------------------------- */ + + for (j = 0 ; j <= ncol ; j++) + { + Cp [j] = Ap [j] ; + } + + if (packed) + { + nz = Ap [ncol] ; + for (p = 0 ; p < nz ; p++) + { + Ci [p] = Ai [p] ; + } + + switch (xtype) + { + case CHOLMOD_REAL: + for (p = 0 ; p < nz ; p++) + { + Cx [p] = Ax [p] ; + } + break ; + + case CHOLMOD_COMPLEX: + for (p = 0 ; p < 2*nz ; p++) + { + Cx [p] = Ax [p] ; + } + break ; + + case CHOLMOD_ZOMPLEX: + for (p = 0 ; p < nz ; p++) + { + Cx [p] = Ax [p] ; + Cz [p] = Az [p] ; + } + break ; + } + + } + else + { + + for (j = 0 ; j < ncol ; j++) + { + Cnz [j] = Anz [j] ; + } + + switch (xtype) + { + case CHOLMOD_PATTERN: + for (j = 0 ; j < ncol ; j++) + { + p = Ap [j] ; + pend = p + Anz [j] ; + for ( ; p < pend ; p++) + { + Ci [p] = Ai [p] ; + } + } + break ; + + case CHOLMOD_REAL: + for (j = 0 ; j < ncol ; j++) + { + p = Ap [j] ; + pend = p + Anz [j] ; + for ( ; p < pend ; p++) + { + Ci [p] = Ai [p] ; + Cx [p] = Ax [p] ; + } + } + break ; + + case CHOLMOD_COMPLEX: + for (j = 0 ; j < ncol ; j++) + { + p = Ap [j] ; + pend = p + Anz [j] ; + for ( ; p < pend ; p++) + { + Ci [p] = Ai [p] ; + Cx [2*p ] = Ax [2*p ] ; + Cx [2*p+1] = Ax [2*p+1] ; + } + } + break ; + + case CHOLMOD_ZOMPLEX: + for (j = 0 ; j < ncol ; j++) + { + p = Ap [j] ; + pend = p + Anz [j] ; + for ( ; p < pend ; p++) + { + Ci [p] = Ai [p] ; + Cx [p] = Ax [p] ; + Cz [p] = Az [p] ; + } + } + break ; + } + } + + /* ---------------------------------------------------------------------- */ + /* return the result */ + /* ---------------------------------------------------------------------- */ + + ASSERT (CHOLMOD(dump_sparse) (C, "C copy", Common) >= 0) ; + return (C) ; +} diff --git a/CHOLMOD/Core/cholmod_transpose.c b/CHOLMOD/Core/cholmod_transpose.c new file mode 100644 index 0000000000..8e3a1af4b0 --- /dev/null +++ b/CHOLMOD/Core/cholmod_transpose.c @@ -0,0 +1,1133 @@ +//------------------------------------------------------------------------------ +// CHOLMOD/Core/cholmod_tranpose: transpose a matrix +//------------------------------------------------------------------------------ + +// CHOLMOD/Core Module. Copyright (C) 2005-2022, University of Florida. +// All Rights Reserved. Author: Timothy A. Davis +// SPDX-License-Identifier: LGPL-2.1+ + +//------------------------------------------------------------------------------ + +/* Core utility routines for the cholmod_sparse object to + * compute the transpose or permuted transpose of a matrix: + * + * Primary routines: + * ----------------- + * cholmod_transpose transpose sparse matrix + * cholmod_ptranspose transpose and permute sparse matrix + * cholmod_sort sort row indices in each column of sparse matrix + * + * Secondary routines: + * ------------------- + * cholmod_transpose_unsym transpose unsymmetric sparse matrix + * cholmod_transpose_sym transpose symmetric sparse matrix + * + * All xtypes (pattern, real, complex, and zomplex) are supported. + * + * --------------------------------------- + * Unsymmetric case: A->stype is zero. + * --------------------------------------- + * + * Computes F = A', F = A (:,f)' or F = A (p,f)', except that the indexing by + * f does not work the same as the MATLAB notation (see below). A->stype + * is zero, which denotes that both the upper and lower triangular parts of + * A are present (and used). A may in fact be symmetric in pattern and/or + * value; A->stype just denotes which part of A are stored. A may be + * rectangular. + * + * p is a permutation of 0:m-1, and f is a subset of 0:n-1, where A is m-by-n. + * There can be no duplicate entries in p or f. + * + * The set f is held in fset and fsize. + * fset = NULL means ":" in MATLAB. fsize is ignored. + * fset != NULL means f = fset [0..fsize-1]. + * fset != NULL and fsize = 0 means f is the empty set. + * + * Columns not in the set f are considered to be zero. That is, + * if A is 5-by-10 then F = A (:,[3 4])' is not 2-by-5, but 10-by-5, and rows + * 3 and 4 of F are equal to columns 3 and 4 of A (the other rows of F are + * zero). More precisely, in MATLAB notation: + * + * [m n] = size (A) ; + * F = A ; + * notf = ones (1,n) ; + * notf (f) = 0 ; + * F (:, find (notf)) = 0 + * F = F' + * + * If you want the MATLAB equivalent F=A(p,f) operation, use cholmod_submatrix + * instead (which does not compute the transpose). + * + * F->nzmax must be large enough to hold the matrix F. It is not modified. + * If F->nz is present then F->nz [j] = # of entries in column j of F. + * + * A can be sorted or unsorted, with packed or unpacked columns. + * + * If f is present and not sorted in ascending order, then F is unsorted + * (that is, it may contain columns whose row indices do not appear in + * ascending order). Otherwise, F is sorted (the row indices in each + * column of F appear in strictly ascending order). + * + * F is returned in packed or unpacked form, depending on F->packed on input. + * If F->packed is false, then F is returned in unpacked form (F->nz must be + * present). Each row i of F is large enough to hold all the entries in row i + * of A, even if f is provided. That is, F->i and + * F->x [F->p [i] .. F->p [i] + F->nz [i] - 1] contain all entries in A (i,f), + * but F->p [i+1] - F->p [i] is equal to the number of nonzeros in A (i,:), + * not just A (i,f). + * + * The cholmod_transpose_unsym routine is the only operation in CHOLMOD that + * can produce an unpacked matrix. + * + * --------------------------------------- + * Symmetric case: A->stype is nonzero. + * --------------------------------------- + * + * Computes F = A' or F = A(p,p)', the transpose or permuted transpose, where + * A->stype is nonzero. + * + * If A->stype > 0, then A is a symmetric matrix where just the upper part + * of the matrix is stored. Entries in the lower triangular part may be + * present, but are ignored. A must be square. If F=A', then F is returned + * sorted; otherwise F is unsorted for the F=A(p,p)' case. + * + * There can be no duplicate entries in p. + * The fset and fsize parameters are not used. + * + * Three kinds of transposes are available, depending on the "values" parameter: + * 0: do not transpose the numerical values; create a CHOLMOD_PATTERN matrix + * 1: array transpose + * 2: complex conjugate transpose (same as 2 if input is real or pattern) + * + * ----------------------------------------------------------------------------- + * + * For cholmod_transpose_unsym and cholmod_transpose_sym, the output matrix + * F must already be pre-allocated by the caller, with the correct dimensions. + * If F is not valid or has the wrong dimensions, it is not modified. + * Otherwise, if F is too small, the transpose is not computed; the contents + * of F->p contain the column pointers of the resulting matrix, where + * F->p [F->ncol] > F->nzmax. In this case, the remaining contents of F are + * not modified. F can still be properly free'd with cholmod_free_sparse. + */ + +#include "cholmod_internal.h" + +/* ========================================================================== */ +/* === TEMPLATE ============================================================= */ +/* ========================================================================== */ + +#define PATTERN +#include "t_cholmod_transpose.c" +#define REAL +#include "t_cholmod_transpose.c" +#define COMPLEX +#include "t_cholmod_transpose.c" +#define COMPLEX +#define NCONJUGATE +#include "t_cholmod_transpose.c" +#define ZOMPLEX +#include "t_cholmod_transpose.c" +#define ZOMPLEX +#define NCONJUGATE +#include "t_cholmod_transpose.c" + +/* ========================================================================== */ +/* === cholmod_transpose_unsym ============================================== */ +/* ========================================================================== */ + +/* Compute F = A', A (:,f)', or A (p,f)', where A is unsymmetric and F is + * already allocated. See cholmod_transpose for a simpler routine. + * + * workspace: + * Iwork (MAX (nrow,ncol)) if fset is present + * Iwork (nrow) if fset is NULL + * + * The xtype of A and F must match, unless values is zero or F->xtype is + * CHOLMOD_PATTERN (in which case only the pattern of A is transpose into F). + */ + +int CHOLMOD(transpose_unsym) +( + /* ---- input ---- */ + cholmod_sparse *A, /* matrix to transpose */ + int values, /* 2: complex conj. transpose, 1: array transpose, + 0: do not transpose the numerical values */ + Int *Perm, /* size nrow, if present (can be NULL) */ + Int *fset, /* subset of 0:(A->ncol)-1 */ + size_t fsize, /* size of fset */ + /* ---- output --- */ + cholmod_sparse *F, /* F = A', A(:,f)', or A(p,f)' */ + /* --------------- */ + cholmod_common *Common +) +{ + Int *Fp, *Fnz, *Ap, *Ai, *Anz, *Wi ; + Int nrow, ncol, permute, use_fset, Apacked, Fpacked, p, pend, + i, j, k, Fsorted, nf, jj, jlast ; + size_t s ; + int ok = TRUE ; + + /* ---------------------------------------------------------------------- */ + /* check inputs */ + /* ---------------------------------------------------------------------- */ + + RETURN_IF_NULL_COMMON (FALSE) ; + RETURN_IF_NULL (A, FALSE) ; + RETURN_IF_NULL (F, FALSE) ; + RETURN_IF_XTYPE_INVALID (A, CHOLMOD_PATTERN, CHOLMOD_ZOMPLEX, FALSE) ; + RETURN_IF_XTYPE_INVALID (F, CHOLMOD_PATTERN, CHOLMOD_ZOMPLEX, FALSE) ; + if (A->nrow != F->ncol || A->ncol != F->nrow) + { + ERROR (CHOLMOD_INVALID, "F has the wrong dimensions") ; + return (FALSE) ; + } + Common->status = CHOLMOD_OK ; + + /* ---------------------------------------------------------------------- */ + /* get inputs */ + /* ---------------------------------------------------------------------- */ + + nf = fsize ; + use_fset = (fset != NULL) ; + nrow = A->nrow ; + ncol = A->ncol ; + + Ap = A->p ; /* size A->ncol+1, column pointers of A */ + Ai = A->i ; /* size nz = Ap [A->ncol], row indices of A */ + Anz = A->nz ; + Apacked = A->packed ; + ASSERT (IMPLIES (!Apacked, Anz != NULL)) ; + + permute = (Perm != NULL) ; + + Fp = F->p ; /* size A->nrow+1, row pointers of F */ + Fnz = F->nz ; + Fpacked = F->packed ; + ASSERT (IMPLIES (!Fpacked, Fnz != NULL)) ; + + nf = (use_fset) ? nf : ncol ; + + /* ---------------------------------------------------------------------- */ + /* allocate workspace */ + /* ---------------------------------------------------------------------- */ + + /* s = nrow + ((fset != NULL) ? ncol : 0) */ + s = CHOLMOD(add_size_t) (nrow, ((fset != NULL) ? ncol : 0), &ok) ; + if (!ok) + { + ERROR (CHOLMOD_TOO_LARGE, "problem too large") ; + return (FALSE) ; + } + + CHOLMOD(allocate_work) (0, s, 0, Common) ; + if (Common->status < CHOLMOD_OK) + { + return (FALSE) ; /* out of memory */ + } + + Wi = Common->Iwork ; /* size nrow (i/l/l) */ + + /* ---------------------------------------------------------------------- */ + /* check Perm and fset */ + /* ---------------------------------------------------------------------- */ + + if (permute) + { + for (i = 0 ; i < nrow ; i++) + { + Wi [i] = 1 ; + } + for (k = 0 ; k < nrow ; k++) + { + i = Perm [k] ; + if (i < 0 || i > nrow || Wi [i] == 0) + { + ERROR (CHOLMOD_INVALID, "invalid permutation") ; + return (FALSE) ; + } + Wi [i] = 0 ; + } + } + + if (use_fset) + { + for (j = 0 ; j < ncol ; j++) + { + Wi [j] = 1 ; + } + for (k = 0 ; k < nf ; k++) + { + j = fset [k] ; + if (j < 0 || j > ncol || Wi [j] == 0) + { + ERROR (CHOLMOD_INVALID, "invalid fset") ; + return (FALSE) ; + } + Wi [j] = 0 ; + } + } + + /* Perm and fset are now valid */ + ASSERT (CHOLMOD(dump_perm) (Perm, nrow, nrow, "Perm", Common)) ; + ASSERT (CHOLMOD(dump_perm) (fset, nf, ncol, "fset", Common)) ; + + /* ---------------------------------------------------------------------- */ + /* count the entries in each row of A or A(:,f) */ + /* ---------------------------------------------------------------------- */ + + for (i = 0 ; i < nrow ; i++) + { + Wi [i] = 0 ; + } + + jlast = EMPTY ; + Fsorted = TRUE ; + + if (use_fset) + { + /* count entries in each row of A(:,f) */ + for (jj = 0 ; jj < nf ; jj++) + { + j = fset [jj] ; + if (j <= jlast) + { + Fsorted = FALSE ; + } + p = Ap [j] ; + pend = (Apacked) ? (Ap [j+1]) : (p + Anz [j]) ; + for ( ; p < pend ; p++) + { + Wi [Ai [p]]++ ; + } + jlast = j ; + } + + /* save the nz counts if F is unpacked, and recount all of A */ + if (!Fpacked) + { + if (permute) + { + for (i = 0 ; i < nrow ; i++) + { + Fnz [i] = Wi [Perm [i]] ; + } + } + else + { + for (i = 0 ; i < nrow ; i++) + { + Fnz [i] = Wi [i] ; + } + } + for (i = 0 ; i < nrow ; i++) + { + Wi [i] = 0 ; + } + + /* count entries in each row of A */ + for (j = 0 ; j < ncol ; j++) + { + p = Ap [j] ; + pend = (Apacked) ? (Ap [j+1]) : (p + Anz [j]) ; + for ( ; p < pend ; p++) + { + Wi [Ai [p]]++ ; + } + } + } + + } + else + { + + /* count entries in each row of A */ + for (j = 0 ; j < ncol ; j++) + { + p = Ap [j] ; + pend = (Apacked) ? (Ap [j+1]) : (p + Anz [j]) ; + for ( ; p < pend ; p++) + { + Wi [Ai [p]]++ ; + } + } + + /* save the nz counts if F is unpacked */ + if (!Fpacked) + { + if (permute) + { + for (i = 0 ; i < nrow ; i++) + { + Fnz [i] = Wi [Perm [i]] ; + } + } + else + { + for (i = 0 ; i < nrow ; i++) + { + Fnz [i] = Wi [i] ; + } + } + } + } + + /* ---------------------------------------------------------------------- */ + /* compute the row pointers */ + /* ---------------------------------------------------------------------- */ + + p = 0 ; + if (permute) + { + for (i = 0 ; i < nrow ; i++) + { + Fp [i] = p ; + p += Wi [Perm [i]] ; + } + for (i = 0 ; i < nrow ; i++) + { + Wi [Perm [i]] = Fp [i] ; + } + } + else + { + for (i = 0 ; i < nrow ; i++) + { + Fp [i] = p ; + p += Wi [i] ; + } + for (i = 0 ; i < nrow ; i++) + { + Wi [i] = Fp [i] ; + } + } + Fp [nrow] = p ; + + if (p > (Int) (F->nzmax)) + { + ERROR (CHOLMOD_INVALID, "F is too small") ; + return (FALSE) ; + } + + /* ---------------------------------------------------------------------- */ + /* transpose matrix, using template routine */ + /* ---------------------------------------------------------------------- */ + + ok = FALSE ; + if (values == 0 || F->xtype == CHOLMOD_PATTERN) + { + ok = p_cholmod_transpose_unsym (A, Perm, fset, nf, F, Common) ; + } + else if (F->xtype == CHOLMOD_REAL) + { + ok = r_cholmod_transpose_unsym (A, Perm, fset, nf, F, Common) ; + } + else if (F->xtype == CHOLMOD_COMPLEX) + { + if (values == 1) + { + /* array transpose */ + ok = ct_cholmod_transpose_unsym (A, Perm, fset, nf, F, Common) ; + } + else + { + /* complex conjugate transpose */ + ok = c_cholmod_transpose_unsym (A, Perm, fset, nf, F, Common) ; + } + } + else if (F->xtype == CHOLMOD_ZOMPLEX) + { + if (values == 1) + { + /* array transpose */ + ok = zt_cholmod_transpose_unsym (A, Perm, fset, nf, F, Common) ; + } + else + { + /* complex conjugate transpose */ + ok = z_cholmod_transpose_unsym (A, Perm, fset, nf, F, Common) ; + } + } + + /* ---------------------------------------------------------------------- */ + /* finalize result F */ + /* ---------------------------------------------------------------------- */ + + if (ok) + { + F->sorted = Fsorted ; + } + ASSERT (CHOLMOD(dump_sparse) (F, "output F unsym", Common) >= 0) ; + return (ok) ; +} + + +/* ========================================================================== */ +/* === cholmod_transpose_sym ================================================ */ +/* ========================================================================== */ + +/* Compute F = A' or A (p,p)', where A is symmetric and F is already allocated. + * See cholmod_transpose for a simpler routine. + * + * workspace: Iwork (nrow) if Perm NULL, Iwork (2*nrow) if Perm non-NULL. + */ + +int CHOLMOD(transpose_sym) +( + /* ---- input ---- */ + cholmod_sparse *A, /* matrix to transpose */ + int values, /* 2: complex conj. transpose, 1: array transpose, + 0: do not transpose the numerical values */ + Int *Perm, /* size nrow, if present (can be NULL) */ + /* ---- output --- */ + cholmod_sparse *F, /* F = A' or A(p,p)' */ + /* --------------- */ + cholmod_common *Common +) +{ + Int *Ap, *Anz, *Ai, *Fp, *Wi, *Pinv, *Iwork ; + Int p, pend, packed, upper, permute, jold, n, i, j, k, iold ; + size_t s ; + int ok = TRUE ; + + /* ---------------------------------------------------------------------- */ + /* check inputs */ + /* ---------------------------------------------------------------------- */ + + RETURN_IF_NULL_COMMON (FALSE) ; + RETURN_IF_NULL (A, FALSE) ; + RETURN_IF_NULL (F, FALSE) ; + RETURN_IF_XTYPE_INVALID (A, CHOLMOD_PATTERN, CHOLMOD_ZOMPLEX, FALSE) ; + RETURN_IF_XTYPE_INVALID (F, CHOLMOD_PATTERN, CHOLMOD_ZOMPLEX, FALSE) ; + if (A->nrow != A->ncol || A->stype == 0) + { + /* this routine handles square symmetric matrices only */ + ERROR (CHOLMOD_INVALID, "matrix must be symmetric") ; + return (FALSE) ; + } + if (A->nrow != F->ncol || A->ncol != F->nrow) + { + ERROR (CHOLMOD_INVALID, "F has the wrong dimensions") ; + return (FALSE) ; + } + Common->status = CHOLMOD_OK ; + + /* ---------------------------------------------------------------------- */ + /* get inputs */ + /* ---------------------------------------------------------------------- */ + + permute = (Perm != NULL) ; + n = A->nrow ; + Ap = A->p ; /* size A->ncol+1, column pointers of A */ + Ai = A->i ; /* size nz = Ap [A->ncol], row indices of A */ + Anz = A->nz ; + packed = A->packed ; + ASSERT (IMPLIES (!packed, Anz != NULL)) ; + upper = (A->stype > 0) ; + + Fp = F->p ; /* size A->nrow+1, row pointers of F */ + + /* ---------------------------------------------------------------------- */ + /* allocate workspace */ + /* ---------------------------------------------------------------------- */ + + /* s = (Perm != NULL) ? 2*n : n */ + s = CHOLMOD(add_size_t) (n, ((Perm != NULL) ? n : 0), &ok) ; + if (!ok) + { + ERROR (CHOLMOD_TOO_LARGE, "problem too large") ; + return (FALSE) ; + } + + CHOLMOD(allocate_work) (0, s, 0, Common) ; + if (Common->status < CHOLMOD_OK) + { + return (FALSE) ; /* out of memory */ + } + + /* ---------------------------------------------------------------------- */ + /* get workspace */ + /* ---------------------------------------------------------------------- */ + + Iwork = Common->Iwork ; + Wi = Iwork ; /* size n (i/l/l) */ + Pinv = Iwork + n ; /* size n (i/i/l) , unused if Perm NULL */ + + /* ---------------------------------------------------------------------- */ + /* check Perm and construct inverse permutation */ + /* ---------------------------------------------------------------------- */ + + if (permute) + { + for (i = 0 ; i < n ; i++) + { + Pinv [i] = EMPTY ; + } + for (k = 0 ; k < n ; k++) + { + i = Perm [k] ; + if (i < 0 || i > n || Pinv [i] != EMPTY) + { + ERROR (CHOLMOD_INVALID, "invalid permutation") ; + return (FALSE) ; + } + Pinv [i] = k ; + } + } + + /* Perm is now valid */ + ASSERT (CHOLMOD(dump_perm) (Perm, n, n, "Perm", Common)) ; + + /* ---------------------------------------------------------------------- */ + /* count the entries in each row of F */ + /* ---------------------------------------------------------------------- */ + + for (i = 0 ; i < n ; i++) + { + Wi [i] = 0 ; + } + + if (packed) + { + if (permute) + { + if (upper) + { + /* packed, permuted, upper */ + for (j = 0 ; j < n ; j++) + { + jold = Perm [j] ; + pend = Ap [jold+1] ; + for (p = Ap [jold] ; p < pend ; p++) + { + iold = Ai [p] ; + if (iold <= jold) + { + i = Pinv [iold] ; + Wi [MIN (i, j)]++ ; + } + } + } + } + else + { + /* packed, permuted, lower */ + for (j = 0 ; j < n ; j++) + { + jold = Perm [j] ; + pend = Ap [jold+1] ; + for (p = Ap [jold] ; p < pend ; p++) + { + iold = Ai [p] ; + if (iold >= jold) + { + i = Pinv [iold] ; + Wi [MAX (i, j)]++ ; + } + } + } + } + } + else + { + if (upper) + { + /* packed, unpermuted, upper */ + for (j = 0 ; j < n ; j++) + { + pend = Ap [j+1] ; + for (p = Ap [j] ; p < pend ; p++) + { + i = Ai [p] ; + if (i <= j) + { + Wi [i]++ ; + } + } + } + } + else + { + /* packed, unpermuted, lower */ + for (j = 0 ; j < n ; j++) + { + pend = Ap [j+1] ; + for (p = Ap [j] ; p < pend ; p++) + { + i = Ai [p] ; + if (i >= j) + { + Wi [i]++ ; + } + } + } + } + } + } + else + { + if (permute) + { + if (upper) + { + /* unpacked, permuted, upper */ + for (j = 0 ; j < n ; j++) + { + jold = Perm [j] ; + p = Ap [jold] ; + pend = p + Anz [jold] ; + for ( ; p < pend ; p++) + { + iold = Ai [p] ; + if (iold <= jold) + { + i = Pinv [iold] ; + Wi [MIN (i, j)]++ ; + } + } + } + } + else + { + /* unpacked, permuted, lower */ + for (j = 0 ; j < n ; j++) + { + jold = Perm [j] ; + p = Ap [jold] ; + pend = p + Anz [jold] ; + for ( ; p < pend ; p++) + { + iold = Ai [p] ; + if (iold >= jold) + { + i = Pinv [iold] ; + Wi [MAX (i, j)]++ ; + } + } + } + } + } + else + { + if (upper) + { + /* unpacked, unpermuted, upper */ + for (j = 0 ; j < n ; j++) + { + p = Ap [j] ; + pend = p + Anz [j] ; + for ( ; p < pend ; p++) + { + i = Ai [p] ; + if (i <= j) + { + Wi [i]++ ; + } + } + } + } + else + { + /* unpacked, unpermuted, lower */ + for (j = 0 ; j < n ; j++) + { + p = Ap [j] ; + pend = p + Anz [j] ; + for ( ; p < pend ; p++) + { + i = Ai [p] ; + if (i >= j) + { + Wi [i]++ ; + } + } + } + } + } + } + + /* ---------------------------------------------------------------------- */ + /* compute the row pointers */ + /* ---------------------------------------------------------------------- */ + + p = 0 ; + for (i = 0 ; i < n ; i++) + { + Fp [i] = p ; + p += Wi [i] ; + } + Fp [n] = p ; + for (i = 0 ; i < n ; i++) + { + Wi [i] = Fp [i] ; + } + + if (p > (Int) (F->nzmax)) + { + ERROR (CHOLMOD_INVALID, "F is too small") ; + return (FALSE) ; + } + + /* ---------------------------------------------------------------------- */ + /* transpose matrix, using template routine */ + /* ---------------------------------------------------------------------- */ + + ok = FALSE ; + if (values == 0 || F->xtype == CHOLMOD_PATTERN) + { + PRINT2 (("\n:::: p_transpose_sym Perm %p\n", Perm)) ; + ok = p_cholmod_transpose_sym (A, Perm, F, Common) ; + } + else if (F->xtype == CHOLMOD_REAL) + { + PRINT2 (("\n:::: r_transpose_sym Perm %p\n", Perm)) ; + ok = r_cholmod_transpose_sym (A, Perm, F, Common) ; + } + else if (F->xtype == CHOLMOD_COMPLEX) + { + if (values == 1) + { + /* array transpose */ + PRINT2 (("\n:::: ct_transpose_sym Perm %p\n", Perm)) ; + ok = ct_cholmod_transpose_sym (A, Perm, F, Common) ; + } + else + { + /* complex conjugate transpose */ + PRINT2 (("\n:::: c_transpose_sym Perm %p\n", Perm)) ; + ok = c_cholmod_transpose_sym (A, Perm, F, Common) ; + } + } + else if (F->xtype == CHOLMOD_ZOMPLEX) + { + if (values == 1) + { + /* array transpose */ + PRINT2 (("\n:::: zt_transpose_sym Perm %p\n", Perm)) ; + ok = zt_cholmod_transpose_sym (A, Perm, F, Common) ; + } + else + { + /* complex conjugate transpose */ + PRINT2 (("\n:::: z_transpose_sym Perm %p\n", Perm)) ; + ok = z_cholmod_transpose_sym (A, Perm, F, Common) ; + } + } + + /* ---------------------------------------------------------------------- */ + /* finalize result F */ + /* ---------------------------------------------------------------------- */ + + /* F is sorted if there is no permutation vector */ + if (ok) + { + F->sorted = !permute ; + F->packed = TRUE ; + F->stype = - SIGN (A->stype) ; /* flip the stype */ + ASSERT (CHOLMOD(dump_sparse) (F, "output F sym", Common) >= 0) ; + } + return (ok) ; +} + + +/* ========================================================================== */ +/* === cholmod_transpose ==================================================== */ +/* ========================================================================== */ + +/* Returns A'. See also cholmod_ptranspose below. */ + +cholmod_sparse *CHOLMOD(transpose) +( + /* ---- input ---- */ + cholmod_sparse *A, /* matrix to transpose */ + int values, /* 2: complex conj. transpose, 1: array transpose, + 0: do not transpose the numerical values + (returns its result as CHOLMOD_PATTERN) */ + /* --------------- */ + cholmod_common *Common +) +{ + return (CHOLMOD(ptranspose) (A, values, NULL, NULL, 0, Common)) ; +} + + +/* ========================================================================== */ +/* === cholmod_ptranspose =================================================== */ +/* ========================================================================== */ + +/* Return A' or A(p,p)' if A is symmetric. Return A', A(:,f)', or A(p,f)' if + * A is unsymmetric. + * + * workspace: + * Iwork (MAX (nrow,ncol)) if unsymmetric and fset is non-NULL + * Iwork (nrow) if unsymmetric and fset is NULL + * Iwork (2*nrow) if symmetric and Perm is non-NULL. + * Iwork (nrow) if symmetric and Perm is NULL. + * + * A simple worst-case upper bound on the workspace is nrow+ncol. + */ + +cholmod_sparse *CHOLMOD(ptranspose) +( + /* ---- input ---- */ + cholmod_sparse *A, /* matrix to transpose */ + int values, /* 2: complex conj. transpose, 1: array transpose, + 0: do not transpose the numerical values */ + Int *Perm, /* if non-NULL, F = A(p,f) or A(p,p) */ + Int *fset, /* subset of 0:(A->ncol)-1 */ + size_t fsize, /* size of fset */ + /* --------------- */ + cholmod_common *Common +) +{ + Int *Ap, *Anz ; + cholmod_sparse *F ; + Int nrow, ncol, use_fset, j, jj, fnz, packed, stype, nf, xtype ; + size_t ineed ; + int ok = TRUE ; + + nf = fsize ; + + /* ---------------------------------------------------------------------- */ + /* check inputs */ + /* ---------------------------------------------------------------------- */ + + RETURN_IF_NULL_COMMON (NULL) ; + RETURN_IF_NULL (A, FALSE) ; + RETURN_IF_XTYPE_INVALID (A, CHOLMOD_PATTERN, CHOLMOD_ZOMPLEX, NULL) ; + stype = A->stype ; + Common->status = CHOLMOD_OK ; + + /* ---------------------------------------------------------------------- */ + /* allocate workspace */ + /* ---------------------------------------------------------------------- */ + + nrow = A->nrow ; + ncol = A->ncol ; + + if (stype != 0) + { + use_fset = FALSE ; + if (Perm != NULL) + { + ineed = CHOLMOD(mult_size_t) (A->nrow, 2, &ok) ; + } + else + { + ineed = A->nrow ; + } + } + else + { + use_fset = (fset != NULL) ; + if (use_fset) + { + ineed = MAX (A->nrow, A->ncol) ; + } + else + { + ineed = A->nrow ; + } + } + + if (!ok) + { + ERROR (CHOLMOD_TOO_LARGE, "problem too large") ; + return (NULL) ; + } + + CHOLMOD(allocate_work) (0, ineed, 0, Common) ; + if (Common->status < CHOLMOD_OK) + { + return (NULL) ; /* out of memory */ + } + + /* ---------------------------------------------------------------------- */ + /* get inputs */ + /* ---------------------------------------------------------------------- */ + + Ap = A->p ; + Anz = A->nz ; + packed = A->packed ; + ASSERT (IMPLIES (!packed, Anz != NULL)) ; + xtype = values ? A->xtype : CHOLMOD_PATTERN ; + + /* ---------------------------------------------------------------------- */ + /* allocate F */ + /* ---------------------------------------------------------------------- */ + + /* determine # of nonzeros in F */ + if (stype != 0) + { + /* F=A' or F=A(p,p)', fset is ignored */ + fnz = CHOLMOD(nnz) (A, Common) ; + } + else + { + nf = (use_fset) ? nf : ncol ; + if (use_fset) + { + fnz = 0 ; + /* F=A(:,f)' or F=A(p,f)' */ + for (jj = 0 ; jj < nf ; jj++) + { + /* The fset is not yet checked; it will be thoroughly checked + * in cholmod_transpose_unsym. For now, just make sure we don't + * access Ap and Anz out of bounds. */ + j = fset [jj] ; + if (j >= 0 && j < ncol) + { + fnz += packed ? (Ap [j+1] - Ap [j]) : MAX (0, Anz [j]) ; + } + } + } + else + { + /* F=A' or F=A(p,:)' */ + fnz = CHOLMOD(nnz) (A, Common) ; + } + } + + /* F is ncol-by-nrow, fnz nonzeros, sorted unless f is present and unsorted, + * packed, of opposite stype as A, and with/without numerical values */ + F = CHOLMOD(allocate_sparse) (ncol, nrow, fnz, TRUE, TRUE, -SIGN(stype), + xtype, Common) ; + if (Common->status < CHOLMOD_OK) + { + return (NULL) ; /* out of memory */ + } + + /* ---------------------------------------------------------------------- */ + /* transpose and optionally permute the matrix A */ + /* ---------------------------------------------------------------------- */ + + if (stype != 0) + { + /* F = A (p,p)', using upper or lower triangular part of A only */ + ok = CHOLMOD(transpose_sym) (A, values, Perm, F, Common) ; + } + else + { + /* F = A (p,f)' */ + ok = CHOLMOD(transpose_unsym) (A, values, Perm, fset, nf, F, Common) ; + } + + /* ---------------------------------------------------------------------- */ + /* return the matrix F, or NULL if an error occured */ + /* ---------------------------------------------------------------------- */ + + if (!ok) + { + CHOLMOD(free_sparse) (&F, Common) ; + } + return (F) ; +} + + +/* ========================================================================== */ +/* === cholmod_sort ========================================================= */ +/* ========================================================================== */ + +/* Sort the columns of A, in place. Returns A in packed form, even if it + * starts as unpacked. Removes entries in the ignored part of a symmetric + * matrix. + * + * workspace: Iwork (max (nrow,ncol)). Allocates additional workspace for a + * temporary copy of A'. + */ + +int CHOLMOD(sort) +( + /* ---- in/out --- */ + cholmod_sparse *A, /* matrix to sort */ + /* --------------- */ + cholmod_common *Common +) +{ + Int *Ap ; + cholmod_sparse *F ; + Int anz, ncol, nrow, stype ; + + /* ---------------------------------------------------------------------- */ + /* check inputs */ + /* ---------------------------------------------------------------------- */ + + RETURN_IF_NULL_COMMON (FALSE) ; + RETURN_IF_NULL (A, FALSE) ; + RETURN_IF_XTYPE_INVALID (A, CHOLMOD_PATTERN, CHOLMOD_ZOMPLEX, FALSE) ; + Common->status = CHOLMOD_OK ; + nrow = A->nrow ; + if (nrow <= 1) + { + /* a 1-by-n sparse matrix must be sorted */ + A->sorted = TRUE ; + return (TRUE) ; + } + + /* ---------------------------------------------------------------------- */ + /* allocate workspace */ + /* ---------------------------------------------------------------------- */ + + ncol = A->ncol ; + CHOLMOD(allocate_work) (0, MAX (nrow, ncol), 0, Common) ; + if (Common->status < CHOLMOD_OK) + { + return (FALSE) ; /* out of memory */ + } + + /* ---------------------------------------------------------------------- */ + /* get inputs */ + /* ---------------------------------------------------------------------- */ + + anz = CHOLMOD(nnz) (A, Common) ; + stype = A->stype ; + + /* ---------------------------------------------------------------------- */ + /* sort the columns of the matrix */ + /* ---------------------------------------------------------------------- */ + + /* allocate workspace for transpose: ncol-by-nrow, same # of nonzeros as A, + * sorted, packed, same stype as A, and of the same numeric type as A. */ + F = CHOLMOD(allocate_sparse) (ncol, nrow, anz, TRUE, TRUE, stype, + A->xtype, Common) ; + if (Common->status < CHOLMOD_OK) + { + return (FALSE) ; /* out of memory */ + } + + if (stype != 0) + { + /* F = A', upper or lower triangular part only */ + CHOLMOD(transpose_sym) (A, 1, NULL, F, Common) ; + A->packed = TRUE ; + /* A = F' */ + CHOLMOD(transpose_sym) (F, 1, NULL, A, Common) ; + } + else + { + /* F = A' */ + CHOLMOD(transpose_unsym) (A, 1, NULL, NULL, 0, F, Common) ; + A->packed = TRUE ; + /* A = F' */ + CHOLMOD(transpose_unsym) (F, 1, NULL, NULL, 0, A, Common) ; + } + + ASSERT (A->sorted && A->packed) ; + ASSERT (CHOLMOD(dump_sparse) (A, "Asorted", Common) >= 0) ; + + /* ---------------------------------------------------------------------- */ + /* reduce A in size, if needed. This must succeed. */ + /* ---------------------------------------------------------------------- */ + + Ap = A->p ; + anz = Ap [ncol] ; + ASSERT ((size_t) anz <= A->nzmax) ; + CHOLMOD(reallocate_sparse) (anz, A, Common) ; + ASSERT (Common->status >= CHOLMOD_OK) ; + + /* ---------------------------------------------------------------------- */ + /* free workspace */ + /* ---------------------------------------------------------------------- */ + + CHOLMOD(free_sparse) (&F, Common) ; + return (TRUE) ; +} diff --git a/CHOLMOD/Core/cholmod_triplet.c b/CHOLMOD/Core/cholmod_triplet.c new file mode 100644 index 0000000000..88beafffe3 --- /dev/null +++ b/CHOLMOD/Core/cholmod_triplet.c @@ -0,0 +1,769 @@ +//------------------------------------------------------------------------------ +// CHOLMOD/Core/cholmod_triplet: core methods for the cholmod_triplet object +//------------------------------------------------------------------------------ + +// CHOLMOD/Core Module. Copyright (C) 2005-2022, University of Florida. +// All Rights Reserved. Author: Timothy A. Davis +// SPDX-License-Identifier: LGPL-2.1+ + +//------------------------------------------------------------------------------ + +/* Core utility routines for the cholmod_triplet object: + * + * A sparse matrix held in triplet form is the simplest one for a user to + * create. It consists of a list of nz entries in arbitrary order, held in + * three arrays: i, j, and x, each of length nk. The kth entry is in row i[k], + * column j[k], with value x[k]. There may be duplicate values; if A(i,j) + * appears more than once, its value is the sum of the entries with those row + * and column indices. + * + * Primary routines: + * ----------------- + * cholmod_allocate_triplet allocate a triplet matrix + * cholmod_free_triplet free a triplet matrix + * + * Secondary routines: + * ------------------- + * cholmod_reallocate_triplet reallocate a triplet matrix + * cholmod_sparse_to_triplet create a triplet matrix copy of a sparse matrix + * cholmod_triplet_to_sparse create a sparse matrix copy of a triplet matrix + * cholmod_copy_triplet create a copy of a triplet matrix + * + * The relationship between an m-by-n cholmod_sparse matrix A and a + * cholmod_triplet matrix (i, j, and x) is identical to how they are used in + * the MATLAB "sparse" and "find" functions: + * + * [i j x] = find (A) + * [m n] = size (A) + * A = sparse (i,j,x,m,n) + * + * with the exception that the cholmod_sparse matrix may be "unpacked", may + * have either sorted or unsorted columns (depending on the option selected), + * and may be symmetric with just the upper or lower triangular part stored. + * Likewise, the cholmod_triplet matrix may contain just the entries in the + * upper or lower triangular part of a symmetric matrix. + * + * MATLAB sparse matrices are always "packed", always have sorted columns, + * and always store both parts of a symmetric matrix. In some cases, MATLAB + * behaves like CHOLMOD by ignoring entries in the upper or lower triangular + * part of a matrix that is otherwise assumed to be symmetric (such as the + * input to chol). In CHOLMOD, that option is a characteristic of the object. + * In MATLAB, that option is based on how a matrix is used as the input to + * a function. + * + * The triplet matrix is provided to give the user a simple way of constructing + * a sparse matrix. There are very few operations supported for triplet + * matrices. The assumption is that they will be converted to cholmod_sparse + * matrix form first. + * + * Adding two triplet matrices simply involves concatenating the contents of + * the three arrays (i, j, and x). To permute a triplet matrix, just replace + * the row and column indices with their permuted values. For example, if + * P is a permutation vector, then P [k] = j means row/column j is the kth + * row/column in C=P*A*P'. In MATLAB notation, C=A(p,p). If Pinv is an array + * of size n and T is the triplet form of A, then: + * + * Ti = T->i ; + * Tj = T->j ; + * for (k = 0 ; k < n ; k++) Pinv [P [k]] = k ; + * for (k = 0 ; k < nz ; k++) Ti [k] = Pinv [Ti [k]] ; + * for (k = 0 ; k < nz ; k++) Tj [k] = Pinv [Tj [k]] ; + * + * overwrites T with the triplet form of C=P*A*P'. The conversion + * + * C = cholmod_triplet_to_sparse (T, 0, &Common) ; + * + * will then return the matrix C = P*A*P'. + * + * Note that T->stype > 0 means that entries in the lower triangular part of + * T are transposed into the upper triangular part when T is converted to + * sparse matrix (cholmod_sparse) form with cholmod_triplet_to_sparse. The + * opposite is true for T->stype < 0. + * + * Since the triplet matrix T is so simple to generate, it's quite easy + * to remove entries that you do not want, prior to converting T to the + * cholmod_sparse form. So if you include these entries in T, CHOLMOD + * assumes that there must be a reason (such as the one above). Thus, + * no entry in a triplet matrix is ever ignored. + * + * Other operations, such as extacting a submatrix, horizontal and vertical + * concatenation, multiply a triplet matrix times a dense matrix, are also + * simple. Multiplying two triplet matrices is not trivial; the simplest + * method is to convert them to cholmod_sparse matrices first. + * + * Supports all xtypes (pattern, real, complex, and zomplex). + */ + +#include "cholmod_internal.h" + +/* ========================================================================== */ +/* === TEMPLATE ============================================================= */ +/* ========================================================================== */ + +#define PATTERN +#include "t_cholmod_triplet.c" +#define REAL +#include "t_cholmod_triplet.c" +#define COMPLEX +#include "t_cholmod_triplet.c" +#define ZOMPLEX +#include "t_cholmod_triplet.c" + +/* ========================================================================== */ +/* === cholmod_allocate_triplet ============================================= */ +/* ========================================================================== */ + +/* allocate space for a triplet matrix + * + * workspace: none + */ + +cholmod_triplet *CHOLMOD(allocate_triplet) +( + /* ---- input ---- */ + size_t nrow, /* # of rows of T */ + size_t ncol, /* # of columns of T */ + size_t nzmax, /* max # of nonzeros of T */ + int stype, /* stype of T */ + int xtype, /* CHOLMOD_PATTERN, _REAL, _COMPLEX, or _ZOMPLEX */ + /* --------------- */ + cholmod_common *Common +) +{ + cholmod_triplet *T ; + size_t nzmax0 ; + int ok = TRUE ; + + /* ---------------------------------------------------------------------- */ + /* get inputs */ + /* ---------------------------------------------------------------------- */ + + RETURN_IF_NULL_COMMON (NULL) ; + if (xtype < CHOLMOD_PATTERN || xtype > CHOLMOD_ZOMPLEX) + { + ERROR (CHOLMOD_INVALID, "xtype invalid") ; + return (NULL) ; + } + /* ensure the dimensions do not cause integer overflow */ + (void) CHOLMOD(add_size_t) (ncol, 2, &ok) ; + if (!ok || (int64_t) nrow >= Int_max + || (int64_t) ncol >= Int_max + || (int64_t) nzmax >= Int_max) + { + ERROR (CHOLMOD_TOO_LARGE, "problem too large") ; + return (NULL) ; + } + + Common->status = CHOLMOD_OK ; + + /* ---------------------------------------------------------------------- */ + /* allocate header */ + /* ---------------------------------------------------------------------- */ + + T = CHOLMOD(malloc) (sizeof (cholmod_triplet), 1, Common) ; + if (Common->status < CHOLMOD_OK) + { + return (NULL) ; /* out of memory */ + } + + PRINT1 (("cholmod_allocate_triplet %d-by-%d nzmax %d xtype %d\n", + nrow, ncol, nzmax, xtype)) ; + + nzmax = MAX (1, nzmax) ; + + T->nrow = nrow ; + T->ncol = ncol ; + T->nzmax = nzmax ; + T->nnz = 0 ; + T->stype = stype ; + T->itype = ITYPE ; + T->xtype = xtype ; + T->dtype = DTYPE ; + + T->j = NULL ; + T->i = NULL ; + T->x = NULL ; + T->z = NULL ; + + /* ---------------------------------------------------------------------- */ + /* allocate the matrix itself */ + /* ---------------------------------------------------------------------- */ + + nzmax0 = 0 ; + CHOLMOD(realloc_multiple) (nzmax, 2, xtype, &(T->i), &(T->j), + &(T->x), &(T->z), &nzmax0, Common) ; + + if (Common->status < CHOLMOD_OK) + { + CHOLMOD(free_triplet) (&T, Common) ; + return (NULL) ; /* out of memory */ + } + + return (T) ; +} + + +/* ========================================================================== */ +/* === cholmod_free_triplet ================================================= */ +/* ========================================================================== */ + +/* free a triplet matrix + * + * workspace: none + */ + +int CHOLMOD(free_triplet) +( + /* ---- in/out --- */ + cholmod_triplet **THandle, /* matrix to deallocate, NULL on output */ + /* --------------- */ + cholmod_common *Common +) +{ + Int nz ; + cholmod_triplet *T ; + + RETURN_IF_NULL_COMMON (FALSE) ; + + if (THandle == NULL) + { + /* nothing to do */ + return (TRUE) ; + } + T = *THandle ; + if (T == NULL) + { + /* nothing to do */ + return (TRUE) ; + } + nz = T->nzmax ; + T->j = CHOLMOD(free) (nz, sizeof (Int), T->j, Common) ; + T->i = CHOLMOD(free) (nz, sizeof (Int), T->i, Common) ; + if (T->xtype == CHOLMOD_REAL) + { + T->x = CHOLMOD(free) (nz, sizeof (double), T->x, Common) ; + } + else if (T->xtype == CHOLMOD_COMPLEX) + { + T->x = CHOLMOD(free) (nz, 2*sizeof (double), T->x, Common) ; + } + else if (T->xtype == CHOLMOD_ZOMPLEX) + { + T->x = CHOLMOD(free) (nz, sizeof (double), T->x, Common) ; + T->z = CHOLMOD(free) (nz, sizeof (double), T->z, Common) ; + } + *THandle = CHOLMOD(free) (1, sizeof (cholmod_triplet), (*THandle), Common) ; + return (TRUE) ; +} + + +/* ========================================================================== */ +/* === cholmod_reallocate_triplet =========================================== */ +/* ========================================================================== */ + +/* Change the size of T->i, T->j, and T->x, or allocate them if their current + * size is zero. T->x is not modified if T->xtype is CHOLMOD_PATTERN. + * + * workspace: none + */ + +int CHOLMOD(reallocate_triplet) +( + /* ---- input ---- */ + size_t nznew, /* new # of entries in T */ + /* ---- in/out --- */ + cholmod_triplet *T, /* triplet matrix to modify */ + /* --------------- */ + cholmod_common *Common +) +{ + + /* ---------------------------------------------------------------------- */ + /* get inputs */ + /* ---------------------------------------------------------------------- */ + + RETURN_IF_NULL_COMMON (FALSE) ; + RETURN_IF_NULL (T, FALSE) ; + RETURN_IF_XTYPE_INVALID (T, CHOLMOD_PATTERN, CHOLMOD_ZOMPLEX, FALSE) ; + Common->status = CHOLMOD_OK ; + PRINT1 (("realloc triplet %d to %d, xtype: %d\n", + T->nzmax, nznew, T->xtype)) ; + + /* ---------------------------------------------------------------------- */ + /* resize the matrix */ + /* ---------------------------------------------------------------------- */ + + CHOLMOD(realloc_multiple) (MAX (1,nznew), 2, T->xtype, &(T->i), &(T->j), + &(T->x), &(T->z), &(T->nzmax), Common) ; + + return (Common->status == CHOLMOD_OK) ; +} + + +/* ========================================================================== */ +/* === cholmod_triplet_to_sparse ============================================ */ +/* ========================================================================== */ + +/* Convert a set of triplets into a cholmod_sparse matrix. In MATLAB notation, + * for unsymmetric matrices: + * + * A = sparse (Ti, Tj, Tx, nrow, ncol, nzmax) ; + * + * For the symmetric upper case: + * + * A = sparse (min(Ti,Tj), max(Ti,Tj), Tx, nrow, ncol, nzmax) ; + * + * For the symmetric lower case: + * + * A = sparse (max(Ti,Tj), min(Ti,Tj), Tx, nrow, ncol, nzmax) ; + * + * If Tx is NULL, then A->x is not allocated, and only the pattern of A is + * computed. A is returned in packed form, and can be of any stype + * (upper/lower/unsymmetric). It has enough space to hold the values in T, + * or nzmax, whichever is larger. + * + * workspace: Iwork (max (nrow,ncol)) + * allocates a temporary copy of its output matrix. + * + * The resulting sparse matrix has the same xtype as the input triplet matrix. + */ + +cholmod_sparse *CHOLMOD(triplet_to_sparse) +( + /* ---- input ---- */ + cholmod_triplet *T, /* matrix to copy */ + size_t nzmax, /* allocate at least this much space in output matrix */ + /* --------------- */ + cholmod_common *Common +) +{ + cholmod_sparse *R, *A = NULL ; + Int *Wj, *Rp, *Ri, *Rnz, *Ti, *Tj ; + Int i, j, p, k, stype, nrow, ncol, nz, ok ; + size_t anz = 0 ; + + /* ---------------------------------------------------------------------- */ + /* check inputs */ + /* ---------------------------------------------------------------------- */ + + RETURN_IF_NULL_COMMON (NULL) ; + RETURN_IF_NULL (T, NULL) ; + Ti = T->i ; + Tj = T->j ; + RETURN_IF_NULL (Ti, NULL) ; + RETURN_IF_NULL (Tj, NULL) ; + RETURN_IF_XTYPE_INVALID (T, CHOLMOD_PATTERN, CHOLMOD_ZOMPLEX, NULL) ; + stype = SIGN (T->stype) ; + if (stype && T->nrow != T->ncol) + { + /* inputs invalid */ + ERROR (CHOLMOD_INVALID, "matrix invalid") ; + return (NULL) ; + } + Common->status = CHOLMOD_OK ; + DEBUG (CHOLMOD(dump_triplet) (T, "T", Common)) ; + + /* ---------------------------------------------------------------------- */ + /* get inputs */ + /* ---------------------------------------------------------------------- */ + + nrow = T->nrow ; + ncol = T->ncol ; + nz = T->nnz ; + + /* ---------------------------------------------------------------------- */ + /* allocate workspace */ + /* ---------------------------------------------------------------------- */ + + CHOLMOD(allocate_work) (0, MAX (nrow, ncol), 0, Common) ; + if (Common->status < CHOLMOD_OK) + { + return (NULL) ; /* out of memory */ + } + + /* ---------------------------------------------------------------------- */ + /* allocate temporary matrix R */ + /* ---------------------------------------------------------------------- */ + + R = CHOLMOD(allocate_sparse) (ncol, nrow, nz, FALSE, FALSE, -stype, + T->xtype, Common) ; + + if (Common->status < CHOLMOD_OK) + { + return (NULL) ; /* out of memory */ + } + + Rp = R->p ; + Ri = R->i ; + Rnz = R->nz ; + + /* ---------------------------------------------------------------------- */ + /* count the entries in each row of A (also counting duplicates) */ + /* ---------------------------------------------------------------------- */ + + for (i = 0 ; i < nrow ; i++) + { + Rnz [i] = 0 ; + } + + if (stype > 0) + { + for (k = 0 ; k < nz ; k++) + { + i = Ti [k] ; + j = Tj [k] ; + if (i < 0 || i >= nrow || j < 0 || j >= ncol) + { + ERROR (CHOLMOD_INVALID, "index out of range") ; + break ; + } + /* A will be symmetric with just the upper triangular part stored. + * Create a matrix R that is lower triangular. Entries in the + * upper part of R are transposed to the lower part. */ + Rnz [MIN (i,j)]++ ; + } + } + else if (stype < 0) + { + for (k = 0 ; k < nz ; k++) + { + i = Ti [k] ; + j = Tj [k] ; + if (i < 0 || i >= nrow || j < 0 || j >= ncol) + { + ERROR (CHOLMOD_INVALID, "index out of range") ; + break ; + } + /* A will be symmetric with just the lower triangular part stored. + * Create a matrix R that is upper triangular. Entries in the + * lower part of R are transposed to the upper part. */ + Rnz [MAX (i,j)]++ ; + } + } + else + { + for (k = 0 ; k < nz ; k++) + { + i = Ti [k] ; + j = Tj [k] ; + if (i < 0 || i >= nrow || j < 0 || j >= ncol) + { + ERROR (CHOLMOD_INVALID, "index out of range") ; + break ; + } + /* constructing an unsymmetric matrix */ + Rnz [i]++ ; + } + } + + if (Common->status < CHOLMOD_OK) + { + /* triplet matrix is invalid */ + CHOLMOD(free_sparse) (&R, Common) ; + return (NULL) ; + } + + /* ---------------------------------------------------------------------- */ + /* construct the row pointers */ + /* ---------------------------------------------------------------------- */ + + p = 0 ; + for (i = 0 ; i < nrow ; i++) + { + Rp [i] = p ; + p += Rnz [i] ; + } + Rp [nrow] = p ; + + /* use Wj (i/l/l) as temporary row pointers */ + Wj = Common->Iwork ; /* size MAX (nrow,ncol) FUTURE WORK: (i/l/l) */ + for (i = 0 ; i < nrow ; i++) + { + Wj [i] = Rp [i] ; + } + + /* ---------------------------------------------------------------------- */ + /* construct triplet matrix, using template routine */ + /* ---------------------------------------------------------------------- */ + + switch (T->xtype) + { + case CHOLMOD_PATTERN: + anz = p_cholmod_triplet_to_sparse (T, R, Common) ; + break ; + + case CHOLMOD_REAL: + anz = r_cholmod_triplet_to_sparse (T, R, Common) ; + break ; + + case CHOLMOD_COMPLEX: + anz = c_cholmod_triplet_to_sparse (T, R, Common) ; + break ; + + case CHOLMOD_ZOMPLEX: + anz = z_cholmod_triplet_to_sparse (T, R, Common) ; + break ; + } + + /* ---------------------------------------------------------------------- */ + /* A = R' (array transpose, not complex conjugate transpose) */ + /* ---------------------------------------------------------------------- */ + + /* workspace: Iwork (R->nrow), which is A->ncol */ + + ASSERT (CHOLMOD(dump_sparse) (R, "R", Common) >= 0) ; + + A = CHOLMOD(allocate_sparse) (nrow, ncol, MAX (anz, nzmax), TRUE, TRUE, + stype, T->xtype, Common) ; + + if (stype) + { + ok = CHOLMOD(transpose_sym) (R, 1, NULL, A, Common) ; + } + else + { + ok = CHOLMOD(transpose_unsym) (R, 1, NULL, NULL, 0, A, Common) ; + } + + CHOLMOD(free_sparse) (&R, Common) ; + if (Common->status < CHOLMOD_OK) + { + CHOLMOD(free_sparse) (&A, Common) ; + } + + /* ---------------------------------------------------------------------- */ + /* return result */ + /* ---------------------------------------------------------------------- */ + + ASSERT (CHOLMOD(dump_sparse) (A, "A = triplet(T) result", Common) >= 0) ; + return (A) ; +} + + +/* ========================================================================== */ +/* === cholmod_sparse_to_triplet ============================================ */ +/* ========================================================================== */ + +/* Converts a sparse column-oriented matrix to triplet form. + * The resulting triplet matrix has the same xtype as the sparse matrix. + * + * workspace: none + */ + +cholmod_triplet *CHOLMOD(sparse_to_triplet) +( + /* ---- input ---- */ + cholmod_sparse *A, /* matrix to copy */ + /* --------------- */ + cholmod_common *Common +) +{ + double *Ax, *Az, *Tx, *Tz ; + Int *Ap, *Ai, *Ti, *Tj, *Anz ; + cholmod_triplet *T ; + Int i, xtype, p, pend, k, j, nrow, ncol, nz, stype, packed, up, lo, + both ; + + /* ---------------------------------------------------------------------- */ + /* check inputs */ + /* ---------------------------------------------------------------------- */ + + RETURN_IF_NULL_COMMON (NULL) ; + RETURN_IF_NULL (A, NULL) ; + RETURN_IF_XTYPE_INVALID (A, CHOLMOD_PATTERN, CHOLMOD_ZOMPLEX, NULL) ; + stype = SIGN (A->stype) ; + nrow = A->nrow ; + ncol = A->ncol ; + if (stype && nrow != ncol) + { + /* inputs invalid */ + ERROR (CHOLMOD_INVALID, "matrix invalid") ; + return (NULL) ; + } + Ax = A->x ; + Az = A->z ; + xtype = A->xtype ; + Common->status = CHOLMOD_OK ; + + ASSERT (CHOLMOD(dump_sparse) (A, "A", Common) >= 0) ; + + /* ---------------------------------------------------------------------- */ + /* allocate triplet matrix */ + /* ---------------------------------------------------------------------- */ + + nz = CHOLMOD(nnz) (A, Common) ; + T = CHOLMOD(allocate_triplet) (nrow, ncol, nz, A->stype, A->xtype, Common) ; + + if (Common->status < CHOLMOD_OK) + { + return (NULL) ; /* out of memory */ + } + + /* ---------------------------------------------------------------------- */ + /* convert to a sparse matrix */ + /* ---------------------------------------------------------------------- */ + + Ap = A->p ; + Ai = A->i ; + Anz = A->nz ; + packed = A->packed ; + + Ti = T->i ; + Tj = T->j ; + Tx = T->x ; + Tz = T->z ; + T->stype = A->stype ; + + both = (A->stype == 0) ; + up = (A->stype > 0) ; + lo = (A->stype < 0) ; + + k = 0 ; + + for (j = 0 ; j < ncol ; j++) + { + p = Ap [j] ; + pend = (packed) ? (Ap [j+1]) : (p + Anz [j]) ; + for ( ; p < pend ; p++) + { + i = Ai [p] ; + if (both || (up && i <= j) || (lo && i >= j)) + { + Ti [k] = Ai [p] ; + Tj [k] = j ; + + if (xtype == CHOLMOD_REAL) + { + Tx [k] = Ax [p] ; + } + else if (xtype == CHOLMOD_COMPLEX) + { + Tx [2*k ] = Ax [2*p ] ; + Tx [2*k+1] = Ax [2*p+1] ; + } + else if (xtype == CHOLMOD_ZOMPLEX) + { + Tx [k] = Ax [p] ; + Tz [k] = Az [p] ; + } + + k++ ; + ASSERT (k <= nz) ; + } + } + } + + T->nnz = k ; + + /* ---------------------------------------------------------------------- */ + /* return result */ + /* ---------------------------------------------------------------------- */ + + ASSERT (CHOLMOD(dump_triplet) (T, "T", Common)) ; + return (T) ; +} + + +/* ========================================================================== */ +/* === cholmod_copy_triplet ================================================= */ +/* ========================================================================== */ + +/* Create an exact copy of a triplet matrix, except that entries in unused + * space are not copied (they might not be initialized, and copying them would + * cause program checkers such as purify and valgrind to complain). + * The output triplet matrix has the same xtype as the input triplet matrix. + */ + +cholmod_triplet *CHOLMOD(copy_triplet) +( + /* ---- input ---- */ + cholmod_triplet *T, /* matrix to copy */ + /* --------------- */ + cholmod_common *Common +) +{ + double *Tx, *Tz, *Cx, *Cz ; + Int *Ci, *Cj, *Ti, *Tj ; + cholmod_triplet *C ; + Int xtype, k, nz ; + + /* ---------------------------------------------------------------------- */ + /* check inputs */ + /* ---------------------------------------------------------------------- */ + + RETURN_IF_NULL_COMMON (NULL) ; + RETURN_IF_NULL (T, NULL) ; + RETURN_IF_XTYPE_INVALID (T, CHOLMOD_PATTERN, CHOLMOD_ZOMPLEX, NULL) ; + nz = T->nnz ; + Ti = T->i ; + Tj = T->j ; + Tx = T->x ; + Tz = T->z ; + xtype = T->xtype ; + RETURN_IF_NULL (Ti, NULL) ; + RETURN_IF_NULL (Tj, NULL) ; + Common->status = CHOLMOD_OK ; + DEBUG (CHOLMOD(dump_triplet) (T, "T input", Common)) ; + + /* ---------------------------------------------------------------------- */ + /* allocate copy */ + /* ---------------------------------------------------------------------- */ + + C = CHOLMOD(allocate_triplet) (T->nrow, T->ncol, T->nzmax, T->stype, + xtype, Common) ; + + if (Common->status < CHOLMOD_OK) + { + return (NULL) ; /* out of memory */ + } + + /* ---------------------------------------------------------------------- */ + /* copy the triplet matrix */ + /* ---------------------------------------------------------------------- */ + + Ci = C->i ; + Cj = C->j ; + Cx = C->x ; + Cz = C->z ; + C->nnz = nz ; + + for (k = 0 ; k < nz ; k++) + { + Ci [k] = Ti [k] ; + } + for (k = 0 ; k < nz ; k++) + { + Cj [k] = Tj [k] ; + } + + if (xtype == CHOLMOD_REAL) + { + for (k = 0 ; k < nz ; k++) + { + Cx [k] = Tx [k] ; + } + } + else if (xtype == CHOLMOD_COMPLEX) + { + for (k = 0 ; k < nz ; k++) + { + Cx [2*k ] = Tx [2*k ] ; + Cx [2*k+1] = Tx [2*k+1] ; + } + } + else if (xtype == CHOLMOD_ZOMPLEX) + { + for (k = 0 ; k < nz ; k++) + { + Cx [k] = Tx [k] ; + Cz [k] = Tz [k] ; + } + } + + /* ---------------------------------------------------------------------- */ + /* return the result */ + /* ---------------------------------------------------------------------- */ + + ASSERT (CHOLMOD(dump_triplet) (C, "C triplet copy", Common)) ; + return (C) ; +} diff --git a/CHOLMOD/Core/cholmod_version.c b/CHOLMOD/Core/cholmod_version.c new file mode 100644 index 0000000000..d78281dc9e --- /dev/null +++ b/CHOLMOD/Core/cholmod_version.c @@ -0,0 +1,33 @@ +//------------------------------------------------------------------------------ +// CHOLMOD/Core/cholmod_version: current version of CHOLMOD +//------------------------------------------------------------------------------ + +// CHOLMOD/Core Module. Copyright (C) 2005-2022, University of Florida. +// All Rights Reserved. Author: Timothy A. Davis +// SPDX-License-Identifier: LGPL-2.1+ +//------------------------------------------------------------------------------ + +/* Return the current version of CHOLMOD. Unlike all other functions in + CHOLMOD, this function does not require the CHOLMOD Common. */ + +#include "cholmod_internal.h" + +int CHOLMOD(version) /* returns CHOLMOD_VERSION */ +( + /* output, contents not defined on input. Not used if NULL. + version [0] = CHOLMOD_MAIN_VERSION ; + version [1] = CHOLMOD_SUB_VERSION ; + version [2] = CHOLMOD_SUBSUB_VERSION ; + */ + int version [3] +) +{ + if (version != NULL) + { + version [0] = CHOLMOD_MAIN_VERSION ; + version [1] = CHOLMOD_SUB_VERSION ; + version [2] = CHOLMOD_SUBSUB_VERSION ; + } + return (CHOLMOD_VERSION) ; +} + diff --git a/CHOLMOD/Utility/lesser.txt b/CHOLMOD/Core/lesser.txt similarity index 100% rename from CHOLMOD/Utility/lesser.txt rename to CHOLMOD/Core/lesser.txt diff --git a/CHOLMOD/Core/t_cholmod_change_factor.c b/CHOLMOD/Core/t_cholmod_change_factor.c new file mode 100644 index 0000000000..807f5ef485 --- /dev/null +++ b/CHOLMOD/Core/t_cholmod_change_factor.c @@ -0,0 +1,658 @@ +//------------------------------------------------------------------------------ +// CHOLMOD/Core/t_cholmod_change_factor: template for cholmod_change_factor +//------------------------------------------------------------------------------ + +// CHOLMOD/Core Module. Copyright (C) 2005-2022, University of Florida. +// All Rights Reserved. Author: Timothy A. Davis +// SPDX-License-Identifier: LGPL-2.1+ + +//------------------------------------------------------------------------------ + +/* Template routine for cholmod_change_factor. All xtypes supported. */ + +#include "cholmod_template.h" + +/* ========================================================================== */ +/* === t_change_simplicial_numeric ========================================== */ +/* ========================================================================== */ + +static void TEMPLATE (change_simplicial_numeric) +( + cholmod_factor *L, + Int to_ll, + Int to_packed, + Int *newLi, + double *newLx, + double *newLz, + Int lnz, + Int grow, + double grow1, + Int grow2, + Int make_ll, + Int make_monotonic, + Int make_ldl, + cholmod_common *Common +) +{ + double xlen, dj [1], ljj [1], lj2 [1] ; + double *Lx, *Lz ; + Int *Lp, *Li, *Lnz ; + Int n, j, len, pnew, pold, k, p, pend ; + + n = L->n ; + Lp = L->p ; + Li = L->i ; + Lx = L->x ; + Lz = L->z ; + Lnz = L->nz ; + + if (make_ll) + { + L->minor = n ; + } + + if (make_monotonic) + { + + /* ------------------------------------------------------------------ */ + /* reorder the columns to make them monotonic */ + /* ------------------------------------------------------------------ */ + + pnew = 0 ; + for (j = 0 ; j < n ; j++) + { + /* copy and pack column j */ + len = Lnz [j] ; + PRINT2 (("j: "ID" Lnz[j] "ID" len "ID" p "ID"\n", + j, Lnz [j], len, pnew)) ; + pold = Lp [j] ; + ASSERT (Li [pold] == j) ; + + if (make_ll) + { + + /* ---------------------------------------------------------- */ + /* copy and convert LDL' to LL' */ + /* ---------------------------------------------------------- */ + + /* dj = Lx [pold] ; */ + ASSIGN_REAL (dj,0, Lx,pold) ; + + if (IS_LE_ZERO (dj [0])) + { + /* Conversion has failed; matrix is not positive definite. + * Do not modify the column so that the LDL' factorization + * can be restored if desired, by converting back to LDL'. + * Continue the conversion, but flag the error. */ + if (L->minor == (size_t) n) + { + ERROR (CHOLMOD_NOT_POSDEF, "L not positive definite") ; + L->minor = j ; + } + for (k = 0 ; k < len ; k++) + { + newLi [pnew + k] = Li [pold + k] ; + /* newLx [pnew + k] = Lx [pold + k] ; */ + ASSIGN (newLx, newLz, pnew+k, Lx, Lz, pold+k) ; + } + } + else + { + ljj [0] = sqrt (dj [0]) ; + newLi [pnew] = j ; + /* newLx [pnew] = ljj ; */ + ASSIGN_REAL (newLx, pnew, ljj, 0) ; + CLEAR_IMAG (newLx, newLz, pnew) ; + + for (k = 1 ; k < len ; k++) + { + newLi [pnew + k] = Li [pold + k] ; + /* newLx [pnew + k] = Lx [pold + k] * ljj ; */ + MULT_REAL (newLx, newLz, pnew+k, Lx, Lz, pold+k, ljj,0); + } + } + + } + else if (make_ldl) + { + + /* ---------------------------------------------------------- */ + /* copy and convert LL' to LDL' */ + /* ---------------------------------------------------------- */ + + /* ljj = Lx [pold] ; */ + ASSIGN_REAL (ljj, 0, Lx, pold) ; + + if (ljj [0] <= 0) + { + /* matrix is not positive-definite; copy column as-is */ + for (k = 0 ; k < len ; k++) + { + newLi [pnew + k] = Li [pold + k] ; + /* newLx [pnew + k] = Lx [pold + k] ; */ + ASSIGN (newLx, newLz, pnew+k, Lx, Lz, pold+k) ; + } + } + else + { + newLi [pnew] = j ; + /* newLx [pnew] = ljj*ljj ; */ + lj2 [0] = ljj [0] * ljj [0] ; + ASSIGN_REAL (newLx, pnew, lj2, 0) ; + CLEAR_IMAG (newLx, newLz, pnew) ; + + for (k = 1 ; k < len ; k++) + { + newLi [pnew + k] = Li [pold + k] ; + /* newLx [pnew + k] = Lx [pold + k] / ljj ; */ + DIV_REAL (newLx, newLz, pnew+k, Lx, Lz, pold+k, ljj,0) ; + } + } + + } + else + { + + /* ---------------------------------------------------------- */ + /* copy and leave LL' or LDL' as-is */ + /* ---------------------------------------------------------- */ + + for (k = 0 ; k < len ; k++) + { + newLi [pnew + k] = Li [pold + k] ; + /* newLx [pnew + k] = Lx [pold + k] ; */ + ASSIGN (newLx, newLz, pnew+k, Lx, Lz, pold+k) ; + } + } + + Lp [j] = pnew ; + + /* compute len in double to avoid integer overflow */ + if (grow) + { + xlen = (double) len ; + xlen = grow1 * xlen + grow2 ; + xlen = MIN (xlen, n-j) ; + len = (Int) xlen ; + } + ASSERT (len >= Lnz [j] && len <= n-j) ; + pnew += len ; + ASSERT (pnew > 0) ; /* integer overflow case already covered */ + } + Lp [n] = pnew ; + PRINT1 (("final pnew = "ID", lnz "ID" lnzmax %g\n", + pnew, lnz, (double) L->nzmax)) ; + ASSERT (pnew <= lnz) ; + + /* free the old L->i and L->x and replace with the new ones */ + CHOLMOD(free) (L->nzmax, sizeof (Int), L->i, Common) ; + +#ifdef REAL + CHOLMOD(free) (L->nzmax, sizeof (double), L->x, Common) ; +#elif defined (COMPLEX) + CHOLMOD(free) (L->nzmax, 2*sizeof (double), L->x, Common) ; +#else + CHOLMOD(free) (L->nzmax, sizeof (double), L->x, Common) ; + CHOLMOD(free) (L->nzmax, sizeof (double), L->z, Common) ; +#endif + + L->i = newLi ; + L->x = newLx ; + L->z = newLz ; + L->nzmax = lnz ; + + /* reconstruct the link list */ + natural_list (L) ; + + } + else if (to_packed) + { + + /* ------------------------------------------------------------------ */ + /* already monotonic, just pack the columns of L */ + /* ------------------------------------------------------------------ */ + + pnew = 0 ; + + if (make_ll) + { + + /* -------------------------------------------------------------- */ + /* pack and convert LDL' to LL' */ + /* -------------------------------------------------------------- */ + + for (j = 0 ; j < n ; j++) + { + /* pack column j */ + pold = Lp [j] ; + len = Lnz [j] ; + ASSERT (len > 0) ; + ASSERT (Li [pold] == j) ; + PRINT2 (("col "ID" pnew "ID" pold "ID"\n", j, pnew, pold)) ; + + /* dj = Lx [pold] ; */ + ASSIGN_REAL (dj,0, Lx,pold) ; + + if (IS_LE_ZERO (dj [0])) + { + /* Conversion has failed; matrix is not positive definite. + * Do not modify the column so that the LDL' factorization + * can be restored if desired, by converting back to LDL'. + * Continue the conversion, but flag the error. */ + if (L->minor == (size_t) n) + { + ERROR (CHOLMOD_NOT_POSDEF, "L not positive definite") ; + L->minor = j ; + } + for (k = 0 ; k < len ; k++) + { + Li [pnew + k] = Li [pold + k] ; + /* Lx [pnew + k] = Lx [pold + k] ; */ + ASSIGN (Lx, Lz, pnew+k, Lx, Lz, pold+k) ; + } + } + else + { + ljj [0] = sqrt (dj [0]) ; + Li [pnew] = j ; + + /* Lx [pnew] = ljj ; */ + ASSIGN_REAL (Lx, pnew, ljj, 0) ; + CLEAR_IMAG (Lx, Lz, pnew) ; + + for (k = 1 ; k < len ; k++) + { + Li [pnew + k] = Li [pold + k] ; + /* Lx [pnew + k] = Lx [pold + k] * ljj ; */ + MULT_REAL (Lx, Lz, pnew+k, Lx, Lz, pold+k, ljj,0) ; + } + } + Lp [j] = pnew ; + pnew += len ; + } + + } + else if (make_ldl) + { + + /* -------------------------------------------------------------- */ + /* pack and convert LL' to LDL' */ + /* -------------------------------------------------------------- */ + + for (j = 0 ; j < n ; j++) + { + /* pack column j */ + pold = Lp [j] ; + len = Lnz [j] ; + + /* ljj = Lx [pold] ; */ + ASSIGN_REAL (ljj, 0, Lx, pold) ; + + ASSERT (len > 0) ; + PRINT2 (("col "ID" pnew "ID" pold "ID"\n", j, pnew, pold)) ; + if (ljj [0] <= 0) + { + /* matrix is not positive-definite; pack column as-is */ + for (k = 0 ; k < len ; k++) + { + Li [pnew + k] = Li [pold + k] ; + /* Lx [pnew + k] = Lx [pold + k] ; */ + ASSIGN (Lx, Lz, pnew+k, Lx, Lz, pold+k) ; + } + } + else + { + Li [pnew] = Li [pold] ; + + /* Lx [pnew] = ljj*ljj ; */ + lj2 [0] = ljj [0] * ljj [0] ; + ASSIGN_REAL (Lx, pnew, lj2, 0) ; + CLEAR_IMAG (Lx, Lz, pnew) ; + + for (k = 1 ; k < len ; k++) + { + Li [pnew + k] = Li [pold + k] ; + /* Lx [pnew + k] = Lx [pold + k] / ljj ; */ + DIV_REAL (Lx, Lz, pnew+k, Lx, Lz, pold+k, ljj,0) ; + } + } + Lp [j] = pnew ; + pnew += len ; + } + + } + else + { + + /* ---------------------------------------------------------- */ + /* pack and leave LL' or LDL' as-is */ + /* ---------------------------------------------------------- */ + + for (j = 0 ; j < n ; j++) + { + /* pack column j */ + pold = Lp [j] ; + len = Lnz [j] ; + ASSERT (len > 0) ; + PRINT2 (("col "ID" pnew "ID" pold "ID"\n", j, pnew, pold)) ; + if (pnew < pold) + { + PRINT2 ((" pack this column\n")) ; + for (k = 0 ; k < len ; k++) + { + Li [pnew + k] = Li [pold + k] ; + /* Lx [pnew + k] = Lx [pold + k] ; */ + ASSIGN (Lx, Lz, pnew+k, Lx, Lz, pold+k) ; + } + Lp [j] = pnew ; + } + pnew += len ; + } + } + + Lp [n] = pnew ; + PRINT2 (("Lp [n] = "ID"\n", pnew)) ; + + } + else if (make_ll) + { + + /* ------------------------------------------------------------------ */ + /* convert LDL' to LL', but do so in-place */ + /* ------------------------------------------------------------------ */ + + for (j = 0 ; j < n ; j++) + { + p = Lp [j] ; + pend = p + Lnz [j] ; + + /* dj = Lx [p] ; */ + ASSIGN_REAL (dj,0, Lx,p) ; + + if (IS_LE_ZERO (dj [0])) + { + /* Conversion has failed; matrix is not positive definite. + * Do not modify the column so that the LDL' factorization + * can be restored if desired, by converting back to LDL'. + * Continue the conversion, but flag the error. */ + if (L->minor == (size_t) n) + { + ERROR (CHOLMOD_NOT_POSDEF, "L not positive definite") ; + L->minor = j ; + } + } + else + { + ljj [0] = sqrt (dj [0]) ; + /* Lx [p] = ljj ; */ + ASSIGN_REAL (Lx,p, ljj,0) ; + CLEAR_IMAG (Lx, Lz, p) ; + + for (p++ ; p < pend ; p++) + { + /* Lx [p] *= ljj ; */ + MULT_REAL (Lx,Lz,p, Lx,Lz,p, ljj,0) ; + } + } + } + + } + else if (make_ldl) + { + + /* ------------------------------------------------------------------ */ + /* convert LL' to LDL', but do so in-place */ + /* ------------------------------------------------------------------ */ + + for (j = 0 ; j < n ; j++) + { + p = Lp [j] ; + pend = p + Lnz [j] ; + + /* ljj = Lx [p] ; */ + ASSIGN_REAL (ljj, 0, Lx, p) ; + + if (ljj [0] > 0) + { + /* Lx [p] = ljj*ljj ; */ + lj2 [0] = ljj [0] * ljj [0] ; + ASSIGN_REAL (Lx, p, lj2, 0) ; + CLEAR_IMAG (Lx, Lz, p) ; + + for (p++ ; p < pend ; p++) + { + /* Lx [p] /= ljj ; */ + DIV_REAL (Lx,Lz,p, Lx,Lz,p, ljj,0) ; + } + } + } + } + + L->is_ll = to_ll ; + + DEBUG (CHOLMOD(dump_factor) (L, "done change simplicial numeric", Common)) ; +} + + +/* ========================================================================== */ +/* === t_ll_super_to_simplicial_numeric ===================================== */ +/* ========================================================================== */ + +/* A supernodal L can only be real or complex, not zomplex */ + +#ifndef ZOMPLEX + +static void TEMPLATE (ll_super_to_simplicial_numeric) +( + cholmod_factor *L, + Int to_packed, + Int to_ll, + cholmod_common *Common +) +{ + double ljj [1], lj2 [1] ; + double *Lx ; + Int *Ls, *Lpi, *Lpx, *Super, *Lp, *Li, *Lnz ; + Int n, lnz, s, nsuper, p, psi, psx, psend, nsrow, nscol, ii, jj, j, k1, k2, + q ; + + L->is_ll = to_ll ; + + Lp = L->p ; + Li = L->i ; + Lx = L->x ; + Lnz = L->nz ; + lnz = L->nzmax ; + + n = L->n ; + nsuper = L->nsuper ; + Lpi = L->pi ; + Lpx = L->px ; + Ls = L->s ; + Super = L->super ; + + p = 0 ; + + for (s = 0 ; s < nsuper ; s++) + { + k1 = Super [s] ; + k2 = Super [s+1] ; + psi = Lpi [s] ; + psend = Lpi [s+1] ; + psx = Lpx [s] ; + nsrow = psend - psi ; + nscol = k2 - k1 ; + + for (jj = 0 ; jj < nscol ; jj++) + { + /* column j of L starts here */ + j = jj + k1 ; + + if (to_ll) + { + if (to_packed) + { + + /* ------------------------------------------------------ */ + /* convert to LL' packed */ + /* ------------------------------------------------------ */ + + Lp [j] = p ; + PRINT2 (("Col j "ID" p "ID"\n", j, p)) ; + for (ii = jj ; ii < nsrow ; ii++) + { + /* get L(i,j) from supernode and store in column j */ + ASSERT (p < (Int) (L->xsize) && p <= psx+ii+jj*nsrow) ; + Li [p] = Ls [psi + ii] ; + /* Lx [p] = Lx [psx + ii + jj*nsrow] ; */ + q = psx + ii + jj*nsrow ; + ASSIGN (Lx,-,p, Lx,-,q) ; + PRINT2 ((" i "ID" ", Li [p])) ; + XPRINT2 (Lx,-,q) ; + PRINT2 (("\n")) ; + p++ ; + } + Lnz [j] = p - Lp [j] ; + + } + else + { + + /* ------------------------------------------------------ */ + /* convert to LL' unpacked */ + /* ------------------------------------------------------ */ + + p = psx + jj + jj*nsrow ; + Lp [j] = p ; + Li [p] = j ; + Lnz [j] = nsrow - jj ; + p++ ; + for (ii = jj + 1 ; ii < nsrow ; ii++) + { + /* get L(i,j) from supernode and store in column j */ + Li [psx + ii + jj*nsrow] = Ls [psi + ii] ; + } + + } + } + else + { + if (to_packed) + { + + /* ------------------------------------------------------ */ + /* convert to LDL' packed */ + /* ------------------------------------------------------ */ + + Lp [j] = p ; + PRINT2 (("Col j "ID" p "ID"\n", Lp [j], p)) ; + /* ljj = Lx [psx + jj + jj*nsrow] ; */ + ASSIGN_REAL (ljj, 0, Lx, psx + jj + jj*nsrow) ; + + if (ljj [0] <= 0) + { + /* the matrix is not positive definite; do not divide */ + /* Lx [p] = ljj ; */ + ASSIGN_REAL (Lx, p, ljj, 0) ; + CLEAR_IMAG (Lx, Lz, p) ; + ljj [0] = 1 ; + } + else + { + lj2 [0] = ljj [0] * ljj [0] ; + /* Lx [p] = ljj*ljj ; */ + ASSIGN_REAL (Lx, p, lj2, 0) ; + CLEAR_IMAG (Lx, Lz, p) ; + } + Li [p] = j ; + p++ ; + for (ii = jj + 1 ; ii < nsrow ; ii++) + { + /* get L(i,j) from supernode and store in column j */ + ASSERT (p < (Int) (L->xsize) && p <= psx+ii+jj*nsrow) ; + Li [p] = Ls [psi + ii] ; + + /* Lx [p] = Lx [psx + ii + jj*nsrow] / ljj ; */ + q = psx + ii + jj*nsrow ; + DIV_REAL (Lx, Lz, p, Lx, Lz, q, ljj,0) ; + + PRINT2 ((" i "ID" %g\n", Li [p], Lx [p])) ; + p++ ; + } + Lnz [j] = p - Lp [j] ; + + } + else + { + + /* ------------------------------------------------------ */ + /* convert to LDL' unpacked */ + /* ------------------------------------------------------ */ + + p = psx + jj + jj*nsrow ; + Lp [j] = p ; + + /* ljj = Lx [p] ; */ + ASSIGN_REAL (ljj,0, Lx,p) ; + + if (ljj [0] <= 0) + { + /* the matrix is not positive definite; do not divide */ + /* Lx [p] = ljj ; */ + ASSIGN_REAL (Lx, p, ljj, 0) ; + CLEAR_IMAG (Lx, Lz, p) ; + ljj [0] = 1 ; + } + else + { + lj2 [0] = ljj [0] * ljj [0] ; + /* Lx [p] = ljj*ljj ; */ + ASSIGN_REAL (Lx, p, lj2, 0) ; + CLEAR_IMAG (Lx, Lz, p) ; + } + Li [p] = j ; + Lnz [j] = nsrow - jj ; + p++ ; + for (ii = jj + 1 ; ii < nsrow ; ii++) + { + /* get L(i,j) from supernode and store in column j */ + Li [psx + ii + jj*nsrow] = Ls [psi + ii] ; + + /* Lx [psx + ii + jj*nsrow] /= ljj ; */ + q = psx + ii + jj*nsrow ; + DIV_REAL (Lx, Lz, q, Lx, Lz, q, ljj,0) ; + } + } + } + } + } + + if (to_packed) + { + Lp [n] = p ; + PRINT1 (("Final Lp "ID" n "ID" lnz "ID"\n", p, n, lnz)) ; + ASSERT (Lp [n] == lnz) ; + ASSERT (lnz <= (Int) (L->xsize)) ; + /* reduce size of L->x to match L->i. This cannot fail. */ + L->x = CHOLMOD(realloc) (lnz, +#ifdef COMPLEX + 2 * +#endif + sizeof (double), L->x, &(L->xsize), Common) ; + ASSERT (lnz == (Int) (L->xsize)) ; + Common->status = CHOLMOD_OK ; + } + else + { + Lp [n] = Lpx [nsuper] ; + ASSERT (MAX (1,Lp [n]) == (Int) (L->xsize)) ; + ASSERT (MAX (1,Lp [n]) == (Int) (L->nzmax)) ; + } +} + +#endif + +#undef PATTERN +#undef REAL +#undef COMPLEX +#undef ZOMPLEX diff --git a/CHOLMOD/Core/t_cholmod_dense.c b/CHOLMOD/Core/t_cholmod_dense.c new file mode 100644 index 0000000000..121098b109 --- /dev/null +++ b/CHOLMOD/Core/t_cholmod_dense.c @@ -0,0 +1,263 @@ +//------------------------------------------------------------------------------ +// CHOLMOD/Core/t_cholmod_dense: template for cholmod_dense +//------------------------------------------------------------------------------ + +// CHOLMOD/Core Module. Copyright (C) 2005-2022, University of Florida. +// All Rights Reserved. Author: Timothy A. Davis +// SPDX-License-Identifier: LGPL-2.1+ + +//------------------------------------------------------------------------------ + +/* Template routine for cholmod_dense. All xtypes supported, except that there + * are no dense matrices with an xtype of pattern. */ + +#include "cholmod_template.h" + +/* ========================================================================== */ +/* === t_cholmod_sparse_to_dense ============================================ */ +/* ========================================================================== */ + +static cholmod_dense *TEMPLATE (cholmod_sparse_to_dense) +( + /* ---- input ---- */ + cholmod_sparse *A, /* matrix to copy */ + /* --------------- */ + cholmod_common *Common +) +{ + double *Ax, *Xx, *Az, *Xz ; + Int *Ap, *Ai, *Anz ; + cholmod_dense *X ; + Int i, j, p, pend, nrow, ncol, packed ; + + /* ---------------------------------------------------------------------- */ + /* get inputs */ + /* ---------------------------------------------------------------------- */ + + nrow = A->nrow ; + ncol = A->ncol ; + packed = A->packed ; + Ap = A->p ; + Ai = A->i ; + Ax = A->x ; + Az = A->z ; + Anz = A->nz ; + + /* ---------------------------------------------------------------------- */ + /* allocate result */ + /* ---------------------------------------------------------------------- */ + + X = CHOLMOD(zeros) (nrow, ncol, XTYPE2, Common) ; + if (Common->status < CHOLMOD_OK) + { + return (NULL) ; /* out of memory */ + } + Xx = X->x ; + Xz = X->z ; + + /* ---------------------------------------------------------------------- */ + /* copy into dense matrix */ + /* ---------------------------------------------------------------------- */ + + if (A->stype < 0) + { + /* A is symmetric with lower stored, but both parts of X are present */ + for (j = 0 ; j < ncol ; j++) + { + p = Ap [j] ; + pend = (packed) ? (Ap [j+1]) : (p + Anz [j]) ; + for ( ; p < pend ; p++) + { + i = Ai [p] ; + if (i >= j) + { + ASSIGN2 (Xx, Xz, i+j*nrow, Ax, Az, p) ; + ASSIGN2_CONJ (Xx, Xz, j+i*nrow, Ax, Az, p) ; + } + } + } + } + else if (A->stype > 0) + { + /* A is symmetric with upper stored, but both parts of X are present */ + for (j = 0 ; j < ncol ; j++) + { + p = Ap [j] ; + pend = (packed) ? (Ap [j+1]) : (p + Anz [j]) ; + for ( ; p < pend ; p++) + { + i = Ai [p] ; + if (i <= j) + { + ASSIGN2 (Xx, Xz, i+j*nrow, Ax, Az, p) ; + ASSIGN2_CONJ (Xx, Xz, j+i*nrow, Ax, Az, p) ; + } + } + } + } + else + { + /* both parts of A and X are present */ + for (j = 0 ; j < ncol ; j++) + { + p = Ap [j] ; + pend = (packed) ? (Ap [j+1]) : (p + Anz [j]) ; + for ( ; p < pend ; p++) + { + i = Ai [p] ; + ASSIGN2 (Xx, Xz, i+j*nrow, Ax, Az, p) ; + } + } + } + + return (X) ; +} + + +#ifndef PATTERN + +/* There are no dense matrices of xtype CHOLMOD_PATTERN */ + +/* ========================================================================== */ +/* === t_cholmod_dense_to_sparse ============================================ */ +/* ========================================================================== */ + +static cholmod_sparse *TEMPLATE (cholmod_dense_to_sparse) +( + /* ---- input ---- */ + cholmod_dense *X, /* matrix to copy */ + int values, /* TRUE if values to be copied, FALSE otherwise */ + /* --------------- */ + cholmod_common *Common +) +{ + double *Xx, *Cx, *Xz, *Cz ; + Int *Ci, *Cp ; + cholmod_sparse *C ; + Int i, j, p, d, nrow, ncol, nz ; + + /* ---------------------------------------------------------------------- */ + /* get inputs */ + /* ---------------------------------------------------------------------- */ + + nrow = X->nrow ; + ncol = X->ncol ; + d = X->d ; + Xx = X->x ; + Xz = X->z ; + + /* ---------------------------------------------------------------------- */ + /* count the number of nonzeros in the result */ + /* ---------------------------------------------------------------------- */ + + nz = 0 ; + for (j = 0 ; j < ncol ; j++) + { + for (i = 0 ; i < nrow ; i++) + { + if (ENTRY_IS_NONZERO (Xx, Xz, i+j*d)) + { + nz++ ; + } + } + } + + /* ---------------------------------------------------------------------- */ + /* allocate the result C */ + /* ---------------------------------------------------------------------- */ + + C = CHOLMOD(allocate_sparse) (nrow, ncol, nz, TRUE, TRUE, 0, + values ? XTYPE : CHOLMOD_PATTERN, Common) ; + if (Common->status < CHOLMOD_OK) + { + return (NULL) ; /* out of memory */ + } + Cp = C->p ; + Ci = C->i ; + Cx = C->x ; + Cz = C->z ; + + /* ---------------------------------------------------------------------- */ + /* copy the dense matrix X into the sparse matrix C */ + /* ---------------------------------------------------------------------- */ + + p = 0 ; + for (j = 0 ; j < ncol ; j++) + { + Cp [j] = p ; + for (i = 0 ; i < nrow ; i++) + { + if (ENTRY_IS_NONZERO (Xx, Xz, i+j*d)) + { + Ci [p] = i ; + if (values) + { + ASSIGN (Cx, Cz, p, Xx, Xz, i+j*d) ; + } + p++ ; + } + } + } + ASSERT (p == nz) ; + Cp [ncol] = nz ; + + /* ---------------------------------------------------------------------- */ + /* return result */ + /* ---------------------------------------------------------------------- */ + + ASSERT (CHOLMOD(dump_sparse) (C, "C", Common) >= 0) ; + return (C) ; +} + + +/* ========================================================================== */ +/* === t_cholmod_copy_dense2 ================================================ */ +/* ========================================================================== */ + +/* Y = X, where X and Y are both already allocated. */ + +static int TEMPLATE (cholmod_copy_dense2) +( + /* ---- input ---- */ + cholmod_dense *X, /* matrix to copy */ + /* ---- output --- */ + cholmod_dense *Y /* copy of matrix X */ +) +{ + double *Xx, *Xz, *Yx, *Yz ; + Int i, j, nrow, ncol, dy, dx ; + + /* ---------------------------------------------------------------------- */ + /* get inputs */ + /* ---------------------------------------------------------------------- */ + + Xx = X->x ; + Xz = X->z ; + Yx = Y->x ; + Yz = Y->z ; + dx = X->d ; + dy = Y->d ; + nrow = X->nrow ; + ncol = X->ncol ; + + /* ---------------------------------------------------------------------- */ + /* copy */ + /* ---------------------------------------------------------------------- */ + + CLEAR (Yx, Yz, 0) ; + for (j = 0 ; j < ncol ; j++) + { + for (i = 0 ; i < nrow ; i++) + { + ASSIGN (Yx, Yz, i+j*dy, Xx, Xz, i+j*dx) ; + } + } + return (TRUE) ; +} + +#endif + +#undef PATTERN +#undef REAL +#undef COMPLEX +#undef ZOMPLEX diff --git a/CHOLMOD/Core/t_cholmod_transpose.c b/CHOLMOD/Core/t_cholmod_transpose.c new file mode 100644 index 0000000000..9b91e16fc3 --- /dev/null +++ b/CHOLMOD/Core/t_cholmod_transpose.c @@ -0,0 +1,315 @@ +//------------------------------------------------------------------------------ +// CHOLMOD/Core/t_cholmod_tranpose: template for cholmod_transpose +//------------------------------------------------------------------------------ + +// CHOLMOD/Core Module. Copyright (C) 2005-2022, University of Florida. +// All Rights Reserved. Author: Timothy A. Davis +// SPDX-License-Identifier: LGPL-2.1+ + +//------------------------------------------------------------------------------ + +/* Template routine for cholmod_transpose. All xtypes are supported. For + * complex matrices, either the array tranpose or complex conjugate transpose + * can be computed. */ + +#include "cholmod_template.h" + +/* ========================================================================== */ +/* === t_cholmod_transpose_unsym ============================================ */ +/* ========================================================================== */ + +/* Compute F = A', A (:,f)', or A (p,f)', where A is unsymmetric and F is + * already allocated. The complex case performs either the array transpose + * or complex conjugate transpose. + * + * workspace: + * Iwork (MAX (nrow,ncol)) if fset is present + * Iwork (nrow) if fset is NULL + */ + +static int TEMPLATE (cholmod_transpose_unsym) +( + /* ---- input ---- */ + cholmod_sparse *A, /* matrix to transpose */ + Int *Perm, /* size nrow, if present (can be NULL) */ + Int *fset, /* subset of 0:(A->ncol)-1 */ + Int nf, /* size of fset */ + /* ---- output --- */ + cholmod_sparse *F, /* F = A', A(:,f)', or A(p,f)' */ + /* --------------- */ + cholmod_common *Common +) +{ + double *Ax, *Az, *Fx, *Fz ; + Int *Ap, *Anz, *Ai, *Fp, *Fnz, *Fj, *Wi, *Iwork ; + Int j, p, pend, nrow, ncol, Apacked, use_fset, fp, Fpacked, jj, permute ; + + /* ---------------------------------------------------------------------- */ + /* check inputs */ + /* ---------------------------------------------------------------------- */ + + /* ensure the xtype of A and F match (ignored if this is pattern version) */ + if (!XTYPE_OK (A->xtype)) + { + ERROR (CHOLMOD_INVALID, "real/complex mismatch") ; + return (FALSE) ; + } + + /* ---------------------------------------------------------------------- */ + /* get inputs */ + /* ---------------------------------------------------------------------- */ + + use_fset = (fset != NULL) ; + nrow = A->nrow ; + ncol = A->ncol ; + + Ap = A->p ; /* size A->ncol+1, column pointers of A */ + Ai = A->i ; /* size nz = Ap [A->ncol], row indices of A */ + Ax = A->x ; /* size nz, real values of A */ + Az = A->z ; /* size nz, imag values of A */ + Anz = A->nz ; + Apacked = A->packed ; + ASSERT (IMPLIES (!Apacked, Anz != NULL)) ; + + permute = (Perm != NULL) ; + + Fp = F->p ; /* size A->nrow+1, row pointers of F */ + Fj = F->i ; /* size nz, column indices of F */ + Fx = F->x ; /* size nz, real values of F */ + Fz = F->z ; /* size nz, imag values of F */ + Fnz = F->nz ; + Fpacked = F->packed ; + ASSERT (IMPLIES (!Fpacked, Fnz != NULL)) ; + + nf = (use_fset) ? nf : ncol ; + + /* ---------------------------------------------------------------------- */ + /* get workspace */ + /* ---------------------------------------------------------------------- */ + + Iwork = Common->Iwork ; + Wi = Iwork ; /* size nrow (i/l/l) */ + + /* ---------------------------------------------------------------------- */ + /* construct the transpose */ + /* ---------------------------------------------------------------------- */ + + for (jj = 0 ; jj < nf ; jj++) + { + j = (use_fset) ? (fset [jj]) : jj ; + p = Ap [j] ; + pend = (Apacked) ? (Ap [j+1]) : (p + Anz [j]) ; + for ( ; p < pend ; p++) + { + fp = Wi [Ai [p]]++ ; + Fj [fp] = j ; +#ifdef NCONJUGATE + ASSIGN (Fx, Fz, fp, Ax, Az, p) ; +#else + ASSIGN_CONJ (Fx, Fz, fp, Ax, Az, p) ; +#endif + } + } + + return (TRUE) ; +} + + +/* ========================================================================== */ +/* === t_cholmod_transpose_sym ============================================== */ +/* ========================================================================== */ + +/* Compute F = A' or A (p,p)', where A is symmetric and F is already allocated. + * The complex case performs either the array transpose or complex conjugate + * transpose. + * + * workspace: Iwork (nrow) if Perm NULL, Iwork (2*nrow) if Perm non-NULL. + */ + +static int TEMPLATE (cholmod_transpose_sym) +( + /* ---- input ---- */ + cholmod_sparse *A, /* matrix to transpose */ + Int *Perm, /* size n, if present (can be NULL) */ + /* ---- output --- */ + cholmod_sparse *F, /* F = A' or A(p,p)' */ + /* --------------- */ + cholmod_common *Common +) +{ + double *Ax, *Az, *Fx, *Fz ; + Int *Ap, *Anz, *Ai, *Fp, *Fj, *Wi, *Pinv, *Iwork ; + Int p, pend, packed, fp, upper, permute, jold, n, i, j, iold ; + + /* ---------------------------------------------------------------------- */ + /* check inputs */ + /* ---------------------------------------------------------------------- */ + + /* ensure the xtype of A and F match (ignored if this is pattern version) */ + if (!XTYPE_OK (A->xtype)) + { + ERROR (CHOLMOD_INVALID, "real/complex mismatch") ; + return (FALSE) ; + } + + /* ---------------------------------------------------------------------- */ + /* get inputs */ + /* ---------------------------------------------------------------------- */ + + permute = (Perm != NULL) ; + n = A->nrow ; + Ap = A->p ; /* size A->ncol+1, column pointers of A */ + Ai = A->i ; /* size nz = Ap [A->ncol], row indices of A */ + Ax = A->x ; /* size nz, real values of A */ + Az = A->z ; /* size nz, imag values of A */ + Anz = A->nz ; + packed = A->packed ; + ASSERT (IMPLIES (!packed, Anz != NULL)) ; + upper = (A->stype > 0) ; + + Fp = F->p ; /* size A->nrow+1, row pointers of F */ + Fj = F->i ; /* size nz, column indices of F */ + Fx = F->x ; /* size nz, real values of F */ + Fz = F->z ; /* size nz, imag values of F */ + + /* ---------------------------------------------------------------------- */ + /* get workspace */ + /* ---------------------------------------------------------------------- */ + + Iwork = Common->Iwork ; + Wi = Iwork ; /* size n (i/l/l) */ + Pinv = Iwork + n ; /* size n (i/i/l) , unused if Perm NULL */ + + /* ---------------------------------------------------------------------- */ + /* construct the transpose */ + /* ---------------------------------------------------------------------- */ + + if (permute) + { + if (upper) + { + /* permuted, upper */ + for (j = 0 ; j < n ; j++) + { + jold = Perm [j] ; + p = Ap [jold] ; + pend = (packed) ? Ap [jold+1] : p + Anz [jold] ; + for ( ; p < pend ; p++) + { + iold = Ai [p] ; + if (iold <= jold) + { + i = Pinv [iold] ; + if (i < j) + { + fp = Wi [i]++ ; + Fj [fp] = j ; +#ifdef NCONJUGATE + ASSIGN (Fx, Fz, fp, Ax, Az, p) ; +#else + ASSIGN_CONJ (Fx, Fz, fp, Ax, Az, p) ; +#endif + } + else + { + fp = Wi [j]++ ; + Fj [fp] = i ; + ASSIGN (Fx, Fz, fp, Ax, Az, p) ; + } + } + } + } + } + else + { + /* permuted, lower */ + for (j = 0 ; j < n ; j++) + { + jold = Perm [j] ; + p = Ap [jold] ; + pend = (packed) ? Ap [jold+1] : p + Anz [jold] ; + for ( ; p < pend ; p++) + { + iold = Ai [p] ; + if (iold >= jold) + { + i = Pinv [iold] ; + if (i > j) + { + fp = Wi [i]++ ; + Fj [fp] = j ; +#ifdef NCONJUGATE + ASSIGN (Fx, Fz, fp, Ax, Az, p) ; +#else + ASSIGN_CONJ (Fx, Fz, fp, Ax, Az, p) ; +#endif + } + else + { + fp = Wi [j]++ ; + Fj [fp] = i ; + ASSIGN (Fx, Fz, fp, Ax, Az, p) ; + } + } + } + } + } + } + else + { + if (upper) + { + /* unpermuted, upper */ + for (j = 0 ; j < n ; j++) + { + p = Ap [j] ; + pend = (packed) ? Ap [j+1] : p + Anz [j] ; + for ( ; p < pend ; p++) + { + i = Ai [p] ; + if (i <= j) + { + fp = Wi [i]++ ; + Fj [fp] = j ; +#ifdef NCONJUGATE + ASSIGN (Fx, Fz, fp, Ax, Az, p) ; +#else + ASSIGN_CONJ (Fx, Fz, fp, Ax, Az, p) ; +#endif + } + } + } + } + else + { + /* unpermuted, lower */ + for (j = 0 ; j < n ; j++) + { + p = Ap [j] ; + pend = (packed) ? Ap [j+1] : p + Anz [j] ; + for ( ; p < pend ; p++) + { + i = Ai [p] ; + if (i >= j) + { + fp = Wi [i]++ ; + Fj [fp] = j ; +#ifdef NCONJUGATE + ASSIGN (Fx, Fz, fp, Ax, Az, p) ; +#else + ASSIGN_CONJ (Fx, Fz, fp, Ax, Az, p) ; +#endif + } + } + } + } + } + + return (TRUE) ; +} + +#undef PATTERN +#undef REAL +#undef COMPLEX +#undef ZOMPLEX +#undef NCONJUGATE diff --git a/CHOLMOD/Core/t_cholmod_triplet.c b/CHOLMOD/Core/t_cholmod_triplet.c new file mode 100644 index 0000000000..f342058fba --- /dev/null +++ b/CHOLMOD/Core/t_cholmod_triplet.c @@ -0,0 +1,173 @@ +//------------------------------------------------------------------------------ +// CHOLMOD/Core/t_cholmod_triplet: template for cholmod_triplet +//------------------------------------------------------------------------------ + +// CHOLMOD/Core Module. Copyright (C) 2005-2022, University of Florida. +// All Rights Reserved. Author: Timothy A. Davis +// SPDX-License-Identifier: LGPL-2.1+ + +//------------------------------------------------------------------------------ + +/* Template routine for cholmod_triplet. All xtypes supported */ + +#include "cholmod_template.h" + +/* ========================================================================== */ +/* === t_cholmod_triplet_to_sparse ========================================== */ +/* ========================================================================== */ + +static size_t TEMPLATE (cholmod_triplet_to_sparse) +( + /* ---- input ---- */ + cholmod_triplet *T, /* matrix to copy */ + /* ---- in/out --- */ + cholmod_sparse *R, /* output matrix */ + /* --------------- */ + cholmod_common *Common +) +{ + double *Rx, *Rz, *Tx, *Tz ; + Int *Wj, *Rp, *Ri, *Rnz, *Ti, *Tj ; + Int i, j, p, p1, p2, pdest, pj, k, stype, nrow, ncol, nz ; + size_t anz ; + + /* ---------------------------------------------------------------------- */ + /* get inputs */ + /* ---------------------------------------------------------------------- */ + + /* Wj contains a copy of Rp on input [ */ + Wj = Common->Iwork ; /* size MAX (nrow,ncol). (i/l/l) */ + + Rp = R->p ; + Ri = R->i ; + Rnz = R->nz ; + Rx = R->x ; + Rz = R->z ; + + Ti = T->i ; + Tj = T->j ; + Tx = T->x ; + Tz = T->z ; + nz = T->nnz ; + nrow = T->nrow ; + ncol = T->ncol ; + stype = SIGN (T->stype) ; + + /* ---------------------------------------------------------------------- */ + /* construct the row form */ + /* ---------------------------------------------------------------------- */ + + /* if Ti is jumbled, this part dominates the run time */ + + if (stype > 0) + { + for (k = 0 ; k < nz ; k++) + { + i = Ti [k] ; + j = Tj [k] ; + if (i < j) + { + /* place triplet (j,i,x) in column i of R */ + p = Wj [i]++ ; + Ri [p] = j ; + } + else + { + /* place triplet (i,j,x) in column j of R */ + p = Wj [j]++ ; + Ri [p] = i ; + } + ASSIGN (Rx, Rz, p, Tx, Tz, k) ; + } + } + else if (stype < 0) + { + for (k = 0 ; k < nz ; k++) + { + i = Ti [k] ; + j = Tj [k] ; + if (i > j) + { + /* place triplet (j,i,x) in column i of R */ + p = Wj [i]++ ; + Ri [p] = j ; + } + else + { + /* place triplet (i,j,x) in column j of R */ + p = Wj [j]++ ; + Ri [p] = i ; + } + ASSIGN (Rx, Rz, p, Tx, Tz, k) ; + } + } + else + { + for (k = 0 ; k < nz ; k++) + { + /* place triplet (i,j,x) in column i of R */ + p = Wj [Ti [k]]++ ; + Ri [p] = Tj [k] ; + ASSIGN (Rx, Rz, p, Tx, Tz, k) ; + } + } + + /* done using Wj (i/l/l) as temporary row pointers ] */ + + /* ---------------------------------------------------------------------- */ + /* sum up duplicates */ + /* ---------------------------------------------------------------------- */ + + /* use Wj (i/l/l) of size ncol to keep track of duplicates in each row [ */ + for (j = 0 ; j < ncol ; j++) + { + Wj [j] = EMPTY ; + } + + anz = 0 ; + for (i = 0 ; i < nrow ; i++) + { + p1 = Rp [i] ; + p2 = Rp [i+1] ; + pdest = p1 ; + /* at this point Wj [j] < p1 holds true for all columns j, because + * Ri/Rx is stored in row oriented manner */ + for (p = p1 ; p < p2 ; p++) + { + j = Ri [p] ; + pj = Wj [j] ; + if (pj >= p1) + { + /* this column index j is already in row i at position pj; + * sum up the duplicate entry */ + /* Rx [pj] += Rx [p] ; */ + ASSEMBLE (Rx, Rz, pj, Rx, Rz, p) ; + } + else + { + /* keep the entry and keep track in Wj [j] for case above */ + Wj [j] = pdest ; + if (pdest != p) + { + Ri [pdest] = j ; + ASSIGN (Rx, Rz, pdest, Rx, Rz, p) ; + } + pdest++ ; + } + } + Rnz [i] = pdest - p1 ; + anz += (pdest - p1) ; + } + /* done using Wj to keep track of duplicate entries in each row ] */ + + /* ---------------------------------------------------------------------- */ + /* return number of entries after summing up duplicates */ + /* ---------------------------------------------------------------------- */ + + return (anz) ; +} + +#undef PATTERN +#undef REAL +#undef COMPLEX +#undef ZOMPLEX diff --git a/CHOLMOD/Demo/cholmod_demo.c b/CHOLMOD/Demo/cholmod_demo.c index ad5dc8c649..9aad7c1377 100644 --- a/CHOLMOD/Demo/cholmod_demo.c +++ b/CHOLMOD/Demo/cholmod_demo.c @@ -23,7 +23,7 @@ * The matrix is assumed to be positive definite (a supernodal LL' or simplicial * LDL' factorization is used). * - * Requires the Utility, Cholesky, MatrixOps, and Check Modules. + * Requires the Core, Cholesky, MatrixOps, and Check Modules. * Optionally uses the Partition and Supernodal Modules. * Does not use the Modify Module. * diff --git a/CHOLMOD/Demo/cholmod_l_demo.c b/CHOLMOD/Demo/cholmod_l_demo.c index 40dd31ddeb..71fb43e6ab 100644 --- a/CHOLMOD/Demo/cholmod_l_demo.c +++ b/CHOLMOD/Demo/cholmod_l_demo.c @@ -23,7 +23,7 @@ * The matrix is assumed to be positive definite (a supernodal LL' or simplicial * LDL' factorization is used). * - * Requires the Utility, Cholesky, MatrixOps, and Check Modules. + * Requires the Core, Cholesky, MatrixOps, and Check Modules. * Optionally uses the Partition and Supernodal Modules. * Does not use the Modify Module. * diff --git a/CHOLMOD/Doc/CHOLMOD_UserGuide.pdf b/CHOLMOD/Doc/CHOLMOD_UserGuide.pdf index 766e961e38..911dff297f 100644 Binary files a/CHOLMOD/Doc/CHOLMOD_UserGuide.pdf and b/CHOLMOD/Doc/CHOLMOD_UserGuide.pdf differ diff --git a/CHOLMOD/Doc/CHOLMOD_UserGuide.tex b/CHOLMOD/Doc/CHOLMOD_UserGuide.tex index cfa6e876f6..184396fb6e 100644 --- a/CHOLMOD/Doc/CHOLMOD_UserGuide.tex +++ b/CHOLMOD/Doc/CHOLMOD_UserGuide.tex @@ -50,7 +50,7 @@ CHOLMOD Copyright\copyright 2005-2023 by Timothy A. Davis, All Rights Reserved. Portions are also copyrighted by William W. Hager (the {\tt Modify} Module), -and the University of Florida (the {\tt Partition} Module). +and the University of Florida (the {\tt Partition} and {\tt Core} Modules). All Rights Reserved. See CHOLMOD/Doc/License.txt for the license. @@ -92,14 +92,14 @@ that can factorize symmetric indefinite matrices if all of their leading submatrices are well-conditioned ($\m{D}$ is diagonal). -A pair of articles on CHOLMOD appears in the ACM Transactions +A pair of articles on CHOLMOD has been submitted to the ACM Transactions on Mathematical Software: \cite{ChenDavisHagerRajamanickam06,DavisHager06}. -CHOLMOD 1.0 replaces {\tt chol} (the sparse case), {\tt symbfact}, and {\tt -etree} in MATLAB 7.2 (R2006a), and is used for {\tt x=A}$\backslash${\tt b} -when {\tt A} is symmetric positive definite \cite{GilbertMolerSchreiber}. It -will replace {\tt sparse} in a future version of MATLAB. +CHOLMOD 1.0 replaces {\tt chol} (the sparse case), {\tt symbfact}, and {\tt etree} +in MATLAB 7.2 (R2006a), and is used for {\tt x=A}$\backslash${\tt b} +when {\tt A} is symmetric positive definite \cite{GilbertMolerSchreiber}. +It will replace {\tt sparse} in a future version of MATLAB. The C-callable CHOLMOD library consists of 133 user-callable routines and one include file. Each routine comes in two versions, one for {\tt int} integers @@ -110,18 +110,6 @@ performance, comparing it with nearly a dozen or so other solvers \cite{GouldHuScott05,GouldHuScott05b}. Its performance was quite competitive. -%------------------------------------------------------------------------------- -\newpage \section{Single-precision sparse matrix support} -%------------------------------------------------------------------------------- - -{\bf CHOLMOD v5.0.0}: introduces the first part of support for single - precision sparse matrices, with the introduction of the new - CHOLMOD:Utility Module. The CHOLMOD:Utility Module replaces the - CHOLMOD:Core Module that appeared in prior versions of CHOLMOD. - Single precision is not yet incorporated into the remaining Modules, - however. This feature will be implemented soon in a later version - of CHOLMOD. - %------------------------------------------------------------------------------- \newpage \section{Primary routines and data structures} %------------------------------------------------------------------------------- @@ -720,7 +708,7 @@ \subsection{Adjustable parameters} \vspace{0.1in} \noindent There are seven Modules that provide user-callable routines for CHOLMOD. \begin{enumerate} - \item {\tt Utility}: basic data structures and definitions + \item {\tt Core}: basic data structures and definitions \item {\tt Check}: prints/checks each of CHOLMOD's objects \item {\tt Cholesky}: sparse Cholesky factorization \item {\tt Modify}: sparse Cholesky update/downdate and row-add/row-delete @@ -739,6 +727,7 @@ \subsection{Adjustable parameters} \item {\tt Doc}: documentation (including this document) \item {\tt MATLAB}: CHOLMOD's interface to MATLAB \item {\tt Tcov}: an exhaustive test coverage (requires Linux or Solaris) + \item {\tt Valgrind}: runs the {\tt Tcov} test under {\tt valgrind} (requires Linux) \item \verb'cmake_modules': how other packages can find CHOLMOD when using cmake. \item \verb'Config': a folder containing the input files to create the @@ -746,11 +735,11 @@ \subsection{Adjustable parameters} \end{enumerate} %------------------------------------------------------------------------------- -\newpage \subsection{{\tt Utility} Module: basic data structures and definitions} +\newpage \subsection{{\tt Core} Module: basic data structures and definitions} %------------------------------------------------------------------------------- -CHOLMOD includes five basic objects, defined in the {\tt Utility} Module. -The {\tt Utility Module} provides basic operations for these objects +CHOLMOD includes five basic objects, defined in the {\tt Core} Module. +The {\tt Core Module} provides basic operations for these objects and is required by all six other CHOLMOD library Modules: \subsubsection{{\tt cholmod\_common}: parameters, statistics, and workspace} @@ -960,7 +949,7 @@ \subsubsection{{\tt cholmod\_version:} Version control} basic objects in CHOLMOD, and three kinds of integer vectors (a set, a permutation, and a tree). It also provides a routine to read a sparse matrix from a file in Matrix Market format (http://www.nist.gov/MatrixMarket). - Requires the {\tt Utility} Module. + Requires the {\tt Core} Module. \vspace{0.1in} \noindent Primary routines: @@ -1008,7 +997,7 @@ \subsubsection{{\tt cholmod\_version:} Version control} The primary routines are all that a user requires to order, analyze, and factorize a sparse symmetric positive definite matrix $\m{A}$ (or $\m{AA}\tr$), and to solve $\m{Ax}=\m{b}$ (or $\m{AA}\tr\m{x}=\m{b}$). The primary routines rely on the secondary -routines, the {\tt Utility} Module, and the AMD and COLAMD packages. They +routines, the {\tt Core} Module, and the AMD and COLAMD packages. They make optional use of the {\tt Supernodal} and {\tt Partition} Modules, the METIS package, the CAMD package, and the CCOLAMD package. The {\tt Cholesky} Module is @@ -1055,9 +1044,9 @@ \subsubsection{{\tt cholmod\_version:} Version control} It can also modify a corresponding solution to $\m{Lx}=\m{b}$ when L is modified. This module is most useful when applied on a Cholesky factorization computed by the {\tt Cholesky} module, but it does not actually require the {\tt Cholesky} module. -The {\tt Utility} module can create an identity Cholesky factorization ($\m{LDL}\tr$ where +The {\tt Core} module can create an identity Cholesky factorization ($\m{LDL}\tr$ where $\m{L}=\m{D}=\m{I}$) that can then be modified by these routines. -Requires the {\tt Utility} module. Not required by any other CHOLMOD Module. +Requires the {\tt Core} module. Not required by any other CHOLMOD Module. \vspace{0.1in} \noindent Primary routine: @@ -1086,7 +1075,7 @@ \subsection{{\tt MatrixOps} Module: basic sparse matrix operations} The {\tt MatrixOps} Module provides basic operations on sparse and dense matrices. -Requires the {\tt Utility} module. Not required by any other CHOLMOD module. +Requires the {\tt Core} module. Not required by any other CHOLMOD module. In the descriptions below, {\tt A}, {\tt B}, and {\tt C:} are sparse matrices ({\tt cholmod\_sparse}), {\tt X} and {\tt Y} are dense matrices ({\tt cholmod\_dense}), @@ -1117,7 +1106,7 @@ \subsection{{\tt Supernodal} Module: supernodal sparse Cholesky factorization} fill-reducing orderings. It normally operates on matrices ordered by the {\tt Cholesky} Module. It does not require the {\tt Cholesky} Module itself, however. -Requires the {\tt Utility} Module, and two external packages: LAPACK and the BLAS. +Requires the {\tt Core} Module, and two external packages: LAPACK and the BLAS. Optionally used by the {\tt Cholesky} Module. All are secondary routines since these functions are more easily used via the {\tt Cholesky} Module. @@ -1140,7 +1129,7 @@ \subsection{{\tt Partition} Module: graph-partitioning-based orderings} interface to CAMD, CCOLAMD, and CSYMAMD, constrained minimum degree ordering methods which order a matrix following constraints determined via nested dissection. -Requires the {\tt Utility} and {\tt Cholesky} Modules, and two packages: {\tt METIS 5.1.0}, CAMD, and CCOLAMD. +Requires the {\tt Core} and {\tt Cholesky} Modules, and two packages: {\tt METIS 5.1.0}, CAMD, and CCOLAMD. Optionally used by the {\tt Cholesky} Module. All are secondary routines since these are more easily used by the {\tt Cholesky} Module. @@ -1219,7 +1208,7 @@ \subsection{{\tt Partition} Module: graph-partitioning-based orderings} the imaginary part is always ignored ({\tt cholmod\_factor\_p}, for example). %------------------------------------------------------------------------------- -\newpage \section{{\tt Utility} Module: {\tt cholmod\_common} object} +\newpage \section{{\tt Core} Module: {\tt cholmod\_common} object} \label{cholmod_common} %------------------------------------------------------------------------------- @@ -1279,7 +1268,7 @@ \subsection{{\tt cholmod\_allocate\_work}: allocate workspace} of the integer {\tt Head}, {\tt Flag}, and {\tt Iwork} arrays, of size {\tt nrow+1}, {\tt nrow}, and {\tt iworksize}, respectively, and a {\tt double} array {\tt Xwork} of size -{\tt xworksize} entries. The {\tt Head} array is normally equal to -1 +{\tt xworksize}. The {\tt Head} array is normally equal to -1 when it is cleared. If the {\tt Flag} array is cleared, all entries are less than {\tt Common->mark}. The {\tt Iwork} array is not kept in any particular state. @@ -1287,15 +1276,6 @@ \subsection{{\tt cholmod\_allocate\_work}: allocate workspace} on whether the {\tt cholmod\_} or {\tt cholmod\_l\_} routines are used. -%--------------------------------------- -% \subsection{{\tt cholmod\_alloc\_work}: allocate workspace} -%--------------------------------------- - -% \input{_alloc_work.tex} -% This is the same as {\tt cholmod\_allocate\_work}, except that -% the {\tt Xwork} array can be {\tt float} or {\tt double}, as -% determined by the {\tt dtype} input parameter. - %--------------------------------------- \subsection{{\tt cholmod\_free\_work}: free workspace} %--------------------------------------- @@ -1356,7 +1336,7 @@ \subsection{{\tt cholmod\_divcomplex}: complex divide} that is not a part of CHOLMOD, but can be used via the function pointer. %------------------------------------------------------------------------------- -\newpage \section{{\tt Utility} Module: {\tt cholmod\_sparse} object} +\newpage \section{{\tt Core} Module: {\tt cholmod\_sparse} object} \label{cholmod_sparse} %------------------------------------------------------------------------------- @@ -1672,7 +1652,7 @@ \subsection{{\tt cholmod\_sparse\_xtype}: change sparse xtype} Changing from complex or zomplex to real discards the imaginary part. %------------------------------------------------------------------------------- -\newpage \section{{\tt Utility} Module: {\tt cholmod\_factor} object} +\newpage \section{{\tt Core} Module: {\tt cholmod\_factor} object} \label{cholmod_factor} %------------------------------------------------------------------------------- @@ -1718,49 +1698,49 @@ \subsection{{\tt cholmod\_reallocate\_factor}: reallocate factor} There are four basic classes of factor types: \begin{enumerate} \item simplicial symbolic: Consists of two size-{\tt n} arrays: the fill-reducing - permutation ({\tt L->Perm}) and the nonzero count for each column of L - ({\tt L->ColCount}). All other factor types also include this information. - {\tt L->ColCount} may be exact (obtained from the analysis routines), or it - may be a guess. During factorization, and certainly after update/downdate, - the columns of {\tt L} can have a different number of nonzeros. {\tt - L->ColCount} is used to allocate space. {\tt L->ColCount} is exact for the - supernodal factorizations. The nonzero pattern of {\tt L} is not kept. +permutation ({\tt L->Perm}) and the nonzero count for each column of L +({\tt L->ColCount}). All other factor types also include this information. +{\tt L->ColCount} may be exact (obtained from the analysis routines), or +it may be a guess. During factorization, and certainly after update/downdate, +the columns of {\tt L} can have a different number of nonzeros. +{\tt L->ColCount} is used to allocate space. {\tt L->ColCount} is exact for the +supernodal factorizations. The nonzero pattern of {\tt L} is not kept. \item simplicial numeric: These represent {\tt L} in a compressed column form. The - variants of this type are: +variants of this type are: - \begin{itemize} - \item $\m{LDL}\tr$: {\tt L} is unit diagonal. Row indices in column {\tt j} are located in - {\tt L->i [L->p [j] ... L->p [j] + L->nz [j]]}, and corresponding numeric - values are in the same locations in {\tt L->x}. The total number of - entries is the sum of {\tt L->nz [j]}. The unit diagonal is not stored; - {\tt D} is stored on the diagonal of {\tt L} instead. {\tt L->p} may or may not be - monotonic. The order of storage of the columns in {\tt L->i} and {\tt L->x} is - given by a doubly-linked list ({\tt L->prev} and {\tt L->next}). {\tt L->p} is of - size {\tt n+1}, but only the first {\tt n} entries are used. - - For the complex case, {\tt L->x} is stored interleaved with real and imaginary - parts, and is of size {\tt 2*lnz*sizeof(double)}. For the zomplex case, - {\tt L->x} is of size {\tt lnz*sizeof(double)} and holds the real part; {\tt L->z} - is the same size and holds the imaginary part. - - \item $\m{LL}\tr$: This is identical to the $\m{LDL}\tr$ form, except that the non-unit - diagonal of {\tt L} is stored as the first entry in each column of {\tt L}. - \end{itemize} +\begin{itemize} +\item $\m{LDL}\tr$: {\tt L} is unit diagonal. Row indices in column {\tt j} are located in + {\tt L->i [L->p [j] ... L->p [j] + L->nz [j]]}, and corresponding numeric + values are in the same locations in {\tt L->x}. The total number of + entries is the sum of {\tt L->nz [j]}. The unit diagonal is not stored; + {\tt D} is stored on the diagonal of {\tt L} instead. {\tt L->p} may or may not be + monotonic. The order of storage of the columns in {\tt L->i} and {\tt L->x} is + given by a doubly-linked list ({\tt L->prev} and {\tt L->next}). {\tt L->p} is of + size {\tt n+1}, but only the first {\tt n} entries are used. + + For the complex case, {\tt L->x} is stored interleaved with real and imaginary + parts, and is of size {\tt 2*lnz*sizeof(double)}. For the zomplex case, + {\tt L->x} is of size {\tt lnz*sizeof(double)} and holds the real part; {\tt L->z} + is the same size and holds the imaginary part. + +\item $\m{LL}\tr$: This is identical to the $\m{LDL}\tr$ form, except that the non-unit + diagonal of {\tt L} is stored as the first entry in each column of {\tt L}. +\end{itemize} \item supernodal symbolic: A representation of the nonzero pattern of the - supernodes for a supernodal factorization. There are {\tt L->nsuper} - supernodes. Columns {\tt L->super [k]} to {\tt L->super [k+1]-1} are in the {\tt k}th - supernode. The row indices for the {\tt k}th supernode are in - {\tt L->s [L->pi [k] ... L->pi [k+1]-1]}. The numerical values are not - allocated ({\tt L->x}), but when they are they will be located in - {\tt L->x [L->px [k] ... L->px [k+1]-1]}, and the {\tt L->px} array is defined - in this factor type. - - For the complex case, {\tt L->x} is stored interleaved with real/imaginary parts, - and is of size \newline - {\tt 2*L->xsize*sizeof(double)}. The zomplex supernodal case - is not supported, since it is not compatible with LAPACK and the BLAS. +supernodes for a supernodal factorization. There are {\tt L->nsuper} +supernodes. Columns {\tt L->super [k]} to {\tt L->super [k+1]-1} are in the {\tt k}th +supernode. The row indices for the {\tt k}th supernode are in +{\tt L->s [L->pi [k] ... L->pi [k+1]-1]}. The numerical values are not +allocated ({\tt L->x}), but when they are they will be located in +{\tt L->x [L->px [k] ... L->px [k+1]-1]}, and the {\tt L->px} array is defined +in this factor type. + +For the complex case, {\tt L->x} is stored interleaved with real/imaginary parts, +and is of size \newline +{\tt 2*L->xsize*sizeof(double)}. The zomplex supernodal case +is not supported, since it is not compatible with LAPACK and the BLAS. \item supernodal numeric: Always an $\m{LL}\tr$ factorization. {\tt L} has a non-unit diagonal. {\tt L->x} contains the numerical values of the supernodes, as @@ -1865,7 +1845,7 @@ \subsection{{\tt cholmod\_factor\_xtype}: change factor xtype} You cannot change a supernodal factor to the zomplex xtype. %------------------------------------------------------------------------------- -\newpage \section{{\tt Utility} Module: {\tt cholmod\_dense} object} +\newpage \section{{\tt Core} Module: {\tt cholmod\_dense} object} \label{cholmod_dense} %------------------------------------------------------------------------------- @@ -1928,13 +1908,6 @@ \subsection{{\tt cholmod\_eye}: dense identity matrix} \input{_sparse_to_dense.tex} Returns a dense copy of a sparse matrix. -%--------------------------------------- -\subsection{{\tt cholmod\_dense\_nnz}: number of nonzeros in a dense matrix} -%--------------------------------------- - -\input{_dense_nnz.tex} -Returns a count of the number of nonzero entries in a dense matrix. - %--------------------------------------- \subsection{{\tt cholmod\_dense\_to\_sparse}: sparse matrix copy of a dense matrix} %--------------------------------------- @@ -1965,7 +1938,7 @@ \subsection{{\tt cholmod\_dense\_xtype}: change dense matrix xtype} Changing from complex or zomplex to real discards the imaginary part. %------------------------------------------------------------------------------- -\newpage \section{{\tt Utility} Module: {\tt cholmod\_triplet} object} +\newpage \section{{\tt Core} Module: {\tt cholmod\_triplet} object} \label{cholmod_triplet} %------------------------------------------------------------------------------- @@ -2034,7 +2007,7 @@ \subsection{{\tt cholmod\_triplet\_xtype}: change triplet xtype} Changing from complex or zomplex to real discards the imaginary part. %------------------------------------------------------------------------------- -\newpage \section{{\tt Utility} Module: memory management} +\newpage \section{{\tt Core} Module: memory management} %------------------------------------------------------------------------------- %--------------------------------------- @@ -2101,7 +2074,7 @@ \subsection{{\tt cholmod\_realloc}: reallocate memory} or all are returned to their original size. %------------------------------------------------------------------------------- -\newpage \section{{\tt Utility} Module: version control} +\newpage \section{{\tt Core} Module: version control} %------------------------------------------------------------------------------- \subsection{{\tt cholmod\_version}: return current CHOLMOD version} @@ -2535,32 +2508,30 @@ \subsection{{\tt cholmod\_analyze}: symbolic factorization} If you truly want the natural ordering with no postordering, you must set {\tt Common->postorder} to {\tt FALSE}. -The factor {\tt L} is returned as simplicial symbolic if {\tt -Common->supernodal} is {\tt CHOLMOD\_SIMPLICIAL} (zero) or as supernodal -symbolic if {\tt Common->supernodal} is {\tt CHOLMOD\_SUPERNODAL} (two). If -\newline {\tt Common->supernodal} is {\tt CHOLMOD\_AUTO} (one), then {\tt L} is -simplicial if the flop count per nonzero in {\tt L} is less than {\tt -Common->supernodal\_switch} (default: 40), and supernodal otherwise. In both -cases, {\tt L->xtype} is {\tt CHOLMOD\_PATTERN}. A subsequent call to {\tt -cholmod\_factorize} will perform a simplicial or supernodal factorization, -depending on the type of {\tt L}. - -For the simplicial case, {\tt L} contains the fill-reducing permutation ({\tt -L->Perm}) and the counts of nonzeros in each column of {\tt L} ({\tt -L->ColCount}). For the supernodal case, {\tt L} also contains the nonzero -pattern of each supernode. - -If a simplicial factorization is selected, it will be $\m{LDL}\tr$ by default, -since this is the kind required by the {\tt Modify} Module. CHOLMOD does not -include a supernodal $\m{LDL}\tr$ factorization, so if a supernodal -factorization is selected, it will be in the form $\m{LL}\tr$. The -$\m{LDL}\tr$ method can be used to factorize positive definite matrices and -indefinite matrices whose leading minors are well-conditioned (2-by-2 pivoting -is not supported). The $\m{LL}\tr$ method is restricted to positive definite -matrices. To factorize a large indefinite matrix, set {\tt Common->supernodal} -to {\tt CHOLMOD\_SIMPLICIAL}, and the simplicial $\m{LDL}\tr$ method will -always be used. This will be significantly slower than a supernodal -$\m{LL}\tr$ factorization, however. +The factor {\tt L} is returned as simplicial symbolic if +{\tt Common->supernodal} is {\tt CHOLMOD\_SIMPLICIAL} (zero) or as supernodal symbolic if +{\tt Common->supernodal} is {\tt CHOLMOD\_SUPERNODAL} (two). If \newline +{\tt Common->supernodal} is {\tt CHOLMOD\_AUTO} (one), +then {\tt L} is simplicial if the flop count per nonzero in {\tt L} is less than +{\tt Common->supernodal\_switch} (default: 40), and +supernodal otherwise. In both cases, {\tt L->xtype} is {\tt CHOLMOD\_PATTERN}. +A subsequent call to {\tt cholmod\_factorize} will perform a +simplicial or supernodal factorization, depending on the type of {\tt L}. + +For the simplicial case, {\tt L} contains the fill-reducing permutation ({\tt L->Perm}) +and the counts of nonzeros in each column of {\tt L} ({\tt L->ColCount}). For the +supernodal case, {\tt L} also contains the nonzero pattern of each supernode. + +If a simplicial factorization is selected, it will be $\m{LDL}\tr$ by default, since +this is the kind required by the {\tt Modify} Module. CHOLMOD does not include a +supernodal $\m{LDL}\tr$ factorization, so if a supernodal factorization is selected, +it will be in the form $\m{LL}\tr$. The $\m{LDL}\tr$ method can be used to +factorize positive definite matrices and indefinite matrices whose leading minors +are well-conditioned (2-by-2 pivoting is not supported). The $\m{LL}\tr$ method +is restricted to positive definite matrices. To factorize a large indefinite matrix, +set {\tt Common->supernodal} to {\tt CHOLMOD\_SIMPLICIAL}, and the simplicial +$\m{LDL}\tr$ method will always be used. This will be significantly slower than +a supernodal $\m{LL}\tr$ factorization, however. Refer to {\tt cholmod\_transpose\_unsym} for a description of {\tt f}. @@ -2568,22 +2539,24 @@ \subsection{{\tt cholmod\_analyze}: symbolic factorization} \subsection{{\tt cholmod\_factorize}: numeric factorization} %--------------------------------------- -\input{_factorize.tex} Computes the numerical factorization of a symmetric -matrix. The inputs to this routine are a sparse matrix {\tt A} and the -symbolic factor {\tt L} from {\tt cholmod\_analyze} or a prior numerical factor -{\tt L}. If {\tt A} is symmetric, this routine factorizes {\tt A(p,p)}. where -p is the fill-reducing permutation ({\tt L->Perm}). If {\tt A} is unsymmetric, -{\tt A(p,:)*A(p,:)'} is factorized. The nonzero pattern of the matrix {\tt A} -must be the same as the matrix passed to {\tt cholmod\_analyze} for the -supernodal case. For the simplicial case, it can be different, but it should -be the same for best performance. - -A simplicial factorization or supernodal factorization is chosen, based on the -type of the factor {\tt L}. If {\tt L->is\_super} is {\tt TRUE}, a supernodal -$\m{LL}\tr$ factorization is computed. Otherwise, a simplicial numeric -factorization is computed, either $\m{LL}\tr$ or $\m{LDL}\tr$, depending on -{\tt Common->final\_ll} (the default for the simplicial case is to compute an -$\m{LDL}\tr$ factorization). +\input{_factorize.tex} +Computes the numerical factorization of a symmetric matrix. The % primary +inputs to this routine are a sparse matrix {\tt A} and the symbolic factor {\tt L} from +{\tt cholmod\_analyze} or a prior numerical factor {\tt L}. If {\tt A} is symmetric, this +routine factorizes {\tt A(p,p)}. %+beta*I (beta can be zero), +where p is the fill-reducing permutation ({\tt L->Perm}). If {\tt A} is unsymmetric, +% either +{\tt A(p,:)*A(p,:)'} % +beta*I or A(p,f)*A(p,f)'+beta*I +is factorized. % The set f and +The nonzero pattern of the matrix {\tt A} must be the same as the matrix passed to +{\tt cholmod\_analyze} for the supernodal case. For the simplicial case, it can +be different, but it should be the same for best performance. % beta is real. + +A simplicial factorization or supernodal factorization is chosen, based on +the type of the factor {\tt L}. If {\tt L->is\_super} is {\tt TRUE}, a supernodal $\m{LL}\tr$ +factorization is computed. Otherwise, a simplicial numeric factorization +is computed, either $\m{LL}\tr$ or $\m{LDL}\tr$, depending on {\tt Common->final\_ll} +(the default for the simplicial case is to compute an $\m{LDL}\tr$ factorization). Once the factorization is complete, it can be left as is or optionally converted into any simplicial numeric type, depending on the @@ -2966,12 +2939,12 @@ \subsection{{\tt cholmod\_resymbol}: re-do symbolic factorization} If an entry in {\tt L} is kept, its numerical value does not change. -This routine is used after a supernodal factorization is converted into a -simplicial one, to remove zero entries that were added due to relaxed supernode -amalgamation. It can also be used after a series of downdates to remove -entries that would no longer be present if the matrix were factorized from -scratch. A downdate ({\tt cholmod\_updown}) does not remove any entries from -{\tt L}. +This routine is used after a supernodal factorization is converted into +a simplicial one, to remove zero entries that were added due to relaxed +supernode amalgamation. It can also be used after a series of downdates +to remove entries that would no longer be present if the matrix were +factorized from scratch. A downdate ({\tt cholmod\_updown}) does not remove any +entries from {\tt L}. %--------------------------------------- \subsection{{\tt cholmod\_resymbol\_noperm}: re-do symbolic factorization} diff --git a/CHOLMOD/Doc/ChangeLog b/CHOLMOD/Doc/ChangeLog index 8b06f49b7a..ae65f71f3e 100644 --- a/CHOLMOD/Doc/ChangeLog +++ b/CHOLMOD/Doc/ChangeLog @@ -1,10 +1,6 @@ -Oct 23, 2023, version 5.0.0 +Oct 16, 2023: version 4.2.2 - * CHOLMOD v5.0.0: introduces the first part of support for single - precision sparse matrices, with the introduction of the new - CHOLMOD:Utility Module. The CHOLMOD:Utility Module replaces - CHOLMOD:Core in prior versions. Single precision is not yet - incorporated into the remaining Modules, however. + * bug fix: incorrect computation of work for nthreads in CHOLMOD/Supernodal Sept 18, 2023: version 4.2.1 diff --git a/CHOLMOD/Doc/License.txt b/CHOLMOD/Doc/License.txt index 902cfa7341..ef860eb267 100644 --- a/CHOLMOD/Doc/License.txt +++ b/CHOLMOD/Doc/License.txt @@ -54,15 +54,20 @@ Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA -------------------------------------------------------------------------------- -==> Utility/License.txt <== +==> Core/License.txt <== -------------------------------------------------------------------------------- - CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights - Reserved. CHOLMOD is also available under other licenses; contact authors - for details. http://www.suitesparse.com + CHOLMOD/Core Module. Copyright (C) 2005-2022, Univ. of Florida. Author: + Timothy A. Davis. CHOLMOD is also available under other licenses; contact + authors for details. http://www.suitesparse.com + + Note that this license is for the CHOLMOD/Core module only. + All CHOLMOD modules are licensed separately. + ---------------------------------------------------------------------------- + This Module is free software; you can redistribute it and/or modify it under the terms of the GNU Lesser General Public License as published by the Free Software Foundation; either @@ -282,3 +287,31 @@ along with this Module; if not, write to the Free Software Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA. +-------------------------------------------------------------------------------- +==> Valgrind/License.txt <== +-------------------------------------------------------------------------------- + + CHOLMOD/Valgrind Module. Copyright (C) 2005-2022, Timothy A. Davis. + CHOLMOD is also available under other licenses; contact authors for details. + http://www.suitesparse.com + + Note that this license is for the CHOLMOD/Valgrind module only. + All CHOLMOD modules are licensed separately. + + + ---------------------------------------------------------------------------- + + + This Module is free software; you can redistribute it and/or + modify it under the terms of the GNU General Public License + as published by the Free Software Foundation; either version 2 + of the License, or (at your option) any later version. + + This Module is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with this Module; if not, write to the Free Software + Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA. diff --git a/CHOLMOD/Doc/Makefile b/CHOLMOD/Doc/Makefile index 178c4a305a..ad540f1148 100644 --- a/CHOLMOD/Doc/Makefile +++ b/CHOLMOD/Doc/Makefile @@ -66,7 +66,7 @@ CHOLMOD_UserGuide.pdf: CHOLMOD_UserGuide.tex UserGuide.bib $(I) $(C) $(M) Makefi ./getproto '/int cholmod_free_work/, /\*\) ;/' ../Include/cholmod.h > _free_work.tex ./getproto '/int64_t cholmod_clear_flag/, /\*\) ;/' ../Include/cholmod.h > _clear_flag.tex ./getproto '/int cholmod_error/, /\*\) ;/' ../Include/cholmod.h > _error.tex - ./getproto '/double cholmod_dbound/, /l_sbound/' ../Include/cholmod.h > _dbound.tex + ./getproto '/double cholmod_dbound/, /\*\) ;/' ../Include/cholmod.h > _dbound.tex ./getproto '/double cholmod_hypot/, /double\) ;/' ../Include/cholmod.h > _hypot.tex ./getproto '/int cholmod_divcomplex/, /\*\) ;/' ../Include/cholmod.h > _divcomplex.tex ./getproto '/typedef struct cholmod_sparse/, /^}/' ../Include/cholmod.h > _sparse.tex @@ -74,7 +74,6 @@ CHOLMOD_UserGuide.pdf: CHOLMOD_UserGuide.tex UserGuide.bib $(I) $(C) $(M) Makefi ./getproto '/int cholmod_free_sparse/, /\*\) ;/' ../Include/cholmod.h > _free_sparse.tex ./getproto '/int cholmod_reallocate_sparse/, /\*\) ;/' ../Include/cholmod.h > _reallocate_sparse.tex ./getproto '/int64_t cholmod_nnz/, /\*\) ;/' ../Include/cholmod.h > _nnz.tex - ./getproto '/int64_t cholmod_dense_nnz/, /\*\) ;/' ../Include/cholmod.h > _dense_nnz.tex ./getproto '/cholmod_sparse \*cholmod_speye/, /\*\) ;/' ../Include/cholmod.h > _speye.tex ./getproto '/cholmod_sparse \*cholmod_spzeros/, /\*\) ;/' ../Include/cholmod.h > _spzeros.tex ./getproto '/cholmod_sparse \*cholmod_transpose/, /\*\) ;/' ../Include/cholmod.h > _transpose.tex @@ -125,7 +124,7 @@ CHOLMOD_UserGuide.pdf: CHOLMOD_UserGuide.tex UserGuide.bib $(I) $(C) $(M) Makefi ./getproto '/void \*cholmod_realloc/, /\*\) ;/' ../Include/cholmod.h > _realloc.tex ./getproto '/int cholmod_realloc_multiple/, /\*\) ;/' ../Include/cholmod.h > _realloc_multiple.tex ./getproto '/int cholmod_version/, /l_version/' ../Include/cholmod.h > _version.tex - ./getproto '/itype: integer sizes/, /define CHOLMOD_SUPERNODAL/' ../Include/cholmod.h > _defn.tex + ./getproto '/itype defines the/, /define CHOLMOD_SUPERNODAL/' ../Include/cholmod.h > _defn.tex ./getproto '/int cholmod_check_common/, /\*\) ;/' ../Include/cholmod.h > _check_common.tex ./getproto '/int cholmod_print_common/, /\*\) ;/' ../Include/cholmod.h > _print_common.tex ./getproto '/int cholmod_check_sparse/, /\*\) ;/' ../Include/cholmod.h > _check_sparse.tex @@ -206,7 +205,7 @@ CHOLMOD_UserGuide.pdf: CHOLMOD_UserGuide.tex UserGuide.bib $(I) $(C) $(M) Makefi bibtex CHOLMOD_UserGuide pdflatex CHOLMOD_UserGuide pdflatex CHOLMOD_UserGuide - - $(RM) _temp.awk + - $(RM) _temp.awk _*.tex - $(RM) -r *.aux *.bbl *.blg *.log *.toc *.dvi *.lof *.lot distclean: purge @@ -214,7 +213,6 @@ distclean: purge purge: clean clean: - - $(RM) _*.tex - - $(RM) _temp.awk + - $(RM) _temp.awk _*.tex - $(RM) -r *.aux *.bbl *.blg *.log *.toc *.dvi *.lof *.lot diff --git a/CHOLMOD/Doc/cholmod_version.tex b/CHOLMOD/Doc/cholmod_version.tex index 214516bbfb..badf2150b5 100644 --- a/CHOLMOD/Doc/cholmod_version.tex +++ b/CHOLMOD/Doc/cholmod_version.tex @@ -1,2 +1,2 @@ % version of SuiteSparse/CHOLMOD -\date{VERSION 5.0.0, Oct 23, 2023} +\date{VERSION 4.2.2, Oct 15, 2023} diff --git a/CHOLMOD/GPU/CMakeLists.txt b/CHOLMOD/GPU/CMakeLists.txt index 4c11d2fa69..f0194e978a 100644 --- a/CHOLMOD/GPU/CMakeLists.txt +++ b/CHOLMOD/GPU/CMakeLists.txt @@ -63,7 +63,7 @@ set ( CHOLMOD_CUDA_INCLUDES ../Check ../../SuiteSparse_config ../Cholesky - ../Utility + ../Core ../Supernodal ../Include ../GPU ) diff --git a/CHOLMOD/GPU/cholmod_gpu.c b/CHOLMOD/GPU/cholmod_gpu.c index 1deef66ecb..e243763390 100644 --- a/CHOLMOD/GPU/cholmod_gpu.c +++ b/CHOLMOD/GPU/cholmod_gpu.c @@ -78,7 +78,7 @@ int CHOLMOD(gpu_memorysize) /* returns 1 on error, 0 otherwise */ *total_mem = 0; *available_mem = 0; -#ifndef CHOLMOD_INT64 +#ifndef DLONG return 0; #endif diff --git a/CHOLMOD/GPU/cholmod_l_gpu.c b/CHOLMOD/GPU/cholmod_l_gpu.c index bb4cd68524..db4dc5bef1 100644 --- a/CHOLMOD/GPU/cholmod_l_gpu.c +++ b/CHOLMOD/GPU/cholmod_l_gpu.c @@ -8,6 +8,6 @@ //------------------------------------------------------------------------------ -#define CHOLMOD_INT64 +#define DLONG #include "cholmod_gpu.c" diff --git a/CHOLMOD/Include/cholmod.h b/CHOLMOD/Include/cholmod.h index d2da4c9c73..7b6e70e7be 100644 --- a/CHOLMOD/Include/cholmod.h +++ b/CHOLMOD/Include/cholmod.h @@ -2,14 +2,14 @@ // CHOLMOD/Include/cholmod.h: include file for CHOLMOD //------------------------------------------------------------------------------ -// CHOLMOD/Include/cholmod.h. Copyright (C) 2005-2023, Timothy A. Davis. +// CHOLMOD/Include/cholmod.h. Copyright (C) 2005-2022, Timothy A. Davis. // All Rights Reserved. // Each Module of CHOLMOD has its own license, and a shared cholmod.h file. // CHOLMOD/Check: SPDX-License-Identifier: LGPL-2.1+ // CHOLMOD/Cholesky: SPDX-License-Identifier: LGPL-2.1+ -// CHOLMOD/Utility: SPDX-License-Identifier: LGPL-2.1+ +// CHOLMOD/Core: SPDX-License-Identifier: LGPL-2.1+ // CHOLMOD/Partition: SPDX-License-Identifier: LGPL-2.1+ // CHOLMOD/Demo: SPDX-License-Identifier: GPL-2.0+ @@ -19,195 +19,433 @@ // CHOLMOD/Modify: SPDX-License-Identifier: GPL-2.0+ // CHOLMOD/Supernodal: SPDX-License-Identifier: GPL-2.0+ // CHOLMOD/Tcov: SPDX-License-Identifier: GPL-2.0+ +// CHOLMOD/Valgrind: SPDX-License-Identifier: GPL-2.0+ //------------------------------------------------------------------------------ -// CHOLMOD consists of a set of Modules, each with their own license: either -// LGPL-2.1+ or GPL-2.0+. This cholmod.h file includes defintions of the -// CHOLMOD API for all Modules, and this cholmod.h file itself is provided to -// you with a permissive license (Apache-2.0). You are permitted to provide -// the hooks for an optional interface to CHOLMOD in a non-GPL/non-LGPL code, -// without requiring you to agree to the GPL/LGPL license of the Modules, as -// long as you don't use the *.c files in the relevant Modules. The Modules -// themselves can only be functional if their GPL or LGPL licenses are used. -// -// The Modify Module is co-authored by William W. Hager. -// -// Acknowledgements: this work was supported in part by the National Science -// Foundation (NFS CCR-0203270 and DMS-9803599), and a grant from Sandia -// National Laboratories (Dept. of Energy) which supported the development of -// CHOLMOD's Partition Module. -// ----------------------------------------------------------------------------- - -// Each routine in CHOLMOD has a consistent interface. -// -// Naming convention: -// ------------------ -// -// All routine names, data types, and CHOLMOD library files use the -// cholmod_ prefix. All macros and other #define's use the CHOLMOD -// prefix. -// -// Return value: -// ------------- -// -// Most CHOLMOD routines return an int (TRUE (1) if successful, or FALSE -// (0) otherwise. An int32_t, int64_t, double, or float return value -// is >= 0 if successful, or -1 otherwise. A size_t return value -// is > 0 if successful, or 0 otherwise. -// -// If a routine returns a pointer, it is a pointer to a newly allocated -// object or NULL if a failure occured, with one exception. cholmod_free -// always returns NULL. -// -// "Common" parameter: -// ------------------ -// -// The last parameter in all CHOLMOD routines is a pointer to the CHOLMOD -// "Common" object. This contains control parameters, statistics, and -// workspace used between calls to CHOLMOD. It is always an input/output -// parameter. -// -// Input, Output, and Input/Output parameters: -// ------------------------------------------- -// -// Input parameters are listed first. They are not modified by CHOLMOD. -// -// Input/output are listed next. They must be defined on input, and -// are modified on output. -// -// Output parameters are listed next. If they are pointers, they must -// point to allocated space on input, but their contents are not defined -// on input. -// -// Workspace parameters appear next. They are used in only two routines -// in the Supernodal module. -// -// The cholmod_common *Common parameter always appears as the last -// parameter. It is always an input/output parameter. + +/* CHOLMOD consists of a set of Modules, each with their own license: either + * LGPL-2.1+ or GPL-2.0+. This cholmod.h file includes defintions of the + * CHOLMOD API for all Modules, and this cholmod.h file itself is provided to + * you with a permissive license (Apache-2.0). You are permitted to provide + * the hooks for an optional interface to CHOLMOD in a non-GPL/non-LGPL code, + * without requiring you to agree to the GPL/LGPL license of the Modules, as + * long as you don't use the *.c files in the relevant Modules. The Modules + * themselves can only be functional if their GPL or LGPL licenses are used. + * + * Portions of CHOLMOD (the Core and Partition Modules) are copyrighted by the + * University of Florida. The Modify Module is co-authored by William W. + * Hager, Univ. of Florida. + * + * Acknowledgements: this work was supported in part by the National Science + * Foundation (NFS CCR-0203270 and DMS-9803599), and a grant from Sandia + * National Laboratories (Dept. of Energy) which supported the development of + * CHOLMOD's Partition Module. + * -------------------------------------------------------------------------- */ + +/* CHOLMOD include file, for inclusion user programs. + * + * The include files listed below include a short description of each user- + * callable routine. Each routine in CHOLMOD has a consistent interface. + * More details about the CHOLMOD data types is in the cholmod_core.h file. + * + * Naming convention: + * ------------------ + * + * All routine names, data types, and CHOLMOD library files use the + * cholmod_ prefix. All macros and other #define's use the CHOLMOD + * prefix. + * + * Return value: + * ------------- + * + * Most CHOLMOD routines return an int (TRUE (1) if successful, or FALSE + * (0) otherwise. An int32_t, int64_t, or double return value is >= 0 if + * successful, or -1 otherwise. A size_t return value is > 0 if + * successful, or 0 otherwise. + * + * If a routine returns a pointer, it is a pointer to a newly allocated + * object or NULL if a failure occured, with one exception. cholmod_free + * always returns NULL. + * + * "Common" parameter: + * ------------------ + * + * The last parameter in all CHOLMOD routines is a pointer to the CHOLMOD + * "Common" object. This contains control parameters, statistics, and + * workspace used between calls to CHOLMOD. It is always an input/output + * parameter. + * + * Input, Output, and Input/Output parameters: + * ------------------------------------------- + * + * Input parameters are listed first. They are not modified by CHOLMOD. + * + * Input/output are listed next. They must be defined on input, and + * are modified on output. + * + * Output parameters are listed next. If they are pointers, they must + * point to allocated space on input, but their contents are not defined + * on input. + * + * Workspace parameters appear next. They are used in only two routines + * in the Supernodal module. + * + * The cholmod_common *Common parameter always appears as the last + * parameter. It is always an input/output parameter. + */ #ifndef CHOLMOD_H #define CHOLMOD_H -//============================================================================== -// version control -//============================================================================== +#define CHOLMOD_DATE "Oct 15, 2023" +#define CHOLMOD_MAIN_VERSION 4 +#define CHOLMOD_SUB_VERSION 2 +#define CHOLMOD_SUBSUB_VERSION 2 -#define CHOLMOD_DATE "Oct 23, 2023" -#define CHOLMOD_MAIN_VERSION 5 -#define CHOLMOD_SUB_VERSION 0 -#define CHOLMOD_SUBSUB_VERSION 0 +/* ========================================================================== */ +/* === Include/cholmod_io64 ================================================= */ +/* ========================================================================== */ -#define CHOLMOD_VER_CODE(main,sub) ((main) * 1000 + (sub)) -#define CHOLMOD_VERSION \ - CHOLMOD_VER_CODE(CHOLMOD_MAIN_VERSION,CHOLMOD_SUB_VERSION) -#define CHOLMOD_HAS_VERSION_FUNCTION +/* assume large file support. If problems occur, compile with -DNLARGEFILE */ -int cholmod_version // returns CHOLMOD_VERSION, defined above -( - // if version is not NULL, then cholmod_version returns its contents as: - // version [0] = CHOLMOD_MAIN_VERSION - // version [1] = CHOLMOD_SUB_VERSION - // version [2] = CHOLMOD_SUBSUB_VERSION - int version [3] -) ; -int cholmod_l_version (int version [3]) ; +/* Definitions required for large file I/O, which must come before any other + * #includes. These are not used if -DNLARGEFILE is defined at compile time. + * Large file support may not be portable across all platforms and compilers; + * if you encounter an error here, compile your code with -DNLARGEFILE. In + * particular, you must use -DNLARGEFILE for MATLAB 6.5 or earlier (which does + * not have the io64.h include file). + */ -//============================================================================== -// Large file support -//============================================================================== +/* skip all of this if NLARGEFILE is defined at the compiler command line */ +#ifndef NLARGEFILE -// CHOLMOD assumes large file support. If problems occur, compile with -// -DNLARGEFILE +#if defined(MATLAB_MEX_FILE) || defined(MATHWORKS) -// Definitions required for large file I/O, which must come before any other -// #includes. These are not used if -DNLARGEFILE is defined at compile time. -// Large file support may not be portable across all platforms and compilers; -// if you encounter an error here, compile your code with -DNLARGEFILE. In -// particular, you must use -DNLARGEFILE for MATLAB 6.5 or earlier (which does -// not have the io64.h include file). +/* CHOLMOD is being compiled as a MATLAB mexFunction, or for use in MATLAB */ +#include "io64.h" + +#else + +/* CHOLMOD is being compiled in a stand-alone library */ +#undef _LARGEFILE64_SOURCE +#define _LARGEFILE64_SOURCE +#undef _FILE_OFFSET_BITS +#define _FILE_OFFSET_BITS 64 -// skip all of this if NLARGEFILE is defined at the compiler command line -#ifndef NLARGEFILE - #if defined(MATLAB_MEX_FILE) || defined(MATHWORKS) - // CHOLMOD compiled as a MATLAB mexFunction, or for use in MATLAB - #include "io64.h" - #else - // CHOLMOD is being compiled in a stand-alone library - #undef _LARGEFILE64_SOURCE - #define _LARGEFILE64_SOURCE - #undef _FILE_OFFSET_BITS - #define _FILE_OFFSET_BITS 64 - #endif #endif -//============================================================================== -// SuiteSparse_config -//============================================================================== +#endif + +/* ========================================================================== */ +/* === SuiteSparse_config.h ================================================= */ +/* ========================================================================== */ #include "SuiteSparse_config.h" -//============================================================================== -// CHOLMOD configuration -//============================================================================== - -// You do not have to edit any CHOLMOD files to compile and install CHOLMOD. -// However, if you do not use all of CHOLMOD's modules, you need to compile -// with the appropriate flag, or edit this file to add the appropriate #define. -// -// Compiler flags for CHOLMOD -// -// -DNCHECK do not include the Check module. -// -DNCHOLESKY do not include the Cholesky module. -// -DNPARTITION do not include the Partition module. -// -DNCAMD do not include the interfaces to CAMD, -// CCOLAMD, CSYMAND in Partition module. -// -DNMATRIXOPS do not include the MatrixOps module. -// -DNMODIFY do not include the Modify module. -// -DNSUPERNODAL do not include the Supernodal module. -// -// -DNPRINT do not print anything -// -// The Utility Module is always included in the CHOLMOD library. - -// Use the compiler flag, or uncomment the definition(s), if you want to use -// one or more non-default installation options: - -// #define NCHECK -// #define NCHOLESKY -// #define NCAMD -// #define NPARTITION -// #define NMATRIXOPS -// #define NMODIFY -// #define NSUPERNODAL -// #define NPRINT -// #define NGPL - -// The NGPL option disables the MatrixOps, Modify, and Supernodal modules. The -// existence of this #define here, and its use in these 3 modules, does not -// affect the license itself; see CHOLMOD/Doc/License.txt for your actual -// license. +/* ========================================================================== */ +/* === Include/cholmod_config.h ============================================= */ +/* ========================================================================== */ + +/* CHOLMOD configuration file, for inclusion in user programs. + * + * You do not have to edit any CHOLMOD files to compile and install CHOLMOD. + * However, if you do not use all of CHOLMOD's modules, you need to compile + * with the appropriate flag, or edit this file to add the appropriate #define. + * + * Compiler flags for CHOLMOD: + * + * -DNCHECK do not include the Check module. + * -DNCHOLESKY do not include the Cholesky module. + * -DNPARTITION do not include the Partition module. + * -DNCAMD do not include the interfaces to CAMD, + * CCOLAMD, CSYMAND in Partition module. + * -DNMATRIXOPS do not include the MatrixOps module. + * -DNMODIFY do not include the Modify module. + * -DNSUPERNODAL do not include the Supernodal module. + * + * -DNPRINT do not print anything + * + * The Core Module is always included in the CHOLMOD library. + */ + +/* Use the compiler flag, or uncomment the definition(s), if you want to use + * one or more non-default installation options: */ + +/* +#define NCHECK +#define NCHOLESKY +#define NCAMD +#define NPARTITION +#define NMATRIXOPS +#define NMODIFY +#define NSUPERNODAL +#define NPRINT +#define NGPL +*/ + +/* The NGPL option disables the MatrixOps, Modify, and Supernodal modules. The + existence of this #define here, and its use in these 3 modules, does not + affect the license itself; see CHOLMOD/Doc/License.txt for your actual + license. + */ #ifdef NGPL - #undef NMATRIXOPS - #define NMATRIXOPS - #undef NMODIFY - #define NMODIFY - #undef NSUPERNODAL - #define NSUPERNODAL +#undef NMATRIXOPS +#define NMATRIXOPS +#undef NMODIFY +#define NMODIFY +#undef NSUPERNODAL +#define NSUPERNODAL #endif -//============================================================================== -// CHOLMOD:Utility Module -//============================================================================== -// the CHOLMOD:Utility Module is always required -#if 1 +/* ========================================================================== */ +/* === Include/cholmod_core.h =============================================== */ +/* ========================================================================== */ -//------------------------------------------------------------------------------ -// CUDA BLAS -//------------------------------------------------------------------------------ +/* CHOLMOD Core module: basic CHOLMOD objects and routines. + * Required by all CHOLMOD modules. Requires no other module or package. + * + * The CHOLMOD modules are: + * + * Core basic data structures and definitions + * Check check/print the 5 CHOLMOD objects, & 3 types of integer vectors + * Cholesky sparse Cholesky factorization + * Modify sparse Cholesky update/downdate/row-add/row-delete + * MatrixOps sparse matrix functions (add, multiply, norm, ...) + * Supernodal supernodal sparse Cholesky factorization + * Partition graph-partitioning based orderings + * + * The CHOLMOD objects: + * -------------------- + * + * cholmod_common parameters, statistics, and workspace + * cholmod_sparse a sparse matrix in compressed column form + * cholmod_factor an LL' or LDL' factorization + * cholmod_dense a dense matrix + * cholmod_triplet a sparse matrix in "triplet" form + * + * The Core module described here defines the CHOLMOD data structures, and + * basic operations on them. To create and solve a sparse linear system Ax=b, + * the user must create A and b, populate them with values, and then pass them + * to the routines in the CHOLMOD Cholesky module. There are two primary + * methods for creating A: (1) allocate space for a column-oriented sparse + * matrix and fill it with pattern and values, or (2) create a triplet form + * matrix and convert it to a sparse matrix. The latter option is simpler. + * + * The matrices b and x are typically dense matrices, but can also be sparse. + * You can allocate and free them as dense matrices with the + * cholmod_allocate_dense and cholmod_free_dense routines. + * + * The cholmod_factor object contains the symbolic and numeric LL' or LDL' + * factorization of sparse symmetric matrix. The matrix must be positive + * definite for an LL' factorization. It need only be symmetric and have well- + * conditioned leading submatrices for it to have an LDL' factorization + * (CHOLMOD does not pivot for numerical stability). It is typically created + * with the cholmod_factorize routine in the Cholesky module, but can also + * be initialized to L=D=I in the Core module and then modified by the Modify + * module. It must be freed with cholmod_free_factor, defined below. + * + * The Core routines for each object are described below. Each list is split + * into two parts: the primary routines and secondary routines. + * + * ============================================================================ + * === cholmod_common ========================================================= + * ============================================================================ + * + * The Common object contains control parameters, statistics, and + * You must call cholmod_start before calling any other CHOLMOD routine, and + * must call cholmod_finish as your last call to CHOLMOD, with two exceptions: + * you may call cholmod_print_common and cholmod_check_common in the Check + * module after calling cholmod_finish. + * + * cholmod_start first call to CHOLMOD + * cholmod_finish last call to CHOLMOD + * ----------------------------- + * cholmod_defaults restore default parameters + * cholmod_maxrank maximum rank for update/downdate + * cholmod_allocate_work allocate workspace in Common + * cholmod_free_work free workspace in Common + * cholmod_clear_flag clear Flag workspace in Common + * cholmod_error called when CHOLMOD encounters an error + * cholmod_dbound for internal use in CHOLMOD only + * cholmod_hypot compute sqrt (x*x + y*y) accurately + * cholmod_divcomplex complex division, c = a/b + * + * ============================================================================ + * === cholmod_sparse ========================================================= + * ============================================================================ + * + * A sparse matrix is held in compressed column form. In the basic type + * ("packed", which corresponds to a MATLAB sparse matrix), an n-by-n matrix + * with nz entries is held in three arrays: p of size n+1, i of size nz, and x + * of size nz. Row indices of column j are held in i [p [j] ... p [j+1]-1] and + * in the same locations in x. There may be no duplicate entries in a column. + * Row indices in each column may be sorted or unsorted (CHOLMOD keeps track). + * A->stype determines the storage mode: 0 if both upper/lower parts are stored, + * -1 if A is symmetric and just tril(A) is stored, +1 if symmetric and triu(A) + * is stored. + * + * cholmod_allocate_sparse allocate a sparse matrix + * cholmod_free_sparse free a sparse matrix + * ----------------------------- + * cholmod_reallocate_sparse change the size (# entries) of sparse matrix + * cholmod_nnz number of nonzeros in a sparse matrix + * cholmod_speye sparse identity matrix + * cholmod_spzeros sparse zero matrix + * cholmod_transpose transpose a sparse matrix + * cholmod_ptranspose transpose/permute a sparse matrix + * cholmod_transpose_unsym transpose/permute an unsymmetric sparse matrix + * cholmod_transpose_sym transpose/permute a symmetric sparse matrix + * cholmod_sort sort row indices in each column of sparse matrix + * cholmod_band C = tril (triu (A,k1), k2) + * cholmod_band_inplace A = tril (triu (A,k1), k2) + * cholmod_aat C = A*A' + * cholmod_copy_sparse C = A, create an exact copy of a sparse matrix + * cholmod_copy C = A, with possible change of stype + * cholmod_add C = alpha*A + beta*B + * cholmod_sparse_xtype change the xtype of a sparse matrix + * + * ============================================================================ + * === cholmod_factor ========================================================= + * ============================================================================ + * + * The data structure for an LL' or LDL' factorization is too complex to + * describe in one sentence. This object can hold the symbolic analysis alone, + * or in combination with a "simplicial" (similar to a sparse matrix) or + * "supernodal" form of the numerical factorization. Only the routine to free + * a factor is primary, since a factor object is created by the factorization + * routine (cholmod_factorize). It must be freed with cholmod_free_factor. + * + * cholmod_free_factor free a factor + * ----------------------------- + * cholmod_allocate_factor allocate a factor (LL' or LDL') + * cholmod_reallocate_factor change the # entries in a factor + * cholmod_change_factor change the type of factor (e.g., LDL' to LL') + * cholmod_pack_factor pack the columns of a factor + * cholmod_reallocate_column resize a single column of a factor + * cholmod_factor_to_sparse create a sparse matrix copy of a factor + * cholmod_copy_factor create a copy of a factor + * cholmod_factor_xtype change the xtype of a factor + * + * Note that there is no cholmod_sparse_to_factor routine to create a factor + * as a copy of a sparse matrix. It could be done, after a fashion, but a + * lower triangular sparse matrix would not necessarily have a chordal graph, + * which would break the many CHOLMOD routines that rely on this property. + * + * ============================================================================ + * === cholmod_dense ========================================================== + * ============================================================================ + * + * The solve routines and some of the MatrixOps and Modify routines use dense + * matrices as inputs. These are held in column-major order. With a leading + * dimension of d, the entry in row i and column j is held in x [i+j*d]. + * + * cholmod_allocate_dense allocate a dense matrix + * cholmod_free_dense free a dense matrix + * ----------------------------- + * cholmod_zeros allocate a dense matrix of all zeros + * cholmod_ones allocate a dense matrix of all ones + * cholmod_eye allocate a dense identity matrix + * cholmod_sparse_to_dense create a dense matrix copy of a sparse matrix + * cholmod_dense_to_sparse create a sparse matrix copy of a dense matrix + * cholmod_copy_dense create a copy of a dense matrix + * cholmod_copy_dense2 copy a dense matrix (pre-allocated) + * cholmod_dense_xtype change the xtype of a dense matrix + * cholmod_ensure_dense ensure a dense matrix has a given size and type + * + * ============================================================================ + * === cholmod_triplet ======================================================== + * ============================================================================ + * + * A sparse matrix held in triplet form is the simplest one for a user to + * create. It consists of a list of nz entries in arbitrary order, held in + * three arrays: i, j, and x, each of length nk. The kth entry is in row i[k], + * column j[k], with value x[k]. There may be duplicate values; if A(i,j) + * appears more than once, its value is the sum of the entries with those row + * and column indices. + * + * cholmod_allocate_triplet allocate a triplet matrix + * cholmod_triplet_to_sparse create a sparse matrix copy of a triplet matrix + * cholmod_free_triplet free a triplet matrix + * ----------------------------- + * cholmod_reallocate_triplet change the # of entries in a triplet matrix + * cholmod_sparse_to_triplet create a triplet matrix copy of a sparse matrix + * cholmod_copy_triplet create a copy of a triplet matrix + * cholmod_triplet_xtype change the xtype of a triplet matrix + * + * ============================================================================ + * === memory management ====================================================== + * ============================================================================ + * + * cholmod_malloc malloc wrapper + * cholmod_calloc calloc wrapper + * cholmod_free free wrapper + * cholmod_realloc realloc wrapper + * cholmod_realloc_multiple realloc wrapper for multiple objects + * + * ============================================================================ + * === Core CHOLMOD prototypes ================================================ + * ============================================================================ + * + * All CHOLMOD routines (in all modules) use the following protocol for return + * values, with one exception: + * + * int TRUE (1) if successful, or FALSE (0) otherwise. + * (exception: cholmod_divcomplex) + * int32_t a value >= 0 if successful, or -1 otherwise. + * int64_t a value >= 0 if successful, or -1 otherwise. + * double a value >= 0 if successful, or -1 otherwise. + * size_t a value > 0 if successful, or 0 otherwise. + * void * a non-NULL pointer to newly allocated memory if + * successful, or NULL otherwise. + * cholmod_sparse * a non-NULL pointer to a newly allocated matrix + * if successful, or NULL otherwise. + * cholmod_factor * a non-NULL pointer to a newly allocated factor + * if successful, or NULL otherwise. + * cholmod_triplet * a non-NULL pointer to a newly allocated triplet + * matrix if successful, or NULL otherwise. + * cholmod_dense * a non-NULL pointer to a newly allocated triplet + * matrix if successful, or NULL otherwise. + * + * The last parameter to all routines is always a pointer to the CHOLMOD + * Common object. + * + * TRUE and FALSE are not defined here, since they may conflict with the user + * program. A routine that described here returning TRUE or FALSE returns 1 + * or 0, respectively. Any TRUE/FALSE parameter is true if nonzero, false if + * zero. + */ -// Define buffering parameters for GPU processing +/* ========================================================================== */ +/* === CHOLMOD version ====================================================== */ +/* ========================================================================== */ + +/* All versions of CHOLMOD will include the following definitions. + * As an example, to test if the version you are using is 1.3 or later: + * + * if (CHOLMOD_VERSION >= CHOLMOD_VER_CODE (1,3)) ... + * + * This also works during compile-time: + * + * #if CHOLMOD_VERSION >= CHOLMOD_VER_CODE (1,3) + * printf ("This is version 1.3 or later\n") ; + * #else + * printf ("This is version is earlier than 1.3\n") ; + * #endif + */ + +#define CHOLMOD_HAS_VERSION_FUNCTION +#define CHOLMOD_VER_CODE(main,sub) ((main) * 1000 + (sub)) +#define CHOLMOD_VERSION \ + CHOLMOD_VER_CODE(CHOLMOD_MAIN_VERSION,CHOLMOD_SUB_VERSION) + + +/* ========================================================================== */ +/* === CUDA BLAS for the GPU ================================================ */ +/* ========================================================================== */ + +/* Define buffering parameters for GPU processing */ #ifndef SUITESPARSE_GPU_EXTERN_ON #ifdef SUITESPARSE_CUDA #include @@ -218,520 +456,724 @@ int cholmod_l_version (int version [3]) ; #define CHOLMOD_HOST_SUPERNODE_BUFFERS 8 #define CHOLMOD_DEVICE_STREAMS 2 -//------------------------------------------------------------------------------ -// CHOLMOD objects -//------------------------------------------------------------------------------ +/* ========================================================================== */ +/* === CHOLMOD objects ====================================================== */ +/* ========================================================================== */ + +/* Each CHOLMOD object has its own type code. */ -// CHOLMOD object enums #define CHOLMOD_COMMON 0 #define CHOLMOD_SPARSE 1 #define CHOLMOD_FACTOR 2 #define CHOLMOD_DENSE 3 #define CHOLMOD_TRIPLET 4 -//------------------------------------------------------------------------------ -// CHOLMOD Common object -//------------------------------------------------------------------------------ +/* ========================================================================== */ +/* === CHOLMOD Common ======================================================= */ +/* ========================================================================== */ + +/* itype defines the types of integer used: */ +#define CHOLMOD_INT 0 /* all integer arrays are int32_t */ +#define CHOLMOD_INTLONG 1 /* most are int32_t, some are int64_t */ +#define CHOLMOD_LONG 2 /* all integer arrays are int64_t */ + +/* The itype of all parameters for all CHOLMOD routines must match. + * FUTURE WORK: CHOLMOD_INTLONG is not yet supported. + */ + +/* dtype defines what the numerical type is (double or float): */ +#define CHOLMOD_DOUBLE 0 /* all numerical values are double */ +#define CHOLMOD_SINGLE 1 /* all numerical values are float */ -// itype: integer sizes -// The itype is held in the Common object and must match the method used. -#define CHOLMOD_INT 0 /* int32, for cholmod_* methods (no _l_) */ -#define CHOLMOD_LONG 2 /* int64, for cholmod_l_* methods */ - -// dtype: floating point sizes (double or float) -// The dtype of all parameters for all CHOLMOD routines must match. -// NOTE: CHOLMOD_SINGLE is still under development. -#define CHOLMOD_DOUBLE 0 /* matrix or factorization is double precision */ -#define CHOLMOD_SINGLE 4 /* matrix or factorization is single precision */ - -// xtype: pattern, real, complex, or zomplex -#define CHOLMOD_PATTERN 0 /* no numerical values */ -#define CHOLMOD_REAL 1 /* real (double or single), not complex */ -#define CHOLMOD_COMPLEX 2 /* complex (double or single), interleaved */ -#define CHOLMOD_ZOMPLEX 3 /* complex (double or single), with real and imag */ - /* parts held in different arrays */ - -// xdtype is (xtype + dtype), which combines the two type parameters into -// a single number handling all 8 cases: -// -// (0) CHOLMOD_DOUBLE + CHOLMOD_PATTERN a pattern-only matrix -// (1) CHOLMOD_DOUBLE + CHOLMOD_REAL a double real matrix -// (2) CHOLMOD_DOUBLE + CHOLMOD_COMPLEX a double complex matrix -// (3) CHOLMOD_DOUBLE + CHOLMOD_ZOMPLEX a double zomplex matrix -// (4) CHOLMOD_SINGLE + CHOLMOD_PATTERN a pattern-only matrix -// (5) CHOLMOD_SINGLE + CHOLMOD_REAL a float real matrix -// (6) CHOLMOD_SINGLE + CHOLMOD_COMPLEX a float complex matrix -// (7) CHOLMOD_SINGLE + CHOLMOD_ZOMPLEX a float zomplex matrix - -// max # of ordering methods in Common -#define CHOLMOD_MAXMETHODS 9 - -// Common->status for error handling: 0 is ok, negative is a fatal error, -// and positive is a warning -#define CHOLMOD_OK (0) -#define CHOLMOD_NOT_INSTALLED (-1) /* module not installed */ -#define CHOLMOD_OUT_OF_MEMORY (-2) /* malloc, calloc, or realloc failed */ -#define CHOLMOD_TOO_LARGE (-3) /* integer overflow */ -#define CHOLMOD_INVALID (-4) /* input invalid */ -#define CHOLMOD_GPU_PROBLEM (-5) /* CUDA error */ -#define CHOLMOD_NOT_POSDEF (1) /* matrix not positive definite */ -#define CHOLMOD_DSMALL (2) /* diagonal entry very small */ - -// ordering method -#define CHOLMOD_NATURAL 0 /* no preordering */ -#define CHOLMOD_GIVEN 1 /* user-provided permutation */ -#define CHOLMOD_AMD 2 /* AMD: approximate minimum degree */ -#define CHOLMOD_METIS 3 /* METIS: mested dissection */ -#define CHOLMOD_NESDIS 4 /* CHOLMOD's nested dissection */ -#define CHOLMOD_COLAMD 5 /* AMD for A, COLAMD for AA' or A'A */ -#define CHOLMOD_POSTORDERED 6 /* natural then postordered */ - -// supernodal strategy -#define CHOLMOD_SIMPLICIAL 0 /* always use simplicial method */ -#define CHOLMOD_AUTO 1 /* auto select simplicial vs supernodal */ -#define CHOLMOD_SUPERNODAL 2 /* always use supernoda method */ +/* The dtype of all parameters for all CHOLMOD routines must match. + * + * Scalar floating-point values are always passed as double arrays of size 2 + * (for the real and imaginary parts). They are typecast to float as needed. + * FUTURE WORK: the float case is not supported yet. + */ + +/* xtype defines the kind of numerical values used: */ +#define CHOLMOD_PATTERN 0 /* pattern only, no numerical values */ +#define CHOLMOD_REAL 1 /* a real matrix */ +#define CHOLMOD_COMPLEX 2 /* a complex matrix (ANSI C99 compatible) */ +#define CHOLMOD_ZOMPLEX 3 /* a complex matrix (MATLAB compatible) */ + +/* The xtype of all parameters for all CHOLMOD routines must match. + * + * CHOLMOD_PATTERN: x and z are ignored. + * CHOLMOD_DOUBLE: x is non-null of size nzmax, z is ignored. + * CHOLMOD_COMPLEX: x is non-null of size 2*nzmax doubles, z is ignored. + * CHOLMOD_ZOMPLEX: x and z are non-null of size nzmax + * + * In the real case, z is ignored. The kth entry in the matrix is x [k]. + * There are two methods for the complex case. In the ANSI C99-compatible + * CHOLMOD_COMPLEX case, the real and imaginary parts of the kth entry + * are in x [2*k] and x [2*k+1], respectively. z is ignored. In the + * MATLAB-compatible CHOLMOD_ZOMPLEX case, the real and imaginary + * parts of the kth entry are in x [k] and z [k]. + * + * Scalar floating-point values are always passed as double arrays of size 2 + * (real and imaginary parts). The imaginary part of a scalar is ignored if + * the routine operates on a real matrix. + * + * These Modules support complex and zomplex matrices, with a few exceptions: + * + * Check all routines + * Cholesky all routines + * Core all except cholmod_aat, add, band, copy + * Demo all routines + * Partition all routines + * Supernodal all routines support any real, complex, or zomplex input. + * There will never be a supernodal zomplex L; a complex + * supernodal L is created if A is zomplex. + * Tcov all routines + * Valgrind all routines + * + * These Modules provide partial support for complex and zomplex matrices: + * + * MATLAB all routines support real and zomplex only, not complex, + * with the exception of ldlupdate, which supports + * real matrices only. This is a minor constraint since + * MATLAB's matrices are all real or zomplex. + * MatrixOps only norm_dense, norm_sparse, and sdmult support complex + * and zomplex + * + * These Modules do not support complex and zomplex matrices at all: + * + * Modify all routines support real matrices only + */ +/* Definitions for cholmod_common: */ +#define CHOLMOD_MAXMETHODS 9 /* maximum number of different methods that */ + /* cholmod_analyze can try. Must be >= 9. */ + +/* Common->status values. zero means success, negative means a fatal error, + * positive is a warning. */ +#define CHOLMOD_OK 0 /* success */ +#define CHOLMOD_NOT_INSTALLED (-1) /* failure: method not installed */ +#define CHOLMOD_OUT_OF_MEMORY (-2) /* failure: out of memory */ +#define CHOLMOD_TOO_LARGE (-3) /* failure: integer overflow occured */ +#define CHOLMOD_INVALID (-4) /* failure: invalid input */ +#define CHOLMOD_GPU_PROBLEM (-5) /* failure: GPU fatal error */ +#define CHOLMOD_NOT_POSDEF (1) /* warning: matrix not pos. def. */ +#define CHOLMOD_DSMALL (2) /* warning: D for LDL' or diag(L) or */ + /* LL' has tiny absolute value */ + +/* ordering method (also used for L->ordering) */ +#define CHOLMOD_NATURAL 0 /* use natural ordering */ +#define CHOLMOD_GIVEN 1 /* use given permutation */ +#define CHOLMOD_AMD 2 /* use minimum degree (AMD) */ +#define CHOLMOD_METIS 3 /* use METIS' nested dissection */ +#define CHOLMOD_NESDIS 4 /* use CHOLMOD's version of nested dissection:*/ + /* node bisector applied recursively, followed + * by constrained minimum degree (CSYMAMD or + * CCOLAMD) */ +#define CHOLMOD_COLAMD 5 /* use AMD for A, COLAMD for A*A' */ + +/* POSTORDERED is not a method, but a result of natural ordering followed by a + * weighted postorder. It is used for L->ordering, not method [ ].ordering. */ +#define CHOLMOD_POSTORDERED 6 /* natural ordering, postordered. */ + +/* supernodal strategy (for Common->supernodal) */ +#define CHOLMOD_SIMPLICIAL 0 /* always do simplicial */ +#define CHOLMOD_AUTO 1 /* select simpl/super depending on matrix */ +#define CHOLMOD_SUPERNODAL 2 /* always do supernodal */ + +/* make it easy for C++ programs to include CHOLMOD */ #ifdef __cplusplus extern "C" { #endif typedef struct cholmod_common_struct { + /* ---------------------------------------------------------------------- */ + /* parameters for symbolic/numeric factorization and update/downdate */ + /* ---------------------------------------------------------------------- */ + + double dbound ; /* Smallest absolute value of diagonal entries of D + * for LDL' factorization and update/downdate/rowadd/ + * rowdel, or the diagonal of L for an LL' factorization. + * Entries in the range 0 to dbound are replaced with dbound. + * Entries in the range -dbound to 0 are replaced with -dbound. No + * changes are made to the diagonal if dbound <= 0. Default: zero */ + + double grow0 ; /* For a simplicial factorization, L->i and L->x can + * grow if necessary. grow0 is the factor by which + * it grows. For the initial space, L is of size MAX (1,grow0) times + * the required space. If L runs out of space, the new size of L is + * MAX(1.2,grow0) times the new required space. If you do not plan on + * modifying the LDL' factorization in the Modify module, set grow0 to + * zero (or set grow2 to 0, see below). Default: 1.2 */ + + double grow1 ; + + size_t grow2 ; /* For a simplicial factorization, each column j of L + * is initialized with space equal to + * grow1*L->ColCount[j] + grow2. If grow0 < 1, grow1 < 1, or grow2 == 0, + * then the space allocated is exactly equal to L->ColCount[j]. If the + * column j runs out of space, it increases to grow1*need + grow2 in + * size, where need is the total # of nonzeros in that column. If you do + * not plan on modifying the factorization in the Modify module, set + * grow2 to zero. Default: grow1 = 1.2, grow2 = 5. */ + + size_t maxrank ; /* rank of maximum update/downdate. Valid values: + * 2, 4, or 8. A value < 2 is set to 2, and a + * value > 8 is set to 8. It is then rounded up to the next highest + * power of 2, if not already a power of 2. Workspace (Xwork, below) of + * size nrow-by-maxrank double's is allocated for the update/downdate. + * If an update/downdate of rank-k is requested, with k > maxrank, + * it is done in steps of maxrank. Default: 8, which is fastest. + * Memory usage can be reduced by setting maxrank to 2 or 4. + */ + + double supernodal_switch ; /* supernodal vs simplicial factorization */ + int supernodal ; /* If Common->supernodal <= CHOLMOD_SIMPLICIAL + * (0) then cholmod_analyze performs a + * simplicial analysis. If >= CHOLMOD_SUPERNODAL (2), then a supernodal + * analysis is performed. If == CHOLMOD_AUTO (1) and + * flop/nnz(L) < Common->supernodal_switch, then a simplicial analysis + * is done. A supernodal analysis done otherwise. + * Default: CHOLMOD_AUTO. Default supernodal_switch = 40 */ + + int final_asis ; /* If TRUE, then ignore the other final_* parameters + * (except for final_pack). + * The factor is left as-is when done. Default: TRUE.*/ + + int final_super ; /* If TRUE, leave a factor in supernodal form when + * supernodal factorization is finished. If FALSE, + * then convert to a simplicial factor when done. + * Default: TRUE */ + + int final_ll ; /* If TRUE, leave factor in LL' form when done. + * Otherwise, leave in LDL' form. Default: FALSE */ + + int final_pack ; /* If TRUE, pack the columns when done. If TRUE, and + * cholmod_factorize is called with a symbolic L, L is + * allocated with exactly the space required, using L->ColCount. If you + * plan on modifying the factorization, set Common->final_pack to FALSE, + * and each column will be given a little extra slack space for future + * growth in fill-in due to updates. Default: TRUE */ + + int final_monotonic ; /* If TRUE, ensure columns are monotonic when done. + * Default: TRUE */ + + int final_resymbol ;/* if cholmod_factorize performed a supernodal + * factorization, final_resymbol is true, and + * final_super is FALSE (convert a simplicial numeric factorization), + * then numerically zero entries that resulted from relaxed supernodal + * amalgamation are removed. This does not remove entries that are zero + * due to exact numeric cancellation, since doing so would break the + * update/downdate rowadd/rowdel routines. Default: FALSE. */ + + /* supernodal relaxed amalgamation parameters: */ + double zrelax [3] ; + size_t nrelax [3] ; + + /* Let ns be the total number of columns in two adjacent supernodes. + * Let z be the fraction of zero entries in the two supernodes if they + * are merged (z includes zero entries from prior amalgamations). The + * two supernodes are merged if: + * (ns <= nrelax [0]) || (no new zero entries added) || + * (ns <= nrelax [1] && z < zrelax [0]) || + * (ns <= nrelax [2] && z < zrelax [1]) || (z < zrelax [2]) + * + * Default parameters result in the following rule: + * (ns <= 4) || (no new zero entries added) || + * (ns <= 16 && z < 0.8) || (ns <= 48 && z < 0.1) || (z < 0.05) + */ + + int prefer_zomplex ; /* X = cholmod_solve (sys, L, B, Common) computes + * x=A\b or solves a related system. If L and B are + * both real, then X is real. Otherwise, X is returned as + * CHOLMOD_COMPLEX if Common->prefer_zomplex is FALSE, or + * CHOLMOD_ZOMPLEX if Common->prefer_zomplex is TRUE. This parameter + * is needed because there is no supernodal zomplex L. Suppose the + * caller wants all complex matrices to be stored in zomplex form + * (MATLAB, for example). A supernodal L is returned in complex form + * if A is zomplex. B can be real, and thus X = cholmod_solve (L,B) + * should return X as zomplex. This cannot be inferred from the input + * arguments L and B. Default: FALSE, since all data types are + * supported in CHOLMOD_COMPLEX form and since this is the native type + * of LAPACK and the BLAS. Note that the MATLAB/cholmod.c mexFunction + * sets this parameter to TRUE, since MATLAB matrices are in + * CHOLMOD_ZOMPLEX form. + */ + + int prefer_upper ; /* cholmod_analyze and cholmod_factorize work + * fastest when a symmetric matrix is stored in + * upper triangular form when a fill-reducing ordering is used. In + * MATLAB, this corresponds to how x=A\b works. When the matrix is + * ordered as-is, they work fastest when a symmetric matrix is in lower + * triangular form. In MATLAB, R=chol(A) does the opposite. This + * parameter affects only how cholmod_read returns a symmetric matrix. + * If TRUE (the default case), a symmetric matrix is always returned in + * upper-triangular form (A->stype = 1). */ + + int quick_return_if_not_posdef ; /* if TRUE, the supernodal numeric + * factorization will return quickly if + * the matrix is not positive definite. Default: FALSE. */ + + int prefer_binary ; /* cholmod_read_triplet converts a symmetric + * pattern-only matrix into a real matrix. If + * prefer_binary is FALSE, the diagonal entries are set to 1 + the degree + * of the row/column, and off-diagonal entries are set to -1 (resulting + * in a positive definite matrix if the diagonal is zero-free). Most + * symmetric patterns are the pattern a positive definite matrix. If + * this parameter is TRUE, then the matrix is returned with a 1 in each + * entry, instead. Default: FALSE. Added in v1.3. */ + + /* ---------------------------------------------------------------------- */ + /* printing and error handling options */ + /* ---------------------------------------------------------------------- */ + + int print ; /* print level. Default: 3 */ + int precise ; /* if TRUE, print 16 digits. Otherwise print 5 */ + + /* CHOLMOD print_function replaced with SuiteSparse_config print_func */ + + int try_catch ; /* if TRUE, then ignore errors; CHOLMOD is in the middle + * of a try/catch block. No error message is printed + * and the Common->error_handler function is not called. */ + + void (*error_handler) (int status, const char *file, + int line, const char *message) ; + + /* Common->error_handler is the user's error handling routine. If not + * NULL, this routine is called if an error occurs in CHOLMOD. status + * can be CHOLMOD_OK (0), negative for a fatal error, and positive for + * a warning. file is a string containing the name of the source code + * file where the error occured, and line is the line number in that + * file. message is a string describing the error in more detail. */ + + /* ---------------------------------------------------------------------- */ + /* ordering options */ + /* ---------------------------------------------------------------------- */ + + /* The cholmod_analyze routine can try many different orderings and select + * the best one. It can also try one ordering method multiple times, with + * different parameter settings. The default is to use three orderings, + * the user's permutation (if provided), AMD which is the fastest ordering + * and generally gives good fill-in, and METIS. CHOLMOD's nested dissection + * (METIS with a constrained AMD) usually gives a better ordering than METIS + * alone (by about 5% to 10%) but it takes more time. + * + * If you know the method that is best for your matrix, set Common->nmethods + * to 1 and set Common->method [0] to the set of parameters for that method. + * If you set it to 1 and do not provide a permutation, then only AMD will + * be called. + * + * If METIS is not available, the default # of methods tried is 2 (the user + * permutation, if any, and AMD). + * + * To try other methods, set Common->nmethods to the number of methods you + * want to try. The suite of default methods and their parameters is + * described in the cholmod_defaults routine, and summarized here: + * + * Common->method [i]: + * i = 0: user-provided ordering (cholmod_analyze_p only) + * i = 1: AMD (for both A and A*A') + * i = 2: METIS + * i = 3: CHOLMOD's nested dissection (NESDIS), default parameters + * i = 4: natural + * i = 5: NESDIS with nd_small = 20000 + * i = 6: NESDIS with nd_small = 4, no constrained minimum degree + * i = 7: NESDIS with no dense node removal + * i = 8: AMD for A, COLAMD for A*A' + * + * You can modify the suite of methods you wish to try by modifying + * Common.method [...] after calling cholmod_start or cholmod_defaults. + * + * For example, to use AMD, followed by a weighted postordering: + * + * Common->nmethods = 1 ; + * Common->method [0].ordering = CHOLMOD_AMD ; + * Common->postorder = TRUE ; + * + * To use the natural ordering (with no postordering): + * + * Common->nmethods = 1 ; + * Common->method [0].ordering = CHOLMOD_NATURAL ; + * Common->postorder = FALSE ; + * + * If you are going to factorize hundreds or more matrices with the same + * nonzero pattern, you may wish to spend a great deal of time finding a + * good permutation. In this case, try setting Common->nmethods to 9. + * The time spent in cholmod_analysis will be very high, but you need to + * call it only once. + * + * cholmod_analyze sets Common->current to a value between 0 and nmethods-1. + * Each ordering method uses the set of options defined by this parameter. + */ + + int nmethods ; /* The number of ordering methods to try. Default: 0. + * nmethods = 0 is a special case. cholmod_analyze + * will try the user-provided ordering (if given) and AMD. Let fl and + * lnz be the flop count and nonzeros in L from AMD's ordering. Let + * anz be the number of nonzeros in the upper or lower triangular part + * of the symmetric matrix A. If fl/lnz < 500 or lnz/anz < 5, then this + * is a good ordering, and METIS is not attempted. Otherwise, METIS is + * tried. The best ordering found is used. If nmethods > 0, the + * methods used are given in the method[ ] array, below. The first + * three methods in the default suite of orderings is (1) use the given + * permutation (if provided), (2) use AMD, and (3) use METIS. Maximum + * allowed value is CHOLMOD_MAXMETHODS. */ + + int current ; /* The current method being tried. Default: 0. Valid + * range is 0 to nmethods-1. */ + + int selected ; /* The best method found. */ + + /* The suite of ordering methods and parameters: */ - //-------------------------------------------------------------------------- - // primary parameters for factorization and update/downdate - //-------------------------------------------------------------------------- - - double dbound ; // Bounds the diagonal entries of D for LDL' - // factorization and update/downdate/rowadd. Entries outside this - // bound are replaced with dbound. Default: 0. - // dbound is used for double precision factorization only. - // See sbound for single precision factorization. - - double grow0 ; // default: 1.2 - double grow1 ; // default: 1.2 - size_t grow2 ; // default: 5 - // Initial space for simplicial factorization is max(grow0,1) times the - // required space. If space is exhausted, L is grown by - // max(grow0,1.2) times the required space. grow1 and grow2 control - // how each column of L can grow in an update/downdate; if space runs - // out, then grow1*(required space) + grow2 is allocated. - - size_t maxrank ; // maximum rank for update/downdate. Valid values are - // 2, 4, and 8. Default is 8. If a larger update/downdate is done, - // it is done in steps of maxrank. - - double supernodal_switch ; // default: 40 - int supernodal ; // default: CHOLMOD_AUTO. - // Controls supernodal vs simplicial factorization. If - // Common->supernodal is CHOLMOD_SIMPLICIAL, a simplicial factorization - // is always done; if CHOLMOD_SUPERNODAL, a supernodal factorization is - // always done. If CHOLMOD_AUTO, then a simplicial factorization is - // down if flops/nnz(L) < Common->supernodal_switch. - - int final_asis ; // if true, other final_* parameters are ignored, - // except for final_pack and the factors are left as-is when done. - // Default: true. - - int final_super ; // if true, leave factor in supernodal form. - // if false, convert to simplicial. Default: true. - - int final_ll ; // if true, simplicial factors are converted to LL', - // otherwise left as LDL. Default: false. - - int final_pack ; // if true, the factorize are allocated with exactly - // the space required. Set this to false if you expect future - // updates/downdates (giving a little extra space for future growth), - // Default: true. - - int final_monotonic ; // if true, columns are sorted when done, by - // ascending row index. Default: true. - - int final_resymbol ; // if true, a supernodal factorization converted - // to simplicial is reanalyzed, to remove zeros added for relaxed - // amalgamation. Default: false. - - double zrelax [3] ; size_t nrelax [3] ; - // The zrelax and nrelax parameters control relaxed supernodal - // amalgamation, If ns is the # of columns in two adjacent supernodes, - // and z is the fraction of zeros in the two supernodes if merged, then - // the two supernodes are merged if any of the 5 following condition - // are true: - // - // no new zero entries added if the two supernodes are merged - // (ns <= nrelax [0]) - // (ns <= nrelax [1] && z < zrelax [0]) - // (ns <= nrelax [2] && z < zrelax [1]) - // (z < zrelax [2]) - // - // With the defaults, the rules become: - // - // no new zero entries added if the two supernodes are merged - // (ns <= 4) - // (ns <= 16 && z < 0.8) - // (ns <= 48 && z < 0.1) - // (z < 0.05) - - int prefer_zomplex ; // if true, and a complex system is solved, - // X is returned as zomplex (with two arrays, one for the real part - // and one for the imaginary part). If false, then X is returned as - // a single array with interleaved real and imaginary parts. - // Default: false. - - int prefer_upper ; // if true, then a preference is given for holding - // a symmetric matrix by just its upper triangular form. This gives - // the best performance by the CHOLMOD analysis and factorization - // methods. Only used by cholmod_read. Default: true. - - int quick_return_if_not_posdef ; // if true, a supernodal factorization - // returns immediately if it finds the matrix is not positive definite. - // If false, the failed supernode is refactorized, up to but not - // including the failed column (required by MATLAB). - - int prefer_binary ; // if true, cholmod_read_triplet converts a symmetric - // pattern-only matrix to a real matrix with all values set to 1. - // if false, diagonal entries A(k,k) are set to one plus the # of - // entries in row/column k, and off-diagonals are set to -1. - // Default: false. - - int print ; // print level. Default is 3. - int precise ; // if true, print 16 digits, otherwise 5. Default: false. - - int try_catch ; // if true, ignore errors (CHOLMOD is assumed to be inside - // a try/catch block. No error messages are printed and the - // error_handler function is not called. Default: false. - - void (*error_handler) (int status, const char *file, int line, - const char *message) ; - // User error handling routine; default is NULL. - // This function is called if an error occurs, with parameters: - // status: the Common->status result. - // file: filename where the error occurred. - // line: line number where the error occurred. - // message: a string that describes the error. - - //-------------------------------------------------------------------------- - // ordering options - //-------------------------------------------------------------------------- - - // CHOLMOD can try many ordering options and then pick the best result it - // finds. The default is to use one or two orderings: the user's - // permutation (if given), and AMD. - - // Common->nmethods is the number of methods to try. If the - // Common->method array is left unmodified, the methods are: - - // (0) given (skipped if no user permutation) - // (1) amd - // (2) metis - // (3) nesdis with defaults (CHOLMOD's nested dissection, based on METIS) - // (4) natural - // (5) nesdis: stop at subgraphs of 20000 nodes - // (6) nesdis: stop at subgraphs of 4 nodes, do not use CAMD - // (7) nesdis: no pruning on of dense rows/cols - // (8) colamd - - // To use all 9 of the above methods, set Common->nmethods to 9. The - // analysis will take a long time, but that might be worth it if the - // ordering will be reused many many times. - - // Common->nmethods and Common->methods can be revised to use a different - // set of orderings. For example, to use just a single method - // (AMD with a weighted postordering): - // - // Common->nmethods = 1 ; - // Common->method [0].ordering = CHOLMOD_AMD ; - // Common->postorder = TRUE ; - // - // - - int nmethods ; // Number of methods to try, default is 0. - // The value of 0 is a special case, and tells CHOLMOD to use the user - // permutation (if not NULL) and then AMD. Next, if fl is lnz are the - // flop counts and number of nonzeros in L as found by AMD, then the - // this ordering is used if fl/lnz < 500 or lnz/anz < 5, where anz is - // the number of entries in A. If this condition fails, METIS is tried - // as well. - // - // Otherwise, if Common->nmethods > 0, then the methods defined by - // Common->method [0 ... Common->nmethods-1] are used. - - int current ; // The current method being tried in the analysis. - int selected ; // The selected method: Common->method [Common->selected] - - // The Common->method parameter is an array of structs that defines up - // to 9 methods: struct cholmod_method_struct { + /* statistics for this method */ + double lnz ; /* nnz(L) excl. zeros from supernodal amalgamation, + * for a "pure" L */ + + double fl ; /* flop count for a "pure", real simplicial LL' + * factorization, with no extra work due to + * amalgamation. Subtract n to get the LDL' flop count. Multiply + * by about 4 if the matrix is complex or zomplex. */ + + /* ordering method parameters */ + double prune_dense ;/* dense row/col control for AMD, SYMAMD, CSYMAMD, + * and NESDIS (cholmod_nested_dissection). For a + * symmetric n-by-n matrix, rows/columns with more than + * MAX (16, prune_dense * sqrt (n)) entries are removed prior to + * ordering. They appear at the end of the re-ordered matrix. + * + * If prune_dense < 0, only completely dense rows/cols are removed. + * + * This paramater is also the dense column control for COLAMD and + * CCOLAMD. For an m-by-n matrix, columns with more than + * MAX (16, prune_dense * sqrt (MIN (m,n))) entries are removed prior + * to ordering. They appear at the end of the re-ordered matrix. + * CHOLMOD factorizes A*A', so it calls COLAMD and CCOLAMD with A', + * not A. Thus, this parameter affects the dense *row* control for + * CHOLMOD's matrix, and the dense *column* control for COLAMD and + * CCOLAMD. + * + * Removing dense rows and columns improves the run-time of the + * ordering methods. It has some impact on ordering quality + * (usually minimal, sometimes good, sometimes bad). + * + * Default: 10. */ + + double prune_dense2 ;/* dense row control for COLAMD and CCOLAMD. + * Rows with more than MAX (16, dense2 * sqrt (n)) + * for an m-by-n matrix are removed prior to ordering. CHOLMOD's + * matrix is transposed before ordering it with COLAMD or CCOLAMD, + * so this controls the dense *columns* of CHOLMOD's matrix, and + * the dense *rows* of COLAMD's or CCOLAMD's matrix. + * + * If prune_dense2 < 0, only completely dense rows/cols are removed. + * + * Default: -1. Note that this is not the default for COLAMD and + * CCOLAMD. -1 is best for Cholesky. 10 is best for LU. */ + + double nd_oksep ; /* in NESDIS, when a node separator is computed, it + * discarded if nsep >= nd_oksep*n, where nsep is + * the number of nodes in the separator, and n is the size of the + * graph being cut. Valid range is 0 to 1. If 1 or greater, the + * separator is discarded if it consists of the entire graph. + * Default: 1 */ + + double other_1 [4] ; /* future expansion */ + + size_t nd_small ; /* do not partition graphs with fewer nodes than + * nd_small, in NESDIS. Default: 200 (same as + * METIS) */ + + size_t other_2 [4] ; /* future expansion */ + + int aggressive ; /* Aggresive absorption in AMD, COLAMD, SYMAMD, + * CCOLAMD, and CSYMAMD. Default: TRUE */ + + int order_for_lu ; /* CCOLAMD can be optimized to produce an ordering + * for LU or Cholesky factorization. CHOLMOD only + * performs a Cholesky factorization. However, you may wish to use + * CHOLMOD as an interface for CCOLAMD but use it for your own LU + * factorization. In this case, order_for_lu should be set to FALSE. + * When factorizing in CHOLMOD itself, you should *** NEVER *** set + * this parameter FALSE. Default: TRUE. */ + + int nd_compress ; /* If TRUE, compress the graph and subgraphs before + * partitioning them in NESDIS. Default: TRUE */ + + int nd_camd ; /* If 1, follow the nested dissection ordering + * with a constrained minimum degree ordering that + * respects the partitioning just found (using CAMD). If 2, use + * CSYMAMD instead. If you set nd_small very small, you may not need + * this ordering, and can save time by setting it to zero (no + * constrained minimum degree ordering). Default: 1. */ + + int nd_components ; /* The nested dissection ordering finds a node + * separator that splits the graph into two parts, + * which may be unconnected. If nd_components is TRUE, each of + * these connected components is split independently. If FALSE, + * each part is split as a whole, even if it consists of more than + * one connected component. Default: FALSE */ + + /* fill-reducing ordering to use */ + int ordering ; + + size_t other_3 [4] ; /* future expansion */ + + } method [CHOLMOD_MAXMETHODS + 1] ; + + int postorder ; /* If TRUE, cholmod_analyze follows the ordering with a + * weighted postorder of the elimination tree. Improves + * supernode amalgamation. Does not affect fundamental nnz(L) and + * flop count. Default: TRUE. */ + + int default_nesdis ; /* Default: FALSE. If FALSE, then the default + * ordering strategy (when Common->nmethods == 0) + * is to try the given ordering (if present), AMD, and then METIS if AMD + * reports high fill-in. If Common->default_nesdis is TRUE then NESDIS + * is used instead in the default strategy. */ + + /* ---------------------------------------------------------------------- */ + /* memory management, complex divide, and hypot function pointers moved */ + /* ---------------------------------------------------------------------- */ + + /* Function pointers moved from here (in CHOLMOD 2.2.0) to + SuiteSparse_config.[ch]. See CHOLMOD/Include/cholmod_back.h + for a set of macros that can be #include'd or copied into your + application to define these function pointers on any version of CHOLMOD. + */ + + /* ---------------------------------------------------------------------- */ + /* METIS workarounds */ + /* ---------------------------------------------------------------------- */ + + /* These workarounds were put into place for METIS 4.0.1. They are safe + to use with METIS 5.1.0, but they might not longer be necessary. */ + + double metis_memory ; /* This is a parameter for CHOLMOD's interface to + * METIS, not a parameter to METIS itself. METIS + * uses an amount of memory that is difficult to estimate precisely + * beforehand. If it runs out of memory, it terminates your program. + * All routines in CHOLMOD except for CHOLMOD's interface to METIS + * return an error status and safely return to your program if they run + * out of memory. To mitigate this problem, the CHOLMOD interface + * can allocate a single block of memory equal in size to an empirical + * upper bound of METIS's memory usage times the Common->metis_memory + * parameter, and then immediately free it. It then calls METIS. If + * this pre-allocation fails, it is possible that METIS will fail as + * well, and so CHOLMOD returns with an out-of-memory condition without + * calling METIS. + * + * METIS_NodeND (used in the CHOLMOD_METIS ordering option) with its + * default parameter settings typically uses about (4*nz+40n+4096) + * times sizeof(int) memory, where nz is equal to the number of entries + * in A for the symmetric case or AA' if an unsymmetric matrix is + * being ordered (where nz includes both the upper and lower parts + * of A or AA'). The observed "upper bound" (with 2 exceptions), + * measured in an instrumented copy of METIS 4.0.1 on thousands of + * matrices, is (10*nz+50*n+4096) * sizeof(int). Two large matrices + * exceeded this bound, one by almost a factor of 2 (Gupta/gupta2). + * + * If your program is terminated by METIS, try setting metis_memory to + * 2.0, or even higher if needed. By default, CHOLMOD assumes that METIS + * does not have this problem (so that CHOLMOD will work correctly when + * this issue is fixed in METIS). Thus, the default value is zero. + * This work-around is not guaranteed anyway. + * + * If a matrix exceeds this predicted memory usage, AMD is attempted + * instead. It, too, may run out of memory, but if it does so it will + * not terminate your program. + */ + + double metis_dswitch ; /* METIS_NodeND in METIS 4.0.1 gives a seg */ + size_t metis_nswitch ; /* fault with one matrix of order n = 3005 and + * nz = 6,036,025. This is a very dense graph. + * The workaround is to use AMD instead of METIS for matrices of dimension + * greater than Common->metis_nswitch (default 3000) or more and with + * density of Common->metis_dswitch (default 0.66) or more. + * cholmod_nested_dissection has no problems with the same matrix, even + * though it uses METIS_ComputeVertexSeparator on this matrix. If this + * seg fault does not affect you, set metis_nswitch to zero or less, + * and CHOLMOD will not switch to AMD based just on the density of the + * matrix (it will still switch to AMD if the metis_memory parameter + * causes the switch). + */ + + /* ---------------------------------------------------------------------- */ + /* workspace */ + /* ---------------------------------------------------------------------- */ + + /* CHOLMOD has several routines that take less time than the size of + * workspace they require. Allocating and initializing the workspace would + * dominate the run time, unless workspace is allocated and initialized + * just once. CHOLMOD allocates this space when needed, and holds it here + * between calls to CHOLMOD. cholmod_start sets these pointers to NULL + * (which is why it must be the first routine called in CHOLMOD). + * cholmod_finish frees the workspace (which is why it must be the last + * call to CHOLMOD). + */ + + size_t nrow ; /* size of Flag and Head */ + int64_t mark ; /* mark value for Flag array */ + size_t iworksize ; /* size of Iwork. Upper bound: 6*nrow+ncol */ + size_t xworksize ; /* size of Xwork, in bytes. + * maxrank*nrow*sizeof(double) for update/downdate. + * 2*nrow*sizeof(double) otherwise */ + + /* initialized workspace: contents needed between calls to CHOLMOD */ + void *Flag ; /* size nrow, an integer array. Kept cleared between + * calls to cholmod rouines (Flag [i] < mark) */ + + void *Head ; /* size nrow+1, an integer array. Kept cleared between + * calls to cholmod routines (Head [i] = EMPTY) */ + + void *Xwork ; /* a double array. Its size varies. It is nrow for + * most routines (cholmod_rowfac, cholmod_add, + * cholmod_aat, cholmod_norm, cholmod_ssmult) for the real case, twice + * that when the input matrices are complex or zomplex. It is of size + * 2*nrow for cholmod_rowadd and cholmod_rowdel. For cholmod_updown, + * its size is maxrank*nrow where maxrank is 2, 4, or 8. Kept cleared + * between calls to cholmod (set to zero). */ + + /* uninitialized workspace, contents not needed between calls to CHOLMOD */ + void *Iwork ; /* size iworksize, 2*nrow+ncol for most routines, + * up to 6*nrow+ncol for cholmod_analyze. */ + + int itype ; /* If CHOLMOD_LONG, Flag, Head, and Iwork are + * int64_t. Otherwise all three are int. */ + + int dtype ; /* double or float */ + + /* Common->itype and Common->dtype are used to define the types of all + * sparse matrices, triplet matrices, dense matrices, and factors + * created using this Common struct. The itypes and dtypes of all + * parameters to all CHOLMOD routines must match. */ + + int no_workspace_reallocate ; /* this is an internal flag, used as a + * precaution by cholmod_analyze. It is normally false. If true, + * cholmod_allocate_work is not allowed to reallocate any workspace; + * they must use the existing workspace in Common (Iwork, Flag, Head, + * and Xwork). Added for CHOLMOD v1.1 */ + + /* ---------------------------------------------------------------------- */ + /* statistics */ + /* ---------------------------------------------------------------------- */ + + /* fl and lnz are set only in cholmod_analyze and cholmod_rowcolcounts, + * in the Cholesky modudle. modfl is set only in the Modify module. */ + + int status ; /* error code */ + double fl ; /* LL' flop count from most recent analysis */ + double lnz ; /* fundamental nz in L */ + double anz ; /* nonzeros in tril(A) if A is symmetric/lower, + * triu(A) if symmetric/upper, or tril(A*A') if + * unsymmetric, in last call to cholmod_analyze. */ + double modfl ; /* flop count from most recent update/downdate/ + * rowadd/rowdel (excluding flops to modify the + * solution to Lx=b, if computed) */ + size_t malloc_count ; /* # of objects malloc'ed minus the # free'd*/ + size_t memory_usage ; /* peak memory usage in bytes */ + size_t memory_inuse ; /* current memory usage in bytes */ + + double nrealloc_col ; /* # of column reallocations */ + double nrealloc_factor ;/* # of factor reallocations due to col. reallocs */ + double ndbounds_hit ; /* # of times diagonal modified by dbound */ + + double rowfacfl ; /* # of flops in last call to cholmod_rowfac */ + double aatfl ; /* # of flops to compute A(:,f)*A(:,f)' */ + + int called_nd ; /* TRUE if the last call to + * cholmod_analyze called NESDIS or METIS. */ + int blas_ok ; /* FALSE if SUITESPARSE_BLAS_INT overflow; + TRUE otherwise */ + + /* ---------------------------------------------------------------------- */ + /* SuiteSparseQR control parameters: */ + /* ---------------------------------------------------------------------- */ + + double SPQR_grain ; /* task size is >= max (total flops / grain) */ + double SPQR_small ; /* task size is >= small */ + int SPQR_shrink ; /* controls stack realloc method */ + int SPQR_nthreads ; /* number of TBB threads, 0 = auto */ + + /* ---------------------------------------------------------------------- */ + /* SuiteSparseQR statistics */ + /* ---------------------------------------------------------------------- */ + + /* was other1 [0:3] */ + double SPQR_flopcount ; /* flop count for SPQR */ + double SPQR_analyze_time ; /* analysis time in seconds for SPQR */ + double SPQR_factorize_time ; /* factorize time in seconds for SPQR */ + double SPQR_solve_time ; /* backsolve time in seconds */ + + /* was SPQR_xstat [0:3] */ + double SPQR_flopcount_bound ; /* upper bound on flop count */ + double SPQR_tol_used ; /* tolerance used */ + double SPQR_norm_E_fro ; /* Frobenius norm of dropped entries */ + + /* was SPQR_istat [0:9] */ + int64_t SPQR_istat [10] ; + + /* ---------------------------------------------------------------------- */ + /* GPU configuration and statistics */ + /* ---------------------------------------------------------------------- */ + + /* useGPU: 1 if gpu-acceleration is requested */ + /* 0 if gpu-acceleration is prohibited */ + /* -1 if gpu-acceleration is undefined in which case the */ + /* environment CHOLMOD_USE_GPU will be queried and used. */ + /* useGPU=-1 is only used by CHOLMOD and treated as 0 by SPQR */ + int useGPU; + + /* for CHOLMOD: */ + size_t maxGpuMemBytes; + double maxGpuMemFraction; + + /* for SPQR: */ + size_t gpuMemorySize; /* Amount of memory in bytes on the GPU */ + double gpuKernelTime; /* Time taken by GPU kernels */ + int64_t gpuFlops; /* Number of flops performed by the GPU */ + int gpuNumKernelLaunches; /* Number of GPU kernel launches */ + + /* If not using the GPU, these items are not used, but they should be + present so that the CHOLMOD Common has the same size whether the GPU + is used or not. This way, all packages will agree on the size of + the CHOLMOD Common, regardless of whether or not they are compiled + with the GPU libraries or not */ - //---------------------------------------------------------------------- - // statistics from the ordering - //---------------------------------------------------------------------- - - double lnz ; // number of nonzeros in L - double fl ; // Cholesky flop count for this ordering (each - // multiply and each add counted once (doesn't count complex - // flops). - - //---------------------------------------------------------------------- - // ordering parameters: - //---------------------------------------------------------------------- - - double prune_dense ; // dense row/col control. Default: 10. - // Rows/cols with more than max (prune_dense*sqrt(n),16) are - // removed prior to orderingm and placed last. If negative, - // only completely dense rows/cols are removed. Removing these - // rows/cols with many entries can speed up the ordering, but - // removing too many can reduce the ordering quality. - // - // For AMD, SYMAMD, and CSYMAMD, this is the only dense row/col - // parameter. For COLAMD and CCOLAMD, this parameter controls - // how dense columns are handled. - - double prune_dense2 ; // dense row control for COLAMD and CCOLAMD. - // Default -1. When computing the Cholesky factorization of AA' - // rows with more than max(prune_dense2*sqrt(n),16) entries - // are removed prior to ordering. If negative, only completely - // dense rows are removed. - - double nd_oksep ; // for CHOLMOD's nesdis method. Default 1. - // A node separator with nsep nodes is discarded if - // nsep >= nd_oksep*n. - - double other_1 [4] ; // unused, for future expansion - - size_t nd_small ; // for CHOLMOD's nesdis method. Default 200. - // Subgraphs with fewer than nd_small nodes are not partitioned. - - double other_2 [4] ; // unused, for future expansion - - int aggressive ; // if true, AMD, COLAMD, SYMAMD, CCOLAMD, and - // CSYMAMD perform aggresive absorption. Default: true - - int order_for_lu ; // Default: false. If the CHOLMOD analysis/ - // ordering methods are used as an ordering method for an LU - // factorization, then set this to true. For use in a Cholesky - // factorization by CHOLMOD itself, never set this to true. - - int nd_compress ; // if true, then the graph and subgraphs are - // compressed before partitioning them in CHOLMOD's nesdis - // method. Default: true. - - int nd_camd ; // if 1, then CHOLMOD's nesdis is followed by - // CAMD. If 2: followed by CSYMAMD. If nd_small is very small, - // then use 0, which skips CAMD or CSYMAMD. Default: 1. - - int nd_components ; // CHOLMOD's nesdis can partition a graph and then - // find that the subgraphs are unconnected. If true, each of these - // components is partitioned separately. If false, the whole - // subgraph is partitioned. Default: false. - - int ordering ; // ordering method to use - - size_t other_3 [4] ; // unused, for future expansion - - } - method [CHOLMOD_MAXMETHODS + 1] ; - - int postorder ; // if true, CHOLMOD performs a weighted postordering - // after its fill-reducing ordering, which improves supernodal - // amalgamation. Has no effect on flop count or nnz(L). - // Default: true. - - int default_nesdis ; // If false, then the default ordering strategy - // when Common->nmethods is zero is to try the user's permutation - // if given, then AMD, and then METIS if the AMD ordering results in - // a lot of fill-in. If true, then nesdis is used instead of METIS. - // Default: false. - - //-------------------------------------------------------------------------- - // METIS workarounds - //-------------------------------------------------------------------------- - - // These workarounds were put into place for METIS 4.0.1. They are safe - // to use with METIS 5.1.0, but they might not longer be necessary. - - double metis_memory ; // default: 0. If METIS terminates your - // program when it runs out of memory, try 2, or higher. - double metis_dswitch ; // default: 0.66 - size_t metis_nswitch ; // default: 3000 - // If a matrix has n > metis_nswitch and a density (nnz(A)/n^2) > - // metis_dswitch, then METIS is not used. - - //-------------------------------------------------------------------------- - // workspace - //-------------------------------------------------------------------------- - - // This workspace is kept in the CHOLMOD Common object. cholmod_start - // sets these arrays to NULL, and cholmod_finish frees them. - - size_t nrow ; // Flag has size nrow, Head has size nrow+1 - int64_t mark ; // Flag is cleared if Flag [0..nrow-1] < mark. - size_t iworksize ; // size of Iwork, in Ints (int32 or int64). - // This is at most 6*nrow + ncol. - size_t xworkbytes ; // size of Xwork, in bytes. for update/downdate: - // maxrank*nrow*sizeof(double or float), 2*nrow*sizeof(double or float) - // otherwise. NOTE: in CHOLMOD v4 and earlier, xworkwise was in terms - // of # of doubles, not # of bytes. - - void *Flag ; // size nrow. If this is "cleared" then - // Flag [i] < mark for all i = 0:nrow-1. Flag is kept cleared between - // calls to CHOLMOD. - - void *Head ; // size nrow+1. If Head [i] = EMPTY (-1) then that - // entry is "cleared". Head is kept cleared between calls to CHOLMOD. - - void *Xwork ; // a double or float array. It has size nrow for most - // routines, or 2*nrow if complex matrices are being handled. - // It has size 2*nrow for cholmod_rowadd/rowdel, and maxrank*nrow for - // cholmod_updown, where maxrank is 2, 4, or 8. Xwork is kept all - // zero between calls to CHOLMOD. - - void *Iwork ; // size iworksize integers (int32's or int64's). - // Uninitialized integer workspace, of size at most 6*nrow+ncol. - - int itype ; // cholmod_start (for int32's) sets this to CHOLMOD_INT, - // and cholmod_l_start sets this to CHOLMOD_LONG. It defines the - // integer sizes for th Flag, Head, and Iwork arrays, and also - // defines the integers for all objects created by CHOLMOD. - // The itype of the Common object must match the function name - // and all objects passed to it. - - int other_5 ; // unused: for future expansion - - int no_workspace_reallocate ; // an internal flag, usually false. - // This is set true to disable any reallocation of the workspace - // in the Common object. - - //-------------------------------------------------------------------------- - // statistics - //-------------------------------------------------------------------------- - - int status ; // status code (0: ok, negative: error, pos: warning - double fl ; // flop count from last analysis - double lnz ; // nnz(L) from last analysis - double anz ; // in last analysis: nnz(tril(A)) or nnz(triu(A)) if A - // symmetric, or tril(A*A') if A is unsymmetric. - double modfl ; // flop count from last update/downdate/rowadd/rowdel, - // not included the flops to revise the solution to Lx=b, - // if that was performed. - - size_t malloc_count ; // # of malloc'd objects not yet freed - size_t memory_usage ; // peak memory usage in bytes - size_t memory_inuse ; // current memory usage in bytes - - double nrealloc_col ; // # of column reallocations - double nrealloc_factor ;// # of factor reallocations due to col. reallocs - double ndbounds_hit ; // # of times diagonal modified by dbound - - double rowfacfl ; // flop count of cholmod_rowfac - double aatfl ; // flop count to compute A(:,f)*A(:,f)' - - int called_nd ; // true if last analysis used nesdis or METIS. - int blas_ok ; // true if no integer overflow has occured when trying to - // call the BLAS. The typical BLAS library uses 32-bit integers for - // its input parameters, even on a 64-bit platform. CHOLMOD uses int64 - // in its cholmod_l_* methods, and these must be typecast to the BLAS - // integer. If integer overflow occurs, this is set false. - - //-------------------------------------------------------------------------- - // SuiteSparseQR control parameters and statistics - //-------------------------------------------------------------------------- - - // SPQR uses the CHOLMOD Common object for its control and statistics. - // These parameters are not used by CHOLMOD itself. - - // control parameters: - double SPQR_grain ; // task size is >= max (total flops / grain) - double SPQR_small ; // task size is >= small - int SPQR_shrink ; // controls stack realloc method - int SPQR_nthreads ; // number of TBB threads, 0 = auto - - // statistics: - double SPQR_flopcount ; // flop count for SPQR - double SPQR_analyze_time ; // analysis time in seconds for SPQR - double SPQR_factorize_time ; // factorize time in seconds for SPQR - double SPQR_solve_time ; // backsolve time in seconds - double SPQR_flopcount_bound ; // upper bound on flop count - double SPQR_tol_used ; // tolerance used - double SPQR_norm_E_fro ; // Frobenius norm of dropped entries - - //-------------------------------------------------------------------------- - // Revised for CHOLMOD v5.0 - //-------------------------------------------------------------------------- - - // was size 10 in CHOLMOD v4.2; reduced to 8 in CHOLMOD v5: - int64_t SPQR_istat [8] ; // other statistics - - //-------------------------------------------------------------------------- - // Added for CHOLMOD v5.0 - //-------------------------------------------------------------------------- - - // These terms have been added to the CHOLMOD Common struct for v5.0, and - // on most systems they will total 16 bytes. The preceding term, - // SPQR_istat, was reduced by 16 bytes, since those last 2 entries were - // unused in CHOLMOD v4.2. As a result, the Common struct in v5.0 has the - // same size as v4.0, and all entries would normally be in the same offset, - // as well. This mitigates any changes between v4.0 and v5.0, and may make - // it easier to upgrade from v4 to v5. - - double nsbounds_hit ; // # of times diagonal modified by sbound. This - // ought to be int64_t, but ndbounds_hit was double in v4 - // (see above), so nsbounds_hit is made the same type for - // consistency. - float sbound ; // Same as dbound, but for single precision factorization. - float other_6 ; // for future expansion - - //-------------------------------------------------------------------------- - // GPU configuration and statistics - //-------------------------------------------------------------------------- - - int useGPU ; // 1 if GPU is requested for CHOLMOD - // 0 if GPU is not requested for CHOLMOD - // -1 if the use of the GPU is in CHOLMOD controled by the - // CHOLMOD_USE_GPU environment variable. - - size_t maxGpuMemBytes ; // GPU control for CHOLMOD - double maxGpuMemFraction ; // GPU control for CHOLMOD - - // for SPQR: - size_t gpuMemorySize ; // Amount of memory in bytes on the GPU - double gpuKernelTime ; // Time taken by GPU kernels - int64_t gpuFlops ; // Number of flops performed by the GPU - int gpuNumKernelLaunches ; // Number of GPU kernel launches - - #ifdef SUITESPARSE_CUDA - // these three types are pointers defined by CUDA: - #define CHOLMOD_CUBLAS_HANDLE cublasHandle_t - #define CHOLMOD_CUDASTREAM cudaStream_t - #define CHOLMOD_CUDAEVENT cudaEvent_t - #else - // they are (void *) if CUDA is not in use: - #define CHOLMOD_CUBLAS_HANDLE void * - #define CHOLMOD_CUDASTREAM void * - #define CHOLMOD_CUDAEVENT void * - #endif +#ifdef SUITESPARSE_CUDA + /* in CUDA, these three types are pointers */ + #define CHOLMOD_CUBLAS_HANDLE cublasHandle_t + #define CHOLMOD_CUDASTREAM cudaStream_t + #define CHOLMOD_CUDAEVENT cudaEvent_t +#else + /* ... so make them void * pointers if the GPU is not being used */ + #define CHOLMOD_CUBLAS_HANDLE void * + #define CHOLMOD_CUDASTREAM void * + #define CHOLMOD_CUDAEVENT void * +#endif CHOLMOD_CUBLAS_HANDLE cublasHandle ; - // a set of streams for general use - CHOLMOD_CUDASTREAM gpuStream [CHOLMOD_HOST_SUPERNODE_BUFFERS] ; + /* a set of streams for general use */ + CHOLMOD_CUDASTREAM gpuStream[CHOLMOD_HOST_SUPERNODE_BUFFERS]; - CHOLMOD_CUDAEVENT cublasEventPotrf [3] ; - CHOLMOD_CUDAEVENT updateCKernelsComplete ; - CHOLMOD_CUDAEVENT updateCBuffersFree [CHOLMOD_HOST_SUPERNODE_BUFFERS] ; + CHOLMOD_CUDAEVENT cublasEventPotrf [3] ; + CHOLMOD_CUDAEVENT updateCKernelsComplete; + CHOLMOD_CUDAEVENT updateCBuffersFree[CHOLMOD_HOST_SUPERNODE_BUFFERS]; - void *dev_mempool ; // pointer to single allocation of device memory - size_t dev_mempool_size ; + void *dev_mempool; /* pointer to single allocation of device memory */ + size_t dev_mempool_size; - void *host_pinned_mempool ; // pointer to single alloc of pinned mem - size_t host_pinned_mempool_size ; + void *host_pinned_mempool; /* pointer to single allocation of pinned mem */ + size_t host_pinned_mempool_size; - size_t devBuffSize ; - int ibuffer ; - double syrkStart ; // time syrk started + size_t devBuffSize; + int ibuffer; - // run times of the different parts of CHOLMOD (GPU and CPU): + double syrkStart ; /* time syrk started */ + + /* run times of the different parts of CHOLMOD (GPU and CPU) */ double cholmod_cpu_gemm_time ; double cholmod_cpu_syrk_time ; double cholmod_cpu_trsm_time ; @@ -743,7 +1185,7 @@ typedef struct cholmod_common_struct double cholmod_assemble_time ; double cholmod_assemble_time2 ; - // number of times the BLAS are called on the CPU and the GPU: + /* number of times the BLAS are called on the CPU and the GPU */ size_t cholmod_cpu_gemm_calls ; size_t cholmod_cpu_syrk_calls ; size_t cholmod_cpu_trsm_calls ; @@ -753,16 +1195,15 @@ typedef struct cholmod_common_struct size_t cholmod_gpu_trsm_calls ; size_t cholmod_gpu_potrf_calls ; - double chunk ; // chunksize for computing # of OpenMP threads to use. - // Given nwork work to do, # of threads is - // max (1, min (floor (work / chunk), nthreads_max)) - - int nthreads_max ; // max # of OpenMP threads to use in CHOLMOD. - // Defaults to SUITESPARSE_OPENMP_MAX_THREADS. + double chunk ; // chunksize for computing # of threads to use. + // Given nwork work to do, # of threads is + // max (1, min (floor (work / chunk), nthreads_max)) + int nthreads_max ; // max # of threads to use in CHOLMOD. Defaults to + // SUITESPARSE_OPENMP_MAX_THREADS. } cholmod_common ; -// size_t BLAS statistcs in Common: +/* size_t BLAS statistcs in Common: */ #define CHOLMOD_CPU_GEMM_CALLS cholmod_cpu_gemm_calls #define CHOLMOD_CPU_SYRK_CALLS cholmod_cpu_syrk_calls #define CHOLMOD_CPU_TRSM_CALLS cholmod_cpu_trsm_calls @@ -772,7 +1213,7 @@ typedef struct cholmod_common_struct #define CHOLMOD_GPU_TRSM_CALLS cholmod_gpu_trsm_calls #define CHOLMOD_GPU_POTRF_CALLS cholmod_gpu_potrf_calls -// double BLAS statistics in Common: +/* double BLAS statistics in Common: */ #define CHOLMOD_CPU_GEMM_TIME cholmod_cpu_gemm_time #define CHOLMOD_CPU_SYRK_TIME cholmod_cpu_syrk_time #define CHOLMOD_CPU_TRSM_TIME cholmod_cpu_trsm_time @@ -784,1138 +1225,1422 @@ typedef struct cholmod_common_struct #define CHOLMOD_ASSEMBLE_TIME cholmod_assemble_time #define CHOLMOD_ASSEMBLE_TIME2 cholmod_assemble_time2 -// for supernodal analysis: +/* for supernodal analysis */ #define CHOLMOD_ANALYZE_FOR_SPQR 0 #define CHOLMOD_ANALYZE_FOR_CHOLESKY 1 #define CHOLMOD_ANALYZE_FOR_SPQRGPU 2 -//------------------------------------------------------------------------------ -// cholmod_start: first call to CHOLMOD -//------------------------------------------------------------------------------ +/* -------------------------------------------------------------------------- */ +/* cholmod_start: first call to CHOLMOD */ +/* -------------------------------------------------------------------------- */ + +int cholmod_start +( + cholmod_common *Common +) ; -int cholmod_start (cholmod_common *Common) ; int cholmod_l_start (cholmod_common *) ; -//------------------------------------------------------------------------------ -// cholmod_finish: last call to CHOLMOD -//------------------------------------------------------------------------------ +/* -------------------------------------------------------------------------- */ +/* cholmod_finish: last call to CHOLMOD */ +/* -------------------------------------------------------------------------- */ + +int cholmod_finish +( + cholmod_common *Common +) ; -int cholmod_finish (cholmod_common *Common) ; int cholmod_l_finish (cholmod_common *) ; -//------------------------------------------------------------------------------ -// cholmod_defaults: set default parameters -//------------------------------------------------------------------------------ +/* -------------------------------------------------------------------------- */ +/* cholmod_defaults: restore default parameters */ +/* -------------------------------------------------------------------------- */ + +int cholmod_defaults +( + cholmod_common *Common +) ; -int cholmod_defaults (cholmod_common *Common) ; int cholmod_l_defaults (cholmod_common *) ; -//------------------------------------------------------------------------------ -// cholmod_maxrank: return valid maximum rank for update/downdate -//------------------------------------------------------------------------------ +/* -------------------------------------------------------------------------- */ +/* cholmod_maxrank: return valid maximum rank for update/downdate */ +/* -------------------------------------------------------------------------- */ -size_t cholmod_maxrank // return validated Common->maxrank +size_t cholmod_maxrank /* returns validated value of Common->maxrank */ ( - size_t n, // # of rows of L and A + /* ---- input ---- */ + size_t n, /* A and L will have n rows */ + /* --------------- */ cholmod_common *Common ) ; -size_t cholmod_l_maxrank (size_t, cholmod_common *) ; -//------------------------------------------------------------------------------ -// cholmod_allocate_work: allocate workspace in Common -//------------------------------------------------------------------------------ +size_t cholmod_l_maxrank (size_t, cholmod_common *) ; -// This method always allocates Xwork as double, for backward compatibility -// with CHOLMOD v4 and earlier. See cholmod_alloc_work for CHOLMOD v5. +/* -------------------------------------------------------------------------- */ +/* cholmod_allocate_work: allocate workspace in Common */ +/* -------------------------------------------------------------------------- */ int cholmod_allocate_work ( - size_t nrow, // size of Common->Flag (nrow int32's) - // and Common->Head (nrow+1 int32's) - size_t iworksize, // size of Common->Iwork (# of int32's) - size_t xworksize, // size of Common->Xwork (# of double's) + /* ---- input ---- */ + size_t nrow, /* size: Common->Flag (nrow), Common->Head (nrow+1) */ + size_t iworksize, /* size of Common->Iwork */ + size_t xworksize, /* size of Common->Xwork */ + /* --------------- */ cholmod_common *Common ) ; -int cholmod_l_allocate_work (size_t, size_t, size_t, cholmod_common *) ; -//------------------------------------------------------------------------------ -// cholmod_alloc_work: allocate workspace in Common -//------------------------------------------------------------------------------ +int cholmod_l_allocate_work (size_t, size_t, size_t, cholmod_common *) ; -// Added for CHOLMOD v5: allocates Xwork as either double or single. +/* -------------------------------------------------------------------------- */ +/* cholmod_free_work: free workspace in Common */ +/* -------------------------------------------------------------------------- */ -int cholmod_alloc_work +int cholmod_free_work ( - size_t nrow, // size of Common->Flag (nrow int32's) - // and Common->Head (nrow+1 int32's) - size_t iworksize, // size of Common->Iwork (# of int32's) - size_t xworksize, // size of Common->Xwork (# of entries) - int dtype, // CHOLMOD_DOUBLE or CHOLMOD_SINGLE cholmod_common *Common ) ; -int cholmod_l_alloc_work (size_t, size_t, size_t, int, cholmod_common *) ; - -//------------------------------------------------------------------------------ -// cholmod_free_work: free workspace in Common -//------------------------------------------------------------------------------ -int cholmod_free_work (cholmod_common *Common) ; int cholmod_l_free_work (cholmod_common *) ; -//------------------------------------------------------------------------------ -// cholmod_clear_flag: clear Flag workspace in Common -//------------------------------------------------------------------------------ +/* -------------------------------------------------------------------------- */ +/* cholmod_clear_flag: clear Flag workspace in Common */ +/* -------------------------------------------------------------------------- */ -// This macro is deprecated; do not use it: -#define CHOLMOD_CLEAR_FLAG(Common) \ -{ \ - Common->mark++ ; \ - if (Common->mark <= 0 || Common->mark >= INT32_MAX) \ - { \ - Common->mark = EMPTY ; \ - CHOLMOD (clear_flag) (Common) ; \ - } \ +/* use a macro for speed */ +#define CHOLMOD_CLEAR_FLAG(Common) \ +{ \ + Common->mark++ ; \ + if (Common->mark <= 0) \ + { \ + Common->mark = EMPTY ; \ + CHOLMOD (clear_flag) (Common) ; \ + } \ } -int64_t cholmod_clear_flag (cholmod_common *Common) ; +int64_t cholmod_clear_flag +( + cholmod_common *Common +) ; + int64_t cholmod_l_clear_flag (cholmod_common *) ; -//------------------------------------------------------------------------------ -// cholmod_error: called when CHOLMOD encounters an error -//------------------------------------------------------------------------------ +/* -------------------------------------------------------------------------- */ +/* cholmod_error: called when CHOLMOD encounters an error */ +/* -------------------------------------------------------------------------- */ int cholmod_error ( - int status, // Common->status - const char *file, // source file where error occurred - int line, // line number where error occurred - const char *message, // error message to print + /* ---- input ---- */ + int status, /* error status */ + const char *file, /* name of source code file where error occured */ + int line, /* line number in source code file where error occured*/ + const char *message,/* error message */ + /* --------------- */ cholmod_common *Common ) ; + int cholmod_l_error (int, const char *, int, const char *, cholmod_common *) ; -//------------------------------------------------------------------------------ -// cholmod_dbound and cholmod_sbound: for internal use in CHOLMOD only -//------------------------------------------------------------------------------ +/* -------------------------------------------------------------------------- */ +/* cholmod_dbound: for internal use in CHOLMOD only */ +/* -------------------------------------------------------------------------- */ -// These were once documented functions but no are no longer meant to be used -// by the user application. They remain here for backward compatibility. +double cholmod_dbound /* returns modified diagonal entry of D or L */ +( + /* ---- input ---- */ + double dj, /* diagonal entry of D for LDL' or L for LL' */ + /* --------------- */ + cholmod_common *Common +) ; -double cholmod_dbound (double, cholmod_common *) ; double cholmod_l_dbound (double, cholmod_common *) ; -float cholmod_sbound (float, cholmod_common *) ; -float cholmod_l_sbound (float, cholmod_common *) ; -//------------------------------------------------------------------------------ -// cholmod_hypot: compute sqrt (x*x + y*y) accurately -//------------------------------------------------------------------------------ +/* -------------------------------------------------------------------------- */ +/* cholmod_hypot: compute sqrt (x*x + y*y) accurately */ +/* -------------------------------------------------------------------------- */ + +double cholmod_hypot +( + /* ---- input ---- */ + double x, double y +) ; -double cholmod_hypot (double x, double y) ; double cholmod_l_hypot (double, double) ; -//------------------------------------------------------------------------------ -// cholmod_divcomplex: complex division, c = a/b -//------------------------------------------------------------------------------ +/* -------------------------------------------------------------------------- */ +/* cholmod_divcomplex: complex division, c = a/b */ +/* -------------------------------------------------------------------------- */ -int cholmod_divcomplex // return 1 if divide-by-zero, 0 if OK +int cholmod_divcomplex /* return 1 if divide-by-zero, 0 otherise */ ( - double ar, double ai, // a (real, imaginary) - double br, double bi, // b (real, imaginary) - double *cr, double *ci // c (real, imaginary) + /* ---- input ---- */ + double ar, double ai, /* real and imaginary parts of a */ + double br, double bi, /* real and imaginary parts of b */ + /* ---- output --- */ + double *cr, double *ci /* real and imaginary parts of c */ ) ; + int cholmod_l_divcomplex (double, double, double, double, double *, double *) ; -//============================================================================== -// cholmod_sparse: a sparse matrix in compressed-column (CSC) form -//============================================================================== + +/* ========================================================================== */ +/* === Core/cholmod_sparse ================================================== */ +/* ========================================================================== */ + +/* A sparse matrix stored in compressed-column form. */ typedef struct cholmod_sparse_struct { - size_t nrow ; // # of rows of the matrix - size_t ncol ; // # of colums of the matrix - size_t nzmax ; // max # of entries that can be held in the matrix - - // int32_t or int64_t arrays: - void *p ; // A->p [0..ncol], column "pointers" of the CSC matrix - void *i ; // A->i [0..nzmax-1], the row indices - - // for unpacked matrices only: - void *nz ; // A->nz [0..ncol-1], is the # of nonzeros in each col. - // This is NULL for a "packed" matrix (conventional CSC). - // For a packed matrix, the jth column is held in A->i and A->x in - // postions A->p [j] to A->p [j+1]-1, with no gaps between columns. - // For an "unpacked" matrix, there can be gaps between columns, so - // the jth columns appears in positions A-p [j] to - // A->p [j] + A->nz [j] - 1. - - // double or float arrays: - void *x ; // size nzmax or 2*nzmax, or NULL - void *z ; // size nzmax, or NULL - - int stype ; // A->stype defines what parts of the matrix is held: - // 0: the matrix is unsymmetric with both lower and upper parts stored. - // >0: the matrix is square and symmetric, with just the upper - // triangular part stored. - // <0: the matrix is square and symmetric, with just the lower - // triangular part stored. - - int itype ; // A->itype defines the integers used for A->p, A->i, and A->nz. - // if CHOLMOD_INT, these arrays are all of type int32_t. - // if CHOLMOD_LONG, these arrays are all of type int64_t. - int xtype ; // pattern, real, complex, or zomplex - int dtype ; // x and z are double or single - int sorted ; // true if columns are sorted, false otherwise - int packed ; // true if packed (A->nz ignored), false if unpacked + size_t nrow ; /* the matrix is nrow-by-ncol */ + size_t ncol ; + size_t nzmax ; /* maximum number of entries in the matrix */ + + /* pointers to int32_t or int64_t: */ + void *p ; /* p [0..ncol], the column pointers */ + void *i ; /* i [0..nzmax-1], the row indices */ + + /* for unpacked matrices only: */ + void *nz ; /* nz [0..ncol-1], the # of nonzeros in each col. In + * packed form, the nonzero pattern of column j is in + * A->i [A->p [j] ... A->p [j+1]-1]. In unpacked form, column j is in + * A->i [A->p [j] ... A->p [j]+A->nz[j]-1] instead. In both cases, the + * numerical values (if present) are in the corresponding locations in + * the array x (or z if A->xtype is CHOLMOD_ZOMPLEX). */ + + /* pointers to double or float: */ + void *x ; /* size nzmax or 2*nzmax, if present */ + void *z ; /* size nzmax, if present */ + + int stype ; /* Describes what parts of the matrix are considered: + * + * 0: matrix is "unsymmetric": use both upper and lower triangular parts + * (the matrix may actually be symmetric in pattern and value, but + * both parts are explicitly stored and used). May be square or + * rectangular. + * >0: matrix is square and symmetric, use upper triangular part. + * Entries in the lower triangular part are ignored. + * <0: matrix is square and symmetric, use lower triangular part. + * Entries in the upper triangular part are ignored. + * + * Note that stype>0 and stype<0 are different for cholmod_sparse and + * cholmod_triplet. See the cholmod_triplet data structure for more + * details. + */ + + int itype ; /* CHOLMOD_INT: p, i, and nz are int32_t. + * CHOLMOD_INTLONG: p is int64_t, + * i and nz are int32_t. + * CHOLMOD_LONG: p, i, and nz are int64_t */ + + int xtype ; /* pattern, real, complex, or zomplex */ + int dtype ; /* x and z are double or float */ + int sorted ; /* TRUE if columns are sorted, FALSE otherwise */ + int packed ; /* TRUE if packed (nz ignored), FALSE if unpacked + * (nz is required) */ } cholmod_sparse ; -//------------------------------------------------------------------------------ -// cholmod_allocate_sparse: allocate a sparse matrix -//------------------------------------------------------------------------------ +typedef struct cholmod_descendant_score_t +{ + double score ; + int64_t d ; +} +descendantScore ; + +/* For sorting descendant supernodes with qsort */ +int cholmod_score_comp (struct cholmod_descendant_score_t *i, + struct cholmod_descendant_score_t *j) ; + +int cholmod_l_score_comp (struct cholmod_descendant_score_t *i, + struct cholmod_descendant_score_t *j) ; + +/* -------------------------------------------------------------------------- */ +/* cholmod_allocate_sparse: allocate a sparse matrix */ +/* -------------------------------------------------------------------------- */ cholmod_sparse *cholmod_allocate_sparse ( - size_t nrow, // # of rows - size_t ncol, // # of columns - size_t nzmax, // max # of entries the matrix can hold - int sorted, // true if columns are sorted - int packed, // true if A is be packed (A->nz NULL), false if unpacked - int stype, // the stype of the matrix (unsym, tril, or triu) - int xdtype, // xtype + dtype of the matrix: - // (CHOLMOD_DOUBLE, _SINGLE) + - // (CHOLMOD_PATTERN, _REAL, _COMPLEX, or _ZOMPLEX) + /* ---- input ---- */ + size_t nrow, /* # of rows of A */ + size_t ncol, /* # of columns of A */ + size_t nzmax, /* max # of nonzeros of A */ + int sorted, /* TRUE if columns of A sorted, FALSE otherwise */ + int packed, /* TRUE if A will be packed, FALSE otherwise */ + int stype, /* stype of A */ + int xtype, /* CHOLMOD_PATTERN, _REAL, _COMPLEX, or _ZOMPLEX */ + /* --------------- */ cholmod_common *Common ) ; + cholmod_sparse *cholmod_l_allocate_sparse (size_t, size_t, size_t, int, int, int, int, cholmod_common *) ; -//------------------------------------------------------------------------------ -// cholmod_free_sparse: free a sparse matrix -//------------------------------------------------------------------------------ +/* -------------------------------------------------------------------------- */ +/* cholmod_free_sparse: free a sparse matrix */ +/* -------------------------------------------------------------------------- */ int cholmod_free_sparse ( - cholmod_sparse **A, // handle of sparse matrix to free + /* ---- in/out --- */ + cholmod_sparse **A, /* matrix to deallocate, NULL on output */ + /* --------------- */ cholmod_common *Common ) ; + int cholmod_l_free_sparse (cholmod_sparse **, cholmod_common *) ; -//------------------------------------------------------------------------------ -// cholmod_reallocate_sparse: change max # of entries in a sparse matrix -//------------------------------------------------------------------------------ +/* -------------------------------------------------------------------------- */ +/* cholmod_reallocate_sparse: change the size (# entries) of sparse matrix */ +/* -------------------------------------------------------------------------- */ int cholmod_reallocate_sparse ( - size_t nznew, // new max # of nonzeros the sparse matrix can hold - cholmod_sparse *A, // sparse matrix to reallocate + /* ---- input ---- */ + size_t nznew, /* new # of entries in A */ + /* ---- in/out --- */ + cholmod_sparse *A, /* matrix to reallocate */ + /* --------------- */ cholmod_common *Common ) ; -int cholmod_l_reallocate_sparse (size_t, cholmod_sparse *, cholmod_common *) ; -//------------------------------------------------------------------------------ -// cholmod_nnz: # of entries in a sparse matrix -//------------------------------------------------------------------------------ +int cholmod_l_reallocate_sparse ( size_t, cholmod_sparse *, cholmod_common *) ; -int64_t cholmod_nnz // return # of entries in the sparse matrix +/* -------------------------------------------------------------------------- */ +/* cholmod_nnz: return number of nonzeros in a sparse matrix */ +/* -------------------------------------------------------------------------- */ + +int64_t cholmod_nnz ( - cholmod_sparse *A, // sparse matrix to query + /* ---- input ---- */ + cholmod_sparse *A, + /* --------------- */ cholmod_common *Common ) ; + int64_t cholmod_l_nnz (cholmod_sparse *, cholmod_common *) ; -//------------------------------------------------------------------------------ -// cholmod_speye: sparse identity matrix (possibly rectangular) -//------------------------------------------------------------------------------ +/* -------------------------------------------------------------------------- */ +/* cholmod_speye: sparse identity matrix */ +/* -------------------------------------------------------------------------- */ cholmod_sparse *cholmod_speye ( - size_t nrow, // # of rows - size_t ncol, // # of columns - int xdtype, // xtype + dtype of the matrix: - // (CHOLMOD_DOUBLE, _SINGLE) + - // (CHOLMOD_PATTERN, _REAL, _COMPLEX, or _ZOMPLEX) + /* ---- input ---- */ + size_t nrow, /* # of rows of A */ + size_t ncol, /* # of columns of A */ + int xtype, /* CHOLMOD_PATTERN, _REAL, _COMPLEX, or _ZOMPLEX */ + /* --------------- */ cholmod_common *Common ) ; -cholmod_sparse *cholmod_l_speye (size_t, size_t, int, cholmod_common *) ; -//------------------------------------------------------------------------------ -// cholmod_spzeros: sparse matrix with no entries -//------------------------------------------------------------------------------ +cholmod_sparse *cholmod_l_speye (size_t, size_t, int, cholmod_common *) ; -// Identical to cholmod_allocate_sparse, with packed = true, sorted = true, -// and stype = 0. +/* -------------------------------------------------------------------------- */ +/* cholmod_spzeros: sparse zero matrix */ +/* -------------------------------------------------------------------------- */ -cholmod_sparse *cholmod_spzeros // return a sparse matrix with no entries +cholmod_sparse *cholmod_spzeros ( - size_t nrow, // # of rows - size_t ncol, // # of columns - size_t nzmax, // max # of entries the matrix can hold - int xdtype, // xtype + dtype of the matrix: - // (CHOLMOD_DOUBLE, _SINGLE) + - // (CHOLMOD_PATTERN, _REAL, _COMPLEX, or _ZOMPLEX) + /* ---- input ---- */ + size_t nrow, /* # of rows of A */ + size_t ncol, /* # of columns of A */ + size_t nzmax, /* max # of nonzeros of A */ + int xtype, /* CHOLMOD_PATTERN, _REAL, _COMPLEX, or _ZOMPLEX */ + /* --------------- */ cholmod_common *Common ) ; + cholmod_sparse *cholmod_l_spzeros (size_t, size_t, size_t, int, cholmod_common *) ; -//------------------------------------------------------------------------------ -// cholmod_transpose: transpose a sparse matrix -//------------------------------------------------------------------------------ +/* -------------------------------------------------------------------------- */ +/* cholmod_transpose: transpose a sparse matrix */ +/* -------------------------------------------------------------------------- */ + +/* Return A' or A.' The "values" parameter is 0, 1, or 2 to denote the pattern + * transpose, the array transpose (A.'), and the complex conjugate transpose + * (A'). + */ -cholmod_sparse *cholmod_transpose // return new sparse matrix C +cholmod_sparse *cholmod_transpose ( - cholmod_sparse *A, // input matrix - int mode, // 2: numerical (conj), 1: numerical (non-conj.), - // <= 0: pattern (with diag) + /* ---- input ---- */ + cholmod_sparse *A, /* matrix to transpose */ + int values, /* 0: pattern, 1: array transpose, 2: conj. transpose */ + /* --------------- */ cholmod_common *Common ) ; + cholmod_sparse *cholmod_l_transpose (cholmod_sparse *, int, cholmod_common *) ; -//------------------------------------------------------------------------------ -// cholmod_transpose_unsym: transpose an unsymmetric sparse matrix -//------------------------------------------------------------------------------ +/* -------------------------------------------------------------------------- */ +/* cholmod_transpose_unsym: transpose an unsymmetric sparse matrix */ +/* -------------------------------------------------------------------------- */ -// Compute C = A', A (:,f)', or A (p,f)', where A is unsymmetric and C is -// already allocated. See cholmod_transpose for a routine with a simpler -// interface. +/* Compute F = A', A (:,f)', or A (p,f)', where A is unsymmetric and F is + * already allocated. See cholmod_transpose for a simpler routine. */ int cholmod_transpose_unsym ( - cholmod_sparse *A, // input matrix - int mode, // 2: numerical (conj), 1: numerical (non-conj.), - // <= 0: pattern (with diag) - int32_t *Perm, // permutation for C=A(p,f)', or NULL - int32_t *fset, // a list of column indices in range 0:A->ncol-1 - size_t fsize, // # of entries in fset - cholmod_sparse *C, // output matrix, must be allocated on input + /* ---- input ---- */ + cholmod_sparse *A, /* matrix to transpose */ + int values, /* 0: pattern, 1: array transpose, 2: conj. transpose */ + int32_t *Perm, /* size nrow, if present (can be NULL) */ + int32_t *fset, /* subset of 0:(A->ncol)-1 */ + size_t fsize, /* size of fset */ + /* ---- output --- */ + cholmod_sparse *F, /* F = A', A(:,f)', or A(p,f)' */ + /* --------------- */ cholmod_common *Common ) ; -int cholmod_l_transpose_unsym (cholmod_sparse *, int, int64_t *, int64_t *, - size_t, cholmod_sparse *, cholmod_common *) ; -//------------------------------------------------------------------------------ -// cholmod_transpose_sym: symmetric permuted transpose -//------------------------------------------------------------------------------ +int cholmod_l_transpose_unsym (cholmod_sparse *, int, int64_t *, + int64_t *, size_t, cholmod_sparse *, cholmod_common *) ; -// C = A' or C = A(p,p)' where A and C are both symmetric and C is already -// allocated. See cholmod_transpose or cholmod_ptranspose for a routine with -// a simpler interface. +/* -------------------------------------------------------------------------- */ +/* cholmod_transpose_sym: transpose a symmetric sparse matrix */ +/* -------------------------------------------------------------------------- */ + +/* Compute F = A' or A (p,p)', where A is symmetric and F is already allocated. + * See cholmod_transpose for a simpler routine. */ int cholmod_transpose_sym ( - cholmod_sparse *A, // input matrix - int mode, // 2: numerical (conj), 1: numerical (non-conj.), - // <= 0: pattern (with diag) - int32_t *Perm, // permutation for C=A(p,p)', or NULL - cholmod_sparse *C, // output matrix, must be allocated on input + /* ---- input ---- */ + cholmod_sparse *A, /* matrix to transpose */ + int values, /* 0: pattern, 1: array transpose, 2: conj. transpose */ + int32_t *Perm, /* size nrow, if present (can be NULL) */ + /* ---- output --- */ + cholmod_sparse *F, /* F = A' or A(p,p)' */ + /* --------------- */ cholmod_common *Common ) ; -int cholmod_l_transpose_sym (cholmod_sparse *, int, int64_t *, cholmod_sparse *, - cholmod_common *) ; -//------------------------------------------------------------------------------ -// cholmod_ptranspose: C = A', A(:,f)', A(p,p)', or A(p,f)' -//------------------------------------------------------------------------------ +int cholmod_l_transpose_sym (cholmod_sparse *, int, int64_t *, + cholmod_sparse *, cholmod_common *) ; -cholmod_sparse *cholmod_ptranspose // return new sparse matrix C +/* -------------------------------------------------------------------------- */ +/* cholmod_ptranspose: transpose a sparse matrix */ +/* -------------------------------------------------------------------------- */ + +/* Return A' or A(p,p)' if A is symmetric. Return A', A(:,f)', or A(p,f)' if + * A is unsymmetric. */ + +cholmod_sparse *cholmod_ptranspose ( - cholmod_sparse *A, // input matrix - int mode, // 2: numerical (conj), 1: numerical (non-conj.), - // <= 0: pattern (with diag) - int32_t *Perm, // permutation for C=A(p,f)', or NULL - int32_t *fset, // a list of column indices in range 0:A->ncol-1 - size_t fsize, // # of entries in fset + /* ---- input ---- */ + cholmod_sparse *A, /* matrix to transpose */ + int values, /* 0: pattern, 1: array transpose, 2: conj. transpose */ + int32_t *Perm, /* if non-NULL, F = A(p,f) or A(p,p) */ + int32_t *fset, /* subset of 0:(A->ncol)-1 */ + size_t fsize, /* size of fset */ + /* --------------- */ cholmod_common *Common ) ; + cholmod_sparse *cholmod_l_ptranspose (cholmod_sparse *, int, int64_t *, int64_t *, size_t, cholmod_common *) ; -//------------------------------------------------------------------------------ -// cholmod_sort: sort the indices of a sparse matrix -//------------------------------------------------------------------------------ +/* -------------------------------------------------------------------------- */ +/* cholmod_sort: sort row indices in each column of sparse matrix */ +/* -------------------------------------------------------------------------- */ int cholmod_sort ( - cholmod_sparse *A, // input/output matrix to sort + /* ---- in/out --- */ + cholmod_sparse *A, /* matrix to sort */ + /* --------------- */ cholmod_common *Common ) ; + int cholmod_l_sort (cholmod_sparse *, cholmod_common *) ; -//------------------------------------------------------------------------------ -// cholmod_band_nnz: # of entries within a band of a sparse matrix -//------------------------------------------------------------------------------ +/* -------------------------------------------------------------------------- */ +/* cholmod_band: C = tril (triu (A,k1), k2) */ +/* -------------------------------------------------------------------------- */ -int64_t cholmod_band_nnz // return # of entries in a band (-1 if error) +cholmod_sparse *cholmod_band ( - cholmod_sparse *A, // matrix to examine - int64_t k1, // count entries in k1:k2 diagonals - int64_t k2, - bool ignore_diag, // if true, exclude any diagonal entries + /* ---- input ---- */ + cholmod_sparse *A, /* matrix to extract band matrix from */ + int64_t k1, /* ignore entries below the k1-st diagonal */ + int64_t k2, /* ignore entries above the k2-nd diagonal */ + int mode, /* >0: numerical, 0: pattern, <0: pattern (no diag) */ + /* --------------- */ cholmod_common *Common ) ; -int64_t cholmod_l_band_nnz (cholmod_sparse *, int64_t, int64_t, bool, - cholmod_common *) ; -//------------------------------------------------------------------------------ -// cholmod_band: C = tril (triu (A,k1), k2) -//------------------------------------------------------------------------------ +cholmod_sparse *cholmod_l_band (cholmod_sparse *, int64_t, + int64_t, int, cholmod_common *) ; -cholmod_sparse *cholmod_band // return a new matrix C -( - cholmod_sparse *A, // input matrix - int64_t k1, // count entries in k1:k2 diagonals - int64_t k2, - int mode, // >0: numerical, 0: pattern, <0: pattern (no diag) - cholmod_common *Common -) ; -cholmod_sparse *cholmod_l_band (cholmod_sparse *, int64_t, int64_t, int, - cholmod_common *) ; - -//------------------------------------------------------------------------------ -// cholmod_band_inplace: A = tril (triu (A,k1), k2) */ -//------------------------------------------------------------------------------ +/* -------------------------------------------------------------------------- */ +/* cholmod_band_inplace: A = tril (triu (A,k1), k2) */ +/* -------------------------------------------------------------------------- */ int cholmod_band_inplace ( - int64_t k1, // count entries in k1:k2 diagonals - int64_t k2, - int mode, // >0: numerical, 0: pattern, <0: pattern (no diag) - cholmod_sparse *A, // input/output matrix + /* ---- input ---- */ + int64_t k1, /* ignore entries below the k1-st diagonal */ + int64_t k2, /* ignore entries above the k2-nd diagonal */ + int mode, /* >0: numerical, 0: pattern, <0: pattern (no diag) */ + /* ---- in/out --- */ + cholmod_sparse *A, /* matrix from which entries not in band are removed */ + /* --------------- */ cholmod_common *Common ) ; -int cholmod_l_band_inplace (int64_t, int64_t, int, cholmod_sparse *, - cholmod_common *) ; -//------------------------------------------------------------------------------ -// cholmod_aat: C = A*A' or A(:,f)*A(:,f)' -//------------------------------------------------------------------------------ +int cholmod_l_band_inplace (int64_t, int64_t, int, + cholmod_sparse *, cholmod_common *) ; -cholmod_sparse *cholmod_aat // return sparse matrix C +/* -------------------------------------------------------------------------- */ +/* cholmod_aat: C = A*A' or A(:,f)*A(:,f)' */ +/* -------------------------------------------------------------------------- */ + +cholmod_sparse *cholmod_aat ( - cholmod_sparse *A, // input matrix - int32_t *fset, // a list of column indices in range 0:A->ncol-1 - size_t fsize, // # of entries in fset - int mode, // 2: numerical (conj), 1: numerical (non-conj.), - // 0: pattern (with diag), -1: pattern (remove diag), - // -2: pattern (remove diag; add ~50% extra space in C) + /* ---- input ---- */ + cholmod_sparse *A, /* input matrix; C=A*A' is constructed */ + int32_t *fset, /* subset of 0:(A->ncol)-1 */ + size_t fsize, /* size of fset */ + int mode, /* >0: numerical, 0: pattern, <0: pattern (no diag), + * -2: pattern only, no diagonal, add 50%+n extra + * space to C */ + /* --------------- */ cholmod_common *Common ) ; -cholmod_sparse *cholmod_l_aat (cholmod_sparse *, int64_t *, size_t, int, - cholmod_common *) ; -//------------------------------------------------------------------------------ -// cholmod_copy_sparse: C = A, create an exact copy of a sparse matrix -//------------------------------------------------------------------------------ +cholmod_sparse *cholmod_l_aat (cholmod_sparse *, int64_t *, size_t, + int, cholmod_common *) ; -// Creates an exact copy of a sparse matrix. For making a copy with a change -// of stype and/or copying the pattern of a numerical matrix, see cholmod_copy. -// For changing the xtype and/or dtype, see cholmod_sparse_xtype. +/* -------------------------------------------------------------------------- */ +/* cholmod_copy_sparse: C = A, create an exact copy of a sparse matrix */ +/* -------------------------------------------------------------------------- */ -cholmod_sparse *cholmod_copy_sparse // return new sparse matrix +cholmod_sparse *cholmod_copy_sparse ( - cholmod_sparse *A, // sparse matrix to copy + /* ---- input ---- */ + cholmod_sparse *A, /* matrix to copy */ + /* --------------- */ cholmod_common *Common ) ; + cholmod_sparse *cholmod_l_copy_sparse (cholmod_sparse *, cholmod_common *) ; -//------------------------------------------------------------------------------ -// cholmod_copy: C = A, with possible change of stype -//------------------------------------------------------------------------------ +/* -------------------------------------------------------------------------- */ +/* cholmod_copy: C = A, with possible change of stype */ +/* -------------------------------------------------------------------------- */ -cholmod_sparse *cholmod_copy // return new sparse matrix +cholmod_sparse *cholmod_copy ( - cholmod_sparse *A, // input matrix, not modified - int stype, // stype of C - int mode, // 2: numerical (conj), 1: numerical (non-conj.), - // 0: pattern (with diag), -1: pattern (remove diag), - // -2: pattern (remove diag; add ~50% extra space in C) + /* ---- input ---- */ + cholmod_sparse *A, /* matrix to copy */ + int stype, /* requested stype of C */ + int mode, /* >0: numerical, 0: pattern, <0: pattern (no diag) */ + /* --------------- */ cholmod_common *Common ) ; + cholmod_sparse *cholmod_l_copy (cholmod_sparse *, int, int, cholmod_common *) ; -//------------------------------------------------------------------------------ -// cholmod_add: C = alpha*A + beta*B -//------------------------------------------------------------------------------ +/* -------------------------------------------------------------------------- */ +/* cholmod_add: C = alpha*A + beta*B */ +/* -------------------------------------------------------------------------- */ -cholmod_sparse *cholmod_add // return C = alpha*A + beta*B +cholmod_sparse *cholmod_add ( - cholmod_sparse *A, // input matrix - cholmod_sparse *B, // input matrix - double alpha [2], // scale factor for A (two entires used if complex) - double beta [2], // scale factor for A (two entires used if complex) - int values, // if TRUE compute the numerical values of C - int sorted, // ignored; C is now always returned as sorted + /* ---- input ---- */ + cholmod_sparse *A, /* matrix to add */ + cholmod_sparse *B, /* matrix to add */ + double alpha [2], /* scale factor for A */ + double beta [2], /* scale factor for B */ + int values, /* if TRUE compute the numerical values of C */ + int sorted, /* if TRUE, sort columns of C */ + /* --------------- */ cholmod_common *Common ) ; + cholmod_sparse *cholmod_l_add (cholmod_sparse *, cholmod_sparse *, double *, double *, int, int, cholmod_common *) ; -//------------------------------------------------------------------------------ -// cholmod_sparse_xtype: change the xtype and/or dtype of a sparse matrix -//------------------------------------------------------------------------------ +/* -------------------------------------------------------------------------- */ +/* cholmod_sparse_xtype: change the xtype of a sparse matrix */ +/* -------------------------------------------------------------------------- */ int cholmod_sparse_xtype ( - int to_xdtype, // requested xtype and dtype - cholmod_sparse *A, // sparse matrix to change + /* ---- input ---- */ + int to_xtype, /* requested xtype (pattern, real, complex, zomplex) */ + /* ---- in/out --- */ + cholmod_sparse *A, /* sparse matrix to change */ + /* --------------- */ cholmod_common *Common ) ; + int cholmod_l_sparse_xtype (int, cholmod_sparse *, cholmod_common *) ; -//============================================================================== -// cholmod_factor: symbolic or numeric factorization (simplicial or supernodal) -//============================================================================== + +/* ========================================================================== */ +/* === Core/cholmod_factor ================================================== */ +/* ========================================================================== */ + +/* A symbolic and numeric factorization, either simplicial or supernodal. + * In all cases, the row indices in the columns of L are kept sorted. */ typedef struct cholmod_factor_struct { - size_t n ; // L is n-by-n - - size_t minor ; // If the factorization failed because of numerical issues - // (the matrix being factorized is found to be singular or not positive - // definte), then L->minor is the column at which it failed. L->minor - // = n means the factorization was successful. - - //-------------------------------------------------------------------------- - // symbolic ordering and analysis - //-------------------------------------------------------------------------- - - void *Perm ; // int32/int64, size n, fill-reducing ordering - void *ColCount ;// int32/int64, size n, # entries in each column of L - void *IPerm ; // int32/int64, size n, created by cholmod_solve2; - // containing the inverse of L->Perm - - //-------------------------------------------------------------------------- - // simplicial factorization (not supernodal) - //-------------------------------------------------------------------------- - - size_t nzmax ; // # of entries that L->i, L->x, and L->z can hold - - void *p ; // int32/int64, size n+1, column pointers - void *i ; // int32/int64, size nzmax, row indices - void *x ; // float/double, size nzmax or 2*nzmax, numerical values - void *z ; // float/double, size nzmax or empty, imaginary values - void *nz ; // int32/int64, size ncol, # of entries in each column - - // The row indices of L(:,j) are held in - // L->i [L->p [j] ... L->p [j] + L->nz [j] - 1]. - - // The numeical values of L(:,j) are held in the same positions in L->x - // (and L->z if L is zomplex) - - // L->next and L->prev hold a link list of columns of L, that tracks the - // order they appear in the arrays L->i, L->x, and L->z. The head and tail - // of the list is n+1 and n, respectively. - - void *next ; // int32/int64, size n+2 - void *prev ; // int32/int64, size n+2 - - //-------------------------------------------------------------------------- - // supernodal factorization (not simplicial) - //-------------------------------------------------------------------------- - - // L->x is shared with the simplicial structure above. L->z is not used - // for the supernodal case since a supernodal factor cannot be zomplex. - - size_t nsuper ; // # of supernodes - size_t ssize ; // # of integers in L->s - size_t xsize ; // # of entries in L->x - size_t maxcsize ; // size of largest update matrix - size_t maxesize ; // max # of rows in supernodes, excl. triangular part - - // the following are int32/int64 and are size nsuper+1: - void *super ; // first column in each supernode - void *pi ; // index into L->s for integer part of a supernode - void *px ; // index into L->x for numeric part of a supernode - - void *s ; // int32/int64, ssize, integer part of supernodes - - //-------------------------------------------------------------------------- - // type of the factorization - //-------------------------------------------------------------------------- - - int ordering ; // the fill-reducing method used (CHOLMOD_NATURAL, - // CHOLMOD_GIVEN, CHOLMOD_AMD, CHOLMOD_METIS, CHOLMOD_NESDIS, - // CHOLMOD_COLAMD, or CHOLMOD_POSTORDERED). - - int is_ll ; // true: an LL' factorization; false: LDL' instead - int is_super ; // true: supernodal; false: simplicial - int is_monotonic ; // true: columns appear in order 0 to n-1 in L, for a - // simplicial factorization only - - // Two boolean values above (is_ll, is_super) and L->xtype (pattern or - // otherwise, define eight types of factorizations, but only 6 are used: - - // If L->xtype is CHOLMOD_PATTERN, then L is a symbolic factor: - // - // simplicial LDL': (is_ll false, is_super false). Nothing is present - // except Perm and ColCount. - // - // simplicial LL': (is_ll true, is_super false). Identical to the - // simplicial LDL', except for the is_ll flag. - // - // supernodal LL': (is_ll true, is_super true). A supernodal symbolic - // factorization. The simplicial symbolic information is present - // (Perm and ColCount), as is all of the supernodal factorization - // except for the numerical values (x and z). - // - // If L->xtype is CHOLMOD_REAL, CHOLMOD_COMPLEX, or CHOLMOD_ZOMPLEX, - // then L is a numeric factor: - // - // - // simplicial LDL': (is_ll false, is_super false). Stored in compressed - // column form, using the simplicial components above (nzmax, p, i, - // x, z, nz, next, and prev). The unit diagonal of L is not stored, - // and D is stored in its place. There are no supernodes. - // - // simplicial LL': (is_ll true, is_super false). Uses the same storage - // scheme as the simplicial LDL', except that D does not appear. - // The first entry of each column of L is the diagonal entry of - // that column of L. - // - // supernodal LL': (is_ll true, is_super true). A supernodal factor, - // using the supernodal components described above (nsuper, ssize, - // xsize, maxcsize, maxesize, super, pi, px, s, x, and z). - // A supernodal factorization is never zomplex. - - int itype ; // integer type for L->Perm, L->ColCount, L->p, L->i, L->nz, - // L->next, L->prev, L->super, L->pi, L->px, and L->s. - // These are all int32 if L->itype is CHOLMOD_INT, or all int64 - // if L->itype is CHOLMOD_LONG. - - int xtype ; // pattern, real, complex, or zomplex - int dtype ; // x and z are double or single - - int useGPU; // if true, symbolic factorization allows for use of the GPU + /* ---------------------------------------------------------------------- */ + /* for both simplicial and supernodal factorizations */ + /* ---------------------------------------------------------------------- */ + + size_t n ; /* L is n-by-n */ + + size_t minor ; /* If the factorization failed, L->minor is the column + * at which it failed (in the range 0 to n-1). A value + * of n means the factorization was successful or + * the matrix has not yet been factorized. */ + + /* ---------------------------------------------------------------------- */ + /* symbolic ordering and analysis */ + /* ---------------------------------------------------------------------- */ + + void *Perm ; /* size n, permutation used */ + void *ColCount ; /* size n, column counts for simplicial L */ + + void *IPerm ; /* size n, inverse permutation. Only created by + * cholmod_solve2 if Bset is used. */ + + /* ---------------------------------------------------------------------- */ + /* simplicial factorization */ + /* ---------------------------------------------------------------------- */ + + size_t nzmax ; /* size of i and x */ + + void *p ; /* p [0..ncol], the column pointers */ + void *i ; /* i [0..nzmax-1], the row indices */ + void *x ; /* x [0..nzmax-1], the numerical values */ + void *z ; + void *nz ; /* nz [0..ncol-1], the # of nonzeros in each column. + * i [p [j] ... p [j]+nz[j]-1] contains the row indices, + * and the numerical values are in the same locatins + * in x. The value of i [p [k]] is always k. */ + + void *next ; /* size ncol+2. next [j] is the next column in i/x */ + void *prev ; /* size ncol+2. prev [j] is the prior column in i/x. + * head of the list is ncol+1, and the tail is ncol. */ + + /* ---------------------------------------------------------------------- */ + /* supernodal factorization */ + /* ---------------------------------------------------------------------- */ + + /* Note that L->x is shared with the simplicial data structure. L->x has + * size L->nzmax for a simplicial factor, and size L->xsize for a supernodal + * factor. */ + + size_t nsuper ; /* number of supernodes */ + size_t ssize ; /* size of s, integer part of supernodes */ + size_t xsize ; /* size of x, real part of supernodes */ + size_t maxcsize ; /* size of largest update matrix */ + size_t maxesize ; /* max # of rows in supernodes, excl. triangular part */ + + void *super ; /* size nsuper+1, first col in each supernode */ + void *pi ; /* size nsuper+1, pointers to integer patterns */ + void *px ; /* size nsuper+1, pointers to real parts */ + void *s ; /* size ssize, integer part of supernodes */ + + /* ---------------------------------------------------------------------- */ + /* factorization type */ + /* ---------------------------------------------------------------------- */ + + int ordering ; /* ordering method used */ + + int is_ll ; /* TRUE if LL', FALSE if LDL' */ + int is_super ; /* TRUE if supernodal, FALSE if simplicial */ + int is_monotonic ; /* TRUE if columns of L appear in order 0..n-1. + * Only applicable to simplicial numeric types. */ + + /* There are 8 types of factor objects that cholmod_factor can represent + * (only 6 are used): + * + * Numeric types (xtype is not CHOLMOD_PATTERN) + * -------------------------------------------- + * + * simplicial LDL': (is_ll FALSE, is_super FALSE). Stored in compressed + * column form, using the simplicial components above (nzmax, p, i, + * x, z, nz, next, and prev). The unit diagonal of L is not stored, + * and D is stored in its place. There are no supernodes. + * + * simplicial LL': (is_ll TRUE, is_super FALSE). Uses the same storage + * scheme as the simplicial LDL', except that D does not appear. + * The first entry of each column of L is the diagonal entry of + * that column of L. + * + * supernodal LDL': (is_ll FALSE, is_super TRUE). Not used. + * FUTURE WORK: add support for supernodal LDL' + * + * supernodal LL': (is_ll TRUE, is_super TRUE). A supernodal factor, + * using the supernodal components described above (nsuper, ssize, + * xsize, maxcsize, maxesize, super, pi, px, s, x, and z). + * + * + * Symbolic types (xtype is CHOLMOD_PATTERN) + * ----------------------------------------- + * + * simplicial LDL': (is_ll FALSE, is_super FALSE). Nothing is present + * except Perm and ColCount. + * + * simplicial LL': (is_ll TRUE, is_super FALSE). Identical to the + * simplicial LDL', except for the is_ll flag. + * + * supernodal LDL': (is_ll FALSE, is_super TRUE). Not used. + * FUTURE WORK: add support for supernodal LDL' + * + * supernodal LL': (is_ll TRUE, is_super TRUE). A supernodal symbolic + * factorization. The simplicial symbolic information is present + * (Perm and ColCount), as is all of the supernodal factorization + * except for the numerical values (x and z). + */ + + int itype ; /* The integer arrays are Perm, ColCount, p, i, nz, + * next, prev, super, pi, px, and s. If itype is + * CHOLMOD_INT, all of these are int arrays. + * CHOLMOD_INTLONG: p, pi, px are int64_t, others int. + * CHOLMOD_LONG: all integer arrays are int64_t. */ + int xtype ; /* pattern, real, complex, or zomplex */ + int dtype ; /* x and z double or float */ + + int useGPU; /* Indicates the symbolic factorization supports + * GPU acceleration */ } cholmod_factor ; -//------------------------------------------------------------------------------ -// cholmod_allocate_factor: allocate a numerical factor -//------------------------------------------------------------------------------ -// L is returned as double precision +/* -------------------------------------------------------------------------- */ +/* cholmod_allocate_factor: allocate a factor (symbolic LL' or LDL') */ +/* -------------------------------------------------------------------------- */ -cholmod_factor *cholmod_allocate_factor // return the new factor L +cholmod_factor *cholmod_allocate_factor ( - size_t n, // L is factorization of an n-by-n matrix + /* ---- input ---- */ + size_t n, /* L is n-by-n */ + /* --------------- */ cholmod_common *Common ) ; -cholmod_factor *cholmod_l_allocate_factor (size_t, cholmod_common *) ; - -//------------------------------------------------------------------------------ -// cholmod_alloc_factor: allocate a numerical factor (double or single) -//------------------------------------------------------------------------------ -cholmod_factor *cholmod_alloc_factor // return the new factor L -( - size_t n, // L is factorization of an n-by-n matrix - int dtype, // CHOLMOD_SINGLE or CHOLMOD_DOUBLE - cholmod_common *Common -) ; -cholmod_factor *cholmod_l_alloc_factor (size_t, int, cholmod_common *) ; +cholmod_factor *cholmod_l_allocate_factor (size_t, cholmod_common *) ; -//------------------------------------------------------------------------------ -// cholmod_free_factor: free a factor -//------------------------------------------------------------------------------ +/* -------------------------------------------------------------------------- */ +/* cholmod_free_factor: free a factor */ +/* -------------------------------------------------------------------------- */ int cholmod_free_factor ( - cholmod_factor **L, // handle of sparse factorization to free + /* ---- in/out --- */ + cholmod_factor **L, /* factor to free, NULL on output */ + /* --------------- */ cholmod_common *Common ) ; + int cholmod_l_free_factor (cholmod_factor **, cholmod_common *) ; -//------------------------------------------------------------------------------ -// cholmod_reallocate_factor: change the # entries in a factor -//------------------------------------------------------------------------------ +/* -------------------------------------------------------------------------- */ +/* cholmod_reallocate_factor: change the # entries in a factor */ +/* -------------------------------------------------------------------------- */ int cholmod_reallocate_factor ( - size_t nznew, // new max # of nonzeros the factor matrix can hold - cholmod_factor *L, // factor to reallocate + /* ---- input ---- */ + size_t nznew, /* new # of entries in L */ + /* ---- in/out --- */ + cholmod_factor *L, /* factor to modify */ + /* --------------- */ cholmod_common *Common ) ; + int cholmod_l_reallocate_factor (size_t, cholmod_factor *, cholmod_common *) ; -//------------------------------------------------------------------------------ -// cholmod_change_factor: change the type of factor (e.g., LDL' to LL') -//------------------------------------------------------------------------------ +/* -------------------------------------------------------------------------- */ +/* cholmod_change_factor: change the type of factor (e.g., LDL' to LL') */ +/* -------------------------------------------------------------------------- */ int cholmod_change_factor ( - int to_xtype, // CHOLMOD_PATTERN, _REAL, _COMPLEX, or _ZOMPLEX - int to_ll, // if true: convert to LL'; else to LDL' - int to_super, // if true: convert to supernodal; else to simplicial - int to_packed, // if true: pack simplicial columns' else: do not pack - int to_monotonic, // if true, put simplicial columns in order - cholmod_factor *L, // factor to change. + /* ---- input ---- */ + int to_xtype, /* to CHOLMOD_PATTERN, _REAL, _COMPLEX, _ZOMPLEX */ + int to_ll, /* TRUE: convert to LL', FALSE: LDL' */ + int to_super, /* TRUE: convert to supernodal, FALSE: simplicial */ + int to_packed, /* TRUE: pack simplicial columns, FALSE: do not pack */ + int to_monotonic, /* TRUE: put simplicial columns in order, FALSE: not */ + /* ---- in/out --- */ + cholmod_factor *L, /* factor to modify */ + /* --------------- */ cholmod_common *Common ) ; -int cholmod_l_change_factor (int, int, int, int, int, cholmod_factor *, + +int cholmod_l_change_factor ( int, int, int, int, int, cholmod_factor *, cholmod_common *) ; -//------------------------------------------------------------------------------ -// cholmod_pack_factor: pack a factor -//------------------------------------------------------------------------------ +/* -------------------------------------------------------------------------- */ +/* cholmod_pack_factor: pack the columns of a factor */ +/* -------------------------------------------------------------------------- */ -// Removes all slack space from all columns in a factor. +/* Pack the columns of a simplicial factor. Unlike cholmod_change_factor, + * it can pack the columns of a factor even if they are not stored in their + * natural order (non-monotonic). */ int cholmod_pack_factor ( - cholmod_factor *L, // factor to pack + /* ---- in/out --- */ + cholmod_factor *L, /* factor to modify */ + /* --------------- */ cholmod_common *Common ) ; + int cholmod_l_pack_factor (cholmod_factor *, cholmod_common *) ; -//------------------------------------------------------------------------------ -// cholmod_reallocate_column: reallocate a single column L(:,j) -//------------------------------------------------------------------------------ +/* -------------------------------------------------------------------------- */ +/* cholmod_reallocate_column: resize a single column of a factor */ +/* -------------------------------------------------------------------------- */ int cholmod_reallocate_column ( - size_t j, // reallocate L(:,j) - size_t need, // space in L(:,j) for this # of entries - cholmod_factor *L, // L factor modified, L(:,j) resized + /* ---- input ---- */ + size_t j, /* the column to reallocate */ + size_t need, /* required size of column j */ + /* ---- in/out --- */ + cholmod_factor *L, /* factor to modify */ + /* --------------- */ cholmod_common *Common ) ; + int cholmod_l_reallocate_column (size_t, size_t, cholmod_factor *, cholmod_common *) ; -//------------------------------------------------------------------------------ -// cholmod_factor_to_sparse: create a sparse matrix copy of a factor -//------------------------------------------------------------------------------ +/* -------------------------------------------------------------------------- */ +/* cholmod_factor_to_sparse: create a sparse matrix copy of a factor */ +/* -------------------------------------------------------------------------- */ + +/* Only operates on numeric factors, not symbolic ones */ -cholmod_sparse *cholmod_factor_to_sparse // return a new sparse matrix +cholmod_sparse *cholmod_factor_to_sparse ( - cholmod_factor *L, // input: factor to convert; output: L is converted - // to a simplicial symbolic factor + /* ---- in/out --- */ + cholmod_factor *L, /* factor to copy, converted to symbolic on output */ + /* --------------- */ cholmod_common *Common ) ; + cholmod_sparse *cholmod_l_factor_to_sparse (cholmod_factor *, - cholmod_common *) ; + cholmod_common *) ; -//------------------------------------------------------------------------------ -// cholmod_copy_factor: create a copy of a factor -//------------------------------------------------------------------------------ +/* -------------------------------------------------------------------------- */ +/* cholmod_copy_factor: create a copy of a factor */ +/* -------------------------------------------------------------------------- */ -cholmod_factor *cholmod_copy_factor // return a copy of the factor +cholmod_factor *cholmod_copy_factor ( - cholmod_factor *L, // factor to copy (not modified) + /* ---- input ---- */ + cholmod_factor *L, /* factor to copy */ + /* --------------- */ cholmod_common *Common ) ; + cholmod_factor *cholmod_l_copy_factor (cholmod_factor *, cholmod_common *) ; -//------------------------------------------------------------------------------ -// cholmod_factor_xtype: change the xtype and/or dtype of a factor -//------------------------------------------------------------------------------ +/* -------------------------------------------------------------------------- */ +/* cholmod_factor_xtype: change the xtype of a factor */ +/* -------------------------------------------------------------------------- */ int cholmod_factor_xtype ( - int to_xdtype, // requested xtype and dtype - cholmod_factor *L, // factor to change + /* ---- input ---- */ + int to_xtype, /* requested xtype (real, complex, or zomplex) */ + /* ---- in/out --- */ + cholmod_factor *L, /* factor to change */ + /* --------------- */ cholmod_common *Common ) ; + int cholmod_l_factor_xtype (int, cholmod_factor *, cholmod_common *) ; -//============================================================================== -// cholmod_dense: a dense matrix, held by column -//============================================================================== + +/* ========================================================================== */ +/* === Core/cholmod_dense =================================================== */ +/* ========================================================================== */ + +/* A dense matrix in column-oriented form. It has no itype since it contains + * no integers. Entry in row i and column j is located in x [i+j*d]. + */ typedef struct cholmod_dense_struct { - size_t nrow ; // the matrix is nrow-by-ncol + size_t nrow ; /* the matrix is nrow-by-ncol */ size_t ncol ; - size_t nzmax ; // maximum number of entries in the matrix - size_t d ; // leading dimension (d >= nrow must hold) - void *x ; // size nzmax or 2*nzmax, if present - void *z ; // size nzmax, if present - int xtype ; // pattern, real, complex, or zomplex - int dtype ; // x and z double or single + size_t nzmax ; /* maximum number of entries in the matrix */ + size_t d ; /* leading dimension (d >= nrow must hold) */ + void *x ; /* size nzmax or 2*nzmax, if present */ + void *z ; /* size nzmax, if present */ + int xtype ; /* pattern, real, complex, or zomplex */ + int dtype ; /* x and z double or float */ } cholmod_dense ; -//------------------------------------------------------------------------------ -// cholmod_allocate_dense: allocate a dense matrix (contents not initialized) -//------------------------------------------------------------------------------ +/* -------------------------------------------------------------------------- */ +/* cholmod_allocate_dense: allocate a dense matrix (contents uninitialized) */ +/* -------------------------------------------------------------------------- */ cholmod_dense *cholmod_allocate_dense ( - size_t nrow, // # of rows - size_t ncol, // # of columns - size_t d, // leading dimension - int xdtype, // xtype + dtype of the matrix: - // (CHOLMOD_DOUBLE, _SINGLE) + - // (CHOLMOD_REAL, _COMPLEX, or _ZOMPLEX) + /* ---- input ---- */ + size_t nrow, /* # of rows of matrix */ + size_t ncol, /* # of columns of matrix */ + size_t d, /* leading dimension */ + int xtype, /* CHOLMOD_REAL, _COMPLEX, or _ZOMPLEX */ + /* --------------- */ cholmod_common *Common ) ; + cholmod_dense *cholmod_l_allocate_dense (size_t, size_t, size_t, int, cholmod_common *) ; -//------------------------------------------------------------------------------ -// cholmod_zeros: allocate a dense matrix and set it to zero -//------------------------------------------------------------------------------ +/* -------------------------------------------------------------------------- */ +/* cholmod_zeros: allocate a dense matrix and set it to zero */ +/* -------------------------------------------------------------------------- */ cholmod_dense *cholmod_zeros ( - size_t nrow, // # of rows - size_t ncol, // # of columns - int xdtype, // xtype + dtype of the matrix: - // (CHOLMOD_DOUBLE, _SINGLE) + - // (CHOLMOD_REAL, _COMPLEX, or _ZOMPLEX) + /* ---- input ---- */ + size_t nrow, /* # of rows of matrix */ + size_t ncol, /* # of columns of matrix */ + int xtype, /* CHOLMOD_REAL, _COMPLEX, or _ZOMPLEX */ + /* --------------- */ cholmod_common *Common ) ; + cholmod_dense *cholmod_l_zeros (size_t, size_t, int, cholmod_common *) ; -//------------------------------------------------------------------------------ -// cholmod_ones: allocate a dense matrix of all 1's -//------------------------------------------------------------------------------ +/* -------------------------------------------------------------------------- */ +/* cholmod_ones: allocate a dense matrix and set it to all ones */ +/* -------------------------------------------------------------------------- */ cholmod_dense *cholmod_ones ( - size_t nrow, // # of rows - size_t ncol, // # of columns - int xdtype, // xtype + dtype of the matrix: - // (CHOLMOD_DOUBLE, _SINGLE) + - // (_REAL, _COMPLEX, or _ZOMPLEX) + /* ---- input ---- */ + size_t nrow, /* # of rows of matrix */ + size_t ncol, /* # of columns of matrix */ + int xtype, /* CHOLMOD_REAL, _COMPLEX, or _ZOMPLEX */ + /* --------------- */ cholmod_common *Common ) ; + cholmod_dense *cholmod_l_ones (size_t, size_t, int, cholmod_common *) ; -//------------------------------------------------------------------------------ -// cholmod_eye: allocate a dense identity matrix -//------------------------------------------------------------------------------ +/* -------------------------------------------------------------------------- */ +/* cholmod_eye: allocate a dense matrix and set it to the identity matrix */ +/* -------------------------------------------------------------------------- */ -cholmod_dense *cholmod_eye // return a dense identity matrix +cholmod_dense *cholmod_eye ( - size_t nrow, // # of rows - size_t ncol, // # of columns - int xdtype, // xtype + dtype of the matrix: - // (CHOLMOD_DOUBLE, _SINGLE) + - // (_REAL, _COMPLEX, or _ZOMPLEX) + /* ---- input ---- */ + size_t nrow, /* # of rows of matrix */ + size_t ncol, /* # of columns of matrix */ + int xtype, /* CHOLMOD_REAL, _COMPLEX, or _ZOMPLEX */ + /* --------------- */ cholmod_common *Common ) ; + cholmod_dense *cholmod_l_eye (size_t, size_t, int, cholmod_common *) ; -//------------------------------------------------------------------------------ -// cholmod_free_dense: free a dense matrix -//------------------------------------------------------------------------------ +/* -------------------------------------------------------------------------- */ +/* cholmod_free_dense: free a dense matrix */ +/* -------------------------------------------------------------------------- */ int cholmod_free_dense ( - cholmod_dense **X, // handle of dense matrix to free + /* ---- in/out --- */ + cholmod_dense **X, /* dense matrix to deallocate, NULL on output */ + /* --------------- */ cholmod_common *Common ) ; + int cholmod_l_free_dense (cholmod_dense **, cholmod_common *) ; -//------------------------------------------------------------------------------ -// cholmod_ensure_dense: ensure a dense matrix has a given size and type -//------------------------------------------------------------------------------ +/* -------------------------------------------------------------------------- */ +/* cholmod_ensure_dense: ensure a dense matrix has a given size and type */ +/* -------------------------------------------------------------------------- */ cholmod_dense *cholmod_ensure_dense ( - cholmod_dense **X, // matrix to resize as needed (*X may be NULL) - size_t nrow, // # of rows - size_t ncol, // # of columns - size_t d, // leading dimension - int xdtype, // xtype + dtype of the matrix: - // (CHOLMOD_DOUBLE, _SINGLE) + - // (CHOLMOD_REAL, _COMPLEX, or _ZOMPLEX) + /* ---- input/output ---- */ + cholmod_dense **XHandle, /* matrix handle to check */ + /* ---- input ---- */ + size_t nrow, /* # of rows of matrix */ + size_t ncol, /* # of columns of matrix */ + size_t d, /* leading dimension */ + int xtype, /* CHOLMOD_REAL, _COMPLEX, or _ZOMPLEX */ + /* --------------- */ cholmod_common *Common ) ; -cholmod_dense *cholmod_l_ensure_dense (cholmod_dense **, size_t, size_t, - size_t, int, cholmod_common *) ; - -//------------------------------------------------------------------------------ -// cholmod_sparse_to_dense: create a dense matrix copy of a sparse matrix -//------------------------------------------------------------------------------ -cholmod_dense *cholmod_sparse_to_dense // return a dense matrix -( - cholmod_sparse *A, // input matrix - cholmod_common *Common -) ; -cholmod_dense *cholmod_l_sparse_to_dense (cholmod_sparse *, cholmod_common *) ; +cholmod_dense *cholmod_l_ensure_dense (cholmod_dense **, size_t, size_t, size_t, + int, cholmod_common *) ; -//------------------------------------------------------------------------------ -// cholmod_dense_nnz: count # of nonzeros in a dense matrix -//------------------------------------------------------------------------------ +/* -------------------------------------------------------------------------- */ +/* cholmod_sparse_to_dense: create a dense matrix copy of a sparse matrix */ +/* -------------------------------------------------------------------------- */ -int64_t cholmod_dense_nnz // return # of entries in the dense matrix +cholmod_dense *cholmod_sparse_to_dense ( - cholmod_dense *X, // input matrix + /* ---- input ---- */ + cholmod_sparse *A, /* matrix to copy */ + /* --------------- */ cholmod_common *Common ) ; -int64_t cholmod_l_dense_nnz (cholmod_dense *, cholmod_common *) ; -//------------------------------------------------------------------------------ -// cholmod_dense_to_sparse: create a sparse matrix copy of a dense matrix -//------------------------------------------------------------------------------ +cholmod_dense *cholmod_l_sparse_to_dense (cholmod_sparse *, + cholmod_common *) ; + +/* -------------------------------------------------------------------------- */ +/* cholmod_dense_to_sparse: create a sparse matrix copy of a dense matrix */ +/* -------------------------------------------------------------------------- */ -cholmod_sparse *cholmod_dense_to_sparse // return a sparse matrix C +cholmod_sparse *cholmod_dense_to_sparse ( - cholmod_dense *X, // input matrix - int values, // if true, copy the values; if false, C is pattern + /* ---- input ---- */ + cholmod_dense *X, /* matrix to copy */ + int values, /* TRUE if values to be copied, FALSE otherwise */ + /* --------------- */ cholmod_common *Common ) ; + cholmod_sparse *cholmod_l_dense_to_sparse (cholmod_dense *, int, cholmod_common *) ; -//------------------------------------------------------------------------------ -// cholmod_copy_dense: create a copy of a dense matrix -//------------------------------------------------------------------------------ +/* -------------------------------------------------------------------------- */ +/* cholmod_copy_dense: create a copy of a dense matrix */ +/* -------------------------------------------------------------------------- */ -cholmod_dense *cholmod_copy_dense // returns new dense matrix +cholmod_dense *cholmod_copy_dense ( - cholmod_dense *X, // input dense matrix + /* ---- input ---- */ + cholmod_dense *X, /* matrix to copy */ + /* --------------- */ cholmod_common *Common ) ; + cholmod_dense *cholmod_l_copy_dense (cholmod_dense *, cholmod_common *) ; -//------------------------------------------------------------------------------ -// cholmod_copy_dense2: copy a dense matrix (pre-allocated) -//------------------------------------------------------------------------------ +/* -------------------------------------------------------------------------- */ +/* cholmod_copy_dense2: copy a dense matrix (pre-allocated) */ +/* -------------------------------------------------------------------------- */ int cholmod_copy_dense2 ( - cholmod_dense *X, // input dense matrix - cholmod_dense *Y, // output dense matrix (already allocated on input) + /* ---- input ---- */ + cholmod_dense *X, /* matrix to copy */ + /* ---- output --- */ + cholmod_dense *Y, /* copy of matrix X */ + /* --------------- */ cholmod_common *Common ) ; + int cholmod_l_copy_dense2 (cholmod_dense *, cholmod_dense *, cholmod_common *) ; -//------------------------------------------------------------------------------ -// cholmod_dense_xtype: change the xtype and/or dtype of a dense matrix -//------------------------------------------------------------------------------ +/* -------------------------------------------------------------------------- */ +/* cholmod_dense_xtype: change the xtype of a dense matrix */ +/* -------------------------------------------------------------------------- */ int cholmod_dense_xtype ( - int to_xdtype, // requested xtype and dtype - cholmod_dense *X, // dense matrix to change + /* ---- input ---- */ + int to_xtype, /* requested xtype (real, complex,or zomplex) */ + /* ---- in/out --- */ + cholmod_dense *X, /* dense matrix to change */ + /* --------------- */ cholmod_common *Common ) ; + int cholmod_l_dense_xtype (int, cholmod_dense *, cholmod_common *) ; -//============================================================================= -// cholmod_triplet: a sparse matrix in triplet form -//============================================================================= + +/* ========================================================================== */ +/* === Core/cholmod_triplet ================================================= */ +/* ========================================================================== */ + +/* A sparse matrix stored in triplet form. */ typedef struct cholmod_triplet_struct { - size_t nrow ; // # of rows of the matrix - size_t ncol ; // # of colums of the matrix - size_t nzmax ; // max # of entries that can be held in the matrix - size_t nnz ; // current # of entries can be held in the matrix - - // int32 or int64 arrays (depending on T->itype) - void *i ; // i [0..nzmax-1], the row indices - void *j ; // j [0..nzmax-1], the column indices - - // double or float arrays: - void *x ; // size nzmax or 2*nzmax, or NULL - void *z ; // size nzmax, or NULL - - int stype ; // T->stype defines what parts of the matrix is held: - // 0: the matrix is unsymmetric with both lower and upper parts stored. - // >0: the matrix is square and symmetric, where entries in the lower - // triangular part are transposed and placed in the upper - // triangular part of A if T is converted into a sparse matrix A. - // <0: the matrix is square and symmetric, where entries in the upper - // triangular part are transposed and placed in the lower - // triangular part of A if T is converted into a sparse matrix A. - // - // Note that A->stype (for a sparse matrix) and T->stype (for a - // triplet matrix) are handled differently. In a triplet matrix T, - // no entry is ever ignored. For a sparse matrix A, if A->stype < 0 - // or A->stype > 0, then entries not in the correct triangular part - // are ignored. - - int itype ; // T->itype defines the integers used for T->i and T->j. - // if CHOLMOD_INT, these arrays are all of type int32_t. - // if CHOLMOD_LONG, these arrays are all of type int64_t. - int xtype ; // pattern, real, complex, or zomplex - int dtype ; // x and z are double or single + size_t nrow ; /* the matrix is nrow-by-ncol */ + size_t ncol ; + size_t nzmax ; /* maximum number of entries in the matrix */ + size_t nnz ; /* number of nonzeros in the matrix */ + + void *i ; /* i [0..nzmax-1], the row indices */ + void *j ; /* j [0..nzmax-1], the column indices */ + void *x ; /* size nzmax or 2*nzmax, if present */ + void *z ; /* size nzmax, if present */ + + int stype ; /* Describes what parts of the matrix are considered: + * + * 0: matrix is "unsymmetric": use both upper and lower triangular parts + * (the matrix may actually be symmetric in pattern and value, but + * both parts are explicitly stored and used). May be square or + * rectangular. + * >0: matrix is square and symmetric. Entries in the lower triangular + * part are transposed and added to the upper triangular part when + * the matrix is converted to cholmod_sparse form. + * <0: matrix is square and symmetric. Entries in the upper triangular + * part are transposed and added to the lower triangular part when + * the matrix is converted to cholmod_sparse form. + * + * Note that stype>0 and stype<0 are different for cholmod_sparse and + * cholmod_triplet. The reason is simple. You can permute a symmetric + * triplet matrix by simply replacing a row and column index with their + * new row and column indices, via an inverse permutation. Suppose + * P = L->Perm is your permutation, and Pinv is an array of size n. + * Suppose a symmetric matrix A is represent by a triplet matrix T, with + * entries only in the upper triangular part. Then the following code: + * + * Ti = T->i ; + * Tj = T->j ; + * for (k = 0 ; k < n ; k++) Pinv [P [k]] = k ; + * for (k = 0 ; k < nz ; k++) Ti [k] = Pinv [Ti [k]] ; + * for (k = 0 ; k < nz ; k++) Tj [k] = Pinv [Tj [k]] ; + * + * creates the triplet form of C=P*A*P'. However, if T initially + * contains just the upper triangular entries (T->stype = 1), after + * permutation it has entries in both the upper and lower triangular + * parts. These entries should be transposed when constructing the + * cholmod_sparse form of A, which is what cholmod_triplet_to_sparse + * does. Thus: + * + * C = cholmod_triplet_to_sparse (T, 0, &Common) ; + * + * will return the matrix C = P*A*P'. + * + * Since the triplet matrix T is so simple to generate, it's quite easy + * to remove entries that you do not want, prior to converting T to the + * cholmod_sparse form. So if you include these entries in T, CHOLMOD + * assumes that there must be a reason (such as the one above). Thus, + * no entry in a triplet matrix is ever ignored. + */ + + int itype ; /* CHOLMOD_LONG: i and j are int64_t. Otherwise int */ + int xtype ; /* pattern, real, complex, or zomplex */ + int dtype ; /* x and z are double or float */ } cholmod_triplet ; -//------------------------------------------------------------------------------ -// cholmod_allocate_triplet: allocate a triplet matrix -//------------------------------------------------------------------------------ +/* -------------------------------------------------------------------------- */ +/* cholmod_allocate_triplet: allocate a triplet matrix */ +/* -------------------------------------------------------------------------- */ -cholmod_triplet *cholmod_allocate_triplet // return triplet matrix T +cholmod_triplet *cholmod_allocate_triplet ( - size_t nrow, // # of rows - size_t ncol, // # of columns - size_t nzmax, // max # of entries the matrix can hold - int stype, // the stype of the matrix (unsym, tril, or triu) - int xdtype, // xtype + dtype of the matrix: - // (CHOLMOD_DOUBLE, _SINGLE) + - // (CHOLMOD_PATTERN, _REAL, _COMPLEX, or _ZOMPLEX) + /* ---- input ---- */ + size_t nrow, /* # of rows of T */ + size_t ncol, /* # of columns of T */ + size_t nzmax, /* max # of nonzeros of T */ + int stype, /* stype of T */ + int xtype, /* CHOLMOD_PATTERN, _REAL, _COMPLEX, or _ZOMPLEX */ + /* --------------- */ cholmod_common *Common ) ; + cholmod_triplet *cholmod_l_allocate_triplet (size_t, size_t, size_t, int, int, cholmod_common *) ; -//------------------------------------------------------------------------------ -// cholmod_free_triplet: free a triplet matrix -//------------------------------------------------------------------------------ +/* -------------------------------------------------------------------------- */ +/* cholmod_free_triplet: free a triplet matrix */ +/* -------------------------------------------------------------------------- */ int cholmod_free_triplet ( - cholmod_triplet **T, // handle of triplet matrix to free + /* ---- in/out --- */ + cholmod_triplet **T, /* triplet matrix to deallocate, NULL on output */ + /* --------------- */ cholmod_common *Common ) ; + int cholmod_l_free_triplet (cholmod_triplet **, cholmod_common *) ; -//------------------------------------------------------------------------------ -// cholmod_reallocate_triplet: change max # of entries in a triplet matrix -//------------------------------------------------------------------------------ +/* -------------------------------------------------------------------------- */ +/* cholmod_reallocate_triplet: change the # of entries in a triplet matrix */ +/* -------------------------------------------------------------------------- */ int cholmod_reallocate_triplet ( - size_t nznew, // new max # of nonzeros the triplet matrix can hold - cholmod_triplet *T, // triplet matrix to reallocate + /* ---- input ---- */ + size_t nznew, /* new # of entries in T */ + /* ---- in/out --- */ + cholmod_triplet *T, /* triplet matrix to modify */ + /* --------------- */ cholmod_common *Common ) ; + int cholmod_l_reallocate_triplet (size_t, cholmod_triplet *, cholmod_common *) ; -//------------------------------------------------------------------------------ -// cholmod_sparse_to_triplet: create a triplet matrix copy of a sparse matrix -//------------------------------------------------------------------------------ +/* -------------------------------------------------------------------------- */ +/* cholmod_sparse_to_triplet: create a triplet matrix copy of a sparse matrix*/ +/* -------------------------------------------------------------------------- */ cholmod_triplet *cholmod_sparse_to_triplet ( - cholmod_sparse *A, // matrix to copy into triplet form T + /* ---- input ---- */ + cholmod_sparse *A, /* matrix to copy */ + /* --------------- */ cholmod_common *Common ) ; + cholmod_triplet *cholmod_l_sparse_to_triplet (cholmod_sparse *, cholmod_common *) ; -//------------------------------------------------------------------------------ -// cholmod_triplet_to_sparse: create a sparse matrix from of triplet matrix -//------------------------------------------------------------------------------ +/* -------------------------------------------------------------------------- */ +/* cholmod_triplet_to_sparse: create a sparse matrix copy of a triplet matrix*/ +/* -------------------------------------------------------------------------- */ -cholmod_sparse *cholmod_triplet_to_sparse // return sparse matrix A +cholmod_sparse *cholmod_triplet_to_sparse ( - cholmod_triplet *T, // input triplet matrix - size_t nzmax, // allocate space for max(nzmax,nnz(A)) entries + /* ---- input ---- */ + cholmod_triplet *T, /* matrix to copy */ + size_t nzmax, /* allocate at least this much space in output matrix */ + /* --------------- */ cholmod_common *Common ) ; + cholmod_sparse *cholmod_l_triplet_to_sparse (cholmod_triplet *, size_t, cholmod_common *) ; -//------------------------------------------------------------------------------ -// cholmod_copy_triplet: copy a triplet matrix -//------------------------------------------------------------------------------ +/* -------------------------------------------------------------------------- */ +/* cholmod_copy_triplet: create a copy of a triplet matrix */ +/* -------------------------------------------------------------------------- */ -cholmod_triplet *cholmod_copy_triplet // return new triplet matrix +cholmod_triplet *cholmod_copy_triplet ( - cholmod_triplet *T, // triplet matrix to copy + /* ---- input ---- */ + cholmod_triplet *T, /* matrix to copy */ + /* --------------- */ cholmod_common *Common ) ; + cholmod_triplet *cholmod_l_copy_triplet (cholmod_triplet *, cholmod_common *) ; -//------------------------------------------------------------------------------ -// cholmod_triplet_xtype: change the xtype and/or dtype of a triplet matrix -//------------------------------------------------------------------------------ +/* -------------------------------------------------------------------------- */ +/* cholmod_triplet_xtype: change the xtype of a triplet matrix */ +/* -------------------------------------------------------------------------- */ int cholmod_triplet_xtype ( - int to_xdtype, // requested xtype and dtype - cholmod_triplet *T, // triplet matrix to change + /* ---- input ---- */ + int to_xtype, /* requested xtype (pattern, real, complex,or zomplex)*/ + /* ---- in/out --- */ + cholmod_triplet *T, /* triplet matrix to change */ + /* --------------- */ cholmod_common *Common ) ; + int cholmod_l_triplet_xtype (int, cholmod_triplet *, cholmod_common *) ; -//============================================================================== -// memory allocation -//============================================================================== -// These methods act like malloc/calloc/realloc/free, with some differences. -// They are simple wrappers around the memory management functions in -// SuiteSparse_config. cholmod_malloc and cholmod_calloc have the same -// signature, unlike malloc and calloc. If cholmod_free is given a NULL -// pointer, it safely does nothing. cholmod_free must be passed the size of -// the object being freed, but that is just to keep track of memory usage -// statistics. cholmod_realloc does not return NULL if it fails; instead, it -// returns the pointer to the unmodified block of memory. +/* ========================================================================== */ +/* === Core/cholmod_memory ================================================== */ +/* ========================================================================== */ + +/* The user may make use of these, just like malloc and free. You can even + * malloc an object and safely free it with cholmod_free, and visa versa + * (except that the memory usage statistics will be corrupted). These routines + * do differ from malloc and free. If cholmod_free is given a NULL pointer, + * for example, it does nothing (unlike the ANSI free). cholmod_realloc does + * not return NULL if given a non-NULL pointer and a nonzero size, even if it + * fails (it returns the original pointer and sets an error code in + * Common->status instead). + * + * CHOLMOD keeps track of the amount of memory it has allocated, and so the + * cholmod_free routine also takes the size of the object being freed. This + * is only used for statistics. If you, the user of CHOLMOD, pass the wrong + * size, the only consequence is that the memory usage statistics will be + * corrupted. + */ -void *cholmod_malloc // return pointer to newly allocated memory +void *cholmod_malloc /* returns pointer to the newly malloc'd block */ ( - size_t n, // number of items - size_t size, // size of each item + /* ---- input ---- */ + size_t n, /* number of items */ + size_t size, /* size of each item */ + /* --------------- */ cholmod_common *Common ) ; + void *cholmod_l_malloc (size_t, size_t, cholmod_common *) ; -void *cholmod_calloc // return pointer to newly allocated memory +void *cholmod_calloc /* returns pointer to the newly calloc'd block */ ( - size_t n, // number of items - size_t size, // size of each item + /* ---- input ---- */ + size_t n, /* number of items */ + size_t size, /* size of each item */ + /* --------------- */ cholmod_common *Common ) ; + void *cholmod_l_calloc (size_t, size_t, cholmod_common *) ; -void *cholmod_free // returns NULL to simplify its usage +void *cholmod_free /* always returns NULL */ ( - size_t n, // number of items - size_t size, // size of each item - void *p, // memory to free + /* ---- input ---- */ + size_t n, /* number of items */ + size_t size, /* size of each item */ + /* ---- in/out --- */ + void *p, /* block of memory to free */ + /* --------------- */ cholmod_common *Common ) ; + void *cholmod_l_free (size_t, size_t, void *, cholmod_common *) ; -void *cholmod_realloc // return newly reallocated block of memory +void *cholmod_realloc /* returns pointer to reallocated block */ ( - size_t nnew, // # of items in newly reallocate memory - size_t size, // size of each item - void *p, // pointer to memory to reallocate (may be NULL) - size_t *n, // # of items in p on input; nnew on output if success + /* ---- input ---- */ + size_t nnew, /* requested # of items in reallocated block */ + size_t size, /* size of each item */ + /* ---- in/out --- */ + void *p, /* block of memory to realloc */ + size_t *n, /* current size on input, nnew on output if successful*/ + /* --------------- */ cholmod_common *Common ) ; + void *cholmod_l_realloc (size_t, size_t, void *, size_t *, cholmod_common *) ; -int cholmod_realloc_multiple // returns true if successful, false otherwise +int cholmod_realloc_multiple ( - size_t nnew, // # of items in newly reallocate memory - int nint, // 0: do not allocate I or J, 1: just I, 2: both I and J - int xdtype, // xtype + dtype of the matrix: - // (CHOLMOD_DOUBLE, _SINGLE) + - // (CHOLMOD_PATTERN, _REAL, _COMPLEX, or _ZOMPLEX) - // input/output: - void **I, // integer block of memory (int32_t or int64_t) - void **J, // integer block of memory (int32_t or int64_t) - void **X, // real or complex, double or single, block - void **Z, // zomplex only: double or single block - size_t *n, // current size of I, J, X, and/or Z blocks on input, - // changed to nnew on output, if successful + /* ---- input ---- */ + size_t nnew, /* requested # of items in reallocated blocks */ + int nint, /* number of int32_t/int64_t blocks */ + int xtype, /* CHOLMOD_PATTERN, _REAL, _COMPLEX, or _ZOMPLEX */ + /* ---- in/out --- */ + void **Iblock, /* int32_t or int64_t block */ + void **Jblock, /* int32_t or int64_t block */ + void **Xblock, /* complex, double, or float block */ + void **Zblock, /* zomplex case only: double or float block */ + size_t *n, /* current size of the I,J,X,Z blocks on input, + * nnew on output if successful */ + /* --------------- */ cholmod_common *Common ) ; + int cholmod_l_realloc_multiple (size_t, int, int, void **, void **, void **, void **, size_t *, cholmod_common *) ; -//============================================================================== -// numerical comparisons -//============================================================================== +/* ========================================================================== */ +/* === version control ====================================================== */ +/* ========================================================================== */ + +int cholmod_version /* returns CHOLMOD_VERSION */ +( + /* output, contents not defined on input. Not used if NULL. + version [0] = CHOLMOD_MAIN_VERSION + version [1] = CHOLMOD_SUB_VERSION + version [2] = CHOLMOD_SUBSUB_VERSION + */ + int version [3] +) ; + +int cholmod_l_version (int version [3]) ; + +/* Versions prior to 2.1.1 do not have the above function. The following + code fragment will work with any version of CHOLMOD: + #ifdef CHOLMOD_HAS_VERSION_FUNCTION + v = cholmod_version (NULL) ; + #else + v = CHOLMOD_VERSION ; + #endif +*/ + +/* ========================================================================== */ +/* === symmetry types ======================================================= */ +/* ========================================================================== */ + +#define CHOLMOD_MM_RECTANGULAR 1 +#define CHOLMOD_MM_UNSYMMETRIC 2 +#define CHOLMOD_MM_SYMMETRIC 3 +#define CHOLMOD_MM_HERMITIAN 4 +#define CHOLMOD_MM_SKEW_SYMMETRIC 5 +#define CHOLMOD_MM_SYMMETRIC_POSDIAG 6 +#define CHOLMOD_MM_HERMITIAN_POSDIAG 7 + +/* ========================================================================== */ +/* === Numerical relop macros =============================================== */ +/* ========================================================================== */ -// These macros were different on Windows for older versions of CHOLMOD. -// They are no longer needed but are kept for backward compatibility. +/* These macros correctly handle the NaN case. + * + * CHOLMOD_IS_NAN(x): + * True if x is NaN. False otherwise. The commonly-existing isnan(x) + * function could be used, but it's not in Kernighan & Ritchie 2nd edition + * (ANSI C89). It may appear in , but I'm not certain about + * portability. The expression x != x is true if and only if x is NaN, + * according to the IEEE 754 floating-point standard. + * + * CHOLMOD_IS_ZERO(x): + * True if x is zero. False if x is nonzero, NaN, or +/- Inf. + * This is (x == 0) if the compiler is IEEE 754 compliant. + * + * CHOLMOD_IS_NONZERO(x): + * True if x is nonzero, NaN, or +/- Inf. False if x zero. + * This is (x != 0) if the compiler is IEEE 754 compliant. + * + * CHOLMOD_IS_LT_ZERO(x): + * True if x is < zero or -Inf. False if x is >= 0, NaN, or +Inf. + * This is (x < 0) if the compiler is IEEE 754 compliant. + * + * CHOLMOD_IS_GT_ZERO(x): + * True if x is > zero or +Inf. False if x is <= 0, NaN, or -Inf. + * This is (x > 0) if the compiler is IEEE 754 compliant. + * + * CHOLMOD_IS_LE_ZERO(x): + * True if x is <= zero or -Inf. False if x is > 0, NaN, or +Inf. + * This is (x <= 0) if the compiler is IEEE 754 compliant. + */ -#define CHOLMOD_IS_NAN(x) isnan (x) -#define CHOLMOD_IS_ZERO(x) ((x) == 0.) -#define CHOLMOD_IS_NONZERO(x) ((x) != 0.) -#define CHOLMOD_IS_LT_ZERO(x) ((x) < 0.) -#define CHOLMOD_IS_GT_ZERO(x) ((x) > 0.) -#define CHOLMOD_IS_LE_ZERO(x) ((x) <= 0.) +#ifdef CHOLMOD_WINDOWS + +/* Yes, this is exceedingly ugly. Blame Microsoft, which hopelessly */ +/* violates the IEEE 754 floating-point standard in a bizarre way. */ +/* If you're using an IEEE 754-compliant compiler, then x != x is true */ +/* iff x is NaN. For Microsoft, (x < x) is true iff x is NaN. */ +/* So either way, this macro safely detects a NaN. */ +#define CHOLMOD_IS_NAN(x) (((x) != (x)) || (((x) < (x)))) +#define CHOLMOD_IS_ZERO(x) (((x) == 0.) && !CHOLMOD_IS_NAN(x)) +#define CHOLMOD_IS_NONZERO(x) (((x) != 0.) || CHOLMOD_IS_NAN(x)) +#define CHOLMOD_IS_LT_ZERO(x) (((x) < 0.) && !CHOLMOD_IS_NAN(x)) +#define CHOLMOD_IS_GT_ZERO(x) (((x) > 0.) && !CHOLMOD_IS_NAN(x)) +#define CHOLMOD_IS_LE_ZERO(x) (((x) <= 0.) && !CHOLMOD_IS_NAN(x)) + +#else + +/* These all work properly, according to the IEEE 754 standard ... except on */ +/* a PC with windows. Works fine in Linux on the same PC... */ +#define CHOLMOD_IS_NAN(x) ((x) != (x)) +#define CHOLMOD_IS_ZERO(x) ((x) == 0.) +#define CHOLMOD_IS_NONZERO(x) ((x) != 0.) +#define CHOLMOD_IS_LT_ZERO(x) ((x) < 0.) +#define CHOLMOD_IS_GT_ZERO(x) ((x) > 0.) +#define CHOLMOD_IS_LE_ZERO(x) ((x) <= 0.) #endif -//============================================================================== -// CHOLMOD:Check Module -//============================================================================== -#ifndef NCHECK -/* Routines that check and print the 5 basic data types in CHOLMOD, and 3 kinds + +/* ========================================================================== */ +/* === Include/cholmod_check.h ============================================== */ +/* ========================================================================== */ + +/* CHOLMOD Check module. + * + * Routines that check and print the 5 basic data types in CHOLMOD, and 3 kinds * of integer vectors (subset, perm, and parent), and read in matrices from a * file: * @@ -1959,13 +2684,15 @@ int cholmod_l_realloc_multiple (size_t, int, int, void **, void **, void **, * cholmod_print_common and cholmod_check_common are the only two routines that * you may call after calling cholmod_finish. * - * Requires the Utility module. Not required by any CHOLMOD module, except when + * Requires the Core module. Not required by any CHOLMOD module, except when * debugging is enabled (in which case all modules require the Check module). * * See cholmod_read.c for a description of the file formats supported by the * cholmod_read_* routines. */ +#ifndef NCHECK + /* -------------------------------------------------------------------------- */ /* cholmod_check_common: check the Common object */ /* -------------------------------------------------------------------------- */ @@ -2112,8 +2839,7 @@ int cholmod_print_triplet cholmod_common *Common ) ; -int cholmod_l_print_triplet (cholmod_triplet *, const char *, - cholmod_common *) ; +int cholmod_l_print_triplet (cholmod_triplet *, const char *, cholmod_common *); /* -------------------------------------------------------------------------- */ /* cholmod_check_subset: check a subset */ @@ -2256,7 +2982,7 @@ cholmod_dense *cholmod_read_dense cholmod_common *Common ) ; -cholmod_dense *cholmod_l_read_dense (FILE *, cholmod_common *) ; +cholmod_dense *cholmod_l_read_dense (FILE *, cholmod_common *) ; /* -------------------------------------------------------------------------- */ /* cholmod_read_matrix: read a sparse or dense matrix from a file */ @@ -2292,7 +3018,7 @@ void *cholmod_l_read_matrix (FILE *, int, int *, cholmod_common *) ; /* cholmod_write_sparse: write a sparse matrix to a file */ /* -------------------------------------------------------------------------- */ -int cholmod_write_sparse // returns the same result as cholmod_symmetry +int cholmod_write_sparse ( /* ---- input ---- */ FILE *f, /* file to write to, must already be open */ @@ -2322,21 +3048,25 @@ int cholmod_write_dense int cholmod_l_write_dense (FILE *, cholmod_dense *, const char *, cholmod_common *) ; - #endif -//============================================================================== -// CHOLMOD:Cholesky Module -//============================================================================== -#ifndef NCHOLESKY -/* Sparse Cholesky routines: analysis, factorization, and solve. + + + +/* ========================================================================== */ +/* === Include/cholmod_cholesky.h =========================================== */ +/* ========================================================================== */ + +/* CHOLMOD Cholesky module. + * + * Sparse Cholesky routines: analysis, factorization, and solve. * * The primary routines are all that a user requires to order, analyze, and * factorize a sparse symmetric positive definite matrix A (or A*A'), and * to solve Ax=b (or A*A'x=b). The primary routines rely on the secondary - * routines, the CHOLMOD Utility module, and the AMD and COLAMD packages. They + * routines, the CHOLMOD Core module, and the AMD and COLAMD packages. They * make optional use of the CHOLMOD Supernodal and Partition modules, the * METIS package, and the CCOLAMD package. * @@ -2367,11 +3097,13 @@ int cholmod_l_write_dense (FILE *, cholmod_dense *, const char *, * cholmod_resymbol_noperm recompute the symbolic pattern of L, no L->Perm * cholmod_postorder postorder a tree * - * Requires the Utility module, and two packages: AMD and COLAMD. + * Requires the Core module, and two packages: AMD and COLAMD. * Optionally uses the Supernodal and Partition modules. * Required by the Partition module. */ +#ifndef NCHOLESKY + /* -------------------------------------------------------------------------- */ /* cholmod_analyze: order and analyze (simplicial or supernodal) */ /* -------------------------------------------------------------------------- */ @@ -2379,7 +3111,7 @@ int cholmod_l_write_dense (FILE *, cholmod_dense *, const char *, /* Orders and analyzes A, AA', PAP', or PAA'P' and returns a symbolic factor * that can later be passed to cholmod_factorize. */ -cholmod_factor *cholmod_analyze // order and analyze +cholmod_factor *cholmod_analyze ( /* ---- input ---- */ cholmod_sparse *A, /* matrix to order and analyze */ @@ -2442,7 +3174,7 @@ cholmod_factor *cholmod_l_analyze_p2 (int, cholmod_sparse *, int64_t *, * routine a second time with another matrix. A must have the same nonzero * pattern as that passed to cholmod_analyze. */ -int cholmod_factorize // simplicial or superodal Cholesky factorization +int cholmod_factorize ( /* ---- input ---- */ cholmod_sparse *A, /* matrix to factorize */ @@ -2818,7 +3550,7 @@ int cholmod_l_row_lsubtree (cholmod_sparse *, int64_t *, size_t, * first permutes A according to L->Perm. A can be upper/lower/unsymmetric, * in contrast to cholmod_resymbol_noperm (which can be lower or unsym). */ -int cholmod_resymbol // recompute symbolic pattern of L +int cholmod_resymbol ( /* ---- input ---- */ cholmod_sparse *A, /* matrix to analyze */ @@ -2887,18 +3619,19 @@ int32_t cholmod_postorder /* return # of nodes postordered */ cholmod_common *Common ) ; -int64_t cholmod_l_postorder (int64_t *, size_t, int64_t *, int64_t *, - cholmod_common *) ; +int64_t cholmod_l_postorder (int64_t *, size_t, + int64_t *, int64_t *, cholmod_common *) ; #endif -//============================================================================== -// CHOLMOD:MatrixOps Module -//============================================================================== -#ifndef NMATRIXOPS +/* ========================================================================== */ +/* === Include/cholmod_matrixops.h ========================================== */ +/* ========================================================================== */ -/* Basic operations on sparse and dense matrices. +/* CHOLMOD MatrixOps module. + * + * Basic operations on sparse and dense matrices. * * cholmod_drop A = entries in A with abs. value >= tol * cholmod_norm_dense s = norm (X), 1-norm, inf-norm, or 2-norm @@ -2914,9 +3647,11 @@ int64_t cholmod_l_postorder (int64_t *, size_t, int64_t *, int64_t *, * X, Y: dense matrices (cholmod_dense) * s: scalar or vector * - * Requires the Utility module. Not required by any other CHOLMOD module. + * Requires the Core module. Not required by any other CHOLMOD module. */ +#ifndef NMATRIXOPS + /* -------------------------------------------------------------------------- */ /* cholmod_drop: drop entries with small absolute value */ /* -------------------------------------------------------------------------- */ @@ -3072,7 +3807,8 @@ cholmod_sparse *cholmod_submatrix ) ; cholmod_sparse *cholmod_l_submatrix (cholmod_sparse *, int64_t *, - int64_t, int64_t *, int64_t, int, int, cholmod_common *) ; + int64_t, int64_t *, int64_t, int, int, + cholmod_common *) ; /* -------------------------------------------------------------------------- */ /* cholmod_vertcat: C = [A ; B] */ @@ -3095,15 +3831,6 @@ cholmod_sparse *cholmod_l_vertcat (cholmod_sparse *, cholmod_sparse *, int, /* cholmod_symmetry: determine if a sparse matrix is symmetric */ /* -------------------------------------------------------------------------- */ -// returns one of the following: -#define CHOLMOD_MM_RECTANGULAR 1 -#define CHOLMOD_MM_UNSYMMETRIC 2 -#define CHOLMOD_MM_SYMMETRIC 3 -#define CHOLMOD_MM_HERMITIAN 4 -#define CHOLMOD_MM_SKEW_SYMMETRIC 5 -#define CHOLMOD_MM_SYMMETRIC_POSDIAG 6 -#define CHOLMOD_MM_HERMITIAN_POSDIAG 7 - int cholmod_symmetry ( /* ---- input ---- */ @@ -3118,16 +3845,18 @@ int cholmod_symmetry cholmod_common *Common ) ; -int cholmod_l_symmetry (cholmod_sparse *, int, int64_t *, int64_t *, int64_t *, - int64_t *, cholmod_common *) ; +int cholmod_l_symmetry (cholmod_sparse *, int, int64_t *, + int64_t *, int64_t *, int64_t *, + cholmod_common *) ; #endif -//============================================================================== -// CHOLMOD:Modify Module -//============================================================================== -#ifndef NMODIFY + + +/* ========================================================================== */ +/* === Include/cholmod_modify.h ============================================= */ +/* ========================================================================== */ /* ----------------------------------------------------------------------------- * CHOLMOD/Include/cholmod_modify.h. @@ -3135,11 +3864,13 @@ int cholmod_l_symmetry (cholmod_sparse *, int, int64_t *, int64_t *, int64_t *, * http://www.suitesparse.com * -------------------------------------------------------------------------- */ -/* Sparse Cholesky modification routines: update / downdate / rowadd / rowdel. +/* CHOLMOD Modify module. + * + * Sparse Cholesky modification routines: update / downdate / rowadd / rowdel. * Can also modify a corresponding solution to Lx=b when L is modified. This * module is most useful when applied on a Cholesky factorization computed by * the Cholesky module, but it does not actually require the Cholesky module. - * The Utility module can create an identity Cholesky factorization (LDL' where + * The Core module can create an identity Cholesky factorization (LDL' where * L=D=I) that can then by modified by these routines. * * Primary routines: @@ -3161,9 +3892,12 @@ int cholmod_l_symmetry (cholmod_sparse *, int, int64_t *, int64_t *, int64_t *, * cholmod_rowdel_solve delete a row, and downdate Lx=b * cholmod_rowdel_mark delete a row, and downdate solution to partial Lx=b * - * Requires the Utility module. Not required by any other CHOLMOD module. + * Requires the Core module. Not required by any other CHOLMOD module. */ + +#ifndef NMODIFY + /* -------------------------------------------------------------------------- */ /* cholmod_updown: multiple rank update/downdate */ /* -------------------------------------------------------------------------- */ @@ -3172,7 +3906,7 @@ int cholmod_l_symmetry (cholmod_sparse *, int, int64_t *, int64_t *, int64_t *, * (a downdate). The factor object L need not be an LDL' factorization; it * is converted to one if it isn't. */ -int cholmod_updown // update/downdate +int cholmod_updown ( /* ---- input ---- */ int update, /* TRUE for update, FALSE for downdate */ @@ -3182,8 +3916,9 @@ int cholmod_updown // update/downdate /* --------------- */ cholmod_common *Common ) ; -int cholmod_l_updown (int, cholmod_sparse *, cholmod_factor *, cholmod_common *) ; +int cholmod_l_updown (int, cholmod_sparse *, cholmod_factor *, + cholmod_common *) ; /* -------------------------------------------------------------------------- */ /* cholmod_updown_solve: update/downdate, and modify solution to Lx=b */ @@ -3295,7 +4030,7 @@ int cholmod_l_updown_mask2 (int, cholmod_sparse *, int64_t *, * computed as the factorization of the kth row/column of the matrix to * factorize, which is provided as a single n-by-1 sparse matrix R. */ -int cholmod_rowadd // add a row to an LDL' factorization +int cholmod_rowadd ( /* ---- input ---- */ size_t k, /* row/column index to add */ @@ -3373,7 +4108,7 @@ int cholmod_l_rowadd_mark (size_t, cholmod_sparse *, double *, * a little more time. */ -int cholmod_rowdel // delete a rw from an LDL' factorization +int cholmod_rowdel ( /* ---- input ---- */ size_t k, /* row/column index to delete */ @@ -3442,11 +4177,11 @@ int cholmod_l_rowdel_mark (size_t, cholmod_sparse *, double *, #endif -//============================================================================== -// CHOLMOD:Partition Module (CAMD, CCOLAMD, and CSYMAMD) -//============================================================================== -#ifndef NCAMD + +/* ========================================================================== */ +/* === Include/cholmod_camd.h =============================================== */ +/* ========================================================================== */ /* CHOLMOD Partition module, interface to CAMD, CCOLAMD, and CSYMAMD * @@ -3460,10 +4195,12 @@ int cholmod_l_rowdel_mark (size_t, cholmod_sparse *, double *, * cholmod_csymamd interface to CSYMAMD ordering * cholmod_camd interface to CAMD ordering * - * Requires the Utility and Cholesky modules, and two packages: CAMD, + * Requires the Core and Cholesky modules, and two packages: CAMD, * and CCOLAMD. Used by functions in the Partition Module. */ +#ifndef NCAMD + /* -------------------------------------------------------------------------- */ /* cholmod_ccolamd */ /* -------------------------------------------------------------------------- */ @@ -3534,13 +4271,9 @@ int cholmod_l_camd (cholmod_sparse *, int64_t *, size_t, #endif -//============================================================================== -// CHOLMOD:Partition Module (graph partition methods) -//============================================================================== - -// These routines still exist if CHOLMOD is compiled with -DNPARTITION, -// but they return Common->status = CHOLMOD_NOT_INSTALLED in that case. -#if 1 +/* ========================================================================== */ +/* === Include/cholmod_partition.h ========================================== */ +/* ========================================================================== */ /* ----------------------------------------------------------------------------- * CHOLMOD/Include/cholmod_partition.h. @@ -3560,7 +4293,7 @@ int cholmod_l_camd (cholmod_sparse *, int64_t *, size_t, * cholmod_bisect graph partitioner (currently based on METIS) * cholmod_metis_bisector direct interface to METIS_ComputeVertexSeparator * - * Requires the Utility and Cholesky modules, and three packages: METIS, CAMD, + * Requires the Core and Cholesky modules, and three packages: METIS, CAMD, * and CCOLAMD. Optionally used by the Cholesky module. * * Note that METIS does not have a version that uses int64_t integers. If you @@ -3571,6 +4304,9 @@ int cholmod_l_camd (cholmod_sparse *, int64_t *, size_t, * idxtype. */ +// These routines still exist if CHOLMOD is compiled with -DNPARTITION, +// but they return Common->status = CHOLMOD_NOT_INSTALLED. + /* -------------------------------------------------------------------------- */ /* cholmod_nested_dissection */ /* -------------------------------------------------------------------------- */ @@ -3598,8 +4334,9 @@ int64_t cholmod_nested_dissection /* returns # of components */ cholmod_common *Common ) ; -int64_t cholmod_l_nested_dissection (cholmod_sparse *, int64_t *, size_t, - int64_t *, int64_t *, int64_t *, cholmod_common *) ; +int64_t cholmod_l_nested_dissection (cholmod_sparse *, + int64_t *, size_t, int64_t *, int64_t *, + int64_t *, cholmod_common *) ; /* -------------------------------------------------------------------------- */ /* cholmod_metis */ @@ -3620,8 +4357,8 @@ int cholmod_metis cholmod_common *Common ) ; -int cholmod_l_metis (cholmod_sparse *, int64_t *, size_t, int, int64_t *, - cholmod_common *) ; +int cholmod_l_metis (cholmod_sparse *, int64_t *, size_t, int, + int64_t *, cholmod_common *) ; /* -------------------------------------------------------------------------- */ /* cholmod_bisect */ @@ -3644,8 +4381,8 @@ int64_t cholmod_bisect /* returns # of nodes in separator */ cholmod_common *Common ) ; -int64_t cholmod_l_bisect (cholmod_sparse *, int64_t *, size_t, int, int64_t *, - cholmod_common *) ; +int64_t cholmod_l_bisect (cholmod_sparse *, int64_t *, + size_t, int, int64_t *, cholmod_common *) ; /* -------------------------------------------------------------------------- */ /* cholmod_metis_bisector */ @@ -3659,7 +4396,7 @@ int64_t cholmod_metis_bisector /* returns separator size */ /* ---- input ---- */ cholmod_sparse *A, /* matrix to bisect */ int32_t *Anw, /* size A->nrow, node weights, can be NULL, */ - /* which means the graph is unweighted. */ + /* which means the graph is unweighted. */ int32_t *Aew, /* size nz, edge weights (silently ignored). */ /* This option was available with METIS 4, but not */ /* in METIS 5. This argument is now unused, but */ @@ -3671,8 +4408,9 @@ int64_t cholmod_metis_bisector /* returns separator size */ cholmod_common *Common ) ; -int64_t cholmod_l_metis_bisector (cholmod_sparse *, int64_t *, int64_t *, - int64_t *, cholmod_common *) ; +int64_t cholmod_l_metis_bisector (cholmod_sparse *, + int64_t *, int64_t *, int64_t *, + cholmod_common *) ; /* -------------------------------------------------------------------------- */ /* cholmod_collapse_septree */ @@ -3694,18 +4432,16 @@ int64_t cholmod_collapse_septree cholmod_common *Common ) ; -int64_t cholmod_l_collapse_septree (size_t, size_t, double, size_t, int64_t *, - int64_t *, cholmod_common *) ; - -#endif - -//============================================================================== -// CHOLMOD:Supernodal Module -//============================================================================== +int64_t cholmod_l_collapse_septree (size_t, size_t, double, size_t, + int64_t *, int64_t *, cholmod_common *) ; -#ifndef NSUPERNODAL +/* ========================================================================== */ +/* === Include/cholmod_supernodal.h ========================================= */ +/* ========================================================================== */ -/* Supernodal analysis, factorization, and solve. The simplest way to use +/* CHOLMOD Supernodal module. + * + * Supernodal analysis, factorization, and solve. The simplest way to use * these routines is via the Cholesky module. It does not provide any * fill-reducing orderings, but does accept the orderings computed by the * Cholesky module. It does not require the Cholesky module itself, however. @@ -3732,10 +4468,12 @@ int64_t cholmod_l_collapse_septree (size_t, size_t, double, size_t, int64_t *, * ---------------- * dpotrf LAPACK: A=chol(tril(A)) * - * Requires the Utility module, and two external packages: LAPACK and the BLAS. + * Requires the Core module, and two external packages: LAPACK and the BLAS. * Optionally used by the Cholesky module. */ +#ifndef NSUPERNODAL + /* -------------------------------------------------------------------------- */ /* cholmod_super_symbolic */ /* -------------------------------------------------------------------------- */ @@ -3758,8 +4496,8 @@ int cholmod_super_symbolic cholmod_common *Common ) ; -int cholmod_l_super_symbolic (cholmod_sparse *, cholmod_sparse *, int64_t *, - cholmod_factor *, cholmod_common *) ; +int cholmod_l_super_symbolic (cholmod_sparse *, cholmod_sparse *, + int64_t *, cholmod_factor *, cholmod_common *) ; /* -------------------------------------------------------------------------- */ /* cholmod_super_symbolic2 */ @@ -3862,37 +4600,19 @@ int cholmod_l_super_ltsolve (cholmod_factor *, cholmod_dense *, cholmod_dense *, } #endif -//============================================================================== -// CHOLMOD:SupernodalGPU Module -//============================================================================== - -//------------------------------------------------------------------------------ -// cholmod_score_comp: for sorting descendant supernodes with qsort -//------------------------------------------------------------------------------ - -#ifdef __cplusplus -extern "C" { -#endif - -typedef struct cholmod_descendant_score_t -{ - double score ; - int64_t d ; -} -descendantScore ; -int cholmod_score_comp (struct cholmod_descendant_score_t *i, - struct cholmod_descendant_score_t *j) ; -int cholmod_l_score_comp (struct cholmod_descendant_score_t *i, - struct cholmod_descendant_score_t *j) ; +/* ========================================================================== */ +/* === Include/cholmod_gpu.h ================================================ */ +/* ========================================================================== */ -#ifdef __cplusplus -} -#endif +/* ----------------------------------------------------------------------------- + * CHOLMOD/Include/cholmod_gpu.h. + * Copyright (C) 2014, Timothy A. Davis + * http://www.suitesparse.com + * -------------------------------------------------------------------------- */ -//------------------------------------------------------------------------------ -// remainder of SupernodalGPU Module -//------------------------------------------------------------------------------ +/* CHOLMOD GPU module + */ #ifdef SUITESPARSE_CUDA @@ -3915,10 +4635,11 @@ int cholmod_l_score_comp (struct cholmod_descendant_score_t *i, #define CHOLMOD_POTRF_LIMIT 512 /* required cols for POTRF & TRSM on GPU */ /* # of host supernodes to perform before checking for free pinned buffers */ -#define CHOLMOD_GPU_SKIP 3 +#define CHOLMOD_GPU_SKIP 3 #define CHOLMOD_HANDLE_CUDA_ERROR(e,s) {if (e) {ERROR(CHOLMOD_GPU_PROBLEM,s);}} +/* make it easy for C++ programs to include CHOLMOD */ #ifdef __cplusplus extern "C" { #endif @@ -3948,7 +4669,7 @@ int cholmod_l_gpu_memorysize /* GPU memory size available, 1 if no GPU */ size_t *available_mem, cholmod_common *Common ) ; - + int cholmod_gpu_probe ( cholmod_common *Common ) ; int cholmod_l_gpu_probe ( cholmod_common *Common ) ; @@ -3968,4 +4689,3 @@ int cholmod_l_gpu_allocate ( cholmod_common *Common ) ; #endif #endif - diff --git a/CHOLMOD/Include/cholmod_internal.h b/CHOLMOD/Include/cholmod_internal.h index 62c6d92750..e14eeb48ce 100644 --- a/CHOLMOD/Include/cholmod_internal.h +++ b/CHOLMOD/Include/cholmod_internal.h @@ -18,7 +18,7 @@ * * Required by all CHOLMOD routines. Not required by any user routine that * uses CHOLMOMD. Unless debugging is enabled, this file does not require any - * CHOLMOD module (not even the Utility module). + * CHOLMOD module (not even the Core module). * * If debugging is enabled, all CHOLMOD modules require the Check module. * Enabling debugging requires that this file be editted. Debugging cannot be @@ -55,6 +55,7 @@ #undef FALSE #define TRUE 1 #define FALSE 0 +#define BOOLEAN(x) ((x) ? TRUE : FALSE) /* NULL should already be defined, but ensure it is here. */ #ifndef NULL @@ -76,11 +77,6 @@ #define MIN(a,b) (((a) < (b)) ? (a) : (b)) #define IMPLIES(p,q) (!(p) || (q)) -// RANGE (k, lo, hi): ensures k is in range lo:hi -#define RANGE(k,lo,hi) \ - (((k) < (lo)) ? (lo) : \ - (((k) > (hi)) ? (hi) : (k))) - /* find the sign: -1 if x < 0, 1 if x > 0, zero otherwise. * Not safe for NaN's */ #define SIGN(x) (((x) < 0) ? (-1) : (((x) > 0) ? 1 : 0)) @@ -97,11 +93,11 @@ { \ if ((A) == NULL) \ { \ - if (Common->status != CHOLMOD_OUT_OF_MEMORY) \ - { \ - ERROR (CHOLMOD_INVALID, "argument missing") ; \ - } \ - return (result) ; \ + if (Common->status != CHOLMOD_OUT_OF_MEMORY) \ + { \ + ERROR (CHOLMOD_INVALID, "argument missing") ; \ + } \ + return (result) ; \ } \ } @@ -110,15 +106,22 @@ { \ if (Common == NULL) \ { \ - return (result) ; \ + return (result) ; \ } \ - if (Common->itype != ITYPE) \ + if (Common->itype != ITYPE || Common->dtype != DTYPE) \ { \ - Common->status = CHOLMOD_INVALID ; \ - return (result) ; \ + Common->status = CHOLMOD_INVALID ; \ + return (result) ; \ } \ } +#define IS_NAN(x) CHOLMOD_IS_NAN(x) +#define IS_ZERO(x) CHOLMOD_IS_ZERO(x) +#define IS_NONZERO(x) CHOLMOD_IS_NONZERO(x) +#define IS_LT_ZERO(x) CHOLMOD_IS_LT_ZERO(x) +#define IS_GT_ZERO(x) CHOLMOD_IS_GT_ZERO(x) +#define IS_LE_ZERO(x) CHOLMOD_IS_LE_ZERO(x) + /* 1e308 is a huge number that doesn't take many characters to print in a * file, in CHOLMOD/Check/cholmod_read and _write. Numbers larger than this * are interpretted as Inf, since sscanf doesn't read in Inf's properly. @@ -126,72 +129,25 @@ * better, except that it takes too many digits to print in a file. */ #define HUGE_DOUBLE 1e308 -//============================================================================== -// int32/int64 and double/single definitions -//============================================================================== +/* ========================================================================== */ +/* === int/long and double/float definitions ================================ */ +/* ========================================================================== */ #include "cholmod_types.h" -#ifndef CHOLMOD_INT64 -// GPU acceleration only available for the CHOLMOD_INT64 case (int64) +#ifndef DLONG +// GPU acceleration only available for the DLONG case (double, int64) #undef SUITESPARSE_CUDA #endif -//------------------------------------------------------------------------------ -// internal routines -//------------------------------------------------------------------------------ - -bool cholmod_mult_uint64_t // c = a*b, return true if ok -( - uint64_t *restrict c, - const uint64_t a, - const uint64_t b -) ; - -size_t cholmod_add_size_t (size_t a, size_t b, int *ok) ; -size_t cholmod_mult_size_t (size_t a, size_t b, int *ok) ; -size_t cholmod_l_add_size_t (size_t a, size_t b, int *ok) ; -size_t cholmod_l_mult_size_t (size_t a, size_t b, int *ok) ; - -int64_t cholmod_cumsum // return sum (Cnz), or -1 if int32_t overflow -( - int32_t *Cp, // size n+1, output array, the cumsum of Cnz - int32_t *Cnz, // size n, input array - size_t n // size of Cp and Cnz -) ; - -int64_t cholmod_l_cumsum // return sum (Cnz), or -1 if int64_t overflow -( - int64_t *Cp, // size n+1, output array, the cumsum of Cnz - int64_t *Cnz, // size n, input array - size_t n // size of Cp and Cnz -) ; - -void cholmod_set_empty -( - int32_t *S, // int32 array of size n - size_t n -) ; - -void cholmod_l_set_empty -( - int64_t *S, // int64 array of size n - size_t n -) ; - -int cholmod_to_simplicial_sym -( - cholmod_factor *L, // sparse factorization to modify - int to_ll, // change L to hold a LL' or LDL' factorization - cholmod_common *Common -) ; +/* -------------------------------------------------------------------------- */ +/* routines for doing arithmetic on size_t, and checking for overflow */ +/* -------------------------------------------------------------------------- */ -int cholmod_l_to_simplicial_sym -( - cholmod_factor *L, // sparse factorization to modify - int to_ll, // change L to hold a LL' or LDL' factorization - cholmod_common *Common -) ; +size_t cholmod_add_size_t (size_t a, size_t b, int *ok) ; +size_t cholmod_mult_size_t (size_t a, size_t k, int *ok) ; +size_t cholmod_l_add_size_t (size_t a, size_t b, int *ok) ; +size_t cholmod_l_mult_size_t (size_t a, size_t k, int *ok) ; /* ========================================================================== */ /* === Include/cholmod_complexity.h ========================================= */ @@ -212,58 +168,51 @@ int cholmod_l_to_simplicial_sym * XTYPE and XTYPE2 are defined in cholmod_template.h. */ -//------------------------------------------------------------------------------ -// pattern: single or double -//------------------------------------------------------------------------------ - -#define P_TEMPLATE(name) p_ ## name -#define P_S_TEMPLATE(name) p_s_ ## name - -#define P_ASSIGN2(x,z,p,ax,az,q) x [p] = 1 -#define P_PRINT(k,x,z,p) PRK(k, ("1")) - -//------------------------------------------------------------------------------ -// real: single or double -//------------------------------------------------------------------------------ - -#define R_TEMPLATE(name) r_ ## name -#define R_S_TEMPLATE(name) r_s_ ## name - -#define R_ASSEMBLE(x,z,p,ax,az,q) x [p] += ax [q] -#define R_ASSIGN(x,z,p,ax,az,q) x [p] = ax [q] -#define R_ASSIGN_CONJ(x,z,p,ax,az,q) x [p] = ax [q] -#define R_ASSIGN_REAL(x,p,ax,q) x [p] = ax [q] -#define R_XTYPE_OK(type) ((type) == CHOLMOD_REAL) -#define R_IS_NONZERO(ax,az,q) (ax [q] != 0) -#define R_IS_ZERO(ax,az,q) (ax [q] == 0) -#define R_IS_ONE(ax,az,q) (ax [q] == 1) -#define R_MULT(x,z,p, ax,az,q, bx,bz,r) x [p] = ax [q] * bx [r] -#define R_MULTADD(x,z,p, ax,az,q, bx,bz,r) x [p] += ax [q] * bx [r] -#define R_MULTSUB(x,z,p, ax,az,q, bx,bz,r) x [p] -= ax [q] * bx [r] -#define R_MULTADDCONJ(x,z,p, ax,az,q, bx,bz,r) x [p] += ax [q] * bx [r] -#define R_MULTSUBCONJ(x,z,p, ax,az,q, bx,bz,r) x [p] -= ax [q] * bx [r] -#define R_ADD(x,z,p, ax,az,q, bx,bz,r) x [p] = ax [q] + bx [r] -#define R_ADD_REAL(x,p, ax,q, bx,r) x [p] = ax [q] + bx [r] -#define R_CLEAR(x,z,p) x [p] = 0 +/* -------------------------------------------------------------------------- */ +/* pattern */ +/* -------------------------------------------------------------------------- */ + +#define P_TEMPLATE(name) p_ ## name +#define P_ASSIGN2(x,z,p,ax,az,q) x [p] = 1 +#define P_PRINT(k,x,z,p) PRK(k, ("1")) + +/* -------------------------------------------------------------------------- */ +/* real */ +/* -------------------------------------------------------------------------- */ + +#define R_TEMPLATE(name) r_ ## name +#define R_ASSEMBLE(x,z,p,ax,az,q) x [p] += ax [q] +#define R_ASSIGN(x,z,p,ax,az,q) x [p] = ax [q] +#define R_ASSIGN_CONJ(x,z,p,ax,az,q) x [p] = ax [q] +#define R_ASSIGN_REAL(x,p,ax,q) x [p] = ax [q] +#define R_XTYPE_OK(type) ((type) == CHOLMOD_REAL) +#define R_IS_NONZERO(ax,az,q) IS_NONZERO (ax [q]) +#define R_IS_ZERO(ax,az,q) IS_ZERO (ax [q]) +#define R_IS_ONE(ax,az,q) (ax [q] == 1) +#define R_MULT(x,z,p, ax,az,q, bx,bz,r) x [p] = ax [q] * bx [r] +#define R_MULTADD(x,z,p, ax,az,q, bx,bz,r) x [p] += ax [q] * bx [r] +#define R_MULTSUB(x,z,p, ax,az,q, bx,bz,r) x [p] -= ax [q] * bx [r] +#define R_MULTADDCONJ(x,z,p, ax,az,q, bx,bz,r) x [p] += ax [q] * bx [r] +#define R_MULTSUBCONJ(x,z,p, ax,az,q, bx,bz,r) x [p] -= ax [q] * bx [r] +#define R_ADD(x,z,p, ax,az,q, bx,bz,r) x [p] = ax [q] + bx [r] +#define R_ADD_REAL(x,p, ax,q, bx,r) x [p] = ax [q] + bx [r] +#define R_CLEAR(x,z,p) x [p] = 0 #define R_CLEAR_IMAG(x,z,p) -#define R_DIV(x,z,p,ax,az,q) x [p] /= ax [q] -#define R_LLDOT(x,p, ax,az,q) x [p] -= ax [q] * ax [q] -#define R_PRINT(k,x,z,p) PRK(k, ("%24.16e", x [p])) +#define R_DIV(x,z,p,ax,az,q) x [p] /= ax [q] +#define R_LLDOT(x,p, ax,az,q) x [p] -= ax [q] * ax [q] +#define R_PRINT(k,x,z,p) PRK(k, ("%24.16e", x [p])) -#define R_DIV_REAL(x,z,p, ax,az,q, bx,r) x [p] = ax [q] / bx [r] -#define R_MULT_REAL(x,z,p, ax,az,q, bx,r) x [p] = ax [q] * bx [r] +#define R_DIV_REAL(x,z,p, ax,az,q, bx,r) x [p] = ax [q] / bx [r] +#define R_MULT_REAL(x,z,p, ax,az,q, bx,r) x [p] = ax [q] * bx [r] -#define R_LDLDOT(x,p, ax,az,q, bx,r) x [p] -=(ax[q] * ax[q])/ bx[r] +#define R_LDLDOT(x,p, ax,az,q, bx,r) x [p] -=(ax[q] * ax[q])/ bx[r] -//------------------------------------------------------------------------------ -// complex: single or double -//------------------------------------------------------------------------------ - -#define C_TEMPLATE(name) c_ ## name -#define CT_TEMPLATE(name) ct_ ## name +/* -------------------------------------------------------------------------- */ +/* complex */ +/* -------------------------------------------------------------------------- */ -#define C_S_TEMPLATE(name) c_s_ ## name -#define CT_S_TEMPLATE(name) ct_s_ ## name +#define C_TEMPLATE(name) c_ ## name +#define CT_TEMPLATE(name) ct_ ## name #define C_ASSEMBLE(x,z,p,ax,az,q) \ x [2*(p) ] += ax [2*(q) ] ; \ @@ -273,44 +222,46 @@ int cholmod_l_to_simplicial_sym x [2*(p) ] = ax [2*(q) ] ; \ x [2*(p)+1] = ax [2*(q)+1] -#define C_ASSIGN_REAL(x,p,ax,q) x [2*(p)] = ax [2*(q)] +#define C_ASSIGN_REAL(x,p,ax,q) x [2*(p)] = ax [2*(q)] #define C_ASSIGN_CONJ(x,z,p,ax,az,q) \ x [2*(p) ] = ax [2*(q) ] ; \ x [2*(p)+1] = -ax [2*(q)+1] -#define C_XTYPE_OK(type) ((type) == CHOLMOD_COMPLEX) +#define C_XTYPE_OK(type) ((type) == CHOLMOD_COMPLEX) -#define C_IS_NONZERO(ax,az,q) ((ax [2*(q)] != 0) || (ax [2*(q)+1] != 0)) +#define C_IS_NONZERO(ax,az,q) \ + (IS_NONZERO (ax [2*(q)]) || IS_NONZERO (ax [2*(q)+1])) -#define C_IS_ZERO(ax,az,q) ((ax [2*(q)] == 0) && (ax [2*(q)+1] == 0)) +#define C_IS_ZERO(ax,az,q) \ + (IS_ZERO (ax [2*(q)]) && IS_ZERO (ax [2*(q)+1])) #define C_IS_ONE(ax,az,q) \ - ((ax [2*(q)] == 1) && (ax [2*(q)+1]) == 0) + ((ax [2*(q)] == 1) && IS_ZERO (ax [2*(q)+1])) -#define C_IMAG_IS_NONZERO(ax,az,q) (ax [2*(q)+1] != 0) +#define C_IMAG_IS_NONZERO(ax,az,q) (IS_NONZERO (ax [2*(q)+1])) #define C_MULT(x,z,p, ax,az,q, bx,bz,r) \ - x [2*(p) ] = ax [2*(q) ] * bx [2*(r)] - ax [2*(q)+1] * bx [2*(r)+1] ; \ - x [2*(p)+1] = ax [2*(q)+1] * bx [2*(r)] + ax [2*(q) ] * bx [2*(r)+1] +x [2*(p) ] = ax [2*(q) ] * bx [2*(r)] - ax [2*(q)+1] * bx [2*(r)+1] ; \ +x [2*(p)+1] = ax [2*(q)+1] * bx [2*(r)] + ax [2*(q) ] * bx [2*(r)+1] #define C_MULTADD(x,z,p, ax,az,q, bx,bz,r) \ - x [2*(p) ] += ax [2*(q) ] * bx [2*(r)] - ax [2*(q)+1] * bx [2*(r)+1] ; \ - x [2*(p)+1] += ax [2*(q)+1] * bx [2*(r)] + ax [2*(q) ] * bx [2*(r)+1] +x [2*(p) ] += ax [2*(q) ] * bx [2*(r)] - ax [2*(q)+1] * bx [2*(r)+1] ; \ +x [2*(p)+1] += ax [2*(q)+1] * bx [2*(r)] + ax [2*(q) ] * bx [2*(r)+1] #define C_MULTSUB(x,z,p, ax,az,q, bx,bz,r) \ - x [2*(p) ] -= ax [2*(q) ] * bx [2*(r)] - ax [2*(q)+1] * bx [2*(r)+1] ; \ - x [2*(p)+1] -= ax [2*(q)+1] * bx [2*(r)] + ax [2*(q) ] * bx [2*(r)+1] +x [2*(p) ] -= ax [2*(q) ] * bx [2*(r)] - ax [2*(q)+1] * bx [2*(r)+1] ; \ +x [2*(p)+1] -= ax [2*(q)+1] * bx [2*(r)] + ax [2*(q) ] * bx [2*(r)+1] /* s += conj(a)*b */ #define C_MULTADDCONJ(x,z,p, ax,az,q, bx,bz,r) \ - x [2*(p) ] += ax [2*(q) ] * bx [2*(r)] + ax [2*(q)+1] * bx [2*(r)+1] ;\ - x [2*(p)+1] += (-ax [2*(q)+1]) * bx [2*(r)] + ax [2*(q) ] * bx [2*(r)+1] +x [2*(p) ] += ax [2*(q) ] * bx [2*(r)] + ax [2*(q)+1] * bx [2*(r)+1] ; \ +x [2*(p)+1] += (-ax [2*(q)+1]) * bx [2*(r)] + ax [2*(q) ] * bx [2*(r)+1] /* s -= conj(a)*b */ #define C_MULTSUBCONJ(x,z,p, ax,az,q, bx,bz,r) \ - x [2*(p) ] -= ax [2*(q) ] * bx [2*(r)] + ax [2*(q)+1] * bx [2*(r)+1] ;\ - x [2*(p)+1] -= (-ax [2*(q)+1]) * bx [2*(r)] + ax [2*(q) ] * bx [2*(r)+1] +x [2*(p) ] -= ax [2*(q) ] * bx [2*(r)] + ax [2*(q)+1] * bx [2*(r)+1] ; \ +x [2*(p)+1] -= (-ax [2*(q)+1]) * bx [2*(r)] + ax [2*(q) ] * bx [2*(r)+1] #define C_ADD(x,z,p, ax,az,q, bx,bz,r) \ x [2*(p) ] = ax [2*(q) ] + bx [2*(r) ] ; \ @@ -326,24 +277,12 @@ int cholmod_l_to_simplicial_sym #define C_CLEAR_IMAG(x,z,p) \ x [2*(p)+1] = 0 -// s = s / a (complex double case) +/* s = s / a */ #define C_DIV(x,z,p,ax,az,q) \ SuiteSparse_config_divcomplex ( \ - x [2*(p)], x [2*(p)+1], \ - ax [2*(q)], ax [2*(q)+1], \ - &x [2*(p)], &x [2*(p)+1]) - -// s = s / a (complex single case) -#define C_S_DIV(x,z,p,ax,az,q) \ -{ \ - double cr, ci ; \ - SuiteSparse_config_divcomplex ( \ - (double) x [2*(p)], (double) x [2*(p)+1], \ - (double) ax [2*(q)], (double) ax [2*(q)+1], \ - &cr, &ci) ; \ - x [2*(p) ] = (float) cr ; \ - x [2*(p)+1] = (float) ci ; \ -} + x [2*(p)], x [2*(p)+1], \ + ax [2*(q)], ax [2*(q)+1], \ + &x [2*(p)], &x [2*(p)+1]) /* s -= conj(a)*a ; note that the result of conj(a)*a is real */ #define C_LLDOT(x,p, ax,az,q) \ @@ -363,15 +302,12 @@ int cholmod_l_to_simplicial_sym #define C_LDLDOT(x,p, ax,az,q, bx,r) \ x [2*(p)] -= (ax [2*(q)] * ax [2*(q)] + ax [2*(q)+1] * ax [2*(q)+1]) / bx[r] -//------------------------------------------------------------------------------ -// zomplex: single or double -//------------------------------------------------------------------------------ +/* -------------------------------------------------------------------------- */ +/* zomplex */ +/* -------------------------------------------------------------------------- */ -#define Z_TEMPLATE(name) z_ ## name -#define ZT_TEMPLATE(name) zt_ ## name - -#define Z_S_TEMPLATE(name) z_s_ ## name -#define ZT_S_TEMPLATE(name) zt_s_ ## name +#define Z_TEMPLATE(name) z_ ## name +#define ZT_TEMPLATE(name) zt_ ## name #define Z_ASSEMBLE(x,z,p,ax,az,q) \ x [p] += ax [q] ; \ @@ -381,21 +317,24 @@ int cholmod_l_to_simplicial_sym x [p] = ax [q] ; \ z [p] = az [q] -#define Z_ASSIGN_REAL(x,p,ax,q) x [p] = ax [q] +#define Z_ASSIGN_REAL(x,p,ax,q) x [p] = ax [q] #define Z_ASSIGN_CONJ(x,z,p,ax,az,q) \ x [p] = ax [q] ; \ z [p] = -az [q] -#define Z_XTYPE_OK(type) ((type) == CHOLMOD_ZOMPLEX) +#define Z_XTYPE_OK(type) ((type) == CHOLMOD_ZOMPLEX) -#define Z_IS_NONZERO(ax,az,q) ((ax [q] != 0) || (az [q] != 0)) +#define Z_IS_NONZERO(ax,az,q) \ + (IS_NONZERO (ax [q]) || IS_NONZERO (az [q])) -#define Z_IS_ZERO(ax,az,q) ((ax [q] == 0) && (az [q] == 0)) +#define Z_IS_ZERO(ax,az,q) \ + (IS_ZERO (ax [q]) && IS_ZERO (az [q])) -#define Z_IS_ONE(ax,az,q) ((ax [q] == 1) && (az [q] == 0)) +#define Z_IS_ONE(ax,az,q) \ + ((ax [q] == 1) && IS_ZERO (az [q])) -#define Z_IMAG_IS_NONZERO(ax,az,q) (az [q] != 0) +#define Z_IMAG_IS_NONZERO(ax,az,q) (IS_NONZERO (az [q])) #define Z_MULT(x,z,p, ax,az,q, bx,bz,r) \ x [p] = ax [q] * bx [r] - az [q] * bz [r] ; \ @@ -418,11 +357,11 @@ int cholmod_l_to_simplicial_sym z [p] -= (-az [q]) * bx [r] + ax [q] * bz [r] #define Z_ADD(x,z,p, ax,az,q, bx,bz,r) \ - x [p] = ax [q] + bx [r] ; \ - z [p] = az [q] + bz [r] + x [p] = ax [q] + bx [r] ; \ + z [p] = az [q] + bz [r] #define Z_ADD_REAL(x,p, ax,q, bx,r) \ - x [p] = ax [q] + bx [r] + x [p] = ax [q] + bx [r] #define Z_CLEAR(x,z,p) \ x [p] = 0 ; \ @@ -431,28 +370,16 @@ int cholmod_l_to_simplicial_sym #define Z_CLEAR_IMAG(x,z,p) \ z [p] = 0 -// s = s / a (zomplex double case) +/* s = s / a */ #define Z_DIV(x,z,p,ax,az,q) \ SuiteSparse_config_divcomplex \ (x [p], z [p], ax [q], az [q], &x [p], &z [p]) -// s = s / a (zomplex single case) -#define Z_S_DIV(x,z,p,ax,az,q) \ -{ \ - double cr, ci ; \ - SuiteSparse_config_divcomplex ( \ - (double) x [p], (double) z [p], \ - (double) ax [q], (double) az [q], \ - &cr, &ci) ; \ - x [p] = (float) cr ; \ - z [p] = (float) ci ; \ -} - /* s -= conj(a)*a ; note that the result of conj(a)*a is real */ #define Z_LLDOT(x,p, ax,az,q) \ x [p] -= ax [q] * ax [q] + az [q] * az [q] -#define Z_PRINT(k,x,z,p) PRK(k, ("(%24.16e,%24.16e)", x [p], z [p])) +#define Z_PRINT(k,x,z,p) PRK(k, ("(%24.16e,%24.16e)", x [p], z [p])) #define Z_DIV_REAL(x,z,p, ax,az,q, bx,r) \ x [p] = ax [q] / bx [r] ; \ @@ -466,141 +393,76 @@ int cholmod_l_to_simplicial_sym #define Z_LDLDOT(x,p, ax,az,q, bx,r) \ x [p] -= (ax [q] * ax [q] + az [q] * az [q]) / bx[r] -//------------------------------------------------------------------------------ -// all classes -//------------------------------------------------------------------------------ - -// Check if A->xtype and the two arrays A->x and A->z are valid. Set status to -// invalid, unless status is already "out of memory". A can be a sparse matrix, -// dense matrix, factor, or triplet. - -#define RETURN_IF_XTYPE_IS_INVALID(xtype,xtype1,xtype2,result) \ - if (xtype < (xtype1) || xtype > (xtype2)) \ - { \ - if (Common->status != CHOLMOD_OUT_OF_MEMORY) \ - { \ - ERROR (CHOLMOD_INVALID, "invalid xtype") ; \ - } \ - return (result) ; \ - } \ - -#define RETURN_IF_XTYPE_INVALID(A,xtype1,xtype2,result) \ -{ \ - if ((A)->xtype < (xtype1) || (A)->xtype > (xtype2) || \ - ((A)->xtype != CHOLMOD_PATTERN && ((A)->x) == NULL) || \ - ((A)->xtype == CHOLMOD_ZOMPLEX && ((A)->z) == NULL) || \ - !(((A)->dtype == CHOLMOD_DOUBLE) || ((A)->dtype == CHOLMOD_SINGLE))) \ - { \ - if (Common->status != CHOLMOD_OUT_OF_MEMORY) \ - { \ - ERROR (CHOLMOD_INVALID, "invalid xtype or dtype") ; \ - } \ - return (result) ; \ - } \ -} +/* -------------------------------------------------------------------------- */ +/* all classes */ +/* -------------------------------------------------------------------------- */ -#define RETURN_IF_DENSE_MATRIX_INVALID(X,result) \ - RETURN_IF_NULL (X, result) ; \ - RETURN_IF_XTYPE_INVALID (X, CHOLMOD_REAL, CHOLMOD_ZOMPLEX, result) ; \ - if ((X)->d < (X)->nrow) \ - { \ - if (Common->status != CHOLMOD_OUT_OF_MEMORY) \ - { \ - ERROR (CHOLMOD_INVALID, "dense matrix invalid") ; \ - } \ - return (result) ; \ - } - -#define RETURN_IF_SPARSE_MATRIX_INVALID(A,result) \ - RETURN_IF_NULL (A, result) ; \ - RETURN_IF_XTYPE_INVALID (A, CHOLMOD_PATTERN, CHOLMOD_ZOMPLEX, result) ; \ - if ((A)->p == NULL || (!(A)->packed && ((A)->nz == NULL)) || \ - (A->stype != 0 && A->nrow != A->ncol)) \ - { \ - if (Common->status != CHOLMOD_OUT_OF_MEMORY) \ - { \ - ERROR (CHOLMOD_INVALID, "sparse matrix invalid") ; \ - } \ - return (result) ; \ - } - -#define RETURN_IF_TRIPLET_MATRIX_INVALID(T,result) \ - RETURN_IF_NULL (T, result) ; \ - RETURN_IF_XTYPE_INVALID (T, CHOLMOD_PATTERN, CHOLMOD_ZOMPLEX, result) ; \ - if ((T)->nnz > 0 && ((T)->i == NULL || (T)->j == NULL || \ - ((T)->xtype != CHOLMOD_PATTERN && (T)->x == NULL) || \ - ((T)->xtype == CHOLMOD_ZOMPLEX && (T)->z == NULL))) \ - { \ - if (Common->status != CHOLMOD_OUT_OF_MEMORY) \ - { \ - ERROR (CHOLMOD_INVALID, "triplet matrix invalid") ; \ - } \ - return (result) ; \ - } +/* Check if A->xtype and the two arrays A->x and A->z are valid. Set status to + * invalid, unless status is already "out of memory". A can be a sparse matrix, + * dense matrix, factor, or triplet. */ -#define RETURN_IF_FACTOR_INVALID(L,result) \ - RETURN_IF_NULL (L, result) ; \ - RETURN_IF_XTYPE_INVALID (L, CHOLMOD_PATTERN, CHOLMOD_ZOMPLEX, result) ; +#define RETURN_IF_XTYPE_INVALID(A,xtype1,xtype2,result) \ +{ \ + if ((A)->xtype < (xtype1) || (A)->xtype > (xtype2) || \ + ((A)->xtype != CHOLMOD_PATTERN && ((A)->x) == NULL) || \ + ((A)->xtype == CHOLMOD_ZOMPLEX && ((A)->z) == NULL)) \ + { \ + if (Common->status != CHOLMOD_OUT_OF_MEMORY) \ + { \ + ERROR (CHOLMOD_INVALID, "invalid xtype") ; \ + } \ + return (result) ; \ + } \ +} -//============================================================================== -// Architecture and BLAS -//============================================================================== +/* ========================================================================== */ +/* === Architecture and BLAS ================================================ */ +/* ========================================================================== */ #if defined (__sun) || defined (MSOL2) || defined (ARCH_SOL2) - - #define CHOLMOD_SOL2 - #define CHOLMOD_ARCHITECTURE "Sun Solaris" +#define CHOLMOD_SOL2 +#define CHOLMOD_ARCHITECTURE "Sun Solaris" #elif defined (__sgi) || defined (MSGI) || defined (ARCH_SGI) - - #define CHOLMOD_SGI - #define CHOLMOD_ARCHITECTURE "SGI Irix" +#define CHOLMOD_SGI +#define CHOLMOD_ARCHITECTURE "SGI Irix" #elif defined (__linux) || defined (MGLNX86) || defined (ARCH_GLNX86) - - #define CHOLMOD_LINUX - #define CHOLMOD_ARCHITECTURE "Linux" +#define CHOLMOD_LINUX +#define CHOLMOD_ARCHITECTURE "Linux" #elif defined (__APPLE__) - - #define CHOLMOD_MAC - #define CHOLMOD_ARCHITECTURE "Mac" +#define CHOLMOD_MAC +#define CHOLMOD_ARCHITECTURE "Mac" #elif defined (_AIX) || defined (MIBM_RS) || defined (ARCH_IBM_RS) - - #define CHOLMOD_AIX - #define CHOLMOD_ARCHITECTURE "IBM AIX" +#define CHOLMOD_AIX +#define CHOLMOD_ARCHITECTURE "IBM AIX" #elif defined (__alpha) || defined (MALPHA) || defined (ARCH_ALPHA) - - #define CHOLMOD_ALPHA - #define CHOLMOD_ARCHITECTURE "Compaq Alpha" +#define CHOLMOD_ALPHA +#define CHOLMOD_ARCHITECTURE "Compaq Alpha" #elif defined (_WIN32) || defined (WIN32) || defined (_WIN64) || defined (WIN64) - - #if defined (__MINGW32__) || defined (__MINGW32__) - #define CHOLMOD_MINGW - #elif defined (__CYGWIN32__) || defined (__CYGWIN32__) - #define CHOLMOD_CYGWIN - #else - #define CHOLMOD_WINDOWS - #endif - #define CHOLMOD_ARCHITECTURE "Microsoft Windows" +#if defined (__MINGW32__) || defined (__MINGW32__) +#define CHOLMOD_MINGW +#elif defined (__CYGWIN32__) || defined (__CYGWIN32__) +#define CHOLMOD_CYGWIN +#else +#define CHOLMOD_WINDOWS +#endif +#define CHOLMOD_ARCHITECTURE "Microsoft Windows" #elif defined (__hppa) || defined (__hpux) || defined (MHPUX) || defined (ARCH_HPUX) - - #define CHOLMOD_HP - #define CHOLMOD_ARCHITECTURE "HP Unix" +#define CHOLMOD_HP +#define CHOLMOD_ARCHITECTURE "HP Unix" #elif defined (__hp700) || defined (MHP700) || defined (ARCH_HP700) - - #define CHOLMOD_HP - #define CHOLMOD_ARCHITECTURE "HP 700 Unix" +#define CHOLMOD_HP +#define CHOLMOD_ARCHITECTURE "HP 700 Unix" #else - - #define CHOLMOD_ARCHITECTURE "unknown" - +#define CHOLMOD_ARCHITECTURE "unknown" #endif //============================================================================== @@ -663,7 +525,7 @@ int cholmod_dump_perm (int *, size_t, size_t, const char *, cholmod_common *) ; int cholmod_dump_parent (int *, size_t, const char *, cholmod_common *) ; void cholmod_dump_init (const char *, cholmod_common *) ; int cholmod_dump_mem (const char *, int64_t, cholmod_common *) ; -void cholmod_dump_real (const char *, double *, int64_t, +void cholmod_dump_real (const char *, Real *, int64_t, int64_t, int, int, cholmod_common *) ; void cholmod_dump_super (int64_t, int *, int *, int *, int *, double *, int, cholmod_common *) ; @@ -687,7 +549,7 @@ int cholmod_l_dump_parent (int64_t *, size_t, const char *, cholmod_common *) ; void cholmod_l_dump_init (const char *, cholmod_common *) ; int cholmod_l_dump_mem (const char *, int64_t, cholmod_common *) ; -void cholmod_l_dump_real (const char *, double *, int64_t, +void cholmod_l_dump_real (const char *, Real *, int64_t, int64_t, int, int, cholmod_common *) ; void cholmod_l_dump_super (int64_t, int64_t *, int64_t *, int64_t *, int64_t *, @@ -718,19 +580,11 @@ int cholmod_l_dump_work(int, int, int64_t, cholmod_common *) ; #define PRINT2(params) PRK (2, params) #define PRINT3(params) PRK (3, params) -void CM_memtable_dump (void) ; -int CM_memtable_n (void) ; -void CM_memtable_clear (void) ; -void CM_memtable_add (void *p, size_t size) ; -size_t CM_memtable_size (void *p) ; -bool CM_memtable_find (void *p) ; -void CM_memtable_remove (void *p) ; - #define PRINTM(params) \ { \ if (CHOLMOD(dump_malloc) > 0) \ { \ - printf params ; \ + printf params ; \ } \ } @@ -750,28 +604,4 @@ void CM_memtable_remove (void *p) ; #define DEBUG(statement) #endif -static bool check_flag (cholmod_common *Common) -{ - int64_t mark = Common->mark ; - size_t n = Common->nrow ; - if (Common->itype == CHOLMOD_LONG) - { - int64_t *Flag = Common->Flag ; - for (int64_t i = 0 ; i < n ; i++) - { - if (Flag [i] >= mark) return (false) ; - } - } - else - { - ASSERT (mark <= INT32_MAX) ; - int32_t *Flag = Common->Flag ; - for (int32_t i = 0 ; i < n ; i++) - { - if (Flag [i] >= mark) return (false) ; - } - } - return (true) ; -} - #endif diff --git a/CHOLMOD/Include/cholmod_template.h b/CHOLMOD/Include/cholmod_template.h index 8ec5283541..77cd84d633 100644 --- a/CHOLMOD/Include/cholmod_template.h +++ b/CHOLMOD/Include/cholmod_template.h @@ -8,23 +8,9 @@ //------------------------------------------------------------------------------ -// The #including file must #define the following: -// -// Floating-point value, one of the following (default is DOUBLE): -// -// #define DOUBLE -// #define SINGLE -// -// pattern/real/complex/zomplex, one of (no default): -// -// #define PATTERN -// #define REAL -// #define COMPLEX -// #define ZOMPLEX - -//------------------------------------------------------------------------------ -// undefine current xtype macros, and then define macros for current type -//------------------------------------------------------------------------------ +/* -------------------------------------------------------------------------- */ +/* undefine current xtype macros, and then define macros for current type */ +/* -------------------------------------------------------------------------- */ #undef TEMPLATE #undef TEMPLATE2 @@ -42,8 +28,6 @@ #undef ASSIGN2 #undef ASSIGN2_CONJ #undef ASSIGN_REAL -#undef ASSIGN_CONJ_OR_NCONJ - #undef MULT #undef MULTADD #undef ADD @@ -67,285 +51,201 @@ #undef XPRINT2 #undef XPRINT3 -#undef Real - -//------------------------------------------------------------------------------ -// single/double -//------------------------------------------------------------------------------ - -#ifdef SINGLE - // single precision - #define Real float -#else - // double precision - #ifndef DOUBLE - #define DOUBLE - #endif - #define Real double -#endif +/* -------------------------------------------------------------------------- */ +/* pattern */ +/* -------------------------------------------------------------------------- */ -//------------------------------------------------------------------------------ -// pattern: both double and single -//------------------------------------------------------------------------------ #ifdef PATTERN - #ifdef SINGLE - #define PREFIX p_s_ - #define TEMPLATE(name) P_S_TEMPLATE(name) - #define TEMPLATE2(name) P_S_TEMPLATE(name) - #else - #define PREFIX p_ - #define TEMPLATE(name) P_TEMPLATE(name) - #define TEMPLATE2(name) P_TEMPLATE(name) - #endif - - #define XTYPE CHOLMOD_PATTERN - #define XTYPE2 CHOLMOD_REAL - #define XTYPE_OK(type) (TRUE) - #define ENTRY_IS_NONZERO(ax,az,q) (TRUE) - #define ENTRY_IS_ZERO(ax,az,q) (FALSE) - #define ENTRY_IS_ONE(ax,az,q) (TRUE) - #define IMAG_IS_NONZERO(ax,az,q) (FALSE) - #define ENTRY_SIZE 0 - - #define ASSEMBLE(x,z,p,ax,az,q) - #define ASSIGN(x,z,p,ax,az,q) - #define ASSIGN_CONJ(x,z,p,ax,az,q) - #define ASSIGN2(x,z,p,ax,az,q) P_ASSIGN2(x,z,p,ax,az,q) - #define ASSIGN2_CONJ(x,z,p,ax,az,q) P_ASSIGN2(x,z,p,ax,az,q) - #define ASSIGN_REAL(x,p,ax,q) - - #define MULT(x,z,p,ax,az,q,bx,bz,pb) - #define MULTADD(x,z,p,ax,az,q,bx,bz,pb) - #define ADD(x,z,p,ax,az,q,bx,bz,pb) - #define ADD_REAL(x,p, ax,q, bx,r) - #define MULTSUB(x,z,p,ax,az,q,bx,bz,pb) - #define MULTADDCONJ(x,z,p,ax,az,q,bx,bz,pb) - #define MULTSUBCONJ(x,z,p,ax,az,q,bx,bz,pb) - #define LLDOT(x,p,ax,az,q) - #define CLEAR(x,z,p) - #define CLEAR_IMAG(x,z,p) - #define DIV(x,z,p,ax,az,q) - #define DIV_REAL(x,z,p, ax,az,q, bx,r) - #define MULT_REAL(x,z,p, ax,az,q, bx,r) - #define LDLDOT(x,p, ax,az,q, bx,r) - - #define XPRINT0(x,z,p) P_PRINT(0,x,z,p) - #define XPRINT1(x,z,p) P_PRINT(1,x,z,p) - #define XPRINT2(x,z,p) P_PRINT(2,x,z,p) - #define XPRINT3(x,z,p) P_PRINT(3,x,z,p) - -//------------------------------------------------------------------------------ -// real: double and single -//------------------------------------------------------------------------------ +#define PREFIX p_ +#define TEMPLATE(name) P_TEMPLATE(name) +#define TEMPLATE2(name) P_TEMPLATE(name) +#define XTYPE CHOLMOD_PATTERN +#define XTYPE2 CHOLMOD_REAL +#define XTYPE_OK(type) (TRUE) +#define ENTRY_IS_NONZERO(ax,az,q) (TRUE) +#define ENTRY_IS_ZERO(ax,az,q) (FALSE) +#define ENTRY_IS_ONE(ax,az,q) (TRUE) +#define IMAG_IS_NONZERO(ax,az,q) (FALSE) +#define ENTRY_SIZE 0 + +#define ASSEMBLE(x,z,p,ax,az,q) +#define ASSIGN(x,z,p,ax,az,q) +#define ASSIGN_CONJ(x,z,p,ax,az,q) +#define ASSIGN2(x,z,p,ax,az,q) P_ASSIGN2(x,z,p,ax,az,q) +#define ASSIGN2_CONJ(x,z,p,ax,az,q) P_ASSIGN2(x,z,p,ax,az,q) +#define ASSIGN_REAL(x,p,ax,q) +#define MULT(x,z,p,ax,az,q,bx,bz,pb) +#define MULTADD(x,z,p,ax,az,q,bx,bz,pb) +#define ADD(x,z,p,ax,az,q,bx,bz,pb) +#define ADD_REAL(x,p, ax,q, bx,r) +#define MULTSUB(x,z,p,ax,az,q,bx,bz,pb) +#define MULTADDCONJ(x,z,p,ax,az,q,bx,bz,pb) +#define MULTSUBCONJ(x,z,p,ax,az,q,bx,bz,pb) +#define LLDOT(x,p,ax,az,q) +#define CLEAR(x,z,p) +#define CLEAR_IMAG(x,z,p) +#define DIV(x,z,p,ax,az,q) +#define DIV_REAL(x,z,p, ax,az,q, bx,r) +#define MULT_REAL(x,z,p, ax,az,q, bx,r) +#define LDLDOT(x,p, ax,az,q, bx,r) + +#define XPRINT0(x,z,p) P_PRINT(0,x,z,p) +#define XPRINT1(x,z,p) P_PRINT(1,x,z,p) +#define XPRINT2(x,z,p) P_PRINT(2,x,z,p) +#define XPRINT3(x,z,p) P_PRINT(3,x,z,p) + +/* -------------------------------------------------------------------------- */ +/* real */ +/* -------------------------------------------------------------------------- */ #elif defined (REAL) - #ifdef SINGLE - #define PREFIX r_s_ - #define TEMPLATE(name) R_S_TEMPLATE(name) - #define TEMPLATE2(name) R_S_TEMPLATE(name) - #else - #define PREFIX r_ - #define TEMPLATE(name) R_TEMPLATE(name) - #define TEMPLATE2(name) R_TEMPLATE(name) - #endif - - #define XTYPE CHOLMOD_REAL - #define XTYPE2 CHOLMOD_REAL - #define XTYPE_OK(type) R_XTYPE_OK(type) - #define ENTRY_IS_NONZERO(ax,az,q) R_IS_NONZERO(ax,az,q) - #define ENTRY_IS_ZERO(ax,az,q) R_IS_ZERO(ax,az,q) - #define ENTRY_IS_ONE(ax,az,q) R_IS_ONE(ax,az,q) - #define IMAG_IS_NONZERO(ax,az,q) (FALSE) - #define ENTRY_SIZE 1 - - #define ASSEMBLE(x,z,p,ax,az,q) R_ASSEMBLE(x,z,p,ax,az,q) - #define ASSIGN(x,z,p,ax,az,q) R_ASSIGN(x,z,p,ax,az,q) - #define ASSIGN_CONJ(x,z,p,ax,az,q) R_ASSIGN(x,z,p,ax,az,q) - #define ASSIGN2(x,z,p,ax,az,q) R_ASSIGN(x,z,p,ax,az,q) - #define ASSIGN2_CONJ(x,z,p,ax,az,q) R_ASSIGN(x,z,p,ax,az,q) - #define ASSIGN_REAL(x,p,ax,q) R_ASSIGN_REAL(x,p,ax,q) - - #define MULT(x,z,p,ax,az,q,bx,bz,pb) R_MULT(x,z,p,ax,az,q,bx,bz,pb) - #define MULTADD(x,z,p,ax,az,q,bx,bz,pb) R_MULTADD(x,z,p,ax,az,q,bx,bz,pb) - #define ADD(x,z,p,ax,az,q,bx,bz,pb) R_ADD(x,z,p,ax,az,q,bx,bz,pb) - #define ADD_REAL(x,p, ax,q, bx,r) R_ADD_REAL(x,p, ax,q, bx,r) - #define MULTSUB(x,z,p,ax,az,q,bx,bz,pb) R_MULTSUB(x,z,p,ax,az,q,bx,bz,pb) - #define MULTADDCONJ(x,z,p,ax,az,q,bx,bz,pb) \ - R_MULTADDCONJ(x,z,p,ax,az,q,bx,bz,pb) - #define MULTSUBCONJ(x,z,p,ax,az,q,bx,bz,pb) \ - R_MULTSUBCONJ(x,z,p,ax,az,q,bx,bz,pb) - #define LLDOT(x,p,ax,az,q) R_LLDOT(x,p,ax,az,q) - #define CLEAR(x,z,p) R_CLEAR(x,z,p) - #define CLEAR_IMAG(x,z,p) R_CLEAR_IMAG(x,z,p) - - #define DIV(x,z,p,ax,az,q) R_DIV(x,z,p,ax,az,q) - - #define DIV_REAL(x,z,p, ax,az,q, bx,r) R_DIV_REAL(x,z,p, ax,az,q, bx,r) - #define MULT_REAL(x,z,p, ax,az,q, bx,r) R_MULT_REAL(x,z,p, ax,az,q, bx,r) - #define LDLDOT(x,p, ax,az,q, bx,r) R_LDLDOT(x,p, ax,az,q, bx,r) - - #define XPRINT0(x,z,p) R_PRINT(0,x,z,p) - #define XPRINT1(x,z,p) R_PRINT(1,x,z,p) - #define XPRINT2(x,z,p) R_PRINT(2,x,z,p) - #define XPRINT3(x,z,p) R_PRINT(3,x,z,p) - -//------------------------------------------------------------------------------ -// complex: both double and single -//------------------------------------------------------------------------------ +#define PREFIX r_ +#define TEMPLATE(name) R_TEMPLATE(name) +#define TEMPLATE2(name) R_TEMPLATE(name) +#define XTYPE CHOLMOD_REAL +#define XTYPE2 CHOLMOD_REAL +#define XTYPE_OK(type) R_XTYPE_OK(type) +#define ENTRY_IS_NONZERO(ax,az,q) R_IS_NONZERO(ax,az,q) +#define ENTRY_IS_ZERO(ax,az,q) R_IS_ZERO(ax,az,q) +#define ENTRY_IS_ONE(ax,az,q) R_IS_ONE(ax,az,q) +#define IMAG_IS_NONZERO(ax,az,q) (FALSE) +#define ENTRY_SIZE 1 + +#define ASSEMBLE(x,z,p,ax,az,q) R_ASSEMBLE(x,z,p,ax,az,q) +#define ASSIGN(x,z,p,ax,az,q) R_ASSIGN(x,z,p,ax,az,q) +#define ASSIGN_CONJ(x,z,p,ax,az,q) R_ASSIGN(x,z,p,ax,az,q) +#define ASSIGN2(x,z,p,ax,az,q) R_ASSIGN(x,z,p,ax,az,q) +#define ASSIGN2_CONJ(x,z,p,ax,az,q) R_ASSIGN(x,z,p,ax,az,q) +#define ASSIGN_REAL(x,p,ax,q) R_ASSIGN_REAL(x,p,ax,q) +#define MULT(x,z,p,ax,az,q,bx,bz,pb) R_MULT(x,z,p,ax,az,q,bx,bz,pb) +#define MULTADD(x,z,p,ax,az,q,bx,bz,pb) R_MULTADD(x,z,p,ax,az,q,bx,bz,pb) +#define ADD(x,z,p,ax,az,q,bx,bz,pb) R_ADD(x,z,p,ax,az,q,bx,bz,pb) +#define ADD_REAL(x,p, ax,q, bx,r) R_ADD_REAL(x,p, ax,q, bx,r) +#define MULTSUB(x,z,p,ax,az,q,bx,bz,pb) R_MULTSUB(x,z,p,ax,az,q,bx,bz,pb) +#define MULTADDCONJ(x,z,p,ax,az,q,bx,bz,pb) \ + R_MULTADDCONJ(x,z,p,ax,az,q,bx,bz,pb) +#define MULTSUBCONJ(x,z,p,ax,az,q,bx,bz,pb) \ + R_MULTSUBCONJ(x,z,p,ax,az,q,bx,bz,pb) +#define LLDOT(x,p,ax,az,q) R_LLDOT(x,p,ax,az,q) +#define CLEAR(x,z,p) R_CLEAR(x,z,p) +#define CLEAR_IMAG(x,z,p) R_CLEAR_IMAG(x,z,p) +#define DIV(x,z,p,ax,az,q) R_DIV(x,z,p,ax,az,q) +#define DIV_REAL(x,z,p, ax,az,q, bx,r) R_DIV_REAL(x,z,p, ax,az,q, bx,r) +#define MULT_REAL(x,z,p, ax,az,q, bx,r) R_MULT_REAL(x,z,p, ax,az,q, bx,r) +#define LDLDOT(x,p, ax,az,q, bx,r) R_LDLDOT(x,p, ax,az,q, bx,r) + +#define XPRINT0(x,z,p) R_PRINT(0,x,z,p) +#define XPRINT1(x,z,p) R_PRINT(1,x,z,p) +#define XPRINT2(x,z,p) R_PRINT(2,x,z,p) +#define XPRINT3(x,z,p) R_PRINT(3,x,z,p) + +/* -------------------------------------------------------------------------- */ +/* complex */ +/* -------------------------------------------------------------------------- */ #elif defined (COMPLEX) - #ifdef SINGLE - #define PREFIX c_s_ - #ifdef NCONJUGATE - // non-conjugate - #define TEMPLATE(name) CT_S_TEMPLATE(name) - #define TEMPLATE2(name) CT_S_TEMPLATE(name) - #else - // conjugate - #define TEMPLATE(name) C_S_TEMPLATE(name) - #define TEMPLATE2(name) C_S_TEMPLATE(name) - #endif - #else - #define PREFIX c_ - #ifdef NCONJUGATE - // non-conjugate - #define TEMPLATE(name) CT_TEMPLATE(name) - #define TEMPLATE2(name) CT_TEMPLATE(name) - #else - // conjugate - #define TEMPLATE(name) C_TEMPLATE(name) - #define TEMPLATE2(name) C_TEMPLATE(name) - #endif - #endif - - #define ASSEMBLE(x,z,p,ax,az,q) C_ASSEMBLE(x,z,p,ax,az,q) - #define ASSIGN(x,z,p,ax,az,q) C_ASSIGN(x,z,p,ax,az,q) - #define ASSIGN_CONJ(x,z,p,ax,az,q) C_ASSIGN_CONJ(x,z,p,ax,az,q) - #define ASSIGN2(x,z,p,ax,az,q) C_ASSIGN(x,z,p,ax,az,q) - #define ASSIGN2_CONJ(x,z,p,ax,az,q) C_ASSIGN_CONJ(x,z,p,ax,az,q) - #define ASSIGN_REAL(x,p,ax,q) C_ASSIGN_REAL(x,p,ax,q) - - #define XTYPE CHOLMOD_COMPLEX - #define XTYPE2 CHOLMOD_COMPLEX - #define XTYPE_OK(type) C_XTYPE_OK(type) - #define ENTRY_IS_NONZERO(ax,az,q) C_IS_NONZERO(ax,az,q) - #define ENTRY_IS_ZERO(ax,az,q) C_IS_ZERO(ax,az,q) - #define ENTRY_IS_ONE(ax,az,q) C_IS_ONE(ax,az,q) - #define IMAG_IS_NONZERO(ax,az,q) C_IMAG_IS_NONZERO(ax,az,q) - #define ENTRY_SIZE 2 - - #define MULTADD(x,z,p,ax,az,q,bx,bz,pb) C_MULTADD(x,z,p,ax,az,q,bx,bz,pb) - #define MULT(x,z,p,ax,az,q,bx,bz,pb) C_MULT(x,z,p,ax,az,q,bx,bz,pb) - #define ADD(x,z,p,ax,az,q,bx,bz,pb) C_ADD(x,z,p,ax,az,q,bx,bz,pb) - #define ADD_REAL(x,p, ax,q, bx,r) C_ADD_REAL(x,p, ax,q, bx,r) - #define MULTSUB(x,z,p,ax,az,q,bx,bz,pb) C_MULTSUB(x,z,p,ax,az,q,bx,bz,pb) - #define MULTADDCONJ(x,z,p,ax,az,q,bx,bz,pb) \ - C_MULTADDCONJ(x,z,p,ax,az,q,bx,bz,pb) - #define MULTSUBCONJ(x,z,p,ax,az,q,bx,bz,pb) \ - C_MULTSUBCONJ(x,z,p,ax,az,q,bx,bz,pb) - #define LLDOT(x,p,ax,az,q) C_LLDOT(x,p,ax,az,q) - #define CLEAR(x,z,p) C_CLEAR(x,z,p) - #define CLEAR_IMAG(x,z,p) C_CLEAR_IMAG(x,z,p) - - #ifdef SINGLE - #define DIV(x,z,p,ax,az,q) C_S_DIV(x,z,p,ax,az,q) - #else - #define DIV(x,z,p,ax,az,q) C_DIV(x,z,p,ax,az,q) - #endif - - #define DIV_REAL(x,z,p, ax,az,q, bx,r) C_DIV_REAL(x,z,p, ax,az,q, bx,r) - #define MULT_REAL(x,z,p, ax,az,q, bx,r) C_MULT_REAL(x,z,p, ax,az,q, bx,r) - #define LDLDOT(x,p, ax,az,q, bx,r) C_LDLDOT(x,p, ax,az,q, bx,r) - - #define XPRINT0(x,z,p) C_PRINT(0,x,z,p) - #define XPRINT1(x,z,p) C_PRINT(1,x,z,p) - #define XPRINT2(x,z,p) C_PRINT(2,x,z,p) - #define XPRINT3(x,z,p) C_PRINT(3,x,z,p) +#define PREFIX c_ -//------------------------------------------------------------------------------ -// zomplex: both double and single -//------------------------------------------------------------------------------ +#ifdef NCONJUGATE +#define TEMPLATE(name) CT_TEMPLATE(name) +#define TEMPLATE2(name) CT_TEMPLATE(name) +#else +#define TEMPLATE(name) C_TEMPLATE(name) +#define TEMPLATE2(name) C_TEMPLATE(name) +#endif + +#define ASSEMBLE(x,z,p,ax,az,q) C_ASSEMBLE(x,z,p,ax,az,q) +#define ASSIGN(x,z,p,ax,az,q) C_ASSIGN(x,z,p,ax,az,q) +#define ASSIGN_CONJ(x,z,p,ax,az,q) C_ASSIGN_CONJ(x,z,p,ax,az,q) +#define ASSIGN2(x,z,p,ax,az,q) C_ASSIGN(x,z,p,ax,az,q) +#define ASSIGN2_CONJ(x,z,p,ax,az,q) C_ASSIGN_CONJ(x,z,p,ax,az,q) +#define ASSIGN_REAL(x,p,ax,q) C_ASSIGN_REAL(x,p,ax,q) +#define XTYPE CHOLMOD_COMPLEX +#define XTYPE2 CHOLMOD_COMPLEX +#define XTYPE_OK(type) C_XTYPE_OK(type) +#define ENTRY_IS_NONZERO(ax,az,q) C_IS_NONZERO(ax,az,q) +#define ENTRY_IS_ZERO(ax,az,q) C_IS_ZERO(ax,az,q) +#define ENTRY_IS_ONE(ax,az,q) C_IS_ONE(ax,az,q) +#define IMAG_IS_NONZERO(ax,az,q) C_IMAG_IS_NONZERO(ax,az,q) +#define ENTRY_SIZE 2 + +#define MULTADD(x,z,p,ax,az,q,bx,bz,pb) C_MULTADD(x,z,p,ax,az,q,bx,bz,pb) +#define MULT(x,z,p,ax,az,q,bx,bz,pb) C_MULT(x,z,p,ax,az,q,bx,bz,pb) +#define ADD(x,z,p,ax,az,q,bx,bz,pb) C_ADD(x,z,p,ax,az,q,bx,bz,pb) +#define ADD_REAL(x,p, ax,q, bx,r) C_ADD_REAL(x,p, ax,q, bx,r) +#define MULTSUB(x,z,p,ax,az,q,bx,bz,pb) C_MULTSUB(x,z,p,ax,az,q,bx,bz,pb) +#define MULTADDCONJ(x,z,p,ax,az,q,bx,bz,pb) \ + C_MULTADDCONJ(x,z,p,ax,az,q,bx,bz,pb) +#define MULTSUBCONJ(x,z,p,ax,az,q,bx,bz,pb) \ + C_MULTSUBCONJ(x,z,p,ax,az,q,bx,bz,pb) +#define LLDOT(x,p,ax,az,q) C_LLDOT(x,p,ax,az,q) +#define CLEAR(x,z,p) C_CLEAR(x,z,p) +#define CLEAR_IMAG(x,z,p) C_CLEAR_IMAG(x,z,p) +#define DIV(x,z,p,ax,az,q) C_DIV(x,z,p,ax,az,q) +#define DIV_REAL(x,z,p, ax,az,q, bx,r) C_DIV_REAL(x,z,p, ax,az,q, bx,r) +#define MULT_REAL(x,z,p, ax,az,q, bx,r) C_MULT_REAL(x,z,p, ax,az,q, bx,r) +#define LDLDOT(x,p, ax,az,q, bx,r) C_LDLDOT(x,p, ax,az,q, bx,r) + +#define XPRINT0(x,z,p) C_PRINT(0,x,z,p) +#define XPRINT1(x,z,p) C_PRINT(1,x,z,p) +#define XPRINT2(x,z,p) C_PRINT(2,x,z,p) +#define XPRINT3(x,z,p) C_PRINT(3,x,z,p) + +/* -------------------------------------------------------------------------- */ +/* zomplex */ +/* -------------------------------------------------------------------------- */ #elif defined (ZOMPLEX) - #ifdef SINGLE - #define PREFIX z_s_ - #ifdef NCONJUGATE - // non-conjugate - #define TEMPLATE(name) ZT_S_TEMPLATE(name) - #define TEMPLATE2(name) CT_S_TEMPLATE(name) - #else - // conjugate - #define TEMPLATE(name) Z_S_TEMPLATE(name) - #define TEMPLATE2(name) C_S_TEMPLATE(name) - #endif - #else - #define PREFIX z_ - #ifdef NCONJUGATE - // non-conjugate - #define TEMPLATE(name) ZT_TEMPLATE(name) - #define TEMPLATE2(name) CT_TEMPLATE(name) - #else - #define TEMPLATE(name) Z_TEMPLATE(name) - #define TEMPLATE2(name) C_TEMPLATE(name) - #endif - #endif - - #define ASSEMBLE(x,z,p,ax,az,q) Z_ASSEMBLE(x,z,p,ax,az,q) - #define ASSIGN(x,z,p,ax,az,q) Z_ASSIGN(x,z,p,ax,az,q) - #define ASSIGN_CONJ(x,z,p,ax,az,q) Z_ASSIGN_CONJ(x,z,p,ax,az,q) - #define ASSIGN2(x,z,p,ax,az,q) Z_ASSIGN(x,z,p,ax,az,q) - #define ASSIGN2_CONJ(x,z,p,ax,az,q) Z_ASSIGN_CONJ(x,z,p,ax,az,q) - #define ASSIGN_REAL(x,p,ax,q) Z_ASSIGN_REAL(x,p,ax,q) - - #define XTYPE CHOLMOD_ZOMPLEX - #define XTYPE2 CHOLMOD_ZOMPLEX - #define XTYPE_OK(type) Z_XTYPE_OK(type) - #define ENTRY_IS_NONZERO(ax,az,q) Z_IS_NONZERO(ax,az,q) - #define ENTRY_IS_ZERO(ax,az,q) Z_IS_ZERO(ax,az,q) - #define ENTRY_IS_ONE(ax,az,q) Z_IS_ONE(ax,az,q) - #define IMAG_IS_NONZERO(ax,az,q) Z_IMAG_IS_NONZERO(ax,az,q) - #define ENTRY_SIZE 1 - - #define MULTADD(x,z,p,ax,az,q,bx,bz,pb) Z_MULTADD(x,z,p,ax,az,q,bx,bz,pb) - #define MULT(x,z,p,ax,az,q,bx,bz,pb) Z_MULT(x,z,p,ax,az,q,bx,bz,pb) - #define ADD(x,z,p,ax,az,q,bx,bz,pb) Z_ADD(x,z,p,ax,az,q,bx,bz,pb) - #define ADD_REAL(x,p, ax,q, bx,r) Z_ADD_REAL(x,p, ax,q, bx,r) - #define MULTSUB(x,z,p,ax,az,q,bx,bz,pb) Z_MULTSUB(x,z,p,ax,az,q,bx,bz,pb) - #define MULTADDCONJ(x,z,p,ax,az,q,bx,bz,pb) \ - Z_MULTADDCONJ(x,z,p,ax,az,q,bx,bz,pb) - #define MULTSUBCONJ(x,z,p,ax,az,q,bx,bz,pb) \ - Z_MULTSUBCONJ(x,z,p,ax,az,q,bx,bz,pb) - #define LLDOT(x,p,ax,az,q) Z_LLDOT(x,p,ax,az,q) - #define CLEAR(x,z,p) Z_CLEAR(x,z,p) - #define CLEAR_IMAG(x,z,p) Z_CLEAR_IMAG(x,z,p) - - #ifdef SINGLE - #define DIV(x,z,p,ax,az,q) Z_S_DIV(x,z,p,ax,az,q) - #else - #define DIV(x,z,p,ax,az,q) Z_DIV(x,z,p,ax,az,q) - #endif - - #define DIV_REAL(x,z,p, ax,az,q, bx,r) Z_DIV_REAL(x,z,p, ax,az,q, bx,r) - #define MULT_REAL(x,z,p, ax,az,q, bx,r) Z_MULT_REAL(x,z,p, ax,az,q, bx,r) - #define LDLDOT(x,p, ax,az,q, bx,r) Z_LDLDOT(x,p, ax,az,q, bx,r) - - #define XPRINT0(x,z,p) Z_PRINT(0,x,z,p) - #define XPRINT1(x,z,p) Z_PRINT(1,x,z,p) - #define XPRINT2(x,z,p) Z_PRINT(2,x,z,p) - #define XPRINT3(x,z,p) Z_PRINT(3,x,z,p) - -#endif +#define PREFIX z_ #ifdef NCONJUGATE - // non-conjugate assign - #define ASSIGN_CONJ_OR_NCONJ(x,z,p,ax,az,q) ASSIGN(x,z,p,ax,az,q) +#define TEMPLATE(name) ZT_TEMPLATE(name) +#define TEMPLATE2(name) CT_TEMPLATE(name) #else - // conjugate assign - #define ASSIGN_CONJ_OR_NCONJ(x,z,p,ax,az,q) ASSIGN_CONJ(x,z,p,ax,az,q) +#define TEMPLATE(name) Z_TEMPLATE(name) +#define TEMPLATE2(name) C_TEMPLATE(name) #endif +#define ASSEMBLE(x,z,p,ax,az,q) Z_ASSEMBLE(x,z,p,ax,az,q) +#define ASSIGN(x,z,p,ax,az,q) Z_ASSIGN(x,z,p,ax,az,q) +#define ASSIGN_CONJ(x,z,p,ax,az,q) Z_ASSIGN_CONJ(x,z,p,ax,az,q) +#define ASSIGN2(x,z,p,ax,az,q) Z_ASSIGN(x,z,p,ax,az,q) +#define ASSIGN2_CONJ(x,z,p,ax,az,q) Z_ASSIGN_CONJ(x,z,p,ax,az,q) +#define ASSIGN_REAL(x,p,ax,q) Z_ASSIGN_REAL(x,p,ax,q) +#define XTYPE CHOLMOD_ZOMPLEX +#define XTYPE2 CHOLMOD_ZOMPLEX +#define XTYPE_OK(type) Z_XTYPE_OK(type) +#define ENTRY_IS_NONZERO(ax,az,q) Z_IS_NONZERO(ax,az,q) +#define ENTRY_IS_ZERO(ax,az,q) Z_IS_ZERO(ax,az,q) +#define ENTRY_IS_ONE(ax,az,q) Z_IS_ONE(ax,az,q) +#define IMAG_IS_NONZERO(ax,az,q) Z_IMAG_IS_NONZERO(ax,az,q) +#define ENTRY_SIZE 1 + +#define MULTADD(x,z,p,ax,az,q,bx,bz,pb) Z_MULTADD(x,z,p,ax,az,q,bx,bz,pb) +#define MULT(x,z,p,ax,az,q,bx,bz,pb) Z_MULT(x,z,p,ax,az,q,bx,bz,pb) +#define ADD(x,z,p,ax,az,q,bx,bz,pb) Z_ADD(x,z,p,ax,az,q,bx,bz,pb) +#define ADD_REAL(x,p, ax,q, bx,r) Z_ADD_REAL(x,p, ax,q, bx,r) +#define MULTSUB(x,z,p,ax,az,q,bx,bz,pb) Z_MULTSUB(x,z,p,ax,az,q,bx,bz,pb) +#define MULTADDCONJ(x,z,p,ax,az,q,bx,bz,pb) \ + Z_MULTADDCONJ(x,z,p,ax,az,q,bx,bz,pb) +#define MULTSUBCONJ(x,z,p,ax,az,q,bx,bz,pb) \ + Z_MULTSUBCONJ(x,z,p,ax,az,q,bx,bz,pb) +#define LLDOT(x,p,ax,az,q) Z_LLDOT(x,p,ax,az,q) +#define CLEAR(x,z,p) Z_CLEAR(x,z,p) +#define CLEAR_IMAG(x,z,p) Z_CLEAR_IMAG(x,z,p) +#define DIV(x,z,p,ax,az,q) Z_DIV(x,z,p,ax,az,q) +#define DIV_REAL(x,z,p, ax,az,q, bx,r) Z_DIV_REAL(x,z,p, ax,az,q, bx,r) +#define MULT_REAL(x,z,p, ax,az,q, bx,r) Z_MULT_REAL(x,z,p, ax,az,q, bx,r) +#define LDLDOT(x,p, ax,az,q, bx,r) Z_LDLDOT(x,p, ax,az,q, bx,r) + +#define XPRINT0(x,z,p) Z_PRINT(0,x,z,p) +#define XPRINT1(x,z,p) Z_PRINT(1,x,z,p) +#define XPRINT2(x,z,p) Z_PRINT(2,x,z,p) +#define XPRINT3(x,z,p) Z_PRINT(3,x,z,p) + +#endif diff --git a/CHOLMOD/Include/cholmod_types.h b/CHOLMOD/Include/cholmod_types.h index ab6dde04f6..e82f783d73 100644 --- a/CHOLMOD/Include/cholmod_types.h +++ b/CHOLMOD/Include/cholmod_types.h @@ -8,75 +8,132 @@ //------------------------------------------------------------------------------ -// CHOLMOD internal include file for defining integer types. This file is -// suitable for inclusion in C and C++ codes. It can be #include'd more than -// once. The #include'ing file defines one of two macros (CHOLMOD_INT32 or -// CHOLMOD_INT64). CHOLMOD is designed for 2 types of integer variables: -// int32_t or int64_t. -// -// The complex types (ANSI-compatible complex, and MATLAB-compatable zomplex) -// are based on the double or float type, and are not selected here. They are -// typically selected via template routines. +// CHOLMOD internal include file: defining integer and floating-point types. +// This file is suitable for inclusion in C and C++ codes. It can be +// #include'd more than once. + +// The #include'ing file defines one of four macros (DINT, DLONG, SINT, or +// SLONG) before #include'ing this file. + +/* ========================================================================== */ +/* === int/long and double/float definitions ================================ */ +/* ========================================================================== */ + +/* CHOLMOD is designed for 3 types of integer variables: + * + * (1) all integers are int + * (2) most integers are int, some are int64_t + * (3) all integers are int64_t + * + * and two kinds of floating-point values: + * + * (1) double + * (2) float + * + * the complex types (ANSI-compatible complex, and MATLAB-compatable zomplex) + * are based on the double or float type, and are not selected here. They + * are typically selected via template routines. + * + * This gives 6 different modes in which CHOLMOD can be compiled (only the + * first two are currently supported): + * + * DINT double, int prefix: cholmod_ + * DLONG double, int64_t prefix: cholmod_l_ + * DMIX double, mixed int/int64_t prefix: cholmod_m_ + * SINT float, int prefix: cholmod_si_ + * SLONG float, int64_t prefix: cholmod_sl_ + * SMIX float, mixed int/log prefix: cholmod_sm_ + * + * These are selected with compile time flags (-DDLONG, for example). If no + * flag is selected, the default is DINT. + * + * All six versions use the same include files. The user-visible include files + * are completely independent of which int/long/double/float version is being + * used. The integer / real types in all data structures (sparse, triplet, + * dense, common, and triplet) are defined at run-time, not compile-time, so + * there is only one "cholmod_sparse" data type. Void pointers are used inside + * that data structure to point to arrays of the proper type. Each data + * structure has an itype and dtype field which determines the kind of basic + * types used. These are defined in Include/cholmod_core.h. + * + * FUTURE WORK: support all six types (float, and mixed int/long) + * SINT and SLONG are in progress. + */ // ----------------------------------------------------------------------------- +#undef Real #undef Int #undef UInt #undef Int_max #undef CHOLMOD #undef ITYPE +#undef DTYPE #undef ID -#undef CLEAR_FLAG -#if defined ( CHOLMOD_INT64 ) +#if defined ( SLONG ) //-------------------------------------------------------------------------- - // CHOLMOD_INT64: int64_t + // SLONG: float (also complex float), int64_t //-------------------------------------------------------------------------- + #define Real float #define Int int64_t #define UInt uint64_t #define Int_max INT64_MAX - #define CHOLMOD(name) cholmod_l_ ## name + #define CHOLMOD(name) cholmod_sl_ ## name #define ITYPE CHOLMOD_LONG + #define DTYPE CHOLMOD_SINGLE #define ID "%" PRId64 - #define CLEAR_FLAG(Common) \ - { \ - Common->mark++ ; \ - if (Common->mark <= 0) \ - { \ - Common->mark = EMPTY ; \ - cholmod_l_clear_flag (Common) ; \ - } \ - } +#elif defined ( SINT ) + + //-------------------------------------------------------------------------- + // SINT: float (also complex float), int32_t + //-------------------------------------------------------------------------- + + #define Real float + #define Int int32_t + #define UInt uint32_t + #define Int_max INT32_MAX + #define CHOLMOD(name) cholmod_si_ ## name + #define ITYPE CHOLMOD_INT + #define DTYPE CHOLMOD_SINGLE + #define ID "%d" + +#elif defined ( DLONG ) + + //-------------------------------------------------------------------------- + // DLONG: double (also complex double), int64_t + //-------------------------------------------------------------------------- + + #define Real double + #define Int int64_t + #define UInt uint64_t + #define Int_max INT64_MAX + #define CHOLMOD(name) cholmod_l_ ## name + #define ITYPE CHOLMOD_LONG + #define DTYPE CHOLMOD_DOUBLE + #define ID "%" PRId64 #else //-------------------------------------------------------------------------- - // CHOLMOD_INT32: int32 + // DINT: double (also complex double), int32 //-------------------------------------------------------------------------- - #ifndef CHOLMOD_INT32 - #define CHOLMOD_INT32 + #ifndef DINT + #define DINT #endif + #define Real double #define Int int32_t #define UInt uint32_t #define Int_max INT32_MAX #define CHOLMOD(name) cholmod_ ## name #define ITYPE CHOLMOD_INT + #define DTYPE CHOLMOD_DOUBLE #define ID "%d" - #define CLEAR_FLAG(Common) \ - { \ - Common->mark++ ; \ - if (Common->mark <= 0 || Common->mark > INT32_MAX) \ - { \ - Common->mark = EMPTY ; \ - cholmod_clear_flag (Common) ; \ - } \ - } - #endif diff --git a/CHOLMOD/MATLAB/analyze.c b/CHOLMOD/MATLAB/analyze.c index 641c1035bf..32e8fa7eed 100644 --- a/CHOLMOD/MATLAB/analyze.c +++ b/CHOLMOD/MATLAB/analyze.c @@ -71,7 +71,7 @@ void mexFunction if (nargin == 3) { cm->nmethods = mxGetScalar (pargin [2]) ; - if (cm->nmethods == -1 || cm->nmethods == 1 || cm->nmethods == 2) + if (cm->nmethods == -1) { /* use AMD only */ cm->nmethods = 1 ; diff --git a/CHOLMOD/MATLAB/cholmod_make.m b/CHOLMOD/MATLAB/cholmod_make.m index a8c3a1e260..715c37f6b1 100644 --- a/CHOLMOD/MATLAB/cholmod_make.m +++ b/CHOLMOD/MATLAB/cholmod_make.m @@ -141,76 +141,20 @@ cholmod_matlab = { 'cholmod_matlab' } ; cholmod_src = { - '../Utility/cholmod_l_aat', ... - '../Utility/cholmod_l_add', ... - '../Utility/cholmod_l_add_size_t', ... - '../Utility/cholmod_l_allocate_dense', ... - '../Utility/cholmod_l_allocate_factor', ... - '../Utility/cholmod_l_allocate_sparse', ... - '../Utility/cholmod_l_allocate_triplet', ... - '../Utility/cholmod_l_allocate_work', ... - '../Utility/cholmod_l_alloc_factor', ... - '../Utility/cholmod_l_alloc_work', ... - '../Utility/cholmod_l_band', ... - '../Utility/cholmod_l_band_nnz', ... - '../Utility/cholmod_l_calloc', ... - '../Utility/cholmod_l_change_factor', ... - '../Utility/cholmod_l_clear_flag', ... - '../Utility/cholmod_l_copy', ... - '../Utility/cholmod_l_copy_dense2', ... - '../Utility/cholmod_l_copy_dense', ... - '../Utility/cholmod_l_copy_factor', ... - '../Utility/cholmod_l_copy_sparse', ... - '../Utility/cholmod_l_copy_triplet', ... - '../Utility/cholmod_l_cumsum', ... - '../Utility/cholmod_l_dbound', ... - '../Utility/cholmod_l_defaults', ... - '../Utility/cholmod_l_dense_nnz', ... - '../Utility/cholmod_l_dense_to_sparse', ... - '../Utility/cholmod_l_divcomplex', ... - '../Utility/cholmod_l_ensure_dense', ... - '../Utility/cholmod_l_error', ... - '../Utility/cholmod_l_eye', ... - '../Utility/cholmod_l_factor_to_sparse', ... - '../Utility/cholmod_l_finish', ... - '../Utility/cholmod_l_free', ... - '../Utility/cholmod_l_free_dense', ... - '../Utility/cholmod_l_free_factor', ... - '../Utility/cholmod_l_free_sparse', ... - '../Utility/cholmod_l_free_triplet', ... - '../Utility/cholmod_l_free_work', ... - '../Utility/cholmod_l_hypot', ... - '../Utility/cholmod_l_malloc', ... - '../Utility/cholmod_l_maxrank', ... - '../Utility/cholmod_l_mult_size_t', ... - '../Utility/cholmod_l_nnz', ... - '../Utility/cholmod_l_ones', ... - '../Utility/cholmod_l_pack_factor', ... - '../Utility/cholmod_l_ptranspose', ... - '../Utility/cholmod_l_reallocate_column', ... - '../Utility/cholmod_l_reallocate_factor', ... - '../Utility/cholmod_l_reallocate_sparse', ... - '../Utility/cholmod_l_reallocate_triplet', ... - '../Utility/cholmod_l_realloc', ... - '../Utility/cholmod_l_realloc_multiple', ... - '../Utility/cholmod_l_sbound', ... - '../Utility/cholmod_l_score_comp', ... - '../Utility/cholmod_l_set_empty', ... - '../Utility/cholmod_l_sort', ... - '../Utility/cholmod_l_sparse_to_dense', ... - '../Utility/cholmod_l_sparse_to_triplet', ... - '../Utility/cholmod_l_speye', ... - '../Utility/cholmod_l_spzeros', ... - '../Utility/cholmod_l_start', ... - '../Utility/cholmod_l_transpose', ... - '../Utility/cholmod_l_transpose_sym', ... - '../Utility/cholmod_l_transpose_unsym', ... - '../Utility/cholmod_l_triplet_to_sparse', ... - '../Utility/cholmod_l_version', ... - '../Utility/cholmod_l_xtype', ... - '../Utility/cholmod_l_zeros', ... - '../Utility/cholmod_mult_uint64_t', ... - '../Utility/cholmod_memdebug', ... + '../Core/cholmod_l_aat', ... + '../Core/cholmod_l_add', ... + '../Core/cholmod_l_band', ... + '../Core/cholmod_l_change_factor', ... + '../Core/cholmod_l_common', ... + '../Core/cholmod_l_complex', ... + '../Core/cholmod_l_copy', ... + '../Core/cholmod_l_dense', ... + '../Core/cholmod_l_error', ... + '../Core/cholmod_l_factor', ... + '../Core/cholmod_l_memory', ... + '../Core/cholmod_l_sparse', ... + '../Core/cholmod_l_transpose', ... + '../Core/cholmod_l_triplet', ... '../Check/cholmod_l_check', ... '../Check/cholmod_l_read', ... '../Check/cholmod_l_write', ... diff --git a/CHOLMOD/MATLAB/cholmod_matlab.c b/CHOLMOD/MATLAB/cholmod_matlab.c index cb86ca5e7e..31a377bdef 100644 --- a/CHOLMOD/MATLAB/cholmod_matlab.c +++ b/CHOLMOD/MATLAB/cholmod_matlab.c @@ -718,8 +718,8 @@ cholmod_sparse *sputil_extract_zeros { for (p = Ap [j] ; p < Ap [j+1] ; p++) { - if ((Ax [p] == 0) && - ((is_complex) ? (Az [p] == 0) : TRUE)) + if (CHOLMOD_IS_ZERO (Ax [p]) && + ((is_complex) ? CHOLMOD_IS_ZERO (Az [p]) : TRUE)) { nzeros++ ; } @@ -741,8 +741,8 @@ cholmod_sparse *sputil_extract_zeros Zp [j] = pz ; for (p = Ap [j] ; p < Ap [j+1] ; p++) { - if ((Ax [p] == 0) && - ((is_complex) ? (Az [p] == 0) : TRUE)) + if (CHOLMOD_IS_ZERO (Ax [p]) && + ((is_complex) ? CHOLMOD_IS_ZERO (Az [p]) : TRUE)) { Zi [pz] = Ai [p] ; Zx [pz] = 1 ; @@ -803,7 +803,7 @@ int64_t sputil_drop_zeros { sik = Sx [p] ; zik = Sz [p] ; - if ((sik != 0) || (zik != 0)) + if (CHOLMOD_IS_NONZERO (sik) || CHOLMOD_IS_NONZERO (zik)) { if (p != pdest) { @@ -826,7 +826,7 @@ int64_t sputil_drop_zeros for ( ; p < pend ; p++) { sik = Sx [p] ; - if ((sik != 0)) + if (CHOLMOD_IS_NONZERO (sik)) { if (p != pdest) { @@ -1078,7 +1078,7 @@ int64_t sputil_copy_ij /* returns the dimension, n */ for (i = 0 ; i < nrow ; i++) \ { \ xij = X [i + j*nrow] ; \ - if (xij != 0) \ + if (CHOLMOD_IS_NONZERO (xij)) \ { \ nz++ ; \ } \ @@ -1099,7 +1099,7 @@ int64_t sputil_copy_ij /* returns the dimension, n */ for (i = 0 ; i < nrow ; i++) \ { \ xij = X [i + j*nrow] ; \ - if (xij != 0) \ + if (CHOLMOD_IS_NONZERO (xij)) \ { \ Si [nz] = i ; \ Sx [nz] = (stype) xij ; \ @@ -1155,7 +1155,7 @@ mxArray *sputil_dense_to_sparse (const mxArray *arg) { xij = X [i + j*nrow] ; zij = Z [i + j*nrow] ; - if ((xij != 0) || (zij != 0)) + if (CHOLMOD_IS_NONZERO (xij) || CHOLMOD_IS_NONZERO (zij)) { nz++ ; } @@ -1174,7 +1174,7 @@ mxArray *sputil_dense_to_sparse (const mxArray *arg) { xij = X [i + j*nrow] ; zij = Z [i + j*nrow] ; - if ((xij != 0) || (zij != 0)) + if (CHOLMOD_IS_NONZERO (xij) || CHOLMOD_IS_NONZERO (zij)) { Si [nz] = i ; Sx [nz] = xij ; @@ -1606,7 +1606,7 @@ mxArray *sputil_copy_sparse (const mxArray *A) { aij = Ax [p] ; zij = Az [p] ; - if ((aij != 0) || (zij != 0)) + if (CHOLMOD_IS_NONZERO (aij) || CHOLMOD_IS_NONZERO (zij)) { snz++ ; } @@ -1629,7 +1629,7 @@ mxArray *sputil_copy_sparse (const mxArray *A) { aij = Ax [p] ; zij = Az [p] ; - if ((aij != 0) || (zij != 0)) + if (CHOLMOD_IS_NONZERO (aij) || CHOLMOD_IS_NONZERO (zij)) { Si [snz] = Ai [p] ; Sx [snz] = aij ; @@ -1652,7 +1652,7 @@ mxArray *sputil_copy_sparse (const mxArray *A) for (p = 0 ; p < anz ; p++) { aij = Ax [p] ; - if (aij != 0) + if (CHOLMOD_IS_NONZERO (aij)) { snz++ ; } @@ -1673,7 +1673,7 @@ mxArray *sputil_copy_sparse (const mxArray *A) for (p = Ap [j] ; p < pend ; p++) { aij = Ax [p] ; - if (aij != 0) + if (CHOLMOD_IS_NONZERO (aij)) { Si [snz] = Ai [p] ; Sx [snz] = aij ; diff --git a/CHOLMOD/MATLAB/mread.c b/CHOLMOD/MATLAB/mread.c index e0cb677d59..6783ef62f0 100644 --- a/CHOLMOD/MATLAB/mread.c +++ b/CHOLMOD/MATLAB/mread.c @@ -89,7 +89,7 @@ void mexFunction mexErrMsgTxt ("could not read file") ; } - /* get the specific matrix (A or X), and change to zomplex if needed */ + /* get the specific matrix (A or X), and change to ZOMPLEX if needed */ if (mtype == CHOLMOD_SPARSE) { A = (cholmod_sparse *) G ; @@ -100,7 +100,7 @@ void mexFunction Ai = A->i ; if (is_complex) { - /* if complex, ensure A is zomplex */ + /* if complex, ensure A is ZOMPLEX */ cholmod_l_sparse_xtype (CHOLMOD_ZOMPLEX, A, cm) ; } Ax = A->x ; @@ -114,7 +114,7 @@ void mexFunction is_complex = (X->xtype == CHOLMOD_COMPLEX) ; if (is_complex) { - /* if complex, ensure X is zomplex */ + /* if complex, ensure X is ZOMPLEX */ cholmod_l_dense_xtype (CHOLMOD_ZOMPLEX, X, cm) ; } Ax = X->x ; diff --git a/CHOLMOD/MatrixOps/cholmod_drop.c b/CHOLMOD/MatrixOps/cholmod_drop.c index eceb86a7ca..005c0ee901 100644 --- a/CHOLMOD/MatrixOps/cholmod_drop.c +++ b/CHOLMOD/MatrixOps/cholmod_drop.c @@ -88,7 +88,7 @@ int CHOLMOD(drop) { i = Ai [p] ; aij = Ax [p] ; - if (i <= j && (fabs (aij) > tol || isnan (aij))) + if (i <= j && (fabs (aij) > tol || IS_NAN (aij))) { Ai [nz] = i ; Ax [nz] = aij ; @@ -114,7 +114,7 @@ int CHOLMOD(drop) { i = Ai [p] ; aij = Ax [p] ; - if (i >= j && (fabs (aij) > tol || isnan (aij))) + if (i >= j && (fabs (aij) > tol || IS_NAN (aij))) { Ai [nz] = i ; Ax [nz] = aij ; @@ -139,7 +139,7 @@ int CHOLMOD(drop) { i = Ai [p] ; aij = Ax [p] ; - if (fabs (aij) > tol || isnan (aij)) + if (fabs (aij) > tol || IS_NAN (aij)) { Ai [nz] = i ; Ax [nz] = aij ; diff --git a/CHOLMOD/MatrixOps/cholmod_l_drop.c b/CHOLMOD/MatrixOps/cholmod_l_drop.c index da5ab9e092..1cfd378d63 100644 --- a/CHOLMOD/MatrixOps/cholmod_l_drop.c +++ b/CHOLMOD/MatrixOps/cholmod_l_drop.c @@ -8,6 +8,6 @@ //------------------------------------------------------------------------------ -#define CHOLMOD_INT64 +#define DLONG #include "cholmod_drop.c" diff --git a/CHOLMOD/MatrixOps/cholmod_l_horzcat.c b/CHOLMOD/MatrixOps/cholmod_l_horzcat.c index a8f9cac9d5..7172b3052f 100644 --- a/CHOLMOD/MatrixOps/cholmod_l_horzcat.c +++ b/CHOLMOD/MatrixOps/cholmod_l_horzcat.c @@ -8,6 +8,6 @@ //------------------------------------------------------------------------------ -#define CHOLMOD_INT64 +#define DLONG #include "cholmod_horzcat.c" diff --git a/CHOLMOD/MatrixOps/cholmod_l_norm.c b/CHOLMOD/MatrixOps/cholmod_l_norm.c index b3bb886ba6..c25c2dc28e 100644 --- a/CHOLMOD/MatrixOps/cholmod_l_norm.c +++ b/CHOLMOD/MatrixOps/cholmod_l_norm.c @@ -8,6 +8,6 @@ //------------------------------------------------------------------------------ -#define CHOLMOD_INT64 +#define DLONG #include "cholmod_norm.c" diff --git a/CHOLMOD/MatrixOps/cholmod_l_scale.c b/CHOLMOD/MatrixOps/cholmod_l_scale.c index 8c56e00e18..89cc869fe2 100644 --- a/CHOLMOD/MatrixOps/cholmod_l_scale.c +++ b/CHOLMOD/MatrixOps/cholmod_l_scale.c @@ -8,6 +8,6 @@ //------------------------------------------------------------------------------ -#define CHOLMOD_INT64 +#define DLONG #include "cholmod_scale.c" diff --git a/CHOLMOD/MatrixOps/cholmod_l_sdmult.c b/CHOLMOD/MatrixOps/cholmod_l_sdmult.c index 94cce98918..02b950caea 100644 --- a/CHOLMOD/MatrixOps/cholmod_l_sdmult.c +++ b/CHOLMOD/MatrixOps/cholmod_l_sdmult.c @@ -8,6 +8,6 @@ //------------------------------------------------------------------------------ -#define CHOLMOD_INT64 +#define DLONG #include "cholmod_sdmult.c" diff --git a/CHOLMOD/MatrixOps/cholmod_l_ssmult.c b/CHOLMOD/MatrixOps/cholmod_l_ssmult.c index 521771f2d9..ce613099eb 100644 --- a/CHOLMOD/MatrixOps/cholmod_l_ssmult.c +++ b/CHOLMOD/MatrixOps/cholmod_l_ssmult.c @@ -8,6 +8,6 @@ //------------------------------------------------------------------------------ -#define CHOLMOD_INT64 +#define DLONG #include "cholmod_ssmult.c" diff --git a/CHOLMOD/MatrixOps/cholmod_l_submatrix.c b/CHOLMOD/MatrixOps/cholmod_l_submatrix.c index 0ceb8037be..d7797fd945 100644 --- a/CHOLMOD/MatrixOps/cholmod_l_submatrix.c +++ b/CHOLMOD/MatrixOps/cholmod_l_submatrix.c @@ -8,6 +8,6 @@ //------------------------------------------------------------------------------ -#define CHOLMOD_INT64 +#define DLONG #include "cholmod_submatrix.c" diff --git a/CHOLMOD/MatrixOps/cholmod_l_symmetry.c b/CHOLMOD/MatrixOps/cholmod_l_symmetry.c index b421762479..d95ede0942 100644 --- a/CHOLMOD/MatrixOps/cholmod_l_symmetry.c +++ b/CHOLMOD/MatrixOps/cholmod_l_symmetry.c @@ -8,6 +8,6 @@ //------------------------------------------------------------------------------ -#define CHOLMOD_INT64 +#define DLONG #include "cholmod_symmetry.c" diff --git a/CHOLMOD/MatrixOps/cholmod_l_vertcat.c b/CHOLMOD/MatrixOps/cholmod_l_vertcat.c index c567f5c94b..2507a141a7 100644 --- a/CHOLMOD/MatrixOps/cholmod_l_vertcat.c +++ b/CHOLMOD/MatrixOps/cholmod_l_vertcat.c @@ -8,6 +8,6 @@ //------------------------------------------------------------------------------ -#define CHOLMOD_INT64 +#define DLONG #include "cholmod_vertcat.c" diff --git a/CHOLMOD/MatrixOps/cholmod_norm.c b/CHOLMOD/MatrixOps/cholmod_norm.c index e4a2b55b77..73d205712c 100644 --- a/CHOLMOD/MatrixOps/cholmod_norm.c +++ b/CHOLMOD/MatrixOps/cholmod_norm.c @@ -144,7 +144,7 @@ double CHOLMOD(norm_dense) for (i = 0 ; i < nrow ; i++) { s = W [i] ; - if ((isnan (s) || s > xnorm) && !isnan (xnorm)) + if ((IS_NAN (s) || s > xnorm) && !IS_NAN (xnorm)) { xnorm = s ; } @@ -166,7 +166,7 @@ double CHOLMOD(norm_dense) { s += abs_value (xtype, Xx, Xz, i+j*d, Common) ; } - if ((isnan (s) || s > xnorm) && !isnan (xnorm)) + if ((IS_NAN (s) || s > xnorm) && !IS_NAN (xnorm)) { xnorm = s ; } @@ -187,7 +187,7 @@ double CHOLMOD(norm_dense) { s += abs_value (xtype, Xx, Xz, i+j*d, Common) ; } - if ((isnan (s) || s > xnorm) && !isnan (xnorm)) + if ((IS_NAN (s) || s > xnorm) && !IS_NAN (xnorm)) { xnorm = s ; } @@ -416,7 +416,7 @@ double CHOLMOD(norm_sparse) s += abs_value (xtype, Ax, Az, p, Common) ; } } - if ((isnan (s) || s > anorm) && !isnan (anorm)) + if ((IS_NAN (s) || s > anorm) && !IS_NAN (anorm)) { anorm = s ; } @@ -432,7 +432,7 @@ double CHOLMOD(norm_sparse) for (i = 0 ; i < nrow ; i++) { s = W [i] ; - if ((isnan (s) || s > anorm) && !isnan (anorm)) + if ((IS_NAN (s) || s > anorm) && !IS_NAN (anorm)) { anorm = s ; } diff --git a/CHOLMOD/MatrixOps/cholmod_sdmult.c b/CHOLMOD/MatrixOps/cholmod_sdmult.c index 6e66448fd6..0a5bf54431 100644 --- a/CHOLMOD/MatrixOps/cholmod_sdmult.c +++ b/CHOLMOD/MatrixOps/cholmod_sdmult.c @@ -115,8 +115,8 @@ int CHOLMOD(sdmult) ASSERT (CHOLMOD(dump_sparse) (A, "A", Common) >= 0) ; DEBUG (CHOLMOD(dump_dense) (X, "X", Common)) ; - DEBUG (if ((beta [0] != 0) - || ((beta [1] != 0) && A->xtype != CHOLMOD_REAL)) + DEBUG (if (IS_NONZERO (beta [0]) + || (IS_NONZERO (beta [1]) && A->xtype != CHOLMOD_REAL)) CHOLMOD(dump_dense) (Y, "Y", Common)) ; switch (A->xtype) diff --git a/CHOLMOD/MatrixOps/cholmod_ssmult.c b/CHOLMOD/MatrixOps/cholmod_ssmult.c index 17a40a60ab..2257851cbe 100644 --- a/CHOLMOD/MatrixOps/cholmod_ssmult.c +++ b/CHOLMOD/MatrixOps/cholmod_ssmult.c @@ -178,7 +178,7 @@ cholmod_sparse *CHOLMOD(ssmult) { /* clear the Flag array */ /* mark = CHOLMOD(clear_flag) (Common) ; */ - CLEAR_FLAG (Common) ; + CHOLMOD_CLEAR_FLAG (Common) ; mark = Common->mark ; /* for each nonzero B(t,j) in column j, do: */ @@ -209,8 +209,7 @@ cholmod_sparse *CHOLMOD(ssmult) } /* mark = CHOLMOD(clear_flag) (Common) ; */ - CLEAR_FLAG (Common) ; - ASSERT (check_flag (Common)) ; + CHOLMOD_CLEAR_FLAG (Common) ; mark = Common->mark ; /* ---------------------------------------------------------------------- */ @@ -331,7 +330,7 @@ cholmod_sparse *CHOLMOD(ssmult) { /* clear the Flag array */ /* mark = CHOLMOD(clear_flag (Common)) ; */ - CLEAR_FLAG (Common) ; + CHOLMOD_CLEAR_FLAG (Common) ; mark = Common->mark ; /* start column j of C */ @@ -380,7 +379,7 @@ cholmod_sparse *CHOLMOD(ssmult) { /* clear the Flag array */ /* mark = CHOLMOD(clear_flag) (Common) ; */ - CLEAR_FLAG (Common) ; + CHOLMOD_CLEAR_FLAG (Common) ; mark = Common->mark ; /* start column j of C */ @@ -420,8 +419,7 @@ cholmod_sparse *CHOLMOD(ssmult) CHOLMOD(free_sparse) (&A2, Common) ; CHOLMOD(free_sparse) (&B2, Common) ; /* CHOLMOD(clear_flag) (Common) ; */ - CLEAR_FLAG (Common) ; - ASSERT (check_flag (Common)) ; + CHOLMOD_CLEAR_FLAG (Common) ; ASSERT (CHOLMOD(dump_work) (TRUE, TRUE, values ? n1:0, Common)) ; /* ---------------------------------------------------------------------- */ @@ -479,7 +477,7 @@ cholmod_sparse *CHOLMOD(ssmult) /* return result */ /* ---------------------------------------------------------------------- */ - ASSERT (CHOLMOD(dump_sparse) (C, "ssmult", Common) >= 0) ; + DEBUG (CHOLMOD(dump_sparse) (C, "ssmult", Common) >= 0) ; ASSERT (CHOLMOD(dump_work) (TRUE, TRUE, values ? n1:0, Common)) ; return (C) ; } diff --git a/CHOLMOD/MatrixOps/cholmod_submatrix.c b/CHOLMOD/MatrixOps/cholmod_submatrix.c index 9d0127c7bc..dcb2942f4a 100644 --- a/CHOLMOD/MatrixOps/cholmod_submatrix.c +++ b/CHOLMOD/MatrixOps/cholmod_submatrix.c @@ -107,13 +107,6 @@ cholmod_sparse *CHOLMOD(submatrix) ERROR (CHOLMOD_INVALID, "symmetric upper or lower case not supported") ; return (NULL) ; } - - if (rsize > Int_max || csize > Int_max) - { - ERROR (CHOLMOD_TOO_LARGE, "problem too large") ; - return (NULL) ; - } - Common->status = CHOLMOD_OK ; /* ---------------------------------------------------------------------- */ @@ -122,9 +115,8 @@ cholmod_sparse *CHOLMOD(submatrix) ancol = A->ncol ; anrow = A->nrow ; - nr = (Int) rsize ; - nc = (Int) csize ; - + nr = rsize ; + nc = csize ; if (rset == NULL) { /* nr = 0 denotes rset = [ ], nr < 0 denotes rset = 0:anrow-1 */ @@ -155,7 +147,6 @@ cholmod_sparse *CHOLMOD(submatrix) } return (C) ; } - PRINT1 (("submatrix nr "ID" nc "ID" Cnrow "ID" Cncol "ID"" " Anrow "ID" Ancol "ID"\n", nr, nc, cnrow, cncol, anrow, ancol)) ; diff --git a/CHOLMOD/Modify/cholmod_l_rowadd.c b/CHOLMOD/Modify/cholmod_l_rowadd.c index 86bcd9cf41..49408762b6 100644 --- a/CHOLMOD/Modify/cholmod_l_rowadd.c +++ b/CHOLMOD/Modify/cholmod_l_rowadd.c @@ -8,6 +8,6 @@ //------------------------------------------------------------------------------ -#define CHOLMOD_INT64 +#define DLONG #include "cholmod_rowadd.c" diff --git a/CHOLMOD/Modify/cholmod_l_rowdel.c b/CHOLMOD/Modify/cholmod_l_rowdel.c index c8839bc116..0268ec114a 100644 --- a/CHOLMOD/Modify/cholmod_l_rowdel.c +++ b/CHOLMOD/Modify/cholmod_l_rowdel.c @@ -8,6 +8,6 @@ //------------------------------------------------------------------------------ -#define CHOLMOD_INT64 +#define DLONG #include "cholmod_rowdel.c" diff --git a/CHOLMOD/Modify/cholmod_l_updown.c b/CHOLMOD/Modify/cholmod_l_updown.c index a37713cb71..9debeffd16 100644 --- a/CHOLMOD/Modify/cholmod_l_updown.c +++ b/CHOLMOD/Modify/cholmod_l_updown.c @@ -8,6 +8,6 @@ //------------------------------------------------------------------------------ -#define CHOLMOD_INT64 +#define DLONG #include "cholmod_updown.c" diff --git a/CHOLMOD/Modify/cholmod_rowadd.c b/CHOLMOD/Modify/cholmod_rowadd.c index 32811db1be..df21326a89 100644 --- a/CHOLMOD/Modify/cholmod_rowadd.c +++ b/CHOLMOD/Modify/cholmod_rowadd.c @@ -344,8 +344,7 @@ int CHOLMOD(rowadd_mark) { /* out of memory, L is now simplicial symbolic */ /* CHOLMOD(clear_flag) (Common) ; */ - CLEAR_FLAG (Common) ; - ASSERT (check_flag (Common)) ; + CHOLMOD_CLEAR_FLAG (Common) ; for (i = 0 ; i < n ; i++) { W [i] = 0 ; @@ -531,7 +530,7 @@ int CHOLMOD(rowadd_mark) /* ensure abs (dk) >= dbound, if dbound is given */ /* ---------------------------------------------------------------------- */ - dk = (Common->dbound > 0) ? (CHOLMOD(dbound) (dk, Common)) : dk ; + dk = (IS_GT_ZERO (Common->dbound)) ? (CHOLMOD(dbound) (dk, Common)) : dk ; PRINT2 (("D [k = "ID"] = %g\n", k, dk)) ; @@ -621,7 +620,7 @@ int CHOLMOD(rowadd_mark) PRINT1 (("rowadd update lnz = "ID"\n", lnz)) ; if (lnz > 0) { - do_update = (dk < 0) ; + do_update = IS_LT_ZERO (dk) ; if (do_update) { dk = -dk ; diff --git a/CHOLMOD/Modify/cholmod_rowdel.c b/CHOLMOD/Modify/cholmod_rowdel.c index d33af94a1b..d040df076c 100644 --- a/CHOLMOD/Modify/cholmod_rowdel.c +++ b/CHOLMOD/Modify/cholmod_rowdel.c @@ -395,7 +395,7 @@ int CHOLMOD(rowdel_mark) } } - do_update = (dk > 0) ; + do_update = IS_GT_ZERO (dk) ; if (!do_update) { dk = -dk ; diff --git a/CHOLMOD/Modify/cholmod_updown.c b/CHOLMOD/Modify/cholmod_updown.c index ce1a1141d2..c2ded58bdf 100644 --- a/CHOLMOD/Modify/cholmod_updown.c +++ b/CHOLMOD/Modify/cholmod_updown.c @@ -541,8 +541,7 @@ int CHOLMOD(updown_mask2) /* ---------------------------------------------------------------------- */ /* mark = CHOLMOD(clear_flag) (Common) ; */ - CLEAR_FLAG (Common) ; - ASSERT (check_flag (Common)) ; + CHOLMOD_CLEAR_FLAG (Common) ; mark = Common->mark ; PRINT1 (("updown, rank %g update %d\n", (double) C->ncol, update)) ; @@ -736,7 +735,7 @@ int CHOLMOD(updown_mask2) if (do_solve) { xj = Xx [j] ; - if (xj != 0) + if (IS_NONZERO (xj)) { xj = Xx [j] ; /* This is first time column j has been seen for entire */ diff --git a/CHOLMOD/Modify/t_cholmod_updown_numkr.c b/CHOLMOD/Modify/t_cholmod_updown_numkr.c index 62c9b75c20..482a8ffbca 100644 --- a/CHOLMOD/Modify/t_cholmod_updown_numkr.c +++ b/CHOLMOD/Modify/t_cholmod_updown_numkr.c @@ -345,7 +345,7 @@ static void NUMERIC (WDIM, RANK) double *Lx ; Int *Li, *Lp, *Lnz ; Int p, k ; - Int use_dbound = (Common->dbound > 0) ; + Int use_dbound = IS_GT_ZERO (Common->dbound) ; Li = L->i ; Lx = L->x ; @@ -386,7 +386,7 @@ static void NUMERIC (WDIM, RANK) double *W0, *W1, *W2, *W3, *Lx ; Int *Li, *Lp, *Lnz ; Int j1, j2, j3, p0, p1, p2, p3, parent, lnz, pend, k ; - Int use_dbound = (Common->dbound > 0) ; + Int use_dbound = IS_GT_ZERO (Common->dbound) ; Li = L->i ; Lx = L->x ; diff --git a/CHOLMOD/Partition/cholmod_camd.c b/CHOLMOD/Partition/cholmod_camd.c index 716410df7f..40747391b0 100644 --- a/CHOLMOD/Partition/cholmod_camd.c +++ b/CHOLMOD/Partition/cholmod_camd.c @@ -177,7 +177,7 @@ int CHOLMOD(camd) Control [CAMD_AGGRESSIVE] = Common->method [Common->current].aggressive; } -#if defined ( CHOLMOD_INT64 ) +#if ( ITYPE == CHOLMOD_LONG ) /* DEBUG (camd_l_debug_init ("cholmod_l_camd")) ; */ camd_l2 (n, C->p, C->i, Len, C->nzmax, cnz, Nv, Next, Perm, Head, Elen, Degree, Wi, Control, Info, Cmember, BucketSet) ; diff --git a/CHOLMOD/Partition/cholmod_ccolamd.c b/CHOLMOD/Partition/cholmod_ccolamd.c index 7251abd7df..08b79c9b54 100644 --- a/CHOLMOD/Partition/cholmod_ccolamd.c +++ b/CHOLMOD/Partition/cholmod_ccolamd.c @@ -67,7 +67,7 @@ static int ccolamd_interface /* ---------------------------------------------------------------------- */ /* get parameters */ -#if defined ( CHOLMOD_INT64 ) +#if ( ITYPE == CHOLMOD_LONG ) ccolamd_l_set_defaults (knobs) ; #else ccolamd_set_defaults (knobs) ; @@ -90,7 +90,7 @@ static int ccolamd_interface if (ok) { -#if defined ( CHOLMOD_INT64 ) +#if ( ITYPE == CHOLMOD_LONG ) ccolamd_l (ncol, nrow, alen, C->i, C->p, knobs, stats, Cmember) ; #else ccolamd (ncol, nrow, alen, C->i, C->p, knobs, stats, Cmember) ; @@ -164,7 +164,7 @@ int CHOLMOD(ccolamd) /* allocate workspace */ /* ---------------------------------------------------------------------- */ -#if defined ( CHOLMOD_INT64 ) +#if ( ITYPE == CHOLMOD_LONG ) alen = ccolamd_l_recommended (A->nzmax, ncol, nrow) ; #else alen = ccolamd_recommended (A->nzmax, ncol, nrow) ; diff --git a/CHOLMOD/Partition/cholmod_csymamd.c b/CHOLMOD/Partition/cholmod_csymamd.c index 6990d34991..03d46e1f70 100644 --- a/CHOLMOD/Partition/cholmod_csymamd.c +++ b/CHOLMOD/Partition/cholmod_csymamd.c @@ -86,7 +86,7 @@ int CHOLMOD(csymamd) perm = Common->Head ; /* size nrow+1 (i/l/l) */ /* get parameters */ -#if defined ( CHOLMOD_INT64 ) +#if ( ITYPE == CHOLMOD_LONG ) ccolamd_l_set_defaults (knobs) ; #else ccolamd_set_defaults (knobs) ; @@ -103,7 +103,7 @@ int CHOLMOD(csymamd) calloc_func = SuiteSparse_config_calloc_func_get ( ) ; free_func = SuiteSparse_config_free_func_get ( ) ; -#if defined ( CHOLMOD_INT64 ) +#if ( ITYPE == CHOLMOD_LONG ) csymamd_l (nrow, A->i, A->p, perm, knobs, stats, calloc_func, free_func, diff --git a/CHOLMOD/Partition/cholmod_l_camd.c b/CHOLMOD/Partition/cholmod_l_camd.c index d4c3809802..6926e41b3d 100644 --- a/CHOLMOD/Partition/cholmod_l_camd.c +++ b/CHOLMOD/Partition/cholmod_l_camd.c @@ -8,6 +8,6 @@ //------------------------------------------------------------------------------ -#define CHOLMOD_INT64 +#define DLONG #include "cholmod_camd.c" diff --git a/CHOLMOD/Partition/cholmod_l_ccolamd.c b/CHOLMOD/Partition/cholmod_l_ccolamd.c index 56faa504de..cfe317c549 100644 --- a/CHOLMOD/Partition/cholmod_l_ccolamd.c +++ b/CHOLMOD/Partition/cholmod_l_ccolamd.c @@ -8,6 +8,6 @@ //------------------------------------------------------------------------------ -#define CHOLMOD_INT64 +#define DLONG #include "cholmod_ccolamd.c" diff --git a/CHOLMOD/Partition/cholmod_l_csymamd.c b/CHOLMOD/Partition/cholmod_l_csymamd.c index 2ffd4dd501..4b816b5887 100644 --- a/CHOLMOD/Partition/cholmod_l_csymamd.c +++ b/CHOLMOD/Partition/cholmod_l_csymamd.c @@ -8,6 +8,6 @@ //------------------------------------------------------------------------------ -#define CHOLMOD_INT64 +#define DLONG #include "cholmod_csymamd.c" diff --git a/CHOLMOD/Partition/cholmod_l_metis.c b/CHOLMOD/Partition/cholmod_l_metis.c index f529e47ccd..ad2c7467a2 100644 --- a/CHOLMOD/Partition/cholmod_l_metis.c +++ b/CHOLMOD/Partition/cholmod_l_metis.c @@ -8,6 +8,6 @@ //------------------------------------------------------------------------------ -#define CHOLMOD_INT64 +#define DLONG #include "cholmod_metis.c" diff --git a/CHOLMOD/Partition/cholmod_l_nesdis.c b/CHOLMOD/Partition/cholmod_l_nesdis.c index 60572c9cb6..51896c5f18 100644 --- a/CHOLMOD/Partition/cholmod_l_nesdis.c +++ b/CHOLMOD/Partition/cholmod_l_nesdis.c @@ -8,6 +8,6 @@ //------------------------------------------------------------------------------ -#define CHOLMOD_INT64 +#define DLONG #include "cholmod_nesdis.c" diff --git a/CHOLMOD/Partition/cholmod_nesdis.c b/CHOLMOD/Partition/cholmod_nesdis.c index 43c9900793..46cb8a1359 100644 --- a/CHOLMOD/Partition/cholmod_nesdis.c +++ b/CHOLMOD/Partition/cholmod_nesdis.c @@ -1007,8 +1007,7 @@ int64_t CHOLMOD(bisect) /* returns # of nodes in separator */ B->ncol = n ; /* restore size for memory usage statistics */ CHOLMOD(free_sparse) (&B, Common) ; Common->mark = EMPTY ; - CLEAR_FLAG (Common) ; - ASSERT (check_flag (Common)) ; + CHOLMOD_CLEAR_FLAG (Common) ; CHOLMOD(free) (csize, sizeof (Int), Bew, Common) ; return (sepsize) ; #else @@ -1200,8 +1199,7 @@ int64_t CHOLMOD(nested_dissection) /* returns # of components, or -1 if error */ /* all nodes start out unmarked and unordered (Type 4, see below) */ Common->mark = EMPTY ; - CLEAR_FLAG (Common) ; - ASSERT (check_flag (Common)) ; + CHOLMOD_CLEAR_FLAG (Common) ; ASSERT (Flag == Common->Flag) ; ASSERT (CHOLMOD(dump_work) (TRUE, TRUE, 0, Common)) ; @@ -1211,7 +1209,7 @@ int64_t CHOLMOD(nested_dissection) /* returns # of components, or -1 if error */ } /* prune dense nodes from B */ - if (isnan (prune_dense) || prune_dense < 0) + if (IS_NAN (prune_dense) || prune_dense < 0) { /* only remove completely dense nodes */ threshold = n-2 ; @@ -1262,8 +1260,7 @@ int64_t CHOLMOD(nested_dissection) /* returns # of components, or -1 if error */ CHOLMOD(free_sparse) (&B, Common) ; CHOLMOD(free) (3*n, sizeof (Int), Work3n, Common) ; Common->mark = EMPTY ; - CLEAR_FLAG (Common) ; - ASSERT (check_flag (Common)) ; + CHOLMOD_CLEAR_FLAG (Common) ; return (1) ; } @@ -1280,8 +1277,7 @@ int64_t CHOLMOD(nested_dissection) /* returns # of components, or -1 if error */ CHOLMOD(free) (csize, sizeof (Int), Cew, Common) ; CHOLMOD(free) (3*n, sizeof (Int), Work3n, Common) ; Common->mark = EMPTY ; - CLEAR_FLAG (Common) ; - ASSERT (check_flag (Common)) ; + CHOLMOD_CLEAR_FLAG (Common) ; PRINT2 (("out of memory for C, etc\n")) ; return (EMPTY) ; } @@ -1507,8 +1503,7 @@ int64_t CHOLMOD(nested_dissection) /* returns # of components, or -1 if error */ CHOLMOD(free) (csize, sizeof (Int), Cew, Common) ; CHOLMOD(free) (3*n, sizeof (Int), Work3n, Common) ; Common->mark = EMPTY ; - CLEAR_FLAG (Common) ; - ASSERT (check_flag (Common)) ; + CHOLMOD_CLEAR_FLAG (Common) ; return (EMPTY) ; } @@ -1836,8 +1831,7 @@ int64_t CHOLMOD(nested_dissection) /* returns # of components, or -1 if error */ /* ---------------------------------------------------------------------- */ Common->mark = EMPTY ; - CLEAR_FLAG (Common) ; - ASSERT (check_flag (Common)) ; + CHOLMOD_CLEAR_FLAG (Common) ; ASSERT (CHOLMOD(dump_work) (TRUE, TRUE, 0, Common)) ; /* ---------------------------------------------------------------------- */ @@ -2043,7 +2037,6 @@ int64_t CHOLMOD(collapse_septree) /* find the first descendant of each node of the separator tree */ /* ---------------------------------------------------------------------- */ - ASSERT (ncomponents >= 1 && ncomponents <= n) ; for (c = 0 ; c < nc ; c++) { First [c] = EMPTY ; diff --git a/CHOLMOD/README.txt b/CHOLMOD/README.txt index 43ed5956c3..2103a52d71 100644 --- a/CHOLMOD/README.txt +++ b/CHOLMOD/README.txt @@ -1,4 +1,4 @@ -CHOLMOD: a sparse CHOLesky MODification package, Copyright (c) 2005-2023. +CHOLMOD: a sparse CHOLesky MODification package, Copyright (c) 2005-2020. http://www.suitesparse.com ----------------------------------------------- @@ -13,12 +13,9 @@ http://www.suitesparse.com C and MATLAB interfaces. This code works on Microsoft Windows and many versions of Unix and Linux. -CHOLMOD v5.0.0 introduces the first part of support for single precision -sparse matrices, with the introduction of the new CHOLMOD:Utility Module. -Single precision is not yet incorporated into the remaining Modules, however. -One CHOLMOD Module is copyrighted by the University of Florida (the -Partition Module). The rest are copyrighted by the authors: +Some Modules of CHOLMOD are copyrighted by the University of Florida (the +Core and Partition Modules). The rest are copyrighted by the authors: Timothy A. Davis (all of them), and William W. Hager (the Modify Module). CHOLMOD relies on several other packages: AMD, CAMD, COLAMD, CCOLAMD, diff --git a/CHOLMOD/SuiteSparse_metis/GKlib/gkregex.c b/CHOLMOD/SuiteSparse_metis/GKlib/gkregex.c index 093505bf11..8a09caab78 100644 --- a/CHOLMOD/SuiteSparse_metis/GKlib/gkregex.c +++ b/CHOLMOD/SuiteSparse_metis/GKlib/gkregex.c @@ -10135,7 +10135,7 @@ check_node_accept_bytes (const re_dfa_t *dfa, int node_idx, { if (char_len <= 1) return 0; - /* fixme: I don't think this if is needed, as both '\n' + /* FIXME: I don't think this if is needed, as both '\n' and '\0' are char_len == 1. */ /* '.' accepts any one character except the following two cases. */ if ((!(dfa->syntax & RE_DOT_NEWLINE) && diff --git a/CHOLMOD/Supernodal/cholmod_l_super_numeric.c b/CHOLMOD/Supernodal/cholmod_l_super_numeric.c index 2f83c3388f..3b0c6a261c 100644 --- a/CHOLMOD/Supernodal/cholmod_l_super_numeric.c +++ b/CHOLMOD/Supernodal/cholmod_l_super_numeric.c @@ -9,6 +9,6 @@ //------------------------------------------------------------------------------ -#define CHOLMOD_INT64 +#define DLONG #include "cholmod_super_numeric.c" diff --git a/CHOLMOD/Supernodal/cholmod_l_super_solve.c b/CHOLMOD/Supernodal/cholmod_l_super_solve.c index a1ff3b2868..515fe4c262 100644 --- a/CHOLMOD/Supernodal/cholmod_l_super_solve.c +++ b/CHOLMOD/Supernodal/cholmod_l_super_solve.c @@ -9,6 +9,6 @@ //------------------------------------------------------------------------------ -#define CHOLMOD_INT64 +#define DLONG #include "cholmod_super_solve.c" diff --git a/CHOLMOD/Supernodal/cholmod_l_super_symbolic.c b/CHOLMOD/Supernodal/cholmod_l_super_symbolic.c index 8a9cd46adc..34e45b648e 100644 --- a/CHOLMOD/Supernodal/cholmod_l_super_symbolic.c +++ b/CHOLMOD/Supernodal/cholmod_l_super_symbolic.c @@ -9,6 +9,6 @@ //------------------------------------------------------------------------------ -#define CHOLMOD_INT64 +#define DLONG #include "cholmod_super_symbolic.c" diff --git a/CHOLMOD/Supernodal/cholmod_super_numeric.c b/CHOLMOD/Supernodal/cholmod_super_numeric.c index fd8f413fac..1148d19e50 100644 --- a/CHOLMOD/Supernodal/cholmod_super_numeric.c +++ b/CHOLMOD/Supernodal/cholmod_super_numeric.c @@ -63,7 +63,7 @@ /* === TEMPLATE codes for GPU and regular numeric factorization ============= */ /* ========================================================================== */ -#ifdef CHOLMOD_INT64 +#ifdef DLONG #ifdef SUITESPARSE_CUDA #include "cholmod_gpu_kernels.h" #define REAL @@ -218,7 +218,7 @@ int CHOLMOD(super_numeric) return (FALSE) ; } } - ASSERT (L->dtype == CHOLMOD_DOUBLE) ; // FIXME + ASSERT (L->dtype == DTYPE) ; ASSERT (L->xtype == CHOLMOD_REAL || L->xtype == CHOLMOD_COMPLEX) ; /* supernodal LDL' is not supported */ @@ -298,8 +298,7 @@ int CHOLMOD(super_numeric) /* Flag array was used as workspace, clear it */ Common->mark = EMPTY ; /* CHOLMOD(clear_flag) (Common) ; */ - CLEAR_FLAG (Common) ; - ASSERT (check_flag (Common)) ; + CHOLMOD_CLEAR_FLAG (Common) ; ASSERT (CHOLMOD(dump_work) (TRUE, TRUE, 0, Common)) ; CHOLMOD(free_dense) (&C, Common) ; return (ok) ; diff --git a/CHOLMOD/Supernodal/cholmod_super_symbolic.c b/CHOLMOD/Supernodal/cholmod_super_symbolic.c index a41b0dea86..c8e1dfc4c1 100644 --- a/CHOLMOD/Supernodal/cholmod_super_symbolic.c +++ b/CHOLMOD/Supernodal/cholmod_super_symbolic.c @@ -130,15 +130,15 @@ static void subtree /* clear workspace used by cholmod_super_symbolic */ -#define FREE_WORKSPACE \ -{ \ - CLEAR_FLAG (Common) ; \ - ASSERT (check_flag (Common)) ; \ - for (k = 0 ; k <= nfsuper ; k++) \ - { \ - Head [k] = EMPTY ; \ - } \ - ASSERT (CHOLMOD(dump_work) (TRUE, TRUE, 0, Common)) ; \ +#define FREE_WORKSPACE \ +{ \ + /* CHOLMOD(clear_flag) (Common) ; */ \ + CHOLMOD_CLEAR_FLAG (Common) ; \ + for (k = 0 ; k <= nfsuper ; k++) \ + { \ + Head [k] = EMPTY ; \ + } \ + ASSERT (CHOLMOD(dump_work) (TRUE, TRUE, 0, Common)) ; \ } \ @@ -249,7 +249,7 @@ int CHOLMOD(super_symbolic2) max_bytes = 0; max_fraction = 0; -#ifdef CHOLMOD_INT64 +#ifdef DLONG if ( Common->useGPU == EMPTY ) { /* useGPU not explicity requested by the user, but not explicitly @@ -363,9 +363,9 @@ int CHOLMOD(super_symbolic2) zrelax1 = Common->zrelax [1] ; zrelax2 = Common->zrelax [2] ; - zrelax0 = isnan (zrelax0) ? 0 : zrelax0 ; - zrelax1 = isnan (zrelax1) ? 0 : zrelax1 ; - zrelax2 = isnan (zrelax2) ? 0 : zrelax2 ; + zrelax0 = IS_NAN (zrelax0) ? 0 : zrelax0 ; + zrelax1 = IS_NAN (zrelax1) ? 0 : zrelax1 ; + zrelax2 = IS_NAN (zrelax2) ? 0 : zrelax2 ; ASSERT (CHOLMOD(dump_parent) (Parent, n, "Parent", Common)) ; @@ -805,7 +805,7 @@ int CHOLMOD(super_symbolic2) /* clear the Flag array and mark the current supernode */ /* mark = CHOLMOD(clear_flag) (Common) ; */ - CLEAR_FLAG (Common) ; + CHOLMOD_CLEAR_FLAG (Common) ; mark = Common->mark ; Flag [s] = mark ; ASSERT (s == SuperMap [k]) ; diff --git a/CHOLMOD/Tcov/.gitignore b/CHOLMOD/Tcov/.gitignore index 3259887a47..dc83e742c4 100644 --- a/CHOLMOD/Tcov/.gitignore +++ b/CHOLMOD/Tcov/.gitignore @@ -7,8 +7,3 @@ l_*.cu *.gcno *.gcov timelog.m -u_*.c -n_*.c -ui_*.c -ul_*.c -o* diff --git a/CHOLMOD/Tcov/Makefile b/CHOLMOD/Tcov/Makefile index 012e8fc5ed..59baf1cfea 100644 --- a/CHOLMOD/Tcov/Makefile +++ b/CHOLMOD/Tcov/Makefile @@ -75,15 +75,14 @@ default: go ################################################################################ -# without valgrind +# valgrind is not used V = + +# covall is used COVER = ./covall -CF = -O0 -g --coverage -fprofile-abs-path -DTEST_COVERAGE -DBLAS32 -fopenmp -# with valgrind -# V = valgrind --suppressions=suppress --quiet -# COVER = -# CF = -O0 -g +# with test coverage and 32-bit BLAS +CF = -O0 -g --coverage -fprofile-abs-path -DTEST_COVERAGE -DBLAS32 -fopenmp # Temp directory T = $(TCOV_TMP)/CHOLMOD_TCOV_TMP @@ -100,10 +99,8 @@ C = $(CC) $(CF) $(CHOLMOD_CONFIG) $(NANTESTS) # no test coverage CN = $(CC) -O0 -g -fopenmp $(CHOLMOD_CONFIG) $(NANTESTS) -# LDLIBS = -L$(SUITESPARSE)/lib -lsuitesparseconfig \ -# -lm $(LAPACK) $(BLAS) -lrt -Wl,-rpath=$(SUITESPARSE)/lib - -LDLIBS = -lm $(LAPACK) $(BLAS) +LDLIBS = -L$(SUITESPARSE)/lib -lsuitesparseconfig \ + -lm $(LAPACK) $(BLAS) -lrt -Wl,-rpath=$(SUITESPARSE)/lib #------------------------------------------------------------------------------- # With the CUDA BLAS: @@ -116,22 +113,20 @@ I = -I.. -I../../AMD/Include -I../../COLAMD/Include \ -I../SuiteSparse_metis/include -I../../CCOLAMD/Include \ -I../../CAMD/Include \ -I../Include -I../../SuiteSparse_config $(CUDA_INC) \ - -I../Check -I../Cholesky -I../Demo -I../Supernodal \ + -I../Core -I../Check -I../Cholesky -I../Demo -I../Supernodal \ -I../Partition -I../Modify -I../MatrixOps -I../GPU \ -I../SuiteSparse_metis \ -I../SuiteSparse_metis/GKlib \ -I../SuiteSparse_metis/libmetis \ -I../../AMD/Source -I../../CAMD/Source \ - -I../../COLAMD/Source -I../../CCOLAMD/Source \ - -I../Utility + -I../../COLAMD/Source -I../../CCOLAMD/Source I += $(GPU_CONFIG) ccode: cm cl zdemo ldemo cmread clread -TEST = cm.c \ - test_ops.c null.c null2.c lpdemo.c memory.c solve.c aug.c unpack.c \ - raw_factor.c cctest.c ctest.c amdtest.c camdtest.c huge.c +TEST = cm.c test_ops.c null.c null2.c lpdemo.c memory.c solve.c aug.c unpack.c \ + raw_factor.c cctest.c ctest.c amdtest.c camdtest.c huge.c LTEST = cl.c amdtest_l.c camdtest_l.c huge_l.c @@ -209,7 +204,7 @@ IPARTITION_OBJ = \ z_csymamd.o \ z_camd.o \ z_metis.o \ - n_metis_wrapper.o \ + z_metis_wrapper.o \ z_nesdis.o LPARTITION_OBJ = \ @@ -217,7 +212,7 @@ LPARTITION_OBJ = \ l_csymamd.o \ l_camd.o \ l_metis.o \ - n_metis_wrapper.o \ + z_metis_wrapper.o \ l_nesdis.o CAMDSRC = ../../CAMD/Source/camd_1.c \ @@ -279,147 +274,22 @@ $(LCAMDOBJ): $(CAMDSRC) # LCAMDOBJ = #------------------------------------------------------------------------------- -IUTIL_OBJ = \ - ui_change_factor.o \ - ui_transpose_unsym.o \ - ui_transpose_sym.o \ - ui_transpose.o \ - ui_ptranspose.o \ - ui_sort.o \ - ui_aat.o \ - ui_factor_to_sparse.o \ - ui_reallocate_column.o \ - ui_copy_factor.o \ - ui_pack_factor.o \ - ui_reallocate_factor.o \ - ui_free_factor.o \ - ui_alloc_factor.o \ - ui_allocate_factor.o \ - ui_copy.o \ - ui_add.o \ - ui_add_size_t.o \ - ui_alloc_work.o \ - ui_allocate_dense.o \ - ui_allocate_sparse.o \ - ui_allocate_triplet.o \ - ui_allocate_work.o \ - ui_band.o \ - ui_band_nnz.o \ - ui_calloc.o \ - ui_clear_flag.o \ - ui_copy_dense.o \ - ui_copy_dense2.o \ - ui_copy_sparse.o \ - ui_copy_triplet.o \ - ui_cumsum.o \ - ui_dbound.o \ - ui_defaults.o \ - ui_dense_nnz.o \ - ui_dense_to_sparse.o \ - ui_divcomplex.o \ - ui_ensure_dense.o \ - ui_error.o \ - ui_eye.o \ - ui_finish.o \ - ui_free.o \ - ui_free_dense.o \ - ui_free_sparse.o \ - ui_free_triplet.o \ - ui_free_work.o \ - ui_hypot.o \ - ui_malloc.o \ - ui_maxrank.o \ - ui_mult_size_t.o \ - ui_nnz.o \ - ui_ones.o \ - ui_realloc.o \ - ui_realloc_multiple.o \ - ui_reallocate_sparse.o \ - ui_reallocate_triplet.o \ - ui_sbound.o \ - ui_score_comp.o \ - ui_set_empty.o \ - ui_sparse_to_dense.o \ - ui_sparse_to_triplet.o \ - ui_speye.o \ - ui_spzeros.o \ - ui_start.o \ - ui_triplet_to_sparse.o \ - ui_version.o \ - ui_xtype.o \ - ui_zeros.o - -LUTIL_OBJ = \ - ul_change_factor.o \ - ul_transpose_unsym.o \ - ul_transpose_sym.o \ - ul_transpose.o \ - ul_ptranspose.o \ - ul_sort.o \ - ul_aat.o \ - ul_factor_to_sparse.o \ - ul_reallocate_column.o \ - ul_copy_factor.o \ - ul_pack_factor.o \ - ul_reallocate_factor.o \ - ul_free_factor.o \ - ul_alloc_factor.o \ - ul_allocate_factor.o \ - ul_copy.o \ - ul_add.o \ - ul_add_size_t.o \ - ul_alloc_work.o \ - ul_allocate_dense.o \ - ul_allocate_sparse.o \ - ul_allocate_triplet.o \ - ul_allocate_work.o \ - ul_band.o \ - ul_band_nnz.o \ - ul_calloc.o \ - ul_clear_flag.o \ - ul_copy_dense.o \ - ul_copy_dense2.o \ - ul_copy_sparse.o \ - ul_copy_triplet.o \ - ul_cumsum.o \ - ul_dbound.o \ - ul_defaults.o \ - ul_dense_nnz.o \ - ul_dense_to_sparse.o \ - ul_divcomplex.o \ - ul_ensure_dense.o \ - ul_error.o \ - ul_eye.o \ - ul_finish.o \ - ul_free.o \ - ul_free_dense.o \ - ul_free_sparse.o \ - ul_free_triplet.o \ - ul_free_work.o \ - ul_hypot.o \ - ul_malloc.o \ - ul_maxrank.o \ - ul_mult_size_t.o \ - ul_nnz.o \ - ul_ones.o \ - ul_realloc.o \ - ul_realloc_multiple.o \ - ul_reallocate_sparse.o \ - ul_reallocate_triplet.o \ - ul_sbound.o \ - ul_score_comp.o \ - ul_set_empty.o \ - ul_sparse_to_dense.o \ - ul_sparse_to_triplet.o \ - ul_speye.o \ - ul_spzeros.o \ - ul_start.o \ - ul_triplet_to_sparse.o \ - ul_version.o \ - ul_xtype.o \ - ul_zeros.o - -IOBJ = $(IUTIL_OBJ) \ +IOBJ = \ + z_common.o \ + z_version.o \ + z_dense.o \ + z_factor.o \ + z_change_factor.o \ + z_memory.o \ + z_sparse.o \ + z_complex.o \ + z_transpose.o \ + z_band.o \ + z_copy.o \ + z_triplet.o \ + z_error.o \ + z_aat.o \ + z_add.o \ z_check.o \ z_read.o \ z_write.o \ @@ -452,7 +322,22 @@ IOBJ = $(IUTIL_OBJ) \ z_super_symbolic.o \ $(IPARTITION_OBJ) -LOBJ = $(LUTIL_OBJ) \ +LOBJ = \ + l_common.o \ + l_version.o \ + l_dense.o \ + l_factor.o \ + l_change_factor.o \ + l_memory.o \ + l_sparse.o \ + l_complex.o \ + l_transpose.o \ + l_band.o \ + l_copy.o \ + l_triplet.o \ + l_error.o \ + l_aat.o \ + l_add.o \ l_check.o \ l_read.o \ l_write.o \ @@ -493,22 +378,18 @@ else LGPU = endif -CONFIG = zz_SuiteSparse_config.o -# CONFIG = - -ILOBJ = u_mult_uint64_t.o u_memdebug.o +# CONFIG = zz_SuiteSparse_config.o +CONFIG = -IALL = $(IOBJ) $(AMDOBJ) $(COLAMDOBJ) $(CCOLAMDOBJ) $(CAMDOBJ) $(CONFIG) $(ILOBJ) $(IGPU) +IALL = $(IOBJ) $(AMDOBJ) $(COLAMDOBJ) $(CCOLAMDOBJ) $(CAMDOBJ) $(CONFIG) $(IGPU) -LALL = $(LOBJ) $(LAMDOBJ) $(LCOLAMDOBJ) $(LCCOLAMDOBJ) $(LCAMDOBJ) $(CONFIG) $(ILOBJ) $(LGPU) +LALL = $(LOBJ) $(LAMDOBJ) $(LCOLAMDOBJ) $(LCCOLAMDOBJ) $(LCAMDOBJ) $(CONFIG) $(LGPU) cm: $(IALL) $(TEST) cm.h Makefile $(C) $(I) $(TEST) -o cm $(IALL) $(LDLIBS) -cl: $(LALL) $(LTEST) cm.h Makefile cm.c \ - test_ops.c null.c null2.c lpdemo.c memory.c solve.c aug.c unpack.c \ - raw_factor.c cctest.c ctest.c amdtest.c camdtest.c huge.c +cl: $(LALL) $(LTEST) cm.h Makefile $(C) $(I) $(LTEST) -o cl $(LALL) $(LDLIBS) cmread: $(IALL) cmread.c Makefile @@ -722,7 +603,7 @@ go: zdemo ldemo cmread clread cm cl $(V) ./cl -n < Matrix/galenet > $(T)/l_galenet_nan.out - $(COVER) $(V) ./cm < Matrix/zero > $(T)/zero.out - $(V) ./cl < Matrix/zero > $(T)/l_zero.out + $(V) ./cl < Matrix/zero > $(T)/zero.out - $(COVER) cov: @@ -749,7 +630,6 @@ clean: - $(RM) -r cm.profile cmread.profile zdemo.profile $(T) - $(RM) -r cl.profile clread.profile ldemo.profile - $(RM) temp*.mtx timelog.m l_*.cu - - $(RM) ui_*.c ul_*.c u_*.c n_*.c - $(RM) -r $(PURGE) - $(RM) -r $(CLEAN) @@ -1004,568 +884,66 @@ z_write.o: ../Check/cholmod_write.c $(C) -c $(I) z_write.c #------------------------------------------------------------------------------- -# Utility, int32 -#------------------------------------------------------------------------------- - -ui_change_factor.o: ../Utility/cholmod_change_factor.c - - ln -s $< ui_change_factor.c - $(C) -c $(I) ui_change_factor.c - -ui_transpose_unsym.o: ../Utility/cholmod_transpose_unsym.c - - ln -s $< ui_transpose_unsym.c - $(C) -c $(I) ui_transpose_unsym.c - -ui_transpose_sym.o: ../Utility/cholmod_transpose_sym.c - - ln -s $< ui_transpose_sym.c - $(C) -c $(I) ui_transpose_sym.c - -ui_transpose.o: ../Utility/cholmod_transpose.c - - ln -s $< ui_transpose.c - $(C) -c $(I) ui_transpose.c - -ui_ptranspose.o: ../Utility/cholmod_ptranspose.c - - ln -s $< ui_ptranspose.c - $(C) -c $(I) ui_ptranspose.c - -ui_sort.o: ../Utility/cholmod_sort.c - - ln -s $< ui_sort.c - $(C) -c $(I) ui_sort.c - -ui_aat.o: ../Utility/cholmod_aat.c - - ln -s $< ui_aat.c - $(C) -c $(I) ui_aat.c - -ui_factor_to_sparse.o: ../Utility/cholmod_factor_to_sparse.c - - ln -s $< ui_factor_to_sparse.c - $(C) -c $(I) ui_factor_to_sparse.c - -ui_reallocate_column.o: ../Utility/cholmod_reallocate_column.c - - ln -s $< ui_reallocate_column.c - $(C) -c $(I) ui_reallocate_column.c - -ui_copy_factor.o: ../Utility/cholmod_copy_factor.c - - ln -s $< ui_copy_factor.c - $(C) -c $(I) ui_copy_factor.c - -ui_pack_factor.o: ../Utility/cholmod_pack_factor.c - - ln -s $< ui_pack_factor.c - $(C) -c $(I) ui_pack_factor.c - -ui_reallocate_factor.o: ../Utility/cholmod_reallocate_factor.c - - ln -s $< ui_reallocate_factor.c - $(C) -c $(I) ui_reallocate_factor.c - -ui_free_factor.o: ../Utility/cholmod_free_factor.c - - ln -s $< ui_free_factor.c - $(C) -c $(I) ui_free_factor.c - -ui_alloc_factor.o: ../Utility/cholmod_alloc_factor.c - - ln -s $< ui_alloc_factor.c - $(C) -c $(I) ui_alloc_factor.c - -ui_allocate_factor.o: ../Utility/cholmod_allocate_factor.c - - ln -s $< ui_allocate_factor.c - $(C) -c $(I) ui_allocate_factor.c - -ui_copy.o: ../Utility/cholmod_copy.c - - ln -s $< ui_copy.c - $(C) -c $(I) ui_copy.c - -ui_add.o: ../Utility/cholmod_add.c - - ln -s $< ui_add.c - $(C) -c $(I) ui_add.c - -ui_add_size_t.o: ../Utility/cholmod_add_size_t.c - - ln -s $< ui_add_size_t.c - $(C) -c $(I) ui_add_size_t.c - -ui_alloc_work.o: ../Utility/cholmod_alloc_work.c - - ln -s $< ui_alloc_work.c - $(C) -c $(I) ui_alloc_work.c - -ui_allocate_dense.o: ../Utility/cholmod_allocate_dense.c - - ln -s $< ui_allocate_dense.c - $(C) -c $(I) ui_allocate_dense.c - -ui_allocate_sparse.o: ../Utility/cholmod_allocate_sparse.c - - ln -s $< ui_allocate_sparse.c - $(C) -c $(I) ui_allocate_sparse.c - -ui_allocate_triplet.o: ../Utility/cholmod_allocate_triplet.c - - ln -s $< ui_allocate_triplet.c - $(C) -c $(I) ui_allocate_triplet.c - -ui_allocate_work.o: ../Utility/cholmod_allocate_work.c - - ln -s $< ui_allocate_work.c - $(C) -c $(I) ui_allocate_work.c - -ui_band.o: ../Utility/cholmod_band.c - - ln -s $< ui_band.c - $(C) -c $(I) ui_band.c - -ui_band_nnz.o: ../Utility/cholmod_band_nnz.c - - ln -s $< ui_band_nnz.c - $(C) -c $(I) ui_band_nnz.c - -ui_calloc.o: ../Utility/cholmod_calloc.c - - ln -s $< ui_calloc.c - $(C) -c $(I) ui_calloc.c - -ui_clear_flag.o: ../Utility/cholmod_clear_flag.c - - ln -s $< ui_clear_flag.c - $(C) -c $(I) ui_clear_flag.c - -ui_copy_dense.o: ../Utility/cholmod_copy_dense.c - - ln -s $< ui_copy_dense.c - $(C) -c $(I) ui_copy_dense.c - -ui_copy_dense2.o: ../Utility/cholmod_copy_dense2.c - - ln -s $< ui_copy_dense2.c - $(C) -c $(I) ui_copy_dense2.c - -ui_copy_sparse.o: ../Utility/cholmod_copy_sparse.c - - ln -s $< ui_copy_sparse.c - $(C) -c $(I) ui_copy_sparse.c - -ui_copy_triplet.o: ../Utility/cholmod_copy_triplet.c - - ln -s $< ui_copy_triplet.c - $(C) -c $(I) ui_copy_triplet.c - -ui_cumsum.o: ../Utility/cholmod_cumsum.c - - ln -s $< ui_cumsum.c - $(C) -c $(I) ui_cumsum.c - -ui_dbound.o: ../Utility/cholmod_dbound.c - - ln -s $< ui_dbound.c - $(C) -c $(I) ui_dbound.c -ui_defaults.o: ../Utility/cholmod_defaults.c - - ln -s $< ui_defaults.c - $(C) -c $(I) ui_defaults.c +z_common.o: ../Core/cholmod_common.c + - ln -s $< z_common.c + $(C) -c $(I) z_common.c -ui_dense_nnz.o: ../Utility/cholmod_dense_nnz.c - - ln -s $< ui_dense_nnz.c - $(C) -c $(I) ui_dense_nnz.c +z_version.o: ../Core/cholmod_version.c + - ln -s $< z_version.c + $(C) -c $(I) z_version.c -ui_dense_to_sparse.o: ../Utility/cholmod_dense_to_sparse.c - - ln -s $< ui_dense_to_sparse.c - $(C) -c $(I) ui_dense_to_sparse.c +z_dense.o: ../Core/cholmod_dense.c + - ln -s $< z_dense.c + $(C) -c $(I) z_dense.c -ui_divcomplex.o: ../Utility/cholmod_divcomplex.c - - ln -s $< ui_divcomplex.c - $(C) -c $(I) ui_divcomplex.c +z_factor.o: ../Core/cholmod_factor.c + - ln -s $< z_factor.c + $(C) -c $(I) z_factor.c -ui_ensure_dense.o: ../Utility/cholmod_ensure_dense.c - - ln -s $< ui_ensure_dense.c - $(C) -c $(I) ui_ensure_dense.c +z_change_factor.o: ../Core/cholmod_change_factor.c + - ln -s $< z_change_factor.c + $(C) -c $(I) z_change_factor.c -ui_error.o: ../Utility/cholmod_error.c - - ln -s $< ui_error.c - $(C) -c $(I) ui_error.c +z_memory.o: ../Core/cholmod_memory.c + - ln -s $< z_memory.c + $(C) -c $(I) z_memory.c -ui_eye.o: ../Utility/cholmod_eye.c - - ln -s $< ui_eye.c - $(C) -c $(I) ui_eye.c +z_sparse.o: ../Core/cholmod_sparse.c + - ln -s $< z_sparse.c + $(C) -c $(I) z_sparse.c -ui_finish.o: ../Utility/cholmod_finish.c - - ln -s $< ui_finish.c - $(C) -c $(I) ui_finish.c +z_complex.o: ../Core/cholmod_complex.c + - ln -s $< z_complex.c + $(C) -c $(I) z_complex.c -ui_free.o: ../Utility/cholmod_free.c - - ln -s $< ui_free.c - $(C) -c $(I) ui_free.c +z_transpose.o: ../Core/cholmod_transpose.c + - ln -s $< z_transpose.c + $(C) -c $(I) z_transpose.c -ui_free_dense.o: ../Utility/cholmod_free_dense.c - - ln -s $< ui_free_dense.c - $(C) -c $(I) ui_free_dense.c +z_band.o: ../Core/cholmod_band.c + - ln -s $< z_band.c + $(C) -c $(I) z_band.c -ui_free_sparse.o: ../Utility/cholmod_free_sparse.c - - ln -s $< ui_free_sparse.c - $(C) -c $(I) ui_free_sparse.c +z_copy.o: ../Core/cholmod_copy.c + - ln -s $< z_copy.c + $(C) -c $(I) z_copy.c -ui_free_triplet.o: ../Utility/cholmod_free_triplet.c - - ln -s $< ui_free_triplet.c - $(C) -c $(I) ui_free_triplet.c +z_triplet.o: ../Core/cholmod_triplet.c + - ln -s $< z_triplet.c + $(C) -c $(I) z_triplet.c -ui_free_work.o: ../Utility/cholmod_free_work.c - - ln -s $< ui_free_work.c - $(C) -c $(I) ui_free_work.c +z_error.o: ../Core/cholmod_error.c + - ln -s $< z_error.c + $(C) -c $(I) z_error.c -ui_hypot.o: ../Utility/cholmod_hypot.c - - ln -s $< ui_hypot.c - $(C) -c $(I) ui_hypot.c +z_aat.o: ../Core/cholmod_aat.c + - ln -s $< z_aat.c + $(C) -c $(I) z_aat.c -ui_malloc.o: ../Utility/cholmod_malloc.c - - ln -s $< ui_malloc.c - $(C) -c $(I) ui_malloc.c - -ui_maxrank.o: ../Utility/cholmod_maxrank.c - - ln -s $< ui_maxrank.c - $(C) -c $(I) ui_maxrank.c - -ui_mult_size_t.o: ../Utility/cholmod_mult_size_t.c - - ln -s $< ui_mult_size_t.c - $(C) -c $(I) ui_mult_size_t.c - -ui_nnz.o: ../Utility/cholmod_nnz.c - - ln -s $< ui_nnz.c - $(C) -c $(I) ui_nnz.c - -ui_ones.o: ../Utility/cholmod_ones.c - - ln -s $< ui_ones.c - $(C) -c $(I) ui_ones.c - -ui_realloc.o: ../Utility/cholmod_realloc.c - - ln -s $< ui_realloc.c - $(C) -c $(I) ui_realloc.c - -ui_realloc_multiple.o: ../Utility/cholmod_realloc_multiple.c - - ln -s $< ui_realloc_multiple.c - $(C) -c $(I) ui_realloc_multiple.c - -ui_reallocate_sparse.o: ../Utility/cholmod_reallocate_sparse.c - - ln -s $< ui_reallocate_sparse.c - $(C) -c $(I) ui_reallocate_sparse.c - -ui_reallocate_triplet.o: ../Utility/cholmod_reallocate_triplet.c - - ln -s $< ui_reallocate_triplet.c - $(C) -c $(I) ui_reallocate_triplet.c - -ui_sbound.o: ../Utility/cholmod_sbound.c - - ln -s $< ui_sbound.c - $(C) -c $(I) ui_sbound.c - -ui_score_comp.o: ../Utility/cholmod_score_comp.c - - ln -s $< ui_score_comp.c - $(C) -c $(I) ui_score_comp.c - -ui_set_empty.o: ../Utility/cholmod_set_empty.c - - ln -s $< ui_set_empty.c - $(C) -c $(I) ui_set_empty.c - -ui_sparse_to_dense.o: ../Utility/cholmod_sparse_to_dense.c - - ln -s $< ui_sparse_to_dense.c - $(C) -c $(I) ui_sparse_to_dense.c - -ui_sparse_to_triplet.o: ../Utility/cholmod_sparse_to_triplet.c - - ln -s $< ui_sparse_to_triplet.c - $(C) -c $(I) ui_sparse_to_triplet.c - -ui_speye.o: ../Utility/cholmod_speye.c - - ln -s $< ui_speye.c - $(C) -c $(I) ui_speye.c - -ui_spzeros.o: ../Utility/cholmod_spzeros.c - - ln -s $< ui_spzeros.c - $(C) -c $(I) ui_spzeros.c - -ui_start.o: ../Utility/cholmod_start.c - - ln -s $< ui_start.c - $(C) -c $(I) ui_start.c - -ui_triplet_to_sparse.o: ../Utility/cholmod_triplet_to_sparse.c - - ln -s $< ui_triplet_to_sparse.c - $(C) -c $(I) ui_triplet_to_sparse.c - -ui_version.o: ../Utility/cholmod_version.c - - ln -s $< ui_version.c - $(C) -c $(I) ui_version.c - -ui_xtype.o: ../Utility/cholmod_xtype.c - - ln -s $< ui_xtype.c - $(C) -c $(I) ui_xtype.c - -ui_zeros.o: ../Utility/cholmod_zeros.c - - ln -s $< ui_zeros.c - $(C) -c $(I) ui_zeros.c - -#------------------------------------------------------------------------------- -# Utility, just one compilation -#------------------------------------------------------------------------------- - -u_mult_uint64_t.o: ../Utility/cholmod_mult_uint64_t.c - - ln -s $< u_mult_uint64_t.c - $(C) -c $(I) u_mult_uint64_t.c - -u_memdebug.o: ../Utility/cholmod_memdebug.c - - ln -s $< u_memdebug.c - $(C) -c $(I) u_memdebug.c - -#------------------------------------------------------------------------------- -# Utility, int64 -#------------------------------------------------------------------------------- - -ul_change_factor.o: ../Utility/cholmod_l_change_factor.c - - ln -s $< ul_change_factor.c - $(C) -c $(I) ul_change_factor.c - -ul_transpose_unsym.o: ../Utility/cholmod_l_transpose_unsym.c - - ln -s $< ul_transpose_unsym.c - $(C) -c $(I) ul_transpose_unsym.c - -ul_transpose_sym.o: ../Utility/cholmod_l_transpose_sym.c - - ln -s $< ul_transpose_sym.c - $(C) -c $(I) ul_transpose_sym.c - -ul_transpose.o: ../Utility/cholmod_l_transpose.c - - ln -s $< ul_transpose.c - $(C) -c $(I) ul_transpose.c - -ul_ptranspose.o: ../Utility/cholmod_l_ptranspose.c - - ln -s $< ul_ptranspose.c - $(C) -c $(I) ul_ptranspose.c - -ul_sort.o: ../Utility/cholmod_l_sort.c - - ln -s $< ul_sort.c - $(C) -c $(I) ul_sort.c - -ul_aat.o: ../Utility/cholmod_l_aat.c - - ln -s $< ul_aat.c - $(C) -c $(I) ul_aat.c - -ul_factor_to_sparse.o: ../Utility/cholmod_l_factor_to_sparse.c - - ln -s $< ul_factor_to_sparse.c - $(C) -c $(I) ul_factor_to_sparse.c - -ul_reallocate_column.o: ../Utility/cholmod_l_reallocate_column.c - - ln -s $< ul_reallocate_column.c - $(C) -c $(I) ul_reallocate_column.c - -ul_copy_factor.o: ../Utility/cholmod_l_copy_factor.c - - ln -s $< ul_copy_factor.c - $(C) -c $(I) ul_copy_factor.c - -ul_pack_factor.o: ../Utility/cholmod_l_pack_factor.c - - ln -s $< ul_pack_factor.c - $(C) -c $(I) ul_pack_factor.c - -ul_reallocate_factor.o: ../Utility/cholmod_l_reallocate_factor.c - - ln -s $< ul_reallocate_factor.c - $(C) -c $(I) ul_reallocate_factor.c - -ul_free_factor.o: ../Utility/cholmod_l_free_factor.c - - ln -s $< ul_free_factor.c - $(C) -c $(I) ul_free_factor.c - -ul_alloc_factor.o: ../Utility/cholmod_l_alloc_factor.c - - ln -s $< ul_alloc_factor.c - $(C) -c $(I) ul_alloc_factor.c - -ul_allocate_factor.o: ../Utility/cholmod_l_allocate_factor.c - - ln -s $< ul_allocate_factor.c - $(C) -c $(I) ul_allocate_factor.c - -ul_copy.o: ../Utility/cholmod_l_copy.c - - ln -s $< ul_copy.c - $(C) -c $(I) ul_copy.c - -ul_add.o: ../Utility/cholmod_l_add.c - - ln -s $< ul_add.c - $(C) -c $(I) ul_add.c - -ul_add_size_t.o: ../Utility/cholmod_l_add_size_t.c - - ln -s $< ul_add_size_t.c - $(C) -c $(I) ul_add_size_t.c - -ul_alloc_work.o: ../Utility/cholmod_l_alloc_work.c - - ln -s $< ul_alloc_work.c - $(C) -c $(I) ul_alloc_work.c - -ul_allocate_dense.o: ../Utility/cholmod_l_allocate_dense.c - - ln -s $< ul_allocate_dense.c - $(C) -c $(I) ul_allocate_dense.c - -ul_allocate_sparse.o: ../Utility/cholmod_l_allocate_sparse.c - - ln -s $< ul_allocate_sparse.c - $(C) -c $(I) ul_allocate_sparse.c - -ul_allocate_triplet.o: ../Utility/cholmod_l_allocate_triplet.c - - ln -s $< ul_allocate_triplet.c - $(C) -c $(I) ul_allocate_triplet.c - -ul_allocate_work.o: ../Utility/cholmod_l_allocate_work.c - - ln -s $< ul_allocate_work.c - $(C) -c $(I) ul_allocate_work.c - -ul_band.o: ../Utility/cholmod_l_band.c - - ln -s $< ul_band.c - $(C) -c $(I) ul_band.c - -ul_band_nnz.o: ../Utility/cholmod_l_band_nnz.c - - ln -s $< ul_band_nnz.c - $(C) -c $(I) ul_band_nnz.c - -ul_calloc.o: ../Utility/cholmod_l_calloc.c - - ln -s $< ul_calloc.c - $(C) -c $(I) ul_calloc.c - -ul_clear_flag.o: ../Utility/cholmod_l_clear_flag.c - - ln -s $< ul_clear_flag.c - $(C) -c $(I) ul_clear_flag.c - -ul_copy_dense.o: ../Utility/cholmod_l_copy_dense.c - - ln -s $< ul_copy_dense.c - $(C) -c $(I) ul_copy_dense.c - -ul_copy_dense2.o: ../Utility/cholmod_l_copy_dense2.c - - ln -s $< ul_copy_dense2.c - $(C) -c $(I) ul_copy_dense2.c - -ul_copy_sparse.o: ../Utility/cholmod_l_copy_sparse.c - - ln -s $< ul_copy_sparse.c - $(C) -c $(I) ul_copy_sparse.c - -ul_copy_triplet.o: ../Utility/cholmod_l_copy_triplet.c - - ln -s $< ul_copy_triplet.c - $(C) -c $(I) ul_copy_triplet.c - -ul_cumsum.o: ../Utility/cholmod_l_cumsum.c - - ln -s $< ul_cumsum.c - $(C) -c $(I) ul_cumsum.c - -ul_dbound.o: ../Utility/cholmod_l_dbound.c - - ln -s $< ul_dbound.c - $(C) -c $(I) ul_dbound.c - -ul_defaults.o: ../Utility/cholmod_l_defaults.c - - ln -s $< ul_defaults.c - $(C) -c $(I) ul_defaults.c - -ul_dense_nnz.o: ../Utility/cholmod_l_dense_nnz.c - - ln -s $< ul_dense_nnz.c - $(C) -c $(I) ul_dense_nnz.c - -ul_dense_to_sparse.o: ../Utility/cholmod_l_dense_to_sparse.c - - ln -s $< ul_dense_to_sparse.c - $(C) -c $(I) ul_dense_to_sparse.c - -ul_divcomplex.o: ../Utility/cholmod_l_divcomplex.c - - ln -s $< ul_divcomplex.c - $(C) -c $(I) ul_divcomplex.c - -ul_ensure_dense.o: ../Utility/cholmod_l_ensure_dense.c - - ln -s $< ul_ensure_dense.c - $(C) -c $(I) ul_ensure_dense.c - -ul_error.o: ../Utility/cholmod_l_error.c - - ln -s $< ul_error.c - $(C) -c $(I) ul_error.c - -ul_eye.o: ../Utility/cholmod_l_eye.c - - ln -s $< ul_eye.c - $(C) -c $(I) ul_eye.c - -ul_finish.o: ../Utility/cholmod_l_finish.c - - ln -s $< ul_finish.c - $(C) -c $(I) ul_finish.c - -ul_free.o: ../Utility/cholmod_l_free.c - - ln -s $< ul_free.c - $(C) -c $(I) ul_free.c - -ul_free_dense.o: ../Utility/cholmod_l_free_dense.c - - ln -s $< ul_free_dense.c - $(C) -c $(I) ul_free_dense.c - -ul_free_sparse.o: ../Utility/cholmod_l_free_sparse.c - - ln -s $< ul_free_sparse.c - $(C) -c $(I) ul_free_sparse.c - -ul_free_triplet.o: ../Utility/cholmod_l_free_triplet.c - - ln -s $< ul_free_triplet.c - $(C) -c $(I) ul_free_triplet.c - -ul_free_work.o: ../Utility/cholmod_l_free_work.c - - ln -s $< ul_free_work.c - $(C) -c $(I) ul_free_work.c - -ul_hypot.o: ../Utility/cholmod_l_hypot.c - - ln -s $< ul_hypot.c - $(C) -c $(I) ul_hypot.c - -ul_malloc.o: ../Utility/cholmod_l_malloc.c - - ln -s $< ul_malloc.c - $(C) -c $(I) ul_malloc.c - -ul_maxrank.o: ../Utility/cholmod_l_maxrank.c - - ln -s $< ul_maxrank.c - $(C) -c $(I) ul_maxrank.c - -ul_mult_size_t.o: ../Utility/cholmod_l_mult_size_t.c - - ln -s $< ul_mult_size_t.c - $(C) -c $(I) ul_mult_size_t.c - -ul_nnz.o: ../Utility/cholmod_l_nnz.c - - ln -s $< ul_nnz.c - $(C) -c $(I) ul_nnz.c - -ul_ones.o: ../Utility/cholmod_l_ones.c - - ln -s $< ul_ones.c - $(C) -c $(I) ul_ones.c - -ul_realloc.o: ../Utility/cholmod_l_realloc.c - - ln -s $< ul_realloc.c - $(C) -c $(I) ul_realloc.c - -ul_realloc_multiple.o: ../Utility/cholmod_l_realloc_multiple.c - - ln -s $< ul_realloc_multiple.c - $(C) -c $(I) ul_realloc_multiple.c - -ul_reallocate_sparse.o: ../Utility/cholmod_l_reallocate_sparse.c - - ln -s $< ul_reallocate_sparse.c - $(C) -c $(I) ul_reallocate_sparse.c - -ul_reallocate_triplet.o: ../Utility/cholmod_l_reallocate_triplet.c - - ln -s $< ul_reallocate_triplet.c - $(C) -c $(I) ul_reallocate_triplet.c - -ul_sbound.o: ../Utility/cholmod_l_sbound.c - - ln -s $< ul_sbound.c - $(C) -c $(I) ul_sbound.c - -ul_score_comp.o: ../Utility/cholmod_l_score_comp.c - - ln -s $< ul_score_comp.c - $(C) -c $(I) ul_score_comp.c - -ul_set_empty.o: ../Utility/cholmod_l_set_empty.c - - ln -s $< ul_set_empty.c - $(C) -c $(I) ul_set_empty.c - -ul_sparse_to_dense.o: ../Utility/cholmod_l_sparse_to_dense.c - - ln -s $< ul_sparse_to_dense.c - $(C) -c $(I) ul_sparse_to_dense.c - -ul_sparse_to_triplet.o: ../Utility/cholmod_l_sparse_to_triplet.c - - ln -s $< ul_sparse_to_triplet.c - $(C) -c $(I) ul_sparse_to_triplet.c - -ul_speye.o: ../Utility/cholmod_l_speye.c - - ln -s $< ul_speye.c - $(C) -c $(I) ul_speye.c - -ul_spzeros.o: ../Utility/cholmod_l_spzeros.c - - ln -s $< ul_spzeros.c - $(C) -c $(I) ul_spzeros.c - -ul_start.o: ../Utility/cholmod_l_start.c - - ln -s $< ul_start.c - $(C) -c $(I) ul_start.c - -ul_triplet_to_sparse.o: ../Utility/cholmod_l_triplet_to_sparse.c - - ln -s $< ul_triplet_to_sparse.c - $(C) -c $(I) ul_triplet_to_sparse.c - -ul_version.o: ../Utility/cholmod_l_version.c - - ln -s $< ul_version.c - $(C) -c $(I) ul_version.c - -ul_xtype.o: ../Utility/cholmod_l_xtype.c - - ln -s $< ul_xtype.c - $(C) -c $(I) ul_xtype.c - -ul_zeros.o: ../Utility/cholmod_l_zeros.c - - ln -s $< ul_zeros.c - $(C) -c $(I) ul_zeros.c +z_add.o: ../Core/cholmod_add.c + - ln -s $< z_add.c + $(C) -c $(I) z_add.c #------------------------------------------------------------------------------- @@ -1639,9 +1017,9 @@ z_nesdis.o: ../Partition/cholmod_nesdis.c $(C) -c $(I) z_nesdis.c # do not use test coverage for this file: -n_metis_wrapper.o: ../Partition/cholmod_metis_wrapper.c - - ln -s $< n_metis_wrapper.c - $(CN) -c $(I) n_metis_wrapper.c +z_metis_wrapper.o: ../Partition/cholmod_metis_wrapper.c + - ln -s $< z_metis_wrapper.c + $(CN) -c $(I) z_metis_wrapper.c #------------------------------------------------------------------------------- @@ -1714,6 +1092,7 @@ z_super_solve.o: ../Supernodal/cholmod_super_solve.c $(C) -c $(I) z_super_solve.c #------------------------------------------------------------------------------- +#------------------------------------------------------------------------------- l_check.o: ../Check/cholmod_l_check.c - ln -s $< l_check.c @@ -1729,6 +1108,68 @@ l_write.o: ../Check/cholmod_l_write.c #------------------------------------------------------------------------------- +l_common.o: ../Core/cholmod_l_common.c + - ln -s $< l_common.c + $(C) -c $(I) l_common.c + +l_version.o: ../Core/cholmod_l_version.c + - ln -s $< l_version.c + $(C) -c $(I) l_version.c + +l_dense.o: ../Core/cholmod_l_dense.c + - ln -s $< l_dense.c + $(C) -c $(I) l_dense.c + +l_factor.o: ../Core/cholmod_l_factor.c + - ln -s $< l_factor.c + $(C) -c $(I) l_factor.c + +l_change_factor.o: ../Core/cholmod_l_change_factor.c + - ln -s $< l_change_factor.c + $(C) -c $(I) l_change_factor.c + +l_memory.o: ../Core/cholmod_l_memory.c + - ln -s $< l_memory.c + $(C) -c $(I) l_memory.c + +l_sparse.o: ../Core/cholmod_l_sparse.c + - ln -s $< l_sparse.c + $(C) -c $(I) l_sparse.c + +l_complex.o: ../Core/cholmod_l_complex.c + - ln -s $< l_complex.c + $(C) -c $(I) l_complex.c + +l_transpose.o: ../Core/cholmod_l_transpose.c + - ln -s $< l_transpose.c + $(C) -c $(I) l_transpose.c + +l_band.o: ../Core/cholmod_l_band.c + - ln -s $< l_band.c + $(C) -c $(I) l_band.c + +l_copy.o: ../Core/cholmod_l_copy.c + - ln -s $< l_copy.c + $(C) -c $(I) l_copy.c + +l_triplet.o: ../Core/cholmod_l_triplet.c + - ln -s $< l_triplet.c + $(C) -c $(I) l_triplet.c + +l_error.o: ../Core/cholmod_l_error.c + - ln -s $< l_error.c + $(C) -c $(I) l_error.c + +l_aat.o: ../Core/cholmod_l_aat.c + - ln -s $< l_aat.c + $(C) -c $(I) l_aat.c + +l_add.o: ../Core/cholmod_l_add.c + - ln -s $< l_add.c + $(C) -c $(I) l_add.c + +#------------------------------------------------------------------------------- + l_amd.o: ../Cholesky/cholmod_l_amd.c - ln -s $< l_amd.c $(C) -c $(I) l_amd.c diff --git a/CHOLMOD/Tcov/amdtest.c b/CHOLMOD/Tcov/amdtest.c index 4301193103..e9b85b94fa 100644 --- a/CHOLMOD/Tcov/amdtest.c +++ b/CHOLMOD/Tcov/amdtest.c @@ -10,12 +10,10 @@ /* Test for amd v2.0 */ -#undef ASSERT #include "amd.h" #include "amd_internal.h" #undef FLIP #undef UNFLIP -#undef ASSERT #include "cm.h" diff --git a/CHOLMOD/Tcov/amdtest_l.c b/CHOLMOD/Tcov/amdtest_l.c index b77e761588..2edf77e0f1 100644 --- a/CHOLMOD/Tcov/amdtest_l.c +++ b/CHOLMOD/Tcov/amdtest_l.c @@ -8,7 +8,6 @@ //------------------------------------------------------------------------------ -#define CHOLMOD_INT64 #define DLONG #include "amdtest.c" diff --git a/CHOLMOD/Tcov/camdtest.c b/CHOLMOD/Tcov/camdtest.c index 6cde21e4a9..f5950d09c2 100644 --- a/CHOLMOD/Tcov/camdtest.c +++ b/CHOLMOD/Tcov/camdtest.c @@ -10,12 +10,10 @@ /* Test for camd v2.0 */ -#undef ASSERT #include "cm.h" #undef FLIP #undef UNFLIP -#undef ASSERT #ifndef NCAMD #include "camd.h" #include "camd_internal.h" diff --git a/CHOLMOD/Tcov/camdtest_l.c b/CHOLMOD/Tcov/camdtest_l.c index f8566e040e..35a62a1e59 100644 --- a/CHOLMOD/Tcov/camdtest_l.c +++ b/CHOLMOD/Tcov/camdtest_l.c @@ -8,7 +8,6 @@ //------------------------------------------------------------------------------ -#define CHOLMOD_INT64 #define DLONG #include "camdtest.c" diff --git a/CHOLMOD/Tcov/cl.c b/CHOLMOD/Tcov/cl.c index 4d0a25386e..5a6f15ff7a 100644 --- a/CHOLMOD/Tcov/cl.c +++ b/CHOLMOD/Tcov/cl.c @@ -8,7 +8,7 @@ //------------------------------------------------------------------------------ -#define CHOLMOD_INT64 +#define DLONG #include "cm.c" #include "test_ops.c" #include "null.c" diff --git a/CHOLMOD/Tcov/clread.c b/CHOLMOD/Tcov/clread.c index 811d5c8f50..faed3b2679 100644 --- a/CHOLMOD/Tcov/clread.c +++ b/CHOLMOD/Tcov/clread.c @@ -8,5 +8,5 @@ //------------------------------------------------------------------------------ -#define CHOLMOD_INT64 +#define DLONG #include "cmread.c" diff --git a/CHOLMOD/Tcov/cm.c b/CHOLMOD/Tcov/cm.c index 823cdd0d97..e7c8d5b52a 100644 --- a/CHOLMOD/Tcov/cm.c +++ b/CHOLMOD/Tcov/cm.c @@ -127,7 +127,7 @@ void progress (Int force, char s) void my_handler (int status, const char *file, int line, const char *msg) { - printf ("Error handler: file %s line %d status %d: %s\n", + printf ("Error handler: file %s line %d status %d: %s\n", file, line, status, msg) ; if (status < CHOLMOD_OK || status > CHOLMOD_DSMALL) { @@ -1261,7 +1261,7 @@ double do_matrix (cholmod_sparse *A) /* test various matrix operations */ /* -------------------------------------------------------------- */ - err = test_ops (A) ; /* RAND */ + err = test_ops (A) ; /* RAND */ MAXERR (maxerr, err, 1) ; /* -------------------------------------------------------------- */ @@ -1523,7 +1523,6 @@ int main (int argc, char **argv) OK (CHOLMOD(print_sparse) (A, "Test matrix, A", cm)) ; C = unpack (A) ; /* RAND */ OK (CHOLMOD(print_sparse) (C, "Unpacked/unsorted version of A", cm)) ; - cm->print = 1 ; if (T != NULL) @@ -1538,16 +1537,7 @@ int main (int argc, char **argv) /* basic error tests */ /* ------------------------------------------------------------------ */ -// printf ("null2:: start malloc count "ID" inuse "ID"\n", -// (Int) cm->malloc_count, -// (Int) cm->memory_inuse) ; - - null2 (T, do_nantests) ; /* RAND */ - -// printf ("null2:: done malloc count "ID" inuse "ID"\n", -// (Int) cm->malloc_count, -// (Int) cm->memory_inuse) ; - + null2 (T, do_nantests) ; /* RAND */ printf ("Null2 OK : no error\n") ; if (do_nantests) { @@ -1580,11 +1570,9 @@ int main (int argc, char **argv) cholmod_sparse *F ; int save = T->stype ; - printf ("triplet to sparse:\n") ; T->stype = 0 ; F = CHOLMOD(triplet_to_sparse) (T, 0, cm) ; T->stype = save ; - // OKP (F) ; /* ET = CHOLMOD(transpose) (E, 2, cm) ; @@ -1631,7 +1619,7 @@ int main (int argc, char **argv) /* matrix ops */ /* ------------------------------------------------------------------ */ - err = test_ops (A) ; /* RAND */ + err = test_ops (A) ; /* RAND */ MAXERR (maxerr, err, 1) ; printf ("initial testops error %.1g\n", err) ; @@ -1756,11 +1744,9 @@ int main (int argc, char **argv) CHOLMOD(finish) (cm) ; cm->print = 5 ; OK (CHOLMOD(print_common) ("cm", cm)) ; - - printf ("FINAL::malloc count "ID" inuse "ID"\n", - (Int) cm->malloc_count, + printf ("malloc count "ID" inuse "ID"\n", + (Int) cm->malloc_count, (Int) cm->memory_inuse) ; - OK (cm->malloc_count == 0) ; OK (cm->memory_inuse == 0) ; t = SuiteSparse_toc (tic) ; diff --git a/CHOLMOD/Tcov/cm.h b/CHOLMOD/Tcov/cm.h index 8a326b8d5c..ce83669294 100644 --- a/CHOLMOD/Tcov/cm.h +++ b/CHOLMOD/Tcov/cm.h @@ -146,7 +146,7 @@ void camdtest (cholmod_sparse *A) ; /* AMD, COLAMD, and CCOLAMD */ /* -------------------------------------------------------------------------- */ -#ifdef CHOLMOD_INT64 +#if ( ITYPE == CHOLMOD_LONG ) #define AMD_order amd_l_order #define AMD_defaults amd_l_defaults diff --git a/CHOLMOD/Tcov/cmread.c b/CHOLMOD/Tcov/cmread.c index 5f366c56dd..be793d7f6d 100644 --- a/CHOLMOD/Tcov/cmread.c +++ b/CHOLMOD/Tcov/cmread.c @@ -17,7 +17,7 @@ #include "cholmod.h" -#ifdef CHOLMOD_INT64 +#ifdef DLONG #define CHOLMOD(routine) cholmod_l_ ## routine #define Int int64_t #define UInt uint64_t diff --git a/CHOLMOD/Tcov/covall b/CHOLMOD/Tcov/covall index 9667506cbd..c50c4a48ad 100755 --- a/CHOLMOD/Tcov/covall +++ b/CHOLMOD/Tcov/covall @@ -6,7 +6,7 @@ # SPDX-License-Identifier: GPL-2.0+ # ------------------------------------------------------------------------------ -./gcovs z_*.c zz_*.c l_*.c ui_*.c ul_*.c zl_*.c +./gcovs z*.c l_*c ./covs *.gcov > covs.out echo -n "statments not yet tested: " grep -c "#####" covs.out diff --git a/CHOLMOD/Tcov/huge.c b/CHOLMOD/Tcov/huge.c index 78c6f2ed19..3d8f2db2ab 100644 --- a/CHOLMOD/Tcov/huge.c +++ b/CHOLMOD/Tcov/huge.c @@ -35,16 +35,17 @@ void huge ( ) cholmod_dense *X ; size_t n, nbig ; int ok = TRUE, save ; - Int junk = 0 ; + Int junk ; FILE *f ; double beta [2] ; n = SIZE_MAX ; CHOLMOD (free_work) (cm) ; CHOLMOD (allocate_work) (n, 0, 0, cm) ; - OK (cm->status == CHOLMOD_TOO_LARGE || cm->status == CHOLMOD_OUT_OF_MEMORY); + OK (cm->status == CHOLMOD_TOO_LARGE) ; - n = CHOLMOD(add_size_t) (n, 1, &ok) ; NOT (ok) ; + n = CHOLMOD(add_size_t) (n, 1, &ok) ; + NOT (ok) ; /* create a fake zero sparse matrix, with huge dimensions */ A = CHOLMOD (spzeros) (1, 1, 0, CHOLMOD_REAL, cm) ; @@ -57,7 +58,7 @@ void huge ( ) OKP (L) ; L->n = SIZE_MAX ; CHOLMOD (factorize) (A, L, cm) ; - OK (cm->status == CHOLMOD_TOO_LARGE || cm->status == CHOLMOD_OUT_OF_MEMORY); + OK (cm->status == CHOLMOD_TOO_LARGE) ; /* free the fake factor */ L->n = 1 ; @@ -77,7 +78,7 @@ void huge ( ) ok = CHOLMOD (resymbol) (C, NULL, 0, 0, L, cm) ; NOT (ok) ; - OK (cm->status == CHOLMOD_TOO_LARGE || cm->status == CHOLMOD_OUT_OF_MEMORY); + OK (cm->status == CHOLMOD_TOO_LARGE) ; printf ("rowfac:\n") ; beta [0] = 1 ; @@ -86,7 +87,7 @@ void huge ( ) L->xtype = CHOLMOD_COMPLEX ; ok = CHOLMOD (rowfac) (C, NULL, beta, 0, 0, L, cm) ; printf ("rowfac %d\n", cm->status) ; - OK (cm->status == CHOLMOD_TOO_LARGE || cm->status == CHOLMOD_OUT_OF_MEMORY); + OK (cm->status == CHOLMOD_TOO_LARGE) ; C->xtype = CHOLMOD_REAL ; L->xtype = CHOLMOD_REAL ; printf ("rowfac done:\n") ; @@ -94,18 +95,18 @@ void huge ( ) C->stype = -1 ; ok = CHOLMOD (resymbol_noperm) (C, NULL, 0, 0, L, cm) ; NOT (ok) ; - OK (cm->status == CHOLMOD_TOO_LARGE || cm->status == CHOLMOD_OUT_OF_MEMORY); + OK (cm->status == CHOLMOD_TOO_LARGE) ; C->ncol = 1 ; CHOLMOD (rowadd) (0, C, L, cm) ; - OK (cm->status == CHOLMOD_TOO_LARGE || cm->status == CHOLMOD_OUT_OF_MEMORY); + OK (cm->status == CHOLMOD_TOO_LARGE) ; CHOLMOD (rowdel) (0, C, L, cm) ; - OK (cm->status == CHOLMOD_TOO_LARGE || cm->status == CHOLMOD_OUT_OF_MEMORY); + OK (cm->status == CHOLMOD_TOO_LARGE) ; C->ncol = 4 ; CHOLMOD (updown) (1, C, L, cm) ; - OK (cm->status == CHOLMOD_TOO_LARGE || cm->status == CHOLMOD_OUT_OF_MEMORY); + OK (cm->status == CHOLMOD_TOO_LARGE) ; C->nrow = 1 ; C->ncol = 1 ; @@ -113,82 +114,74 @@ void huge ( ) CHOLMOD (free_sparse) (&C, cm) ; CHOLMOD (free_factor) (&L, cm) ; - C = CHOLMOD (allocate_sparse) (SIZE_MAX, SIZE_MAX, SIZE_MAX, - 0, 0, 0, 0, cm) ; - printf ("cm->status %d\n", cm->status) ; + C = CHOLMOD (allocate_sparse) (SIZE_MAX, SIZE_MAX, SIZE_MAX, 0, 0, 0, 0, cm); NOP (C) ; - OK (cm->status == CHOLMOD_TOO_LARGE || cm->status == CHOLMOD_OUT_OF_MEMORY); + OK (cm->status == CHOLMOD_TOO_LARGE) ; CHOLMOD (rowcolcounts) (A, NULL, 0, &junk, &junk, &junk, &junk, &junk, &junk, cm) ; - OK (cm->status == CHOLMOD_TOO_LARGE || cm->status == CHOLMOD_OUT_OF_MEMORY); - - C = CHOLMOD (submatrix) (A, &junk, SIZE_MAX/4, &junk, SIZE_MAX/4, - 0, 0, cm) ; + OK (cm->status == CHOLMOD_TOO_LARGE) ; + C = CHOLMOD (submatrix) (A, &junk, SIZE_MAX/2, &junk, SIZE_MAX/2, 0, 0, cm) ; NOP (C) ; - OK (cm->status == CHOLMOD_TOO_LARGE || cm->status == CHOLMOD_OUT_OF_MEMORY); + OK (cm->status == CHOLMOD_TOO_LARGE) ; ok = CHOLMOD (transpose_unsym) (A, 0, &junk, &junk, SIZE_MAX, A, cm) ; NOT (ok) ; - OK (cm->status == CHOLMOD_TOO_LARGE || - cm->status == CHOLMOD_OUT_OF_MEMORY || - cm->status == CHOLMOD_INVALID); + OK (cm->status == CHOLMOD_TOO_LARGE) ; A->stype = 1 ; ok = CHOLMOD (transpose_sym) (A, 0, &junk, A, cm) ; NOT (ok) ; - OK (cm->status == CHOLMOD_TOO_LARGE || - cm->status == CHOLMOD_OUT_OF_MEMORY || - cm->status == CHOLMOD_INVALID); + OK (cm->status == CHOLMOD_TOO_LARGE) ; C = CHOLMOD (ptranspose) (A, 0, &junk, NULL, 0, cm) ; NOP (C) ; - OK (cm->status == CHOLMOD_TOO_LARGE || cm->status == CHOLMOD_OUT_OF_MEMORY); + OK (cm->status == CHOLMOD_TOO_LARGE) ; A->stype = 0 ; CHOLMOD (amd) (A, NULL, 0, &junk, cm) ; - OK (cm->status == CHOLMOD_TOO_LARGE || cm->status == CHOLMOD_OUT_OF_MEMORY); + OK (cm->status == CHOLMOD_TOO_LARGE) ; L = CHOLMOD (analyze) (A, cm) ; - OK (cm->status == CHOLMOD_TOO_LARGE || cm->status == CHOLMOD_OUT_OF_MEMORY); + OK (cm->status == CHOLMOD_TOO_LARGE) ; NOP (L) ; #ifndef NCAMD CHOLMOD (camd) (A, NULL, 0, &junk, NULL, cm) ; - OK (cm->status == CHOLMOD_TOO_LARGE || cm->status == CHOLMOD_OUT_OF_MEMORY); + OK (cm->status == CHOLMOD_TOO_LARGE) ; #endif printf ("calling colamd\n") ; CHOLMOD (colamd) (A, NULL, 0, 0, &junk, cm) ; - OK (cm->status == CHOLMOD_TOO_LARGE || cm->status == CHOLMOD_OUT_OF_MEMORY); + OK (cm->status == CHOLMOD_TOO_LARGE) ; #ifndef NCAMD printf ("calling ccolamd\n") ; CHOLMOD (ccolamd) (A, NULL, 0, NULL, &junk, cm) ; - OK (cm->status == CHOLMOD_TOO_LARGE || cm->status == CHOLMOD_OUT_OF_MEMORY); + OK (cm->status == CHOLMOD_TOO_LARGE) ; #endif CHOLMOD (etree) (A, &junk, cm) ; - OK (cm->status == CHOLMOD_TOO_LARGE || cm->status == CHOLMOD_OUT_OF_MEMORY); + OK (cm->status == CHOLMOD_TOO_LARGE) ; L = CHOLMOD (allocate_factor) (SIZE_MAX, cm) ; - OK (cm->status == CHOLMOD_TOO_LARGE || cm->status == CHOLMOD_OUT_OF_MEMORY); + OK (cm->status == CHOLMOD_TOO_LARGE) ; NOP (L) ; #ifndef NPARTITION CHOLMOD (metis) (A, NULL, 0, 0, &junk, cm) ; - OK (cm->status == CHOLMOD_TOO_LARGE || cm->status == CHOLMOD_OUT_OF_MEMORY); + OK (cm->status == CHOLMOD_TOO_LARGE) ; CHOLMOD (bisect) (A, NULL, 0, 0, &junk, cm) ; - OK (cm->status == CHOLMOD_TOO_LARGE || cm->status == CHOLMOD_OUT_OF_MEMORY); + OK (cm->status == CHOLMOD_TOO_LARGE) ; CHOLMOD (nested_dissection) (A, NULL, 0, &junk, &junk, &junk, cm) ; - OK (cm->status == CHOLMOD_TOO_LARGE || cm->status == CHOLMOD_OUT_OF_MEMORY); + OK (cm->status == CHOLMOD_TOO_LARGE) ; #endif CHOLMOD (postorder) (&junk, SIZE_MAX, &junk, &junk, cm) ; - OK (cm->status == CHOLMOD_TOO_LARGE || cm->status == CHOLMOD_OUT_OF_MEMORY); + OK (cm->status == CHOLMOD_TOO_LARGE) ; /* causes overflow in 32-bit version, but not 64-bit */ f = fopen ("../Tcov/Matrix/mega.tri", "r") ; @@ -203,9 +196,8 @@ void huge ( ) n = SIZE_MAX ; X = CHOLMOD (allocate_dense) (n, 1, n, CHOLMOD_REAL, cm) ; - printf ("status %d\n", cm->status) ; - OK (cm->status == CHOLMOD_TOO_LARGE || cm->status == CHOLMOD_OUT_OF_MEMORY); NOP (X) ; + OK (cm->status == CHOLMOD_TOO_LARGE) ; /* supernodal symbolic test */ C = CHOLMOD (speye) (1, 1, CHOLMOD_REAL, cm) ; @@ -219,7 +211,7 @@ void huge ( ) C->ncol = SIZE_MAX ; L->n = SIZE_MAX ; CHOLMOD (super_symbolic) (C, C, &junk, L, cm) ; - OK (cm->status == CHOLMOD_TOO_LARGE || cm->status == CHOLMOD_OUT_OF_MEMORY); + OK (cm->status == CHOLMOD_TOO_LARGE) ; cm->supernodal = save ; C->nrow = 1 ; C->ncol = 1 ; diff --git a/CHOLMOD/Tcov/huge_l.c b/CHOLMOD/Tcov/huge_l.c index be413254de..21b79f6c68 100644 --- a/CHOLMOD/Tcov/huge_l.c +++ b/CHOLMOD/Tcov/huge_l.c @@ -8,7 +8,6 @@ //------------------------------------------------------------------------------ -#define CHOLMOD_INT64 -#include "cholmod_internal.h" +#define DLONG #include "huge.c" diff --git a/CHOLMOD/Tcov/null.c b/CHOLMOD/Tcov/null.c index 1f13e8fbc1..4f4a7ab8d6 100644 --- a/CHOLMOD/Tcov/null.c +++ b/CHOLMOD/Tcov/null.c @@ -66,7 +66,7 @@ void null_test (cholmod_common *cn) #endif /* ---------------------------------------------------------------------- */ - /* Utility */ + /* Core */ /* ---------------------------------------------------------------------- */ if (cn == NULL) @@ -282,7 +282,7 @@ void null_test2 (void) int ok ; /* ---------------------------------------------------------------------- */ - /* Test Common */ + /* Test Core Common */ /* ---------------------------------------------------------------------- */ ok = CHOLMOD(allocate_work)(SIZE_MAX, 1, 1, cm) ; NOT (ok) ; @@ -308,13 +308,9 @@ void null_test2 (void) /* dense */ /* ---------------------------------------------------------------------- */ - X = CHOLMOD(allocate_dense)(5, 4, 1, CHOLMOD_REAL, cm) ; - OKP (X) ; - OK (X->d == 5) ; - CHOLMOD(free_dense)(&X, cm) ; - + X = CHOLMOD(allocate_dense)(5, 4, 1, CHOLMOD_REAL, cm) ; NOP (X) ; X = CHOLMOD(allocate_dense)(1, Int_max, 1, CHOLMOD_REAL, cm) ; NOP (X) ; - X = CHOLMOD(allocate_dense)(1, 1, 1, CHOLMOD_PATTERN, cm) ; NOP (X) ; + X = CHOLMOD(allocate_dense)(1, 1, 1, -1, cm) ; NOP (X) ; CHOLMOD(free_dense)(&X, cm) ; /* free a NULL dense matrix */ @@ -322,13 +318,9 @@ void null_test2 (void) ok = CHOLMOD(free_dense)(NULL, cm) ; OK (ok) ; /* make an invalid sparse matrix */ - printf ("\nspeye:\n") ; - Sbad = CHOLMOD(speye)(2, 3, CHOLMOD_REAL, cm) ; - OKP (Sbad) ; - + Sbad = CHOLMOD(speye)(2, 3, CHOLMOD_REAL, cm) ; OKP (Sbad) ; Sbad->stype = 1 ; ok = CHOLMOD(check_sparse)(Sbad, cm) ; NOT (ok) ; - printf ("\nSparse to dense:\n") ; X = CHOLMOD(sparse_to_dense)(Sbad, cm) ; NOP (X) ; ok = CHOLMOD(free_sparse)(&Sbad, cm) ; OK (ok) ; @@ -349,7 +341,7 @@ void null_test2 (void) /* free a NULL sparse matrix */ ok = CHOLMOD(free_sparse)(&A, cm) ; OK (ok) ; ok = CHOLMOD(free_sparse)(NULL, cm) ; OK (ok) ; - A = CHOLMOD(copy_sparse)(NULL, cm) ; NOP (A) ; + A = CHOLMOD(copy_sparse)(NULL, cm) ; NOP (A) ; /* ---------------------------------------------------------------------- */ /* error tests done */ diff --git a/CHOLMOD/Tcov/null2.c b/CHOLMOD/Tcov/null2.c index 72a0e1bc88..4b17bbf67d 100644 --- a/CHOLMOD/Tcov/null2.c +++ b/CHOLMOD/Tcov/null2.c @@ -26,12 +26,12 @@ void null2 (cholmod_triplet *Tok, int do_nantests) { double nm, gsave0, gsave1, r, anorm, beta [2], maxerr, xnan, rcond, - ax, az, bx, bz, cx, cz, dx, dz, fx, fz ; + ax, az, bx, bz, cx, cz, dx, dz, ex, ez ; cholmod_sparse *A, *C, *AT, *E, *F, *G, *Sok, *R0, *R1, *Aboth, *Axbad, *I1, *Abad, *R, *Acopy, *R3, *Abad2, *I, *I3, *Abad3, *AA, *Rt, *AF, *AFT, *I7, *C2, *R2, *Z ; cholmod_dense *Xok, *Bok, *Two, *X, *W, *XX, *YY, *Xbad2, *B, *Scale, - *Y, *X1, *B1, *B2, *X7, *B7 ; + *Y, *X1, *B1, *B2, *X7, *B7 ; cholmod_factor *L, *L2, *L3, *L4, *L5, *L6, *Lcopy, *Lbad, *L7 ; cholmod_triplet *T, *T2, *Tz, *T3 ; Int *fsetok, *Pok, *Flag, *Head, *Cp, *Ci, *P2, *Parent, *Lperm, @@ -55,7 +55,6 @@ void null2 (cholmod_triplet *Tok, int do_nantests) xnan = 0 ; xtype = Tok->xtype ; - printf ("Tok xtype is %d\n", (int) xtype) ; isreal = (xtype == CHOLMOD_REAL) ; /* ---------------------------------------------------------------------- */ @@ -83,9 +82,9 @@ void null2 (cholmod_triplet *Tok, int do_nantests) dx = cx * bx - cz * bz ; dz = cz * bx + cx * bz ; /* e = d-a, which should be zero */ - fx = dx - ax ; - fz = dz - az ; - r = CHOLMOD(hypot)(fx, fz) ; + ex = dx - ax ; + ez = dz - az ; + r = CHOLMOD(hypot)(ex, ez) ; MAXERR (maxerr, r, 1) ; OK (r < 1e-14) ; } @@ -267,62 +266,48 @@ void null2 (cholmod_triplet *Tok, int do_nantests) C = CHOLMOD(ptranspose)(A, 1, Pbad, NULL, 0, cm) ; NOP (C) ; } - if (A->stype == 0) - { - C = CHOLMOD(allocate_sparse)(ncol, nrow, anz, TRUE, TRUE, - -(A->stype), xtype, cm) ; OKP (C) ; - ok = CHOLMOD(transpose_unsym)(A, 1, NULL, NULL, 0, - C, cm) ; OK (ok); - ok = CHOLMOD(free_sparse)(&C, cm) ; OK (ok) ; - - C = CHOLMOD(allocate_sparse)(ncol, nrow, anz, TRUE, FALSE, - -(A->stype), xtype, cm) ; OKP (C) ; - ok = CHOLMOD(transpose_unsym)(A, 1, NULL, NULL, 0, - C, cm) ; OK (ok); - ok = CHOLMOD(free_sparse)(&C, cm) ; OK (ok) ; - - C = CHOLMOD(allocate_sparse)(ncol, nrow, anz, TRUE, FALSE, - -(A->stype), xtype, cm) ; OKP (C) ; - ok = CHOLMOD(transpose_unsym)(A, 1, Pok, NULL, 0, - C, cm) ; OK (ok); - ok = CHOLMOD(free_sparse)(&C, cm) ; OK (ok) ; - - C = CHOLMOD(allocate_sparse)(ncol, nrow, anz, TRUE, FALSE, - -(A->stype), xtype, cm) ; OKP (C) ; - ok = CHOLMOD(transpose_unsym)(A, 1, Pok, fsetok, fsizeok, - C, cm) ; OK (ok); - ok = CHOLMOD(free_sparse)(&C, cm) ; OK (ok) ; - - C = CHOLMOD(allocate_sparse)(ncol, nrow, anz, TRUE, FALSE, - -(A->stype), xtype, cm) ; OKP (C) ; - ok = CHOLMOD(transpose_unsym)(A, 1, NULL, fsetok, fsizeok, - C, cm) ; OK (ok); - ok = CHOLMOD(free_sparse)(&C, cm) ; OK (ok) ; - - C = CHOLMOD(allocate_sparse)(ncol, nrow, anz, TRUE, FALSE, - -(A->stype), CHOLMOD_PATTERN, cm) ; OKP (C) ; - ok = CHOLMOD(transpose_unsym)(A, 1, NULL, fsetok, fsizeok, - C, cm) ; OK (ok); - - E = CHOLMOD(allocate_sparse)(nrow, ncol, anz, TRUE, FALSE, - (A->stype), CHOLMOD_PATTERN, cm) ; OKP (C) ; - enz = CHOLMOD(nnz)(E, cm) ; - OK (enz == 0) ; - ok = CHOLMOD(transpose_unsym)(C, 1, NULL, Pok, nrow, - E, cm) ; OK (ok); - ok = CHOLMOD(free_sparse)(&E, cm) ; OK (ok) ; + C = CHOLMOD(allocate_sparse)(ncol, nrow, anz, TRUE, TRUE, + -(A->stype), xtype, cm) ; OKP (C) ; + ok = CHOLMOD(transpose_unsym)(A, 1, NULL, NULL, 0, + C, cm) ; OK (ok); + ok = CHOLMOD(free_sparse)(&C, cm) ; OK (ok) ; - } - else - { - // A is symmetric so transpose_unsym will fail - C = CHOLMOD(allocate_sparse)(ncol, nrow, anz, TRUE, TRUE, - -(A->stype), xtype, cm) ; OKP (C) ; - ok = CHOLMOD(transpose_unsym)(A, 1, NULL, NULL, 0, - C, cm) ; NOT (ok); - OK (cm->status == CHOLMOD_INVALID) ; - ok = CHOLMOD(free_sparse)(&C, cm) ; OK (ok) ; - } + C = CHOLMOD(allocate_sparse)(ncol, nrow, anz, TRUE, FALSE, + -(A->stype), xtype, cm) ; OKP (C) ; + ok = CHOLMOD(transpose_unsym)(A, 1, NULL, NULL, 0, + C, cm) ; OK (ok); + ok = CHOLMOD(free_sparse)(&C, cm) ; OK (ok) ; + + C = CHOLMOD(allocate_sparse)(ncol, nrow, anz, TRUE, FALSE, + -(A->stype), xtype, cm) ; OKP (C) ; + ok = CHOLMOD(transpose_unsym)(A, 1, Pok, NULL, 0, + C, cm) ; OK (ok); + ok = CHOLMOD(free_sparse)(&C, cm) ; OK (ok) ; + + C = CHOLMOD(allocate_sparse)(ncol, nrow, anz, TRUE, FALSE, + -(A->stype), xtype, cm) ; OKP (C) ; + ok = CHOLMOD(transpose_unsym)(A, 1, Pok, fsetok, fsizeok, + C, cm) ; OK (ok); + ok = CHOLMOD(free_sparse)(&C, cm) ; OK (ok) ; + + C = CHOLMOD(allocate_sparse)(ncol, nrow, anz, TRUE, FALSE, + -(A->stype), xtype, cm) ; OKP (C) ; + ok = CHOLMOD(transpose_unsym)(A, 1, NULL, fsetok, fsizeok, + C, cm) ; OK (ok); + ok = CHOLMOD(free_sparse)(&C, cm) ; OK (ok) ; + + C = CHOLMOD(allocate_sparse)(ncol, nrow, anz, TRUE, FALSE, + -(A->stype), CHOLMOD_PATTERN, cm) ; OKP (C) ; + ok = CHOLMOD(transpose_unsym)(A, 1, NULL, fsetok, fsizeok, + C, cm) ; OK (ok); + + E = CHOLMOD(allocate_sparse)(nrow, ncol, anz, TRUE, FALSE, + (A->stype), CHOLMOD_PATTERN, cm) ; OKP (C) ; + enz = CHOLMOD(nnz)(E, cm) ; + OK (enz == 0) ; + ok = CHOLMOD(transpose_unsym)(C, 1, NULL, Pok, nrow, + E, cm) ; OK (ok); + ok = CHOLMOD(free_sparse)(&E, cm) ; OK (ok) ; if (A->nrow != A->ncol) { @@ -343,40 +328,25 @@ void null2 (cholmod_triplet *Tok, int do_nantests) ok = CHOLMOD(transpose_unsym)(C, 1, NULL, NULL, 0, Abad3, cm) ;NOT (ok); ok = CHOLMOD(transpose_unsym)(Abad3, 1, NULL, NULL, 0, C, cm) ;NOT (ok); - printf ("xtypes %d %d %d\n", C->xtype, E->xtype, (int) xtype) ; - switch (xtype) { case CHOLMOD_REAL: - printf ("make E complex:1\n") ; - ok = CHOLMOD(sparse_xtype)(CHOLMOD_COMPLEX, E, cm) ; - OK (ok) ; + CHOLMOD(sparse_xtype)(CHOLMOD_COMPLEX, E, cm) ; break ; case CHOLMOD_COMPLEX: - printf ("make E zomplex\n") ; - ok = CHOLMOD(sparse_xtype)(CHOLMOD_ZOMPLEX, E, cm) ; - OK (ok) ; + CHOLMOD(sparse_xtype)(CHOLMOD_ZOMPLEX, E, cm) ; break ; case CHOLMOD_ZOMPLEX: - printf ("make E complex\n") ; - ok = CHOLMOD(sparse_xtype)(CHOLMOD_COMPLEX, E, cm) ; - OK (ok) ; + CHOLMOD(sparse_xtype)(CHOLMOD_COMPLEX, E, cm) ; break ; } - printf ("xtypes %d %d %d now\n", C->xtype, E->xtype, (int) xtype) ; - printf ("dtypes %d %d\n", C->dtype, E->dtype) ; - printf ("mismatch start [:\n") ; ok = CHOLMOD(transpose_sym)(C, 1, NULL, E, cm) ; NOT (ok) ; ok = CHOLMOD(transpose_sym)(E, 1, NULL, C, cm) ; NOT (ok) ; ok = CHOLMOD(transpose_sym)(C, 2, NULL, E, cm) ; NOT (ok) ; ok = CHOLMOD(transpose_sym)(E, 2, NULL, C, cm) ; NOT (ok) ; - - printf ("unsym transpose:\n") ; - ok = CHOLMOD(transpose_unsym)(C, 1, NULL, NULL, 0, E, cm) ; - NOT (ok); - + ok = CHOLMOD(transpose_unsym)(C, 1, NULL, NULL, 0, E, cm) ; NOT (ok); ok = CHOLMOD(transpose_unsym)(E, 1, NULL, NULL, 0, C, cm) ; NOT (ok); ok = CHOLMOD(transpose_unsym)(C, 2, NULL, NULL, 0, E, cm) ; NOT (ok); ok = CHOLMOD(transpose_unsym)(E, 2, NULL, NULL, 0, C, cm) ; NOT (ok); @@ -441,9 +411,9 @@ void null2 (cholmod_triplet *Tok, int do_nantests) C = CHOLMOD(add)(A, NULL, one, one, TRUE, TRUE, cm) ; NOP (C) ; C = CHOLMOD(add)(NULL, AT, one, one, TRUE, TRUE, cm) ; NOP (C) ; + C = CHOLMOD(add)(A, AT, one, one, TRUE, TRUE, cm) ; if (A->nrow == A->ncol && isreal) { - C = CHOLMOD(add)(A, AT, one, one, TRUE, TRUE, cm) ; OKP (C) ; /* C should equal 2*A if A=A' */ if (stype) @@ -516,21 +486,15 @@ void null2 (cholmod_triplet *Tok, int do_nantests) } CHOLMOD(free_sparse)(&C, cm) ; } + else + { + NOP (C) ; + } Axbad = CHOLMOD(copy_sparse)(A, cm) ; /* [ */ Axbad_type = Axbad->xtype ; Axbad->xtype = CHOLMOD_COMPLEX ; - C = CHOLMOD(add)(A, Axbad, one, one, TRUE, TRUE, cm) ; - bool Axbad_is_ok = (Axbad_type == CHOLMOD_COMPLEX) ; - if (Axbad_is_ok) - { - OKP (C) ; - ok = CHOLMOD(free_sparse)(&C, cm) ; OK (ok) ; - } - else - { - NOP (C) ; - } + C = CHOLMOD(add)(A, Axbad, one, one, TRUE, TRUE, cm) ; NOP (C) ; if (nrow > 1 && xtype == CHOLMOD_REAL) { @@ -549,8 +513,8 @@ void null2 (cholmod_triplet *Tok, int do_nantests) cm->print = 4 ; ok = CHOLMOD(reallocate_sparse)(10, NULL, cm) ; NOT (ok) ; - ok = CHOLMOD(reallocate_sparse)(2 * Abad2->nzmax, Abad2, cm) ; NOT (ok) ; - + C = CHOLMOD(allocate_sparse)(10, 10, 10, TRUE, TRUE, 0, -1, cm) ; NOP (C) ; + ok = CHOLMOD(reallocate_sparse)(Abad2->nzmax, Abad2, cm) ; NOT (ok) ; C = CHOLMOD(copy_sparse)(Abad2, cm) ; NOP (C) ; C = CHOLMOD(allocate_sparse)(2, 3, 6, TRUE, TRUE, 1, 0, cm) ; NOP (C) ; @@ -638,9 +602,6 @@ void null2 (cholmod_triplet *Tok, int do_nantests) /* analyze */ /* ---------------------------------------------------------------------- */ - cm->print = 4 ; - ok = CHOLMOD(print_common)("OKcm", cm) ; OK (ok) ; - cm->nmethods = 1 ; cm->method [0].ordering = -1 ; ok = CHOLMOD(print_common)("Bad cm", cm) ; NOT (ok) ; @@ -883,8 +844,6 @@ void null2 (cholmod_triplet *Tok, int do_nantests) Head [0] = -1 ; ok = CHOLMOD(print_common)("ok Head", cm) ; OK (ok) ; - cm->status = CHOLMOD_OK ; - printf ("\nbad Xwork:\n") ; Xwork = cm->Xwork ; cm->Xwork = NULL ; ok = CHOLMOD(print_common)("bad Xwork", cm) ; NOT (ok) ; @@ -913,11 +872,13 @@ void null2 (cholmod_triplet *Tok, int do_nantests) cm->print = 3 ; C->itype = EMPTY ; ok = CHOLMOD(print_sparse)(C, "CIbad", cm) ; NOT (ok) ; + C->itype = CHOLMOD_INTLONG ; + ok = CHOLMOD(print_sparse)(C, "Cibad", cm) ; NOT (ok) ; C->itype = cm->itype ; cm->print = 1 ; cm->print = 4 ; -#if defined ( CHOLMOD_INT64 ) +#if ( ITYPE == CHOLMOD_LONG ) C->itype = CHOLMOD_INT ; #else C->itype = CHOLMOD_LONG ; @@ -927,7 +888,7 @@ void null2 (cholmod_triplet *Tok, int do_nantests) cm->print = 1 ; C->dtype = CHOLMOD_SINGLE ; - ok = CHOLMOD(print_sparse)(C, "C single: OK", cm) ; OK (ok) ; + ok = CHOLMOD(print_sparse)(C, "Cdbad", cm) ; NOT (ok) ; C->dtype = EMPTY ; ok = CHOLMOD(print_sparse)(C, "CDbad", cm) ; NOT (ok) ; C->dtype = CHOLMOD_DOUBLE ; @@ -1097,7 +1058,7 @@ void null2 (cholmod_triplet *Tok, int do_nantests) ok = CHOLMOD(print_dense)(X, "X OK", cm) ; OK (ok) ; X->dtype = CHOLMOD_SINGLE ; - ok = CHOLMOD(print_dense)(X, "X float: OK", cm) ; OK (ok) ; + ok = CHOLMOD(print_dense)(X, "X float", cm) ; NOT (ok) ; X->dtype = -1 ; ok = CHOLMOD(print_dense)(X, "X unknown", cm) ; NOT (ok) ; X->dtype = CHOLMOD_DOUBLE ; @@ -1214,13 +1175,15 @@ void null2 (cholmod_triplet *Tok, int do_nantests) OK (L->xtype == CHOLMOD_PATTERN) ; OK (L->is_super) ; + L->itype = CHOLMOD_INTLONG ; + ok = CHOLMOD(print_factor)(L, "L int/long", cm) ; NOT (ok) ; L->itype = -1 ; ok = CHOLMOD(print_factor)(L, "L int unknown", cm) ; NOT (ok) ; L->itype = cm->itype ; ok = CHOLMOD(print_factor)(L, "L OK", cm) ; OK (ok) ; cm->print = 4 ; -#if defined ( CHOLMOD_INT64 ) +#if ( ITYPE == CHOLMOD_LONG ) L->itype = CHOLMOD_INT ; #else L->itype = CHOLMOD_LONG ; @@ -1282,7 +1245,7 @@ void null2 (cholmod_triplet *Tok, int do_nantests) ok = CHOLMOD(super_symbolic)(A, Abad2, Parent, L, cm) ; NOT (ok) ; ok = CHOLMOD(super_symbolic)(Abad2, A, Parent, L, cm) ; NOT (ok) ; - W = CHOLMOD(zeros)(L->maxesize, 1, L->xtype, cm) ; OKP (W) ; + W = CHOLMOD(zeros)(nrow, 1, L->xtype, cm) ; OKP (W) ; X = CHOLMOD(ones)(nrow, 1, L->xtype, cm) ; OKP (X) ; ok = CHOLMOD(super_lsolve)(L, X, W, cm) ; OK (ok) ; ok = CHOLMOD(super_ltsolve)(L, X, W, cm) ; OK (ok) ; @@ -1355,7 +1318,7 @@ void null2 (cholmod_triplet *Tok, int do_nantests) ok = CHOLMOD(print_factor)(L, "L OK", cm) ; OK (ok) ; L->dtype = CHOLMOD_SINGLE ; - ok = CHOLMOD(print_factor)(L, "L float: OK", cm) ; OK (ok) ; + ok = CHOLMOD(print_factor)(L, "L float", cm) ; NOT (ok) ; L->dtype = -1 ; ok = CHOLMOD(print_factor)(L, "L unknown", cm) ; NOT (ok) ; L->dtype = CHOLMOD_DOUBLE ; @@ -1394,7 +1357,7 @@ void null2 (cholmod_triplet *Tok, int do_nantests) /* check LDL' unpacked */ ok = CHOLMOD(print_factor)(L, "L OK for L2 copy", cm) ; OK (ok) ; L2 = CHOLMOD(copy_factor)(L, cm) ; /* [ */ OKP (L2) ; - ok = CHOLMOD(change_factor)(L->xtype, FALSE, FALSE, FALSE, + ok = CHOLMOD(change_factor)(L->xtype, FALSE, FALSE, FALSE, TRUE, L2, cm) ; /* check LDL' packed */ @@ -1700,7 +1663,7 @@ void null2 (cholmod_triplet *Tok, int do_nantests) if (nrow > 0 && Lpi [1] - Lpi [0] > 3) { - p = Ls [2] ; + p = Ls [2] ; Ls [2] = Ls [1] ; ok = CHOLMOD(print_factor)(L, "L unsorted s", cm) ; NOT (ok) ; Ls [2] = p ; @@ -1732,7 +1695,7 @@ void null2 (cholmod_triplet *Tok, int do_nantests) if (nrow > 0 && Lpi [1] - Lpi [0] > 3) { - p = Ls [2] ; + p = Ls [2] ; Ls [2] = Ls [1] ; ok = CHOLMOD(print_factor)(L3, "Lsym unsorted s", cm) ; NOT (ok) ; Ls [2] = p ; @@ -1745,7 +1708,7 @@ void null2 (cholmod_triplet *Tok, int do_nantests) Int nsrow = Lpi [1] - Lpi [0] ; if (nsrow > nscol + 1) { - p = Ls [nscol] ; + p = Ls [nscol] ; Ls [nscol] = Ls [nscol+1] ; ok = CHOLMOD(print_factor)(L3, "Lsym unsorted s2", cm) ; NOT (ok) ; Ls [nscol] = p ; @@ -1865,6 +1828,9 @@ void null2 (cholmod_triplet *Tok, int do_nantests) ok = CHOLMOD(resymbol)(I1, NULL, 0, TRUE, L, cm) ; NOT (ok) ; ok = CHOLMOD(resymbol_noperm)(I1, NULL, 0, TRUE, L, cm) ; NOT (ok) ; + ok = CHOLMOD(change_factor)(-1, FALSE, FALSE, FALSE, FALSE, L, cm) ; + NOT (ok) ; + ok = CHOLMOD(change_factor)(L->xtype, FALSE, FALSE, FALSE, FALSE, Lbad, cm); NOT (ok) ; @@ -1925,7 +1891,7 @@ void null2 (cholmod_triplet *Tok, int do_nantests) ok = CHOLMOD(print_factor)(L4, "L4 ok, for colrealloc", cm) ; OK (ok) ; OK (nrow == (Int)(L->n)) ; ok = CHOLMOD(reallocate_column)(nrow, 1, L4, cm) ; NOT (ok) ; -// ok = CHOLMOD(reallocate_column)(nrow-1, 0, L4, cm) ; NOT (ok) ; + ok = CHOLMOD(reallocate_column)(nrow-1, 0, L4, cm) ; NOT (ok) ; ok = CHOLMOD(reallocate_column)(nrow-1, 10, L4, cm) ; OK (ok) ; cm->grow0 = 2e10 ; @@ -2356,10 +2322,8 @@ if (do_nantests) C = CHOLMOD(horzcat)(A, AT, TRUE, cm) ; NOP (C) ; C = CHOLMOD(vertcat)(A, AT, TRUE, cm) ; NOP (C) ; } - - C = CHOLMOD(horzcat)(A, Axbad, TRUE, cm) ; NOP (C) ; - C = CHOLMOD(vertcat)(A, Axbad, TRUE, cm) ; NOP (C) ; - + C = CHOLMOD(horzcat)(A, Axbad, TRUE, cm) ; NOP (C) ; + C = CHOLMOD(vertcat)(A, Axbad, TRUE, cm) ; NOP (C) ; C = CHOLMOD(vertcat)(A, NULL, TRUE, cm) ; NOP (C) ; C = CHOLMOD(vertcat)(NULL, AT, TRUE, cm) ; NOP (C) ; C = CHOLMOD(horzcat)(A, NULL, TRUE, cm) ; NOP (C) ; @@ -2399,11 +2363,13 @@ if (do_nantests) T->itype = -1 ; ok = CHOLMOD(print_triplet)(T, "T itype bad", cm) ; NOT (ok) ; + T->itype = CHOLMOD_INTLONG ; + ok = CHOLMOD(print_triplet)(T, "T itype bad", cm) ; NOT (ok) ; T->itype = cm->itype ; ok = CHOLMOD(print_triplet)(T, "T ok", cm) ; OK (ok) ; cm->print = 4 ; -#if defined ( CHOLMOD_INT64 ) +#if ( ITYPE == CHOLMOD_LONG ) T->itype = CHOLMOD_INT ; #else T->itype = CHOLMOD_LONG ; @@ -2422,7 +2388,7 @@ if (do_nantests) T->dtype = -1 ; ok = CHOLMOD(print_triplet)(T, "T dtype bad", cm) ; NOT (ok) ; T->dtype = CHOLMOD_SINGLE ; - ok = CHOLMOD(print_triplet)(T, "T dtype float: OK", cm) ; OK (ok) ; + ok = CHOLMOD(print_triplet)(T, "T dtype bad", cm) ; NOT (ok) ; T->dtype = CHOLMOD_DOUBLE ; ok = CHOLMOD(print_triplet)(T, "T ok", cm) ; OK (ok) ; @@ -2463,7 +2429,6 @@ if (do_nantests) } cm->print = 4 ; -// ok = CHOLMOD(print_triplet)(T, "T ok", cm) ; OK (ok) ; CHOLMOD(triplet_xtype)(CHOLMOD_PATTERN, T, cm) ; ok = CHOLMOD(print_triplet)(T, "T pattern ok", cm) ; OK (ok) ; cm->print = 1 ; @@ -2489,32 +2454,12 @@ if (do_nantests) Ti = T->i ; T->i = NULL ; - C = CHOLMOD(triplet_to_sparse)(T, 0, cm) ; - if (T->nnz == 0) - { - OKP (C) ; - ASSERT (CHOLMOD(nnz) (C, cm) == 0) ; - ok = CHOLMOD(free_sparse)(&C, cm) ; OK (ok) ; - } - else - { - NOP (C) ; - } + C = CHOLMOD(triplet_to_sparse)(T, 0, cm) ; NOP (C) ; T->i = Ti ; Tj = T->j ; T->j = NULL ; - C = CHOLMOD(triplet_to_sparse)(T, 0, cm) ; - if (T->nnz == 0) - { - OKP (C) ; - ASSERT (CHOLMOD(nnz) (C, cm) == 0) ; - ok = CHOLMOD(free_sparse)(&C, cm) ; OK (ok) ; - } - else - { - NOP (C) ; - } + C = CHOLMOD(triplet_to_sparse)(T, 0, cm) ; NOP (C) ; T->j = Tj ; T->stype = 1 ; @@ -2574,10 +2519,10 @@ if (do_nantests) ok = CHOLMOD(reallocate_triplet)(16, T2, cm) ; NOT (ok) ; T = CHOLMOD(copy_triplet)(T2, cm) ; NOP (T) ; C = CHOLMOD(triplet_to_sparse)(T2, 100, cm) ; NOP (C) ; - T2->xtype = CHOLMOD_REAL ; + T2->xtype = CHOLMOD_REAL ; CHOLMOD(free_triplet)(&T2, cm) ; -// T = CHOLMOD(allocate_triplet)(4, 4, 16, 0, -1, cm); NOP (T) ; + T = CHOLMOD(allocate_triplet)(4, 4, 16, 0, -1, cm); NOP (T) ; T = CHOLMOD(sparse_to_triplet)(Abad2, cm) ; NOP (T) ; @@ -2623,32 +2568,13 @@ if (do_nantests) Ti = T->i ; T->i = NULL ; - T2 = CHOLMOD(copy_triplet)(T, cm) ; - - if (T->nnz == 0) - { - OKP (T2) ; - } - else - { - NOP (T2) ; - } + T2 = CHOLMOD(copy_triplet)(T, cm) ; NOP (T2) ; T->i = Ti ; - ok = CHOLMOD(free_triplet)(&T2, cm) ; OK (ok) ; Tj = T->j ; T->j = NULL ; - T2 = CHOLMOD(copy_triplet)(T, cm) ; - if (T->nnz == 0) - { - OKP (T2) ; - } - else - { - NOP (T2) ; - } + T2 = CHOLMOD(copy_triplet)(T, cm) ; NOP (T2) ; T->j = Tj ; - ok = CHOLMOD(free_triplet)(&T2, cm) ; OK (ok) ; ok = CHOLMOD(free_triplet)(&T, cm) ; OK (ok) ; A->stype = 1 ; @@ -3003,11 +2929,11 @@ if (do_nantests) ok = CHOLMOD(free_dense)(&W, cm) ; OK (ok) ; C = CHOLMOD(speye)(4, 4, CHOLMOD_COMPLEX, cm) ; OKP (C) ; - ok = CHOLMOD(sparse_xtype)(-1, C, cm) ; OK (ok) ; + ok = CHOLMOD(sparse_xtype)(-1, C, cm) ; NOT (ok) ; ok = CHOLMOD(sparse_xtype)(CHOLMOD_ZOMPLEX, C, cm) ; OK (ok) ; ok = CHOLMOD(sparse_xtype)(CHOLMOD_ZOMPLEX, NULL, cm) ; NOT (ok) ; T = CHOLMOD(sparse_to_triplet)(C, cm) ; OKP (T) ; - ok = CHOLMOD(triplet_xtype)(-1, T, cm) ; OK (ok) ; + ok = CHOLMOD(triplet_xtype)(-1, T, cm) ; NOT (ok) ; ok = CHOLMOD(triplet_xtype)(CHOLMOD_ZOMPLEX, T, cm) ; OK (ok) ; ok = CHOLMOD(triplet_xtype)(CHOLMOD_ZOMPLEX, NULL, cm) ; NOT (ok) ; @@ -3124,7 +3050,7 @@ if (do_nantests) } C = CHOLMOD(ssmult)(NULL, A, 0, TRUE, TRUE, cm) ; NOP (C) ; C = CHOLMOD(ssmult)(A, NULL, 0, TRUE, TRUE, cm) ; NOP (C) ; - C = CHOLMOD(ssmult)(A, Axbad, 0, TRUE, TRUE, cm) ; NOP (C) ; + C = CHOLMOD(ssmult)(A, Axbad, 0, TRUE, TRUE, cm) ; NOP (C) ; } /* ---------------------------------------------------------------------- */ @@ -3324,7 +3250,7 @@ if (do_nantests) NOT (ok) ; ok = CHOLMOD (allocate_work) (1, 2, 1, cm) ; NOT (ok) ; - ok = CHOLMOD (allocate_work) (1, 1, 8, cm) ; + ok = CHOLMOD (allocate_work) (1, 1, 2, cm) ; NOT (ok) ; cm->no_workspace_reallocate = FALSE ; ok = CHOLMOD (allocate_work) (1, 1, 2, cm) ; @@ -3412,11 +3338,10 @@ if (do_nantests) ok = CHOLMOD(rowfac)(A, NULL, beta, 0, 0, L, cm) ; NOT (ok) ; ok = CHOLMOD(transpose_unsym)(A, 1, Pok, NULL, 0, R, cm) ; NOT (ok) ; ok = CHOLMOD(transpose_sym)(A, 1, Pok, R, cm) ; NOT (ok) ; -// if (nrow > 1) -// { -// ok = CHOLMOD(sort)(A, cm) ; -// NOT (ok) ; -// } + if (nrow > 1) + { + ok = CHOLMOD(sort)(A, cm) ; NOT (ok) ; + } ok = CHOLMOD(row_subtree)(A, AT, 0, Parent, R3, cm) ; NOT (ok) ; ATi = (AT == NULL) ? NULL : AT->i ; diff --git a/CHOLMOD/Tcov/solve.c b/CHOLMOD/Tcov/solve.c index 92060cd58e..e86fb9e428 100644 --- a/CHOLMOD/Tcov/solve.c +++ b/CHOLMOD/Tcov/solve.c @@ -706,26 +706,13 @@ double solve (cholmod_sparse *A) CHOLMOD(free) (ncol, sizeof (Int), fset, cm) ; G = CHOLMOD(ssmult) (AF, AFt, 0, TRUE, TRUE, cm) ; -// int save = cm->print ; -// cm->print = 5 ; -// CHOLMOD (print_sparse) (A, "HERE A", cm) ; -// CHOLMOD (print_sparse) (AFt, "HERE AFt", cm) ; -// CHOLMOD (print_sparse) (AF, "HERE AF", cm) ; -// CHOLMOD (print_sparse) (G, "HERE G", cm) ; - /* also try aat */ H = CHOLMOD(aat) (AF, NULL, 0, 1, cm) ; - -// CHOLMOD (print_sparse) (H, "HERE H", cm) ; -// printf ("status %d\n", cm->status) ; -// cm->print = save ; - E = CHOLMOD(add) (G, H, one, minusone, TRUE, FALSE, cm) ; - enorm = CHOLMOD(norm_sparse) (E, 0, cm) ; gnorm = CHOLMOD(norm_sparse) (G, 0, cm) ; MAXERR (maxerr, enorm, gnorm) ; - if (1) // (cm->print > 1) + if (cm->print > 1) { printf ("enorm %g gnorm %g hnorm %g\n", enorm, gnorm, CHOLMOD(norm_sparse) (H, 0, cm)) ; @@ -739,7 +726,6 @@ double solve (cholmod_sparse *A) CHOLMOD(free_sparse) (&AF, cm) ; CHOLMOD(free_sparse) (&E, cm) ; CHOLMOD(free_sparse) (&H, cm) ; - } else { diff --git a/CHOLMOD/Tcov/test_ops.c b/CHOLMOD/Tcov/test_ops.c index 50ad63ba98..4d99ba8f21 100644 --- a/CHOLMOD/Tcov/test_ops.c +++ b/CHOLMOD/Tcov/test_ops.c @@ -152,7 +152,6 @@ static void check_equality (cholmod_sparse *E, cholmod_sparse *D, Int xtype) OK (E->ncol == D->ncol) ; OK (E->nrow == D->nrow) ; - OK (E->packed == D->packed) ; ncol = E->ncol ; @@ -241,9 +240,6 @@ double test_ops (cholmod_sparse *A) /* E = pattern of A */ E = CHOLMOD(copy) (A, 0, 0, cm) ; CHOLMOD(print_sparse) (E, "E = pattern of A", cm) ; -// int64_t enz = CHOLMOD (nnz) (E, cm) ; -// int64_t anz = CHOLMOD (nnz) (A, cm) ; -// if (E->stype == A->stype) { OK (enz == anz) ; } r1 = CHOLMOD(norm_sparse) (E, 1, cm) ; rinf = CHOLMOD(norm_sparse) (E, 0, cm) ; OK (r1 <= nrow) ; @@ -290,6 +286,13 @@ double test_ops (cholmod_sparse *A) /* read/write */ /* ---------------------------------------------------------------------- */ +/* + i = cm->print ; + cm->print = 4 ; + CHOLMOD(print_sparse) (A, "A for read/write", cm) ; + cm->print = i ; +*/ + /* delete the contents of the temp1.mtx and temp2.mtx file */ f = fopen ("temp1.mtx", "w") ; fprintf (f, "temp1\n") ; @@ -425,7 +428,7 @@ double test_ops (cholmod_sparse *A) S = CHOLMOD(sparse_to_triplet) (A, cm) ; /* [ */ - if (S != NULL && nmin > 0 && S->nnz > 0) + if (S != NULL && nmin > 0) { /* double the number of entries in S */ @@ -746,7 +749,7 @@ double test_ops (cholmod_sparse *A) /* G = E+F */ G = CHOLMOD(add) (E, F, one, one, TRUE, TRUE, cm) ; - CHOLMOD(print_sparse) (G, "G=E+F (1)", cm) ; + CHOLMOD(print_sparse) (G, "G=E+F", cm) ; /* D = A-G, which should be empty */ D = CHOLMOD(add) (G, A, one, minusone, TRUE, TRUE, cm) ; @@ -804,7 +807,7 @@ double test_ops (cholmod_sparse *A) /* G = E+C */ G = CHOLMOD(add) (E, C, one, one, TRUE, FALSE, cm) ; - CHOLMOD(print_sparse) (G, "G = E+F", cm) ; + CHOLMOD(print_sparse) (G, "G=E+F", cm) ; CHOLMOD(sort) (G, cm) ; CHOLMOD(drop) (0, G, cm) ; @@ -844,6 +847,7 @@ double test_ops (cholmod_sparse *A) /* try CHOLMOD's interface to METIS_ComputeVertexSeparator */ cm->metis_memory = 2.0 ; + /* cm->print = 5 ; */ CHOLMOD(print_sparse) (A, "A for bisect", cm) ; csep = CHOLMOD(bisect) (A, NULL, 0, TRUE, Partition, cm) ; if (csep != EMPTY) @@ -935,7 +939,7 @@ double test_ops (cholmod_sparse *A) nc_new = CHOLMOD(collapse_septree) (1, 1, 0.1, 400, CParent, Cmember, cm) ; OK (nc_new == 1 || nc_new == EMPTY) ; - nc_new = CHOLMOD(collapse_septree) (SIZE_MAX, SIZE_MAX, + nc_new = CHOLMOD(collapse_septree) (Int_max, Int_max, 0.1, 400, CParent, Cmember, cm) ; OK (nc_new == EMPTY) ; @@ -982,12 +986,8 @@ double test_ops (cholmod_sparse *A) { F = CHOLMOD(add) (E, D, one, minusone, TRUE, TRUE, cm) ; r = CHOLMOD(norm_sparse) (F, 0, cm) ; - if (F != NULL && cm->status == CHOLMOD_OK) + if (F != NULL) { - if (r != 0) - { - printf ("r %g at %d:%s\n", r, __LINE__, __FILE__) ; - } OK (r == 0) ; } CHOLMOD(free_sparse) (&F, cm) ; @@ -1020,21 +1020,19 @@ double test_ops (cholmod_sparse *A) F = CHOLMOD(transpose) (E, 1, cm) ; G = CHOLMOD(add) (D, F, one, minusone, TRUE, FALSE, cm) ; r = CHOLMOD(norm_sparse) (G, 0, cm) ; - if (G != NULL && cm->status == CHOLMOD_OK) + if (G != NULL) { OK (r == 0) ; } CHOLMOD(drop) (0, G, cm) ; r = CHOLMOD(norm_sparse) (G, 0, cm) ; - if (G != NULL && cm->status == CHOLMOD_OK) - { - OK (r == 0) ; - } nz = CHOLMOD(nnz) (G, cm) ; - if (G != NULL && cm->status == CHOLMOD_OK) + if (G != NULL) { + OK (r == 0) ; OK (nz == 0) ; } + CHOLMOD(free_sparse) (&C, cm) ; CHOLMOD(free_sparse) (&D, cm) ; CHOLMOD(free_sparse) (&E, cm) ; @@ -1061,16 +1059,10 @@ double test_ops (cholmod_sparse *A) C = CHOLMOD(copy_sparse) (A, cm) ; CHOLMOD(sort) (C, cm) ; - int cstype = (C == NULL) ? 0 : C->stype ; - E = CHOLMOD(copy) (C, cstype, 1, cm) ; - F = CHOLMOD(copy) (D, cstype, 1, cm) ; - /* C and D should be equal */ - check_equality (E, F, xtype) ; + check_equality (C, D, xtype) ; CHOLMOD(free_sparse) (&C, cm) ; CHOLMOD(free_sparse) (&D, cm) ; - CHOLMOD(free_sparse) (&E, cm) ; - CHOLMOD(free_sparse) (&F, cm) ; /* C = A.' */ C = CHOLMOD(transpose) (A, 1, cm) ; @@ -1084,16 +1076,10 @@ double test_ops (cholmod_sparse *A) C = CHOLMOD(copy_sparse) (A, cm) ; CHOLMOD(sort) (C, cm) ; - cstype = (C == NULL) ? 0 : C->stype ; - E = CHOLMOD(copy) (C, cstype, 1, cm) ; - F = CHOLMOD(copy) (D, cstype, 1, cm) ; - /* C and D should be equal */ - check_equality (E, F, xtype) ; + check_equality (C, D, xtype) ; CHOLMOD(free_sparse) (&C, cm) ; CHOLMOD(free_sparse) (&D, cm) ; - CHOLMOD(free_sparse) (&E, cm) ; - CHOLMOD(free_sparse) (&F, cm) ; } /* ---------------------------------------------------------------------- */ diff --git a/CHOLMOD/Utility/cholmod_alloc_work.c b/CHOLMOD/Utility/cholmod_alloc_work.c deleted file mode 100644 index 46b0029a88..0000000000 --- a/CHOLMOD/Utility/cholmod_alloc_work.c +++ /dev/null @@ -1,13 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/cholmod_alloc_work: alloc workspace (double/single, int32) -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -#define CHOLMOD_INT32 -#include "t_cholmod_alloc_work.c" - diff --git a/CHOLMOD/Utility/cholmod_allocate_dense.c b/CHOLMOD/Utility/cholmod_allocate_dense.c deleted file mode 100644 index e0497697ec..0000000000 --- a/CHOLMOD/Utility/cholmod_allocate_dense.c +++ /dev/null @@ -1,13 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/cholmod_allocate_dense: allocate dense matrix (int32) -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -#define CHOLMOD_INT32 -#include "t_cholmod_allocate_dense.c" - diff --git a/CHOLMOD/Utility/cholmod_allocate_factor.c b/CHOLMOD/Utility/cholmod_allocate_factor.c deleted file mode 100644 index 5ac43cae7c..0000000000 --- a/CHOLMOD/Utility/cholmod_allocate_factor.c +++ /dev/null @@ -1,25 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/cholmod_allocate_factor: allocate a simplicial factor -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -// For backward compatibilty; L is returned as double precision. -// Use cholmod_alloc_factor to allocate a single precision factor. - -#define CHOLMOD_INT32 -#include "cholmod_internal.h" - -cholmod_factor *cholmod_allocate_factor // return the new factor L -( - size_t n, // L is factorization of an n-by-n matrix - cholmod_common *Common -) -{ - return (cholmod_alloc_factor (n, CHOLMOD_DOUBLE, Common)) ; -} - diff --git a/CHOLMOD/Utility/cholmod_allocate_sparse.c b/CHOLMOD/Utility/cholmod_allocate_sparse.c deleted file mode 100644 index 1cc566b8ae..0000000000 --- a/CHOLMOD/Utility/cholmod_allocate_sparse.c +++ /dev/null @@ -1,13 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/cholmod_allocate_sparse: allocate a sparse matrix -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -#define CHOLMOD_INT32 -#include "t_cholmod_allocate_sparse.c" - diff --git a/CHOLMOD/Utility/cholmod_allocate_triplet.c b/CHOLMOD/Utility/cholmod_allocate_triplet.c deleted file mode 100644 index 0bce378eac..0000000000 --- a/CHOLMOD/Utility/cholmod_allocate_triplet.c +++ /dev/null @@ -1,13 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/cholmod_allocate_triplet: allocate triplet matrix (int32) -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -#define CHOLMOD_INT32 -#include "t_cholmod_allocate_triplet.c" - diff --git a/CHOLMOD/Utility/cholmod_allocate_work.c b/CHOLMOD/Utility/cholmod_allocate_work.c deleted file mode 100644 index 61e4996a3b..0000000000 --- a/CHOLMOD/Utility/cholmod_allocate_work.c +++ /dev/null @@ -1,24 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/cholmod_allocate_work: alloc workspace (double, int32) -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -#include "cholmod_internal.h" - -int cholmod_allocate_work -( - size_t nrow, - size_t iworksize, - size_t xworksize, - cholmod_common *Common -) -{ - return (cholmod_alloc_work (nrow, iworksize, xworksize, CHOLMOD_DOUBLE, - Common)) ; -} - diff --git a/CHOLMOD/Utility/cholmod_band.c b/CHOLMOD/Utility/cholmod_band.c deleted file mode 100644 index 20efa58c46..0000000000 --- a/CHOLMOD/Utility/cholmod_band.c +++ /dev/null @@ -1,13 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/cholmod_band: extract the band of a sparse matrix -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -#define CHOLMOD_INT32 -#include "t_cholmod_band.c" - diff --git a/CHOLMOD/Utility/cholmod_band_nnz.c b/CHOLMOD/Utility/cholmod_band_nnz.c deleted file mode 100644 index 7efc5c04a0..0000000000 --- a/CHOLMOD/Utility/cholmod_band_nnz.c +++ /dev/null @@ -1,13 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/cholmod_band_nnz: # of entries in a band of sparse matrix -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -#define CHOLMOD_INT32 -#include "t_cholmod_band_nnz.c" - diff --git a/CHOLMOD/Utility/cholmod_calloc.c b/CHOLMOD/Utility/cholmod_calloc.c deleted file mode 100644 index 90cbe6e9de..0000000000 --- a/CHOLMOD/Utility/cholmod_calloc.c +++ /dev/null @@ -1,15 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/cholmod_calloc: calloc (int32 version) -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -#define CHOLMOD_ALLOC_FUNCTION cholmod_calloc -#define SUITESPARSE_ALLOC_FUNCTION SuiteSparse_calloc -#define CHOLMOD_INT32 -#include "t_cholmod_malloc.c" - diff --git a/CHOLMOD/Utility/cholmod_change_factor.c b/CHOLMOD/Utility/cholmod_change_factor.c deleted file mode 100644 index 3f9b0492e1..0000000000 --- a/CHOLMOD/Utility/cholmod_change_factor.c +++ /dev/null @@ -1,13 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/cholmod_change_factor: change format of a factor object -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -#define CHOLMOD_INT32 -#include "t_cholmod_change_factor.c" - diff --git a/CHOLMOD/Utility/cholmod_clear_flag.c b/CHOLMOD/Utility/cholmod_clear_flag.c deleted file mode 100644 index 753064822b..0000000000 --- a/CHOLMOD/Utility/cholmod_clear_flag.c +++ /dev/null @@ -1,13 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/cholmod_clear_flag: clear Common->Flag -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -#define CHOLMOD_INT32 -#include "t_cholmod_clear_flag.c" - diff --git a/CHOLMOD/Utility/cholmod_copy.c b/CHOLMOD/Utility/cholmod_copy.c deleted file mode 100644 index d2c92f6081..0000000000 --- a/CHOLMOD/Utility/cholmod_copy.c +++ /dev/null @@ -1,13 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/cholmod_copy: copy a sparse matrix (with change of stype) -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -#define CHOLMOD_INT32 -#include "t_cholmod_copy.c" - diff --git a/CHOLMOD/Utility/cholmod_copy_dense.c b/CHOLMOD/Utility/cholmod_copy_dense.c deleted file mode 100644 index 20795d1224..0000000000 --- a/CHOLMOD/Utility/cholmod_copy_dense.c +++ /dev/null @@ -1,13 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/cholmod_copy_dense: copy a dense matrix -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -#define CHOLMOD_INT32 -#include "t_cholmod_copy_dense.c" - diff --git a/CHOLMOD/Utility/cholmod_copy_dense2.c b/CHOLMOD/Utility/cholmod_copy_dense2.c deleted file mode 100644 index 65efdea67b..0000000000 --- a/CHOLMOD/Utility/cholmod_copy_dense2.c +++ /dev/null @@ -1,13 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/cholmod_copy_dense2: copy a dense matrix -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -#define CHOLMOD_INT32 -#include "t_cholmod_copy_dense2.c" - diff --git a/CHOLMOD/Utility/cholmod_copy_factor.c b/CHOLMOD/Utility/cholmod_copy_factor.c deleted file mode 100644 index bafdd7e3a4..0000000000 --- a/CHOLMOD/Utility/cholmod_copy_factor.c +++ /dev/null @@ -1,13 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/cholmod_copy_factor: copy a factor -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -#define CHOLMOD_INT32 -#include "t_cholmod_copy_factor.c" - diff --git a/CHOLMOD/Utility/cholmod_copy_sparse.c b/CHOLMOD/Utility/cholmod_copy_sparse.c deleted file mode 100644 index 24cb68fdde..0000000000 --- a/CHOLMOD/Utility/cholmod_copy_sparse.c +++ /dev/null @@ -1,13 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/cholmod_copy_sparse: copy a sparse matrix -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -#define CHOLMOD_INT32 -#include "t_cholmod_copy_sparse.c" - diff --git a/CHOLMOD/Utility/cholmod_copy_triplet.c b/CHOLMOD/Utility/cholmod_copy_triplet.c deleted file mode 100644 index d97d6a3a8b..0000000000 --- a/CHOLMOD/Utility/cholmod_copy_triplet.c +++ /dev/null @@ -1,13 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/cholmod_copy_triplet: copy a triplet matrix -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -#define CHOLMOD_INT32 -#include "t_cholmod_copy_triplet.c" - diff --git a/CHOLMOD/Utility/cholmod_cumsum.c b/CHOLMOD/Utility/cholmod_cumsum.c deleted file mode 100644 index cd4b229839..0000000000 --- a/CHOLMOD/Utility/cholmod_cumsum.c +++ /dev/null @@ -1,13 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/cholmod_cumsum: cumulative sum (int32) -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -#define CHOLMOD_INT32 -#include "t_cholmod_cumsum.c" - diff --git a/CHOLMOD/Utility/cholmod_dbound.c b/CHOLMOD/Utility/cholmod_dbound.c deleted file mode 100644 index ab2050abdb..0000000000 --- a/CHOLMOD/Utility/cholmod_dbound.c +++ /dev/null @@ -1,18 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/cholmod_dbound: bound diagonal of LDL (double, int32) -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -#define CHOLMOD_BOUND_FUNCTION cholmod_dbound -#define COMMON_BOUND (Common->dbound) -#define COMMON_BOUNDS_HIT (Common->ndbounds_hit) -#define Real double - -#define CHOLMOD_INT32 -#include "t_cholmod_bound.c" - diff --git a/CHOLMOD/Utility/cholmod_defaults.c b/CHOLMOD/Utility/cholmod_defaults.c deleted file mode 100644 index ed8560936d..0000000000 --- a/CHOLMOD/Utility/cholmod_defaults.c +++ /dev/null @@ -1,13 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/cholmod_defaults: set CHOLMOD defaults (int32 version) -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -#define CHOLMOD_INT32 -#include "t_cholmod_defaults.c" - diff --git a/CHOLMOD/Utility/cholmod_dense_nnz.c b/CHOLMOD/Utility/cholmod_dense_nnz.c deleted file mode 100644 index bf504b483d..0000000000 --- a/CHOLMOD/Utility/cholmod_dense_nnz.c +++ /dev/null @@ -1,13 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/cholmod_dense_nnz: # of nonzeros in a dense matrix -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -#define CHOLMOD_INT32 -#include "t_cholmod_dense_nnz.c" - diff --git a/CHOLMOD/Utility/cholmod_dense_to_sparse.c b/CHOLMOD/Utility/cholmod_dense_to_sparse.c deleted file mode 100644 index 02a726d430..0000000000 --- a/CHOLMOD/Utility/cholmod_dense_to_sparse.c +++ /dev/null @@ -1,13 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/cholmod_dense_to_sparse: convert a dense matrix to sparse -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -#define CHOLMOD_INT32 -#include "t_cholmod_dense_to_sparse.c" - diff --git a/CHOLMOD/Utility/cholmod_divcomplex.c b/CHOLMOD/Utility/cholmod_divcomplex.c deleted file mode 100644 index cc3edb6e9e..0000000000 --- a/CHOLMOD/Utility/cholmod_divcomplex.c +++ /dev/null @@ -1,24 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/cholmod_divcomplex: complex divide -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -#include "cholmod_internal.h" - -// Compute c = a/b - -int cholmod_divcomplex -( - double ar, double ai, // a (real, imaginary) - double br, double bi, // b (real, imaginary) - double *cr, double *ci // c (real, imaginary) -) -{ - return (SuiteSparse_config_divcomplex (ar, ai, br, bi, cr, ci)) ; -} - diff --git a/CHOLMOD/Utility/cholmod_ensure_dense.c b/CHOLMOD/Utility/cholmod_ensure_dense.c deleted file mode 100644 index d0f3de2623..0000000000 --- a/CHOLMOD/Utility/cholmod_ensure_dense.c +++ /dev/null @@ -1,13 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/cholmod_ensure_dense: ensure dense matrix has a given size -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -#define CHOLMOD_INT32 -#include "t_cholmod_ensure_dense.c" - diff --git a/CHOLMOD/Utility/cholmod_error.c b/CHOLMOD/Utility/cholmod_error.c deleted file mode 100644 index 1d6a2f3b46..0000000000 --- a/CHOLMOD/Utility/cholmod_error.c +++ /dev/null @@ -1,13 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/cholmod_error: CHOLMOD error handling -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -#define CHOLMOD_INT32 -#include "t_cholmod_error.c" - diff --git a/CHOLMOD/Utility/cholmod_eye.c b/CHOLMOD/Utility/cholmod_eye.c deleted file mode 100644 index 3d80185fba..0000000000 --- a/CHOLMOD/Utility/cholmod_eye.c +++ /dev/null @@ -1,13 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/cholmod_eye: dense identity matrix -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -#define CHOLMOD_INT32 -#include "t_cholmod_eye.c" - diff --git a/CHOLMOD/Utility/cholmod_factor_to_sparse.c b/CHOLMOD/Utility/cholmod_factor_to_sparse.c deleted file mode 100644 index f22616fa0b..0000000000 --- a/CHOLMOD/Utility/cholmod_factor_to_sparse.c +++ /dev/null @@ -1,13 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/cholmod_factor_to_sparse: convert factor to sparse matrix -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -#define CHOLMOD_INT32 -#include "t_cholmod_factor_to_sparse.c" - diff --git a/CHOLMOD/Utility/cholmod_finish.c b/CHOLMOD/Utility/cholmod_finish.c deleted file mode 100644 index 6f22775899..0000000000 --- a/CHOLMOD/Utility/cholmod_finish.c +++ /dev/null @@ -1,13 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/cholmod_finish: finish CHOLMOD (int32 version) -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -#define CHOLMOD_INT32 -#include "t_cholmod_finish.c" - diff --git a/CHOLMOD/Utility/cholmod_free.c b/CHOLMOD/Utility/cholmod_free.c deleted file mode 100644 index 3bb235a52e..0000000000 --- a/CHOLMOD/Utility/cholmod_free.c +++ /dev/null @@ -1,13 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/cholmod_free: free (int32 version) -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -#define CHOLMOD_INT32 -#include "t_cholmod_free.c" - diff --git a/CHOLMOD/Utility/cholmod_free_dense.c b/CHOLMOD/Utility/cholmod_free_dense.c deleted file mode 100644 index 89d0e59f94..0000000000 --- a/CHOLMOD/Utility/cholmod_free_dense.c +++ /dev/null @@ -1,13 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/cholmod_free_dense: free dense matrix -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -#define CHOLMOD_INT32 -#include "t_cholmod_free_dense.c" - diff --git a/CHOLMOD/Utility/cholmod_free_factor.c b/CHOLMOD/Utility/cholmod_free_factor.c deleted file mode 100644 index a3f2caf045..0000000000 --- a/CHOLMOD/Utility/cholmod_free_factor.c +++ /dev/null @@ -1,13 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/cholmod_free_factor: free a sparse factorization -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -#define CHOLMOD_INT32 -#include "t_cholmod_free_factor.c" - diff --git a/CHOLMOD/Utility/cholmod_free_sparse.c b/CHOLMOD/Utility/cholmod_free_sparse.c deleted file mode 100644 index 2a5f9399fe..0000000000 --- a/CHOLMOD/Utility/cholmod_free_sparse.c +++ /dev/null @@ -1,13 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/cholmod_free_sparse: free sparse matrix -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -#define CHOLMOD_INT32 -#include "t_cholmod_free_sparse.c" - diff --git a/CHOLMOD/Utility/cholmod_free_triplet.c b/CHOLMOD/Utility/cholmod_free_triplet.c deleted file mode 100644 index 1734cf2f1e..0000000000 --- a/CHOLMOD/Utility/cholmod_free_triplet.c +++ /dev/null @@ -1,13 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/cholmod_free_triplet: free triplet matrix -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -#define CHOLMOD_INT32 -#include "t_cholmod_free_triplet.c" - diff --git a/CHOLMOD/Utility/cholmod_free_work.c b/CHOLMOD/Utility/cholmod_free_work.c deleted file mode 100644 index 6695a4a725..0000000000 --- a/CHOLMOD/Utility/cholmod_free_work.c +++ /dev/null @@ -1,13 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/cholmod_free_work: free workspace in Common (int32) -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -#define CHOLMOD_INT32 -#include "t_cholmod_free_work.c" - diff --git a/CHOLMOD/Utility/cholmod_hypot.c b/CHOLMOD/Utility/cholmod_hypot.c deleted file mode 100644 index 57ea322ada..0000000000 --- a/CHOLMOD/Utility/cholmod_hypot.c +++ /dev/null @@ -1,17 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/cholmod_hypot: complex hypot -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -#include "cholmod_internal.h" - -double cholmod_hypot (double x, double y) -{ - return (SuiteSparse_config_hypot (x, y)) ; -} - diff --git a/CHOLMOD/Utility/cholmod_l_add_size_t.c b/CHOLMOD/Utility/cholmod_l_add_size_t.c deleted file mode 100644 index 60a461fe4c..0000000000 --- a/CHOLMOD/Utility/cholmod_l_add_size_t.c +++ /dev/null @@ -1,13 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/cholmod_add_size_t: add two size_t values -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -#define CHOLMOD_INT64 -#include "t_cholmod_add_size_t.c" - diff --git a/CHOLMOD/Utility/cholmod_l_alloc_factor.c b/CHOLMOD/Utility/cholmod_l_alloc_factor.c deleted file mode 100644 index 6dac2c02e0..0000000000 --- a/CHOLMOD/Utility/cholmod_l_alloc_factor.c +++ /dev/null @@ -1,13 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/cholmod_l_alloc_factor: allocate a simplicial factor -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -#define CHOLMOD_INT64 -#include "t_cholmod_alloc_factor.c" - diff --git a/CHOLMOD/Utility/cholmod_l_alloc_work.c b/CHOLMOD/Utility/cholmod_l_alloc_work.c deleted file mode 100644 index 4843297344..0000000000 --- a/CHOLMOD/Utility/cholmod_l_alloc_work.c +++ /dev/null @@ -1,13 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/cholmod_l_alloc_work: alloc workspace (double/single, int64) -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -#define CHOLMOD_INT64 -#include "t_cholmod_alloc_work.c" - diff --git a/CHOLMOD/Utility/cholmod_l_allocate_dense.c b/CHOLMOD/Utility/cholmod_l_allocate_dense.c deleted file mode 100644 index 581e0c0781..0000000000 --- a/CHOLMOD/Utility/cholmod_l_allocate_dense.c +++ /dev/null @@ -1,13 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/cholmod_l_allocate_dense: allocate dense matrix (int64) -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -#define CHOLMOD_INT64 -#include "t_cholmod_allocate_dense.c" - diff --git a/CHOLMOD/Utility/cholmod_l_allocate_factor.c b/CHOLMOD/Utility/cholmod_l_allocate_factor.c deleted file mode 100644 index cf81b411f0..0000000000 --- a/CHOLMOD/Utility/cholmod_l_allocate_factor.c +++ /dev/null @@ -1,25 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/cholmod_l_allocate_factor: allocate a simplicial factor -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -// For backward compatibilty; L is returned as double precision. -// Use cholmod_l_alloc_factor to allocate a single precision factor. - -#define CHOLMOD_INT64 -#include "cholmod_internal.h" - -cholmod_factor *cholmod_l_allocate_factor // return the new factor L -( - size_t n, // L is factorization of an n-by-n matrix - cholmod_common *Common -) -{ - return (cholmod_l_alloc_factor (n, CHOLMOD_DOUBLE, Common)) ; -} - diff --git a/CHOLMOD/Utility/cholmod_l_allocate_sparse.c b/CHOLMOD/Utility/cholmod_l_allocate_sparse.c deleted file mode 100644 index bef6996d11..0000000000 --- a/CHOLMOD/Utility/cholmod_l_allocate_sparse.c +++ /dev/null @@ -1,13 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/cholmod_l_allocate_sparse: allocate a sparse matrix -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -#define CHOLMOD_INT64 -#include "t_cholmod_allocate_sparse.c" - diff --git a/CHOLMOD/Utility/cholmod_l_allocate_triplet.c b/CHOLMOD/Utility/cholmod_l_allocate_triplet.c deleted file mode 100644 index 7e578e8a07..0000000000 --- a/CHOLMOD/Utility/cholmod_l_allocate_triplet.c +++ /dev/null @@ -1,13 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/cholmod_l_allocate_triplet: allocate triplet matrix (int64) -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -#define CHOLMOD_INT64 -#include "t_cholmod_allocate_triplet.c" - diff --git a/CHOLMOD/Utility/cholmod_l_allocate_work.c b/CHOLMOD/Utility/cholmod_l_allocate_work.c deleted file mode 100644 index ee167e3548..0000000000 --- a/CHOLMOD/Utility/cholmod_l_allocate_work.c +++ /dev/null @@ -1,24 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/cholmod_l_allocate_work: alloc workspace (double, int64) -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -#include "cholmod_internal.h" - -int cholmod_l_allocate_work -( - size_t nrow, - size_t iworksize, - size_t xworksize, - cholmod_common *Common -) -{ - return (cholmod_l_alloc_work (nrow, iworksize, xworksize, CHOLMOD_DOUBLE, - Common)) ; -} - diff --git a/CHOLMOD/Utility/cholmod_l_band_nnz.c b/CHOLMOD/Utility/cholmod_l_band_nnz.c deleted file mode 100644 index 343a03e5a1..0000000000 --- a/CHOLMOD/Utility/cholmod_l_band_nnz.c +++ /dev/null @@ -1,13 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/cholmod_l_band_nnz: # of entries in a band of sparse matrix -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -#define CHOLMOD_INT64 -#include "t_cholmod_band_nnz.c" - diff --git a/CHOLMOD/Utility/cholmod_l_calloc.c b/CHOLMOD/Utility/cholmod_l_calloc.c deleted file mode 100644 index 004e17eced..0000000000 --- a/CHOLMOD/Utility/cholmod_l_calloc.c +++ /dev/null @@ -1,15 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/cholmod_l_calloc: calloc (int64 version) -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -#define CHOLMOD_ALLOC_FUNCTION cholmod_l_calloc -#define SUITESPARSE_ALLOC_FUNCTION SuiteSparse_calloc -#define CHOLMOD_INT64 -#include "t_cholmod_malloc.c" - diff --git a/CHOLMOD/Utility/cholmod_l_clear_flag.c b/CHOLMOD/Utility/cholmod_l_clear_flag.c deleted file mode 100644 index cd604a29aa..0000000000 --- a/CHOLMOD/Utility/cholmod_l_clear_flag.c +++ /dev/null @@ -1,13 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/cholmod_l_clear_flag: clear Common->Flag -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -#define CHOLMOD_INT64 -#include "t_cholmod_clear_flag.c" - diff --git a/CHOLMOD/Utility/cholmod_l_copy_dense.c b/CHOLMOD/Utility/cholmod_l_copy_dense.c deleted file mode 100644 index dfe71cb9e8..0000000000 --- a/CHOLMOD/Utility/cholmod_l_copy_dense.c +++ /dev/null @@ -1,13 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/cholmod_l_copy_dense: copy a dense matrix -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -#define CHOLMOD_INT64 -#include "t_cholmod_copy_dense.c" - diff --git a/CHOLMOD/Utility/cholmod_l_copy_dense2.c b/CHOLMOD/Utility/cholmod_l_copy_dense2.c deleted file mode 100644 index 561ae16a91..0000000000 --- a/CHOLMOD/Utility/cholmod_l_copy_dense2.c +++ /dev/null @@ -1,13 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/cholmod_l_copy_dense2: copy a dense matrix -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -#define CHOLMOD_INT64 -#include "t_cholmod_copy_dense2.c" - diff --git a/CHOLMOD/Utility/cholmod_l_copy_factor.c b/CHOLMOD/Utility/cholmod_l_copy_factor.c deleted file mode 100644 index ed0d0d6609..0000000000 --- a/CHOLMOD/Utility/cholmod_l_copy_factor.c +++ /dev/null @@ -1,13 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/cholmod_l_copy_factor: copy a factor -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -#define CHOLMOD_INT64 -#include "t_cholmod_copy_factor.c" - diff --git a/CHOLMOD/Utility/cholmod_l_copy_sparse.c b/CHOLMOD/Utility/cholmod_l_copy_sparse.c deleted file mode 100644 index f5eaf83ccf..0000000000 --- a/CHOLMOD/Utility/cholmod_l_copy_sparse.c +++ /dev/null @@ -1,13 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/cholmod_l_copy_sparse: copy a sparse matrix -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -#define CHOLMOD_INT64 -#include "t_cholmod_copy_sparse.c" - diff --git a/CHOLMOD/Utility/cholmod_l_copy_triplet.c b/CHOLMOD/Utility/cholmod_l_copy_triplet.c deleted file mode 100644 index e580ec1513..0000000000 --- a/CHOLMOD/Utility/cholmod_l_copy_triplet.c +++ /dev/null @@ -1,13 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/cholmod_l_copy_triplet: copy a triplet matrix -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -#define CHOLMOD_INT64 -#include "t_cholmod_copy_triplet.c" - diff --git a/CHOLMOD/Utility/cholmod_l_cumsum.c b/CHOLMOD/Utility/cholmod_l_cumsum.c deleted file mode 100644 index f3e2f73f4a..0000000000 --- a/CHOLMOD/Utility/cholmod_l_cumsum.c +++ /dev/null @@ -1,13 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/cholmod_l_cumsum: cumulative sum (int64) -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -#define CHOLMOD_INT64 -#include "t_cholmod_cumsum.c" - diff --git a/CHOLMOD/Utility/cholmod_l_dbound.c b/CHOLMOD/Utility/cholmod_l_dbound.c deleted file mode 100644 index 9ee6798847..0000000000 --- a/CHOLMOD/Utility/cholmod_l_dbound.c +++ /dev/null @@ -1,18 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/cholmod_l_dbound: bound diagonal of LDL (double, int64) -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -#define CHOLMOD_BOUND_FUNCTION cholmod_l_dbound -#define COMMON_BOUND (Common->dbound) -#define COMMON_BOUNDS_HIT (Common->ndbounds_hit) -#define Real double - -#define CHOLMOD_INT64 -#include "t_cholmod_bound.c" - diff --git a/CHOLMOD/Utility/cholmod_l_defaults.c b/CHOLMOD/Utility/cholmod_l_defaults.c deleted file mode 100644 index d5990258f7..0000000000 --- a/CHOLMOD/Utility/cholmod_l_defaults.c +++ /dev/null @@ -1,13 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/cholmod_l_defaults: set CHOLMOD defaults (int64 version) -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -#define CHOLMOD_INT64 -#include "t_cholmod_defaults.c" - diff --git a/CHOLMOD/Utility/cholmod_l_dense_nnz.c b/CHOLMOD/Utility/cholmod_l_dense_nnz.c deleted file mode 100644 index 4611f6091c..0000000000 --- a/CHOLMOD/Utility/cholmod_l_dense_nnz.c +++ /dev/null @@ -1,13 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/cholmod_l_dense_nnz: # of nonzeros in a dense matrix -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -#define CHOLMOD_INT64 -#include "t_cholmod_dense_nnz.c" - diff --git a/CHOLMOD/Utility/cholmod_l_dense_to_sparse.c b/CHOLMOD/Utility/cholmod_l_dense_to_sparse.c deleted file mode 100644 index d1cd953265..0000000000 --- a/CHOLMOD/Utility/cholmod_l_dense_to_sparse.c +++ /dev/null @@ -1,13 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/cholmod_l_dense_to_sparse: convert a dense matrix to sparse -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -#define CHOLMOD_INT64 -#include "t_cholmod_dense_to_sparse.c" - diff --git a/CHOLMOD/Utility/cholmod_l_divcomplex.c b/CHOLMOD/Utility/cholmod_l_divcomplex.c deleted file mode 100644 index 1a8901a0b5..0000000000 --- a/CHOLMOD/Utility/cholmod_l_divcomplex.c +++ /dev/null @@ -1,22 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/cholmod_l_divcomplex: complex divide -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -#include "cholmod_internal.h" - -int cholmod_l_divcomplex -( - double ar, double ai, // a (real, imaginary) - double br, double bi, // b (real, imaginary) - double *cr, double *ci // c (real, imaginary) -) -{ - return (SuiteSparse_config_divcomplex (ar, ai, br, bi, cr, ci)) ; -} - diff --git a/CHOLMOD/Utility/cholmod_l_ensure_dense.c b/CHOLMOD/Utility/cholmod_l_ensure_dense.c deleted file mode 100644 index e53d82645c..0000000000 --- a/CHOLMOD/Utility/cholmod_l_ensure_dense.c +++ /dev/null @@ -1,13 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/cholmod_l_ensure_dense: ensure dense matrix has a given size -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -#define CHOLMOD_INT64 -#include "t_cholmod_ensure_dense.c" - diff --git a/CHOLMOD/Utility/cholmod_l_eye.c b/CHOLMOD/Utility/cholmod_l_eye.c deleted file mode 100644 index 49014647f7..0000000000 --- a/CHOLMOD/Utility/cholmod_l_eye.c +++ /dev/null @@ -1,13 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/cholmod_l_eye: dense identity matrix -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -#define CHOLMOD_INT64 -#include "t_cholmod_eye.c" - diff --git a/CHOLMOD/Utility/cholmod_l_factor_to_sparse.c b/CHOLMOD/Utility/cholmod_l_factor_to_sparse.c deleted file mode 100644 index 74a63289cb..0000000000 --- a/CHOLMOD/Utility/cholmod_l_factor_to_sparse.c +++ /dev/null @@ -1,13 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/cholmod_l_factor_to_sparse: convert factor to sparse matrix -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -#define CHOLMOD_INT64 -#include "t_cholmod_factor_to_sparse.c" - diff --git a/CHOLMOD/Utility/cholmod_l_finish.c b/CHOLMOD/Utility/cholmod_l_finish.c deleted file mode 100644 index a0066f1505..0000000000 --- a/CHOLMOD/Utility/cholmod_l_finish.c +++ /dev/null @@ -1,13 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/cholmod_l_finish: finish CHOLMOD (int64 version) -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -#define CHOLMOD_INT64 -#include "t_cholmod_finish.c" - diff --git a/CHOLMOD/Utility/cholmod_l_free.c b/CHOLMOD/Utility/cholmod_l_free.c deleted file mode 100644 index cc4ff9ef77..0000000000 --- a/CHOLMOD/Utility/cholmod_l_free.c +++ /dev/null @@ -1,13 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/cholmod_l_free: free (int64 version) -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -#define CHOLMOD_INT64 -#include "t_cholmod_free.c" - diff --git a/CHOLMOD/Utility/cholmod_l_free_dense.c b/CHOLMOD/Utility/cholmod_l_free_dense.c deleted file mode 100644 index f692f29a3f..0000000000 --- a/CHOLMOD/Utility/cholmod_l_free_dense.c +++ /dev/null @@ -1,13 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/cholmod_l_free_dense: free dense matrix -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -#define CHOLMOD_INT64 -#include "t_cholmod_free_dense.c" - diff --git a/CHOLMOD/Utility/cholmod_l_free_factor.c b/CHOLMOD/Utility/cholmod_l_free_factor.c deleted file mode 100644 index 182bccdb1d..0000000000 --- a/CHOLMOD/Utility/cholmod_l_free_factor.c +++ /dev/null @@ -1,13 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/cholmod_l_free_factor: free a sparse factorization -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -#define CHOLMOD_INT64 -#include "t_cholmod_free_factor.c" - diff --git a/CHOLMOD/Utility/cholmod_l_free_sparse.c b/CHOLMOD/Utility/cholmod_l_free_sparse.c deleted file mode 100644 index d8717fa9eb..0000000000 --- a/CHOLMOD/Utility/cholmod_l_free_sparse.c +++ /dev/null @@ -1,13 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/cholmod_l_free_sparse: free sparse matrix -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -#define CHOLMOD_INT64 -#include "t_cholmod_free_sparse.c" - diff --git a/CHOLMOD/Utility/cholmod_l_free_triplet.c b/CHOLMOD/Utility/cholmod_l_free_triplet.c deleted file mode 100644 index c65d4bd5d8..0000000000 --- a/CHOLMOD/Utility/cholmod_l_free_triplet.c +++ /dev/null @@ -1,13 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/cholmod_l_free_triplet: free triplet matrix -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -#define CHOLMOD_INT64 -#include "t_cholmod_free_triplet.c" - diff --git a/CHOLMOD/Utility/cholmod_l_free_work.c b/CHOLMOD/Utility/cholmod_l_free_work.c deleted file mode 100644 index 8b1cbb90e2..0000000000 --- a/CHOLMOD/Utility/cholmod_l_free_work.c +++ /dev/null @@ -1,13 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/cholmod_l_free_work: free workspace in Common (int64) -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -#define CHOLMOD_INT64 -#include "t_cholmod_free_work.c" - diff --git a/CHOLMOD/Utility/cholmod_l_hypot.c b/CHOLMOD/Utility/cholmod_l_hypot.c deleted file mode 100644 index f6a6470676..0000000000 --- a/CHOLMOD/Utility/cholmod_l_hypot.c +++ /dev/null @@ -1,17 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/cholmod_l_hypot: complex hypot -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -#include "cholmod_internal.h" - -double cholmod_l_hypot (double x, double y) -{ - return (SuiteSparse_config_hypot (x, y)) ; -} - diff --git a/CHOLMOD/Utility/cholmod_l_malloc.c b/CHOLMOD/Utility/cholmod_l_malloc.c deleted file mode 100644 index d344e627aa..0000000000 --- a/CHOLMOD/Utility/cholmod_l_malloc.c +++ /dev/null @@ -1,15 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/cholmod_l_malloc: malloc (int64 version) -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -#define CHOLMOD_ALLOC_FUNCTION cholmod_l_malloc -#define SUITESPARSE_ALLOC_FUNCTION SuiteSparse_malloc -#define CHOLMOD_INT64 -#include "t_cholmod_malloc.c" - diff --git a/CHOLMOD/Utility/cholmod_l_maxrank.c b/CHOLMOD/Utility/cholmod_l_maxrank.c deleted file mode 100644 index fc6991e34d..0000000000 --- a/CHOLMOD/Utility/cholmod_l_maxrank.c +++ /dev/null @@ -1,13 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/cholmod_l_maxrank: find valid value of Common->maxrank -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -#define CHOLMOD_INT64 -#include "t_cholmod_maxrank.c" - diff --git a/CHOLMOD/Utility/cholmod_l_mult_size_t.c b/CHOLMOD/Utility/cholmod_l_mult_size_t.c deleted file mode 100644 index 53d5310b21..0000000000 --- a/CHOLMOD/Utility/cholmod_l_mult_size_t.c +++ /dev/null @@ -1,13 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/cholmod_l_mult_size_t: multiply two size_t values -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -#define CHOLMOD_INT64 -#include "t_cholmod_mult_size_t.c" - diff --git a/CHOLMOD/Utility/cholmod_l_nnz.c b/CHOLMOD/Utility/cholmod_l_nnz.c deleted file mode 100644 index 2b21822f9b..0000000000 --- a/CHOLMOD/Utility/cholmod_l_nnz.c +++ /dev/null @@ -1,13 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/cholmod_l_nnz: # of entries in a sparse matrix -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -#define CHOLMOD_INT64 -#include "t_cholmod_nnz.c" - diff --git a/CHOLMOD/Utility/cholmod_l_ones.c b/CHOLMOD/Utility/cholmod_l_ones.c deleted file mode 100644 index 71ff5bddcf..0000000000 --- a/CHOLMOD/Utility/cholmod_l_ones.c +++ /dev/null @@ -1,13 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/cholmod_l_ones: dense matrix of all ones -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -#define CHOLMOD_INT64 -#include "t_cholmod_ones.c" - diff --git a/CHOLMOD/Utility/cholmod_l_pack_factor.c b/CHOLMOD/Utility/cholmod_l_pack_factor.c deleted file mode 100644 index 72fa3e1f2d..0000000000 --- a/CHOLMOD/Utility/cholmod_l_pack_factor.c +++ /dev/null @@ -1,13 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/cholmod_l_pack_factor: pack a simplicial factorization -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -#define CHOLMOD_INT64 -#include "t_cholmod_pack_factor.c" - diff --git a/CHOLMOD/Utility/cholmod_l_ptranspose.c b/CHOLMOD/Utility/cholmod_l_ptranspose.c deleted file mode 100644 index f7cf6880b5..0000000000 --- a/CHOLMOD/Utility/cholmod_l_ptranspose.c +++ /dev/null @@ -1,13 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/cholmod_l_ptranspose: permuted transpose -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -#define CHOLMOD_INT64 -#include "t_cholmod_ptranspose.c" - diff --git a/CHOLMOD/Utility/cholmod_l_realloc.c b/CHOLMOD/Utility/cholmod_l_realloc.c deleted file mode 100644 index 4c0320a764..0000000000 --- a/CHOLMOD/Utility/cholmod_l_realloc.c +++ /dev/null @@ -1,13 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/cholmod_l_realloc: realloc (int64 version) -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -#define CHOLMOD_INT64 -#include "t_cholmod_realloc.c" - diff --git a/CHOLMOD/Utility/cholmod_l_realloc_multiple.c b/CHOLMOD/Utility/cholmod_l_realloc_multiple.c deleted file mode 100644 index 8cea78c9af..0000000000 --- a/CHOLMOD/Utility/cholmod_l_realloc_multiple.c +++ /dev/null @@ -1,13 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/cholmod_l_realloc_multiple: multiple realloc (int64 version) -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -#define CHOLMOD_INT64 -#include "t_cholmod_realloc_multiple.c" - diff --git a/CHOLMOD/Utility/cholmod_l_reallocate_column.c b/CHOLMOD/Utility/cholmod_l_reallocate_column.c deleted file mode 100644 index 34d75b7fe5..0000000000 --- a/CHOLMOD/Utility/cholmod_l_reallocate_column.c +++ /dev/null @@ -1,13 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/cholmod_l_reallocate_column: reallocate a column of a factor -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -#define CHOLMOD_INT64 -#include "t_cholmod_reallocate_column.c" - diff --git a/CHOLMOD/Utility/cholmod_l_reallocate_factor.c b/CHOLMOD/Utility/cholmod_l_reallocate_factor.c deleted file mode 100644 index a8986990b8..0000000000 --- a/CHOLMOD/Utility/cholmod_l_reallocate_factor.c +++ /dev/null @@ -1,13 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/cholmod_l_reallocate_factor: reallocate a factor -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -#define CHOLMOD_INT64 -#include "t_cholmod_reallocate_factor.c" - diff --git a/CHOLMOD/Utility/cholmod_l_reallocate_sparse.c b/CHOLMOD/Utility/cholmod_l_reallocate_sparse.c deleted file mode 100644 index 3d69bd0df1..0000000000 --- a/CHOLMOD/Utility/cholmod_l_reallocate_sparse.c +++ /dev/null @@ -1,13 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/cholmod_l_reallocate_sparse: reallocate sparse matrix -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -#define CHOLMOD_INT64 -#include "t_cholmod_reallocate_sparse.c" - diff --git a/CHOLMOD/Utility/cholmod_l_reallocate_triplet.c b/CHOLMOD/Utility/cholmod_l_reallocate_triplet.c deleted file mode 100644 index 964bdba254..0000000000 --- a/CHOLMOD/Utility/cholmod_l_reallocate_triplet.c +++ /dev/null @@ -1,13 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/cholmod_l_reallocate_triplet: reallocate triplet matrix -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -#define CHOLMOD_INT64 -#include "t_cholmod_reallocate_triplet.c" - diff --git a/CHOLMOD/Utility/cholmod_l_sbound.c b/CHOLMOD/Utility/cholmod_l_sbound.c deleted file mode 100644 index 7cc46b496c..0000000000 --- a/CHOLMOD/Utility/cholmod_l_sbound.c +++ /dev/null @@ -1,18 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/cholmod_l_sbound: bound diagonal of LDL (single, int64) -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -#define CHOLMOD_BOUND_FUNCTION cholmod_l_sbound -#define COMMON_BOUND (Common->sbound) -#define COMMON_BOUNDS_HIT (Common->nsbounds_hit) -#define Real float - -#define CHOLMOD_INT64 -#include "t_cholmod_bound.c" - diff --git a/CHOLMOD/Utility/cholmod_l_score_comp.c b/CHOLMOD/Utility/cholmod_l_score_comp.c deleted file mode 100644 index b654c9e1d3..0000000000 --- a/CHOLMOD/Utility/cholmod_l_score_comp.c +++ /dev/null @@ -1,13 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/cholmod_l_score_comp: for sorting supernodes -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -#define CHOLMOD_INT64 -#include "t_cholmod_score_comp.c" - diff --git a/CHOLMOD/Utility/cholmod_l_set_empty.c b/CHOLMOD/Utility/cholmod_l_set_empty.c deleted file mode 100644 index 0d20de058f..0000000000 --- a/CHOLMOD/Utility/cholmod_l_set_empty.c +++ /dev/null @@ -1,13 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/cholmod_l_set_empty: set an int64 array to EMPTY -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -#define CHOLMOD_INT64 -#include "t_cholmod_set_empty.c" - diff --git a/CHOLMOD/Utility/cholmod_l_sort.c b/CHOLMOD/Utility/cholmod_l_sort.c deleted file mode 100644 index b64f074396..0000000000 --- a/CHOLMOD/Utility/cholmod_l_sort.c +++ /dev/null @@ -1,13 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/cholmod_l_sort: sort a sparse matrix -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -#define CHOLMOD_INT64 -#include "t_cholmod_sort.c" - diff --git a/CHOLMOD/Utility/cholmod_l_sparse_to_dense.c b/CHOLMOD/Utility/cholmod_l_sparse_to_dense.c deleted file mode 100644 index 6889cdf505..0000000000 --- a/CHOLMOD/Utility/cholmod_l_sparse_to_dense.c +++ /dev/null @@ -1,13 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/cholmod_l_sparse_to_dense: convert a sparse matrix to dense -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -#define CHOLMOD_INT64 -#include "t_cholmod_sparse_to_dense.c" - diff --git a/CHOLMOD/Utility/cholmod_l_sparse_to_triplet.c b/CHOLMOD/Utility/cholmod_l_sparse_to_triplet.c deleted file mode 100644 index f3b819b52b..0000000000 --- a/CHOLMOD/Utility/cholmod_l_sparse_to_triplet.c +++ /dev/null @@ -1,13 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/cholmod_l_sparse_to_triplet: convert sparse to triplet -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -#define CHOLMOD_INT64 -#include "t_cholmod_sparse_to_triplet.c" - diff --git a/CHOLMOD/Utility/cholmod_l_speye.c b/CHOLMOD/Utility/cholmod_l_speye.c deleted file mode 100644 index 5f8e951099..0000000000 --- a/CHOLMOD/Utility/cholmod_l_speye.c +++ /dev/null @@ -1,13 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/cholmod_l_speye: sparse identity matrix -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -#define CHOLMOD_INT64 -#include "t_cholmod_speye.c" - diff --git a/CHOLMOD/Utility/cholmod_l_spzeros.c b/CHOLMOD/Utility/cholmod_l_spzeros.c deleted file mode 100644 index 857d2e64ce..0000000000 --- a/CHOLMOD/Utility/cholmod_l_spzeros.c +++ /dev/null @@ -1,13 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/cholmod_l_spzeros: all-zero sparse matrix -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -#define CHOLMOD_INT64 -#include "t_cholmod_spzeros.c" - diff --git a/CHOLMOD/Utility/cholmod_l_start.c b/CHOLMOD/Utility/cholmod_l_start.c deleted file mode 100644 index a0ed14a57b..0000000000 --- a/CHOLMOD/Utility/cholmod_l_start.c +++ /dev/null @@ -1,13 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/cholmod_l_start: start CHOLMOD (int64 version) -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -#define CHOLMOD_INT64 -#include "t_cholmod_start.c" - diff --git a/CHOLMOD/Utility/cholmod_l_transpose_sym.c b/CHOLMOD/Utility/cholmod_l_transpose_sym.c deleted file mode 100644 index b844026a78..0000000000 --- a/CHOLMOD/Utility/cholmod_l_transpose_sym.c +++ /dev/null @@ -1,13 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/cholmod_l_transpose_sym: symmetric permuted transpose -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -#define CHOLMOD_INT64 -#include "t_cholmod_transpose_sym.c" - diff --git a/CHOLMOD/Utility/cholmod_l_transpose_unsym.c b/CHOLMOD/Utility/cholmod_l_transpose_unsym.c deleted file mode 100644 index 264ecabb6e..0000000000 --- a/CHOLMOD/Utility/cholmod_l_transpose_unsym.c +++ /dev/null @@ -1,13 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/cholmod_l_transpose_unsym: unsymmetric permuted transpose -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -#define CHOLMOD_INT64 -#include "t_cholmod_transpose_unsym.c" - diff --git a/CHOLMOD/Utility/cholmod_l_triplet_to_sparse.c b/CHOLMOD/Utility/cholmod_l_triplet_to_sparse.c deleted file mode 100644 index 31e7126e6e..0000000000 --- a/CHOLMOD/Utility/cholmod_l_triplet_to_sparse.c +++ /dev/null @@ -1,13 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/cholmod_l_triplet_to_sparse: convert triplet to sparse -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -#define CHOLMOD_INT64 -#include "t_cholmod_triplet_to_sparse.c" - diff --git a/CHOLMOD/Utility/cholmod_l_xtype.c b/CHOLMOD/Utility/cholmod_l_xtype.c deleted file mode 100644 index 1f8703271f..0000000000 --- a/CHOLMOD/Utility/cholmod_l_xtype.c +++ /dev/null @@ -1,13 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/cholmod_l_xtype.c: change xtype and/or dtype -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -#define CHOLMOD_INT64 -#include "t_cholmod_change_xdtype.c" - diff --git a/CHOLMOD/Utility/cholmod_l_zeros.c b/CHOLMOD/Utility/cholmod_l_zeros.c deleted file mode 100644 index 8868d51658..0000000000 --- a/CHOLMOD/Utility/cholmod_l_zeros.c +++ /dev/null @@ -1,13 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/cholmod_l_zeros: allocate an all-zero dense matrix -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -#define CHOLMOD_INT64 -#include "t_cholmod_zeros.c" - diff --git a/CHOLMOD/Utility/cholmod_malloc.c b/CHOLMOD/Utility/cholmod_malloc.c deleted file mode 100644 index 8946b189dd..0000000000 --- a/CHOLMOD/Utility/cholmod_malloc.c +++ /dev/null @@ -1,15 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/cholmod_malloc: malloc (int32 version) -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -#define CHOLMOD_ALLOC_FUNCTION cholmod_malloc -#define SUITESPARSE_ALLOC_FUNCTION SuiteSparse_malloc -#define CHOLMOD_INT32 -#include "t_cholmod_malloc.c" - diff --git a/CHOLMOD/Utility/cholmod_maxrank.c b/CHOLMOD/Utility/cholmod_maxrank.c deleted file mode 100644 index 713cfcd405..0000000000 --- a/CHOLMOD/Utility/cholmod_maxrank.c +++ /dev/null @@ -1,13 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/cholmod_maxrank: find valid value of Common->maxrank -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -#define CHOLMOD_INT32 -#include "t_cholmod_maxrank.c" - diff --git a/CHOLMOD/Utility/cholmod_memdebug.c b/CHOLMOD/Utility/cholmod_memdebug.c deleted file mode 100644 index eda9d86340..0000000000 --- a/CHOLMOD/Utility/cholmod_memdebug.c +++ /dev/null @@ -1,182 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/cholmod_memdebug: memory debugging -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis -// All Rights Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -#include "cholmod_internal.h" - -#ifndef NDEBUG - - #define CM_MEMTABLE_SIZE 10000 - static void *memtable_p [CM_MEMTABLE_SIZE] ; - static size_t memtable_s [CM_MEMTABLE_SIZE] ; - static int nmemtable = 0 ; - -//------------------------------------------------------------------------------ -// CM_memtable_dump: dump the memtable -//------------------------------------------------------------------------------ - -void CM_memtable_dump (void) -{ - printf ("\nmemtable dump: %d\n", nmemtable) ; - for (int k = 0 ; k < nmemtable ; k++) - { - printf (" %4d: %12p : %ld\n", k, memtable_p [k], memtable_s [k]) ; - } -} - -//------------------------------------------------------------------------------ -// CM_memtable_n: return # of items in the memtable -//------------------------------------------------------------------------------ - -int CM_memtable_n (void) -{ - return (nmemtable) ; -} - -//------------------------------------------------------------------------------ -// CM_memtable_clear: clear the memtable -//------------------------------------------------------------------------------ - -void CM_memtable_clear (void) -{ - nmemtable = 0 ; -} - -//------------------------------------------------------------------------------ -// CM_memtable_add: add a pointer to the memtable of malloc'd blocks -//------------------------------------------------------------------------------ - -void CM_memtable_add (void *p, size_t size) -{ - if (p == NULL) return ; - - bool fail = false ; - #ifdef CM_MEMDUMP - printf ("memtable add %p size %ld\n", p, size) ; - #endif - - int n = nmemtable ; - fail = (n > CM_MEMTABLE_SIZE) ; - if (!fail) - { - for (int i = 0 ; i < n ; i++) - { - if (p == memtable_p [i]) - { - printf ("\nadd duplicate %p size %ld\n", p, size) ; - CM_memtable_dump ( ) ; - fail = true ; - break ; - } - } - } - if (!fail && p != NULL) - { - memtable_p [n] = p ; - memtable_s [n] = size ; - nmemtable++ ; - } - - ASSERT (!fail) ; - #ifdef CM_MEMDUMP - CM_memtable_dump ( ) ; - #endif -} - -//------------------------------------------------------------------------------ -// CM_memtable_size: get the size of a malloc'd block -//------------------------------------------------------------------------------ - -size_t CM_memtable_size (void *p) -{ - size_t size = 0 ; - - if (p == NULL) return (0) ; - bool found = false ; - - int n = nmemtable ; - for (int i = 0 ; i < n ; i++) - { - if (p == memtable_p [i]) - { - size = memtable_s [i] ; - found = true ; - break ; - } - } - - if (!found) - { - printf ("\nFAIL: %p not found\n", p) ; - CM_memtable_dump ( ) ; - ASSERT (0) ; - } - return (size) ; -} - -//------------------------------------------------------------------------------ -// CM_memtable_find: test if a malloc'd block is in the table -//------------------------------------------------------------------------------ - -bool CM_memtable_find (void *p) -{ - bool found = false ; - if (p == NULL) return (false) ; - int n = nmemtable ; - for (int i = 0 ; i < n ; i++) - { - if (p == memtable_p [i]) - { - found = true ; - break ; - } - } - return (found) ; -} - -//------------------------------------------------------------------------------ -// CM_memtable_remove: remove a pointer from the table of malloc'd blocks -//------------------------------------------------------------------------------ - -void CM_memtable_remove (void *p) -{ - if (p == NULL) return ; - - bool found = false ; - #ifdef CM_MEMDUMP - printf ("memtable remove %p ", p) ; - #endif - - int n = nmemtable ; - for (int i = 0 ; i < n ; i++) - { - if (p == memtable_p [i]) - { - // found p in the table; remove it - memtable_p [i] = memtable_p [n-1] ; - memtable_s [i] = memtable_s [n-1] ; - nmemtable -- ; - found = true ; - break ; - } - } - - if (!found) - { - printf ("remove %p NOT FOUND\n", p) ; - CM_memtable_dump ( ) ; - } - ASSERT (found) ; - #ifdef CM_MEMDUMP - CM_memtable_dump ( ) ; - #endif -} - -#endif - diff --git a/CHOLMOD/Utility/cholmod_mult_size_t.c b/CHOLMOD/Utility/cholmod_mult_size_t.c deleted file mode 100644 index 09a3a0163b..0000000000 --- a/CHOLMOD/Utility/cholmod_mult_size_t.c +++ /dev/null @@ -1,13 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/cholmod_mult_size_t: multiply two size_t values -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -#define CHOLMOD_INT32 -#include "t_cholmod_mult_size_t.c" - diff --git a/CHOLMOD/Utility/cholmod_mult_uint64_t.c b/CHOLMOD/Utility/cholmod_mult_uint64_t.c deleted file mode 100644 index 42a3a46530..0000000000 --- a/CHOLMOD/Utility/cholmod_mult_uint64_t.c +++ /dev/null @@ -1,90 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/cholmod_mult_uint64_t: multiply two uint64_t values -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. This file is licensed the same as GraphBLAS (Apache-2.0). -// SPDX-License-Identifier: Apache-2.0 - -//------------------------------------------------------------------------------ - -// c = a*b but check for overflow - -// If c=a*b is large, c = UINT64_MAX is set, and the function returns false. -// "large" means that c=a*b might overflow; see details below. - -// Otherwise c = a*b < INT64_MAX is guaranteed to be returned, and the function -// returns true. - -// Derived from GraphBLAS/Source/GB_uint64_multiply. - -#include "cholmod_internal.h" - -bool cholmod_mult_uint64_t // c = a*b, return true if ok -( - uint64_t *restrict c, - const uint64_t a, - const uint64_t b -) -{ - - if (a <= 1 || b <= 1) - { - (*c) = a*b ; - return (true) ; - } - - uint64_t a1 = a >> 30 ; // a1 = a / 2^30 - uint64_t b1 = b >> 30 ; // b1 = b / 2^30 - if (a1 > 0 && b1 > 0) - { - // c = a*b will likely overflow, since both a and b are >= 2^30 and - // thus c >= 2^60. This is slightly pessimistic. - (*c) = UINT64_MAX ; - return (false) ; - } - - // a = a1 * 2^30 + a0 - uint64_t a0 = a & 0x3FFFFFFFL ; - - // b = b1 * 2^30 + b0 - uint64_t b0 = b & 0x3FFFFFFFL ; - - // a*b = (a1*b1) * 2^60 + (a1*b0 + a0*b1) * 2^30 + a0*b0 - - // since either a1 or b1 are zero, a1*b1 is zero - - // a0, b0 are < 2^30 - // a1, b1 are < 2^34 - - // a1*b0 < 2^64 - // a0*b1 < 2^64 - // a0*b0 < 2^60 - // thus - - // a*b = (a1*b0 + a0*b1) * 2^30 + a0*b0 - // < (2^64 + 2^64 ) * 2^30 + 2^60 - - // so it is safe to compute t0 and t1 without risk of overflow: - - uint64_t t0 = a1*b0 ; - uint64_t t1 = a0*b1 ; - - // a*b = (t0 + t1) * 2^30 + a0*b0 - - if (t0 >= 0x40000000L || t1 >= 0x40000000L) - { - // t >= 2^31, so t * 2^30 might overflow. This is also slightly - // pessimistic, but good enough for the usage of this function. - (*c) = UINT64_MAX ; - return (false) ; - } - - // t = t0 + t1 < 2^30 + 2^30 < 2^31, so - - // c = a*b = t * 2^30 + a0*b0 < 2^61 + 2^60 < 2^62, no overflow possible - uint64_t t = t0 + t1 ; - (*c) = (t << 30) + a0*b0 ; - return (true) ; -} - diff --git a/CHOLMOD/Utility/cholmod_nnz.c b/CHOLMOD/Utility/cholmod_nnz.c deleted file mode 100644 index 2464e541ca..0000000000 --- a/CHOLMOD/Utility/cholmod_nnz.c +++ /dev/null @@ -1,13 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/cholmod_nnz: # of entries in a sparse matrix -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -#define CHOLMOD_INT32 -#include "t_cholmod_nnz.c" - diff --git a/CHOLMOD/Utility/cholmod_ones.c b/CHOLMOD/Utility/cholmod_ones.c deleted file mode 100644 index c237afcdf8..0000000000 --- a/CHOLMOD/Utility/cholmod_ones.c +++ /dev/null @@ -1,13 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/cholmod_ones: dense matrix of all ones -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -#define CHOLMOD_INT32 -#include "t_cholmod_ones.c" - diff --git a/CHOLMOD/Utility/cholmod_pack_factor.c b/CHOLMOD/Utility/cholmod_pack_factor.c deleted file mode 100644 index d1943828ea..0000000000 --- a/CHOLMOD/Utility/cholmod_pack_factor.c +++ /dev/null @@ -1,13 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/cholmod_pack_factor: pack a simplicial factorization -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -#define CHOLMOD_INT32 -#include "t_cholmod_pack_factor.c" - diff --git a/CHOLMOD/Utility/cholmod_ptranspose.c b/CHOLMOD/Utility/cholmod_ptranspose.c deleted file mode 100644 index a06e1244d0..0000000000 --- a/CHOLMOD/Utility/cholmod_ptranspose.c +++ /dev/null @@ -1,13 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/cholmod_ptranspose: permuted transpose -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -#define CHOLMOD_INT32 -#include "t_cholmod_ptranspose.c" - diff --git a/CHOLMOD/Utility/cholmod_realloc.c b/CHOLMOD/Utility/cholmod_realloc.c deleted file mode 100644 index 3346b660d5..0000000000 --- a/CHOLMOD/Utility/cholmod_realloc.c +++ /dev/null @@ -1,13 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/cholmod_realloc: realloc (int32 version) -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -#define CHOLMOD_INT32 -#include "t_cholmod_realloc.c" - diff --git a/CHOLMOD/Utility/cholmod_realloc_multiple.c b/CHOLMOD/Utility/cholmod_realloc_multiple.c deleted file mode 100644 index 0124dcac52..0000000000 --- a/CHOLMOD/Utility/cholmod_realloc_multiple.c +++ /dev/null @@ -1,13 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/cholmod_realloc_multiple: multiple realloc (int32 version) -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -#define CHOLMOD_INT32 -#include "t_cholmod_realloc_multiple.c" - diff --git a/CHOLMOD/Utility/cholmod_reallocate_column.c b/CHOLMOD/Utility/cholmod_reallocate_column.c deleted file mode 100644 index 09d880bb8e..0000000000 --- a/CHOLMOD/Utility/cholmod_reallocate_column.c +++ /dev/null @@ -1,13 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/cholmod_reallocate_column: reallocate a column of a factor -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -#define CHOLMOD_INT32 -#include "t_cholmod_reallocate_column.c" - diff --git a/CHOLMOD/Utility/cholmod_reallocate_factor.c b/CHOLMOD/Utility/cholmod_reallocate_factor.c deleted file mode 100644 index 4ca9c01bda..0000000000 --- a/CHOLMOD/Utility/cholmod_reallocate_factor.c +++ /dev/null @@ -1,13 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/cholmod_reallocate_factor: reallocate a factor -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -#define CHOLMOD_INT32 -#include "t_cholmod_reallocate_factor.c" - diff --git a/CHOLMOD/Utility/cholmod_reallocate_sparse.c b/CHOLMOD/Utility/cholmod_reallocate_sparse.c deleted file mode 100644 index 943b247928..0000000000 --- a/CHOLMOD/Utility/cholmod_reallocate_sparse.c +++ /dev/null @@ -1,13 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/cholmod_reallocate_sparse: reallocate sparse matrix -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -#define CHOLMOD_INT32 -#include "t_cholmod_reallocate_sparse.c" - diff --git a/CHOLMOD/Utility/cholmod_reallocate_triplet.c b/CHOLMOD/Utility/cholmod_reallocate_triplet.c deleted file mode 100644 index 90c27b4eee..0000000000 --- a/CHOLMOD/Utility/cholmod_reallocate_triplet.c +++ /dev/null @@ -1,13 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/cholmod_reallocate_triplet: reallocate triplet matrix -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -#define CHOLMOD_INT32 -#include "t_cholmod_reallocate_triplet.c" - diff --git a/CHOLMOD/Utility/cholmod_sbound.c b/CHOLMOD/Utility/cholmod_sbound.c deleted file mode 100644 index e0764502a4..0000000000 --- a/CHOLMOD/Utility/cholmod_sbound.c +++ /dev/null @@ -1,18 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/cholmod_sbound: bound diagonal of LDL (single, int32) -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -#define CHOLMOD_BOUND_FUNCTION cholmod_sbound -#define COMMON_BOUND (Common->sbound) -#define COMMON_BOUNDS_HIT (Common->nsbounds_hit) -#define Real float - -#define CHOLMOD_INT32 -#include "t_cholmod_bound.c" - diff --git a/CHOLMOD/Utility/cholmod_score_comp.c b/CHOLMOD/Utility/cholmod_score_comp.c deleted file mode 100644 index 1863d82018..0000000000 --- a/CHOLMOD/Utility/cholmod_score_comp.c +++ /dev/null @@ -1,13 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/cholmod_score_comp: for sorting supernodes -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -#define CHOLMOD_INT32 -#include "t_cholmod_score_comp.c" - diff --git a/CHOLMOD/Utility/cholmod_set_empty.c b/CHOLMOD/Utility/cholmod_set_empty.c deleted file mode 100644 index 68d476f01c..0000000000 --- a/CHOLMOD/Utility/cholmod_set_empty.c +++ /dev/null @@ -1,13 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/cholmod_set_empty: set an int32 array to EMPTY -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -#define CHOLMOD_INT32 -#include "t_cholmod_set_empty.c" - diff --git a/CHOLMOD/Utility/cholmod_sort.c b/CHOLMOD/Utility/cholmod_sort.c deleted file mode 100644 index 7259eab6fb..0000000000 --- a/CHOLMOD/Utility/cholmod_sort.c +++ /dev/null @@ -1,13 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/cholmod_sort: sort a sparse matrix -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -#define CHOLMOD_INT32 -#include "t_cholmod_sort.c" - diff --git a/CHOLMOD/Utility/cholmod_sparse_to_dense.c b/CHOLMOD/Utility/cholmod_sparse_to_dense.c deleted file mode 100644 index 8d92f7f2a0..0000000000 --- a/CHOLMOD/Utility/cholmod_sparse_to_dense.c +++ /dev/null @@ -1,13 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/cholmod_sparse_to_dense: convert a sparse matrix to dense -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -#define CHOLMOD_INT32 -#include "t_cholmod_sparse_to_dense.c" - diff --git a/CHOLMOD/Utility/cholmod_speye.c b/CHOLMOD/Utility/cholmod_speye.c deleted file mode 100644 index 877aa7be1d..0000000000 --- a/CHOLMOD/Utility/cholmod_speye.c +++ /dev/null @@ -1,13 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/cholmod_speye: sparse identity matrix -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -#define CHOLMOD_INT32 -#include "t_cholmod_speye.c" - diff --git a/CHOLMOD/Utility/cholmod_spzeros.c b/CHOLMOD/Utility/cholmod_spzeros.c deleted file mode 100644 index 94ae9840e4..0000000000 --- a/CHOLMOD/Utility/cholmod_spzeros.c +++ /dev/null @@ -1,13 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/cholmod_spzeros: all-zero sparse matrix -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -#define CHOLMOD_INT32 -#include "t_cholmod_spzeros.c" - diff --git a/CHOLMOD/Utility/cholmod_start.c b/CHOLMOD/Utility/cholmod_start.c deleted file mode 100644 index 35ac72ec39..0000000000 --- a/CHOLMOD/Utility/cholmod_start.c +++ /dev/null @@ -1,13 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/cholmod_start: start CHOLMOD (int32 version) -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -#define CHOLMOD_INT32 -#include "t_cholmod_start.c" - diff --git a/CHOLMOD/Utility/cholmod_transpose.c b/CHOLMOD/Utility/cholmod_transpose.c deleted file mode 100644 index 6949bd5f51..0000000000 --- a/CHOLMOD/Utility/cholmod_transpose.c +++ /dev/null @@ -1,13 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/cholmod_transpose: transpose a sparse matrix -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -#define CHOLMOD_INT32 -#include "t_cholmod_transpose.c" - diff --git a/CHOLMOD/Utility/cholmod_transpose_sym.c b/CHOLMOD/Utility/cholmod_transpose_sym.c deleted file mode 100644 index b82c177dd4..0000000000 --- a/CHOLMOD/Utility/cholmod_transpose_sym.c +++ /dev/null @@ -1,13 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/cholmod_transpose_sym: symmetric permuted transpose -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -#define CHOLMOD_INT32 -#include "t_cholmod_transpose_sym.c" - diff --git a/CHOLMOD/Utility/cholmod_transpose_unsym.c b/CHOLMOD/Utility/cholmod_transpose_unsym.c deleted file mode 100644 index 69c1af7bf9..0000000000 --- a/CHOLMOD/Utility/cholmod_transpose_unsym.c +++ /dev/null @@ -1,13 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/cholmod_transpose_unsym: unsymmetric permuted transpose -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -#define CHOLMOD_INT32 -#include "t_cholmod_transpose_unsym.c" - diff --git a/CHOLMOD/Utility/cholmod_triplet_to_sparse.c b/CHOLMOD/Utility/cholmod_triplet_to_sparse.c deleted file mode 100644 index 343ff3ed67..0000000000 --- a/CHOLMOD/Utility/cholmod_triplet_to_sparse.c +++ /dev/null @@ -1,13 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/cholmod_triplet_to_sparse: convert triplet to sparse -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -#define CHOLMOD_INT32 -#include "t_cholmod_triplet_to_sparse.c" - diff --git a/CHOLMOD/Utility/cholmod_version.c b/CHOLMOD/Utility/cholmod_version.c deleted file mode 100644 index bcedb35f15..0000000000 --- a/CHOLMOD/Utility/cholmod_version.c +++ /dev/null @@ -1,13 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/cholmod_version: CHOLMOD version -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -#define CHOLMOD_INT32 -#include "t_cholmod_version.c" - diff --git a/CHOLMOD/Utility/cholmod_xtype.c b/CHOLMOD/Utility/cholmod_xtype.c deleted file mode 100644 index f6b38821bd..0000000000 --- a/CHOLMOD/Utility/cholmod_xtype.c +++ /dev/null @@ -1,13 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/cholmod_xtype.c: change xtype and/or dtype -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -#define CHOLMOD_INT32 -#include "t_cholmod_change_xdtype.c" - diff --git a/CHOLMOD/Utility/cholmod_zeros.c b/CHOLMOD/Utility/cholmod_zeros.c deleted file mode 100644 index a15ab703cf..0000000000 --- a/CHOLMOD/Utility/cholmod_zeros.c +++ /dev/null @@ -1,13 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/cholmod_zeros: allocate an all-zero dense matrix -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -#define CHOLMOD_INT32 -#include "t_cholmod_zeros.c" - diff --git a/CHOLMOD/Utility/t_cholmod_aat.c b/CHOLMOD/Utility/t_cholmod_aat.c deleted file mode 100644 index 4147879c84..0000000000 --- a/CHOLMOD/Utility/t_cholmod_aat.c +++ /dev/null @@ -1,260 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/t_cholmod_aat: compute A*A' or A(:,f)*A(:,f)' -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -// C = A*A' or C = A(:,f)*A(:,f)', where for complex/zomplex matrices, A' can -// be computed as a matrix (complex conjugate) transpose, or an array (complex -// non-conjugate) transpose. On output the C->stype is zero. The input matrix -// A must have A->stype = 0. - -// workspace: -// Iwork of size max (nrow,ncol) -// Xwork of size n if real and mode > 0, or 2*n if complex and mode > 0 - -// The mode parameter: -// 2 numerical, with conjugate transpose -// 1 numerical, with non-conjugate transpose -// 0 pattern, keeping the diagonal -// -1 pattern, remove the diagonal -// -2 pattern, and add 50% + n extra space to C -// as elbow room for AMD and CAMD, when converting -// a symmetric matrix A to an unsymmetric matrix C - -#include "cholmod_internal.h" - -#define RETURN_IF_ERROR \ - if (Common->status < CHOLMOD_OK) \ - { \ - CHOLMOD(free_sparse) (&C, Common) ; \ - CHOLMOD(free_sparse) (&F, Common) ; \ - return (NULL) ; \ - } - -//------------------------------------------------------------------------------ -// t_cholmod_aat_worker template -//------------------------------------------------------------------------------ - -#define PATTERN -#include "t_cholmod_aat_worker.c" - -#define DOUBLE -#define REAL -#include "t_cholmod_aat_worker.c" -#define COMPLEX -#include "t_cholmod_aat_worker.c" -#define ZOMPLEX -#include "t_cholmod_aat_worker.c" - -#undef DOUBLE -#define SINGLE -#define REAL -#include "t_cholmod_aat_worker.c" -#define COMPLEX -#include "t_cholmod_aat_worker.c" -#define ZOMPLEX -#include "t_cholmod_aat_worker.c" - -//------------------------------------------------------------------------------ -// cholmod_aat: C=A*A' or A(:,f)*A(:,f)' -//------------------------------------------------------------------------------ - -cholmod_sparse *CHOLMOD(aat) -( - cholmod_sparse *A, // input matrix - Int *fset, // a list of column indices in range 0:A->ncol-1 - size_t fsize, // # of entries in fset - int mode, // 2: numerical (conj), 1: numerical (non-conj.), - // 0: pattern (with diag), -1: pattern (remove diag), - // -2: pattern (remove diag; add ~50% extra space in C) - cholmod_common *Common -) -{ - - //-------------------------------------------------------------------------- - // check inputs - //-------------------------------------------------------------------------- - - RETURN_IF_NULL_COMMON (NULL) ; - RETURN_IF_SPARSE_MATRIX_INVALID (A, NULL) ; - Common->status = CHOLMOD_OK ; - cholmod_sparse *C = NULL, *F = NULL ; - ASSERT (CHOLMOD(dump_sparse) (A, "aat:A", Common) >= 0) ; - - if (A->stype != 0) - { - ERROR (CHOLMOD_INVALID, "input matrix must be unsymmetric") ; - return (NULL) ; - } - - //-------------------------------------------------------------------------- - // get inputs - //-------------------------------------------------------------------------- - - bool ignore_diag = (mode < 0) ; - bool values = (mode > 0) && (A->xtype != CHOLMOD_PATTERN) ; - int axtype = (values) ? A->xtype : CHOLMOD_PATTERN ; - bool conj = (mode >= 2) ; - - Int nrow = A->nrow ; - Int ncol = A->ncol ; - Int n = A->nrow ; - - Int *Ap = (Int *) A->p ; - Int *Anz = (Int *) A->nz ; - Int *Ai = (Int *) A->i ; - bool packed = A->packed ; - - //-------------------------------------------------------------------------- - // get the sizes of the entries of C and A - //-------------------------------------------------------------------------- - - size_t ei = sizeof (Int) ; - size_t e = (A->dtype == CHOLMOD_SINGLE) ? sizeof (float) : sizeof (double) ; - size_t ew = ((axtype == CHOLMOD_PATTERN) ? 0 : - ((axtype == CHOLMOD_COMPLEX) ? 2 : 1)) ; - size_t ex = e * ew ; - size_t ez = e * ((axtype == CHOLMOD_ZOMPLEX) ? 1 : 0) ; - - //-------------------------------------------------------------------------- - // allocate workspace - //-------------------------------------------------------------------------- - - CHOLMOD(alloc_work) (0, MAX (ncol, nrow), ew, A->dtype, Common) ; - RETURN_IF_ERROR ; - - //-------------------------------------------------------------------------- - // construct the transpose F = A' or F = A(:,f)', or complex conjugate - //-------------------------------------------------------------------------- - - // no row permutation (Perm is NULL) - // uses Common->Iwork if fset is not NULL - F = CHOLMOD(ptranspose) (A, mode, /* Perm: */ NULL, fset, fsize, Common) ; - RETURN_IF_ERROR ; - - Int *Fp = (Int *) F->p ; - Int *Fi = (Int *) F->i ; - - Int *W = Common->Iwork ; // size n, not yet initialized - CHOLMOD(set_empty) (W, n) ; // W [0..n-1] = EMPTY - - //-------------------------------------------------------------------------- - // cnz = nnz (C) - //-------------------------------------------------------------------------- - - int64_t cnz = 0 ; - for (Int j = 0 ; j < n ; j++) - { - - //---------------------------------------------------------------------- - // If W [i] != jmark then row i has not yet been seen in C(:,j) - //---------------------------------------------------------------------- - - Int jmark = -j-2 ; - - //---------------------------------------------------------------------- - // compute # of entries in C(:,j) = A*F(:,j) - //---------------------------------------------------------------------- - - for (Int pf = Fp [j] ; pf < Fp [j+1] ; pf++) - { - - //------------------------------------------------------------------ - // get the F(t,j) entry - //------------------------------------------------------------------ - - Int t = Fi [pf] ; - - //------------------------------------------------------------------ - // add any entries A(i,t) not already in C(:,j) pattern - //------------------------------------------------------------------ - - Int p = Ap [t] ; - Int pend = (packed) ? (Ap [t+1]) : (p + Anz [t]) ; - for ( ; p < pend ; p++) - { - // get A(i,t); it is seen for first time if W [i] != jmark - Int i = Ai [p] ; - if (ignore_diag && i == j) continue ; - if (W [i] != jmark) - { - W [i] = jmark ; - cnz++ ; - } - } - } - - //---------------------------------------------------------------------- - // check for integer overflow - //---------------------------------------------------------------------- - - if (cnz < 0 || cnz >= Int_max / sizeof (Int)) - { - Common->status = CHOLMOD_TOO_LARGE ; - break ; - } - } - - RETURN_IF_ERROR ; - - //-------------------------------------------------------------------------- - // allocate C - //-------------------------------------------------------------------------- - - size_t cnzmax = cnz + ((mode == -2) ? (cnz/2 + n) : 0) ; - C = CHOLMOD(allocate_sparse) (n, n, cnzmax, - /* C is not sorted: */ FALSE, /* C is packed: */ TRUE, - /* C stype: */ 0, axtype + A->dtype, Common) ; - RETURN_IF_ERROR ; - - //-------------------------------------------------------------------------- - // compute the pattern and values of C - //-------------------------------------------------------------------------- - - switch ((C->xtype + C->dtype) % 8) - { - - default: - p_cholmod_aat_worker (C, A, F, ignore_diag, Common) ; - break ; - - case CHOLMOD_SINGLE + CHOLMOD_REAL: - r_s_cholmod_aat_worker (C, A, F, ignore_diag, Common) ; - break ; - - case CHOLMOD_SINGLE + CHOLMOD_COMPLEX: - c_s_cholmod_aat_worker (C, A, F, ignore_diag, Common) ; - break ; - - case CHOLMOD_SINGLE + CHOLMOD_ZOMPLEX: - z_s_cholmod_aat_worker (C, A, F, ignore_diag, Common) ; - break ; - - case CHOLMOD_DOUBLE + CHOLMOD_REAL: - r_cholmod_aat_worker (C, A, F, ignore_diag, Common) ; - break ; - - case CHOLMOD_DOUBLE + CHOLMOD_COMPLEX: - c_cholmod_aat_worker (C, A, F, ignore_diag, Common) ; - break ; - - case CHOLMOD_DOUBLE + CHOLMOD_ZOMPLEX: - z_cholmod_aat_worker (C, A, F, ignore_diag, Common) ; - break ; - } - - //-------------------------------------------------------------------------- - // free workspace and return result - //-------------------------------------------------------------------------- - - DEBUG (size_t nnzdiag = CHOLMOD(dump_sparse) (C, "aat:C", Common)) ; - ASSERT (IMPLIES (ignore_diag, nnzdiag == 0)) ; - CHOLMOD(free_sparse) (&F, Common) ; - return (C) ; -} - diff --git a/CHOLMOD/Utility/t_cholmod_aat_worker.c b/CHOLMOD/Utility/t_cholmod_aat_worker.c deleted file mode 100644 index 07dda10d05..0000000000 --- a/CHOLMOD/Utility/t_cholmod_aat_worker.c +++ /dev/null @@ -1,142 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/t_cholmod_aat_worker: C = A*A' or A(:,f)*A*(:,f)' -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -#include "cholmod_template.h" - -static void TEMPLATE (cholmod_aat_worker) -( - cholmod_sparse *C, // output matrix - cholmod_sparse *A, // input matrix, not modified - cholmod_sparse *F, // input matrix, not modified, F = A' or A(:,f)' - bool ignore_diag, // if true, ignore diagonal - cholmod_common *Common -) -{ - - //-------------------------------------------------------------------------- - // check inputs - //-------------------------------------------------------------------------- - - ASSERT (A->stype == 0) ; - ASSERT (C->stype == 0) ; - - //-------------------------------------------------------------------------- - // get inputs - //-------------------------------------------------------------------------- - - Int n = A->nrow ; - Int *Ap = (Int *) A->p ; - Int *Anz = (Int *) A->nz ; - Int *Ai = (Int *) A->i ; - Real *Ax = (Real *) A->x ; - Real *Az = (Real *) A->z ; - bool packed = A->packed ; - - Int *Fp = (Int *) F->p ; - Int *Fi = (Int *) F->i ; - Real *Fx = (Real *) F->x ; - Real *Fz = (Real *) F->z ; - ASSERT (F->packed) ; - - Int *Cp = (Int *) C->p ; - Int *Ci = (Int *) C->i ; - Real *Cx = (Real *) C->x ; - Real *Cz = (Real *) C->z ; - ASSERT (C->packed) ; - - //-------------------------------------------------------------------------- - // get workspace - //-------------------------------------------------------------------------- - - // W is all negative, because jmark in t_cholmod_aat is always negative. - - Int *W = Common->Iwork ; // size n, all < 0 - #ifndef NDEBUG - for (Int i = 0 ; i < n ; i++) - { - ASSERT (W [i] < 0) ; - } - #endif - - //-------------------------------------------------------------------------- - // C = A*A' or A(:,f)*A(:,f)' - //-------------------------------------------------------------------------- - - Int pc = 0 ; - - for (Int j = 0 ; j < n ; j++) - { - - //---------------------------------------------------------------------- - // log the start of C(:,j) - //---------------------------------------------------------------------- - - Int pc_start = pc ; - Cp [j] = pc ; - - //---------------------------------------------------------------------- - // compute C(:,j) = A*F(:,j) - //---------------------------------------------------------------------- - - for (Int pf = Fp [j] ; pf < Fp [j+1] ; pf++) - { - - //------------------------------------------------------------------ - // get the F(t,j) entry - //------------------------------------------------------------------ - - Int t = Fi [pf] ; - Real fx [2] = {0,0} ; - Real fz [1] = {0} ; - ASSIGN (fx, fz, 0, Fx, Fz, pf) ; - - //------------------------------------------------------------------ - // C(:,j) += A(:,t)*F(t,j) - //------------------------------------------------------------------ - - Int p = Ap [t] ; - Int pend = (packed) ? (Ap [t+1]) : (p + Anz [t]) ; - for ( ; p < pend ; p++) - { - // get the A(i,t) entry - Int i = Ai [p] ; - if (ignore_diag && i == j) continue ; - Int pi = W [i] ; - if (pi < pc_start) - { - // C(i,j) is a new entry; log its position - Ci [pc] = i ; - W [i] = pc ; - // C(i,j) = A(i,t) * F(t,j) - MULT (Cx, Cz, pc, Ax, Az, p, fx, fz, 0) ; - pc++ ; - } - else - { - // C(i,j) exists in C(:,j) at position pi - // C(i,j) += A(i,t) * F(t,j) - MULTADD (Cx, Cz, pi, Ax, Az, p, fx, fz, 0) ; - } - } - } - } - - //-------------------------------------------------------------------------- - // log the end of the last column of C - //-------------------------------------------------------------------------- - - Cp [n] = pc ; -} - -#undef PATTERN -#undef REAL -#undef COMPLEX -#undef ZOMPLEX - diff --git a/CHOLMOD/Utility/t_cholmod_add.c b/CHOLMOD/Utility/t_cholmod_add.c deleted file mode 100644 index e618998e76..0000000000 --- a/CHOLMOD/Utility/t_cholmod_add.c +++ /dev/null @@ -1,261 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/t_cholmod_add: C = alpha*A + beta*B -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -// The C matrix is returned as packed and sorted. A and B must have the same -// xtype, unless one of them is pattern, in which case only the patterns of A -// and B are used, and C has xtype of pattern. A, B, and C must all have the -// same dtype. If A->stype and B->stype differ, then C is computed as -// unsymmetric (stype of 0). - -#include "cholmod_internal.h" - -#define RETURN_IF_ERROR \ - if (Common->status < CHOLMOD_OK) \ - { \ - CHOLMOD(free_sparse) (&C, Common) ; \ - CHOLMOD(free_sparse) (&A2, Common) ; \ - CHOLMOD(free_sparse) (&B2, Common) ; \ - return (NULL) ; \ - } - -//------------------------------------------------------------------------------ -// t_cholmod_add_worker template -//------------------------------------------------------------------------------ - -#define PATTERN -#include "t_cholmod_add_worker.c" - -#define DOUBLE -#define REAL -#include "t_cholmod_add_worker.c" -#define COMPLEX -#include "t_cholmod_add_worker.c" -#define ZOMPLEX -#include "t_cholmod_add_worker.c" - -#undef DOUBLE -#define SINGLE -#define REAL -#include "t_cholmod_add_worker.c" -#define COMPLEX -#include "t_cholmod_add_worker.c" -#define ZOMPLEX -#include "t_cholmod_add_worker.c" - -//------------------------------------------------------------------------------ -// cholmod_add: C = alpha*A + beta*B -//------------------------------------------------------------------------------ - -cholmod_sparse *CHOLMOD(add) // return C = alpha*A + beta*B -( - cholmod_sparse *A, // input matrix - cholmod_sparse *B, // input matrix - double alpha [2], // scale factor for A (two entires used if complex) - double beta [2], // scale factor for B (two entries used if complex) - int values, // if TRUE compute the numerical values of C - int sorted, // ignored; C is now always returned as sorted - cholmod_common *Common -) -{ - - //-------------------------------------------------------------------------- - // check inputs and determine the xtype and dtype of C - //-------------------------------------------------------------------------- - - RETURN_IF_NULL_COMMON (NULL) ; - RETURN_IF_SPARSE_MATRIX_INVALID (A, NULL) ; - RETURN_IF_SPARSE_MATRIX_INVALID (B, NULL) ; - ASSERT (CHOLMOD(dump_sparse) (A, "add:A", Common) >= 0) ; - ASSERT (CHOLMOD(dump_sparse) (B, "add:B", Common) >= 0) ; - Common->status = CHOLMOD_OK ; - cholmod_sparse *A2 = NULL, *B2 = NULL, *C = NULL ; - - if (A->nrow != B->nrow || A->ncol != B->ncol) - { - ERROR (CHOLMOD_INVALID, "A and B dimensions do not match") ; - return (NULL) ; - } - - int axtype = A->xtype ; - int bxtype = B->xtype ; - if (!values || axtype == CHOLMOD_PATTERN || bxtype == CHOLMOD_PATTERN) - { - // treat A and B as if they are pattern-only matrices; C is pattern - values = FALSE ; - axtype = CHOLMOD_PATTERN ; - bxtype = CHOLMOD_PATTERN ; - } - - if (axtype != bxtype) - { - ERROR (CHOLMOD_INVALID, "A and B xtypes do not match") ; - return (NULL) ; - } - - if (values && A->dtype != B->dtype) - { - ERROR (CHOLMOD_INVALID, "A and B dtypes do not match") ; - return (NULL) ; - } - - int xtype = axtype ; - int dtype = A->dtype ; - - //-------------------------------------------------------------------------- - // get the sizes of the entries of C, A, and B - //-------------------------------------------------------------------------- - - size_t ei = sizeof (Int) ; - size_t e = (dtype == CHOLMOD_SINGLE) ? sizeof (float) : sizeof (double) ; - size_t ex = e * ((xtype == CHOLMOD_PATTERN) ? 0 : - ((xtype == CHOLMOD_COMPLEX) ? 2 : 1)) ; - size_t ez = e * ((xtype == CHOLMOD_ZOMPLEX) ? 1 : 0) ; - - //-------------------------------------------------------------------------- - // convert/sort A and/or B, if needed - //-------------------------------------------------------------------------- - - int mode = values ? 1 : 0 ; - - if (A->stype == B->stype) - { - - //---------------------------------------------------------------------- - // A and B have the same stype, but make sure they are both sorted - //---------------------------------------------------------------------- - - // A2 = sorted copy of A, if A is not sorted, with same stype as A - if (!A->sorted) - { - A2 = CHOLMOD(copy) (A, A->stype, mode, Common) ; - RETURN_IF_ERROR ; - CHOLMOD(sort) (A2, Common) ; - RETURN_IF_ERROR ; - A = A2 ; - } - - // B2 = sorted copy of B, if B is not sorted, with same stype as B - if (!B->sorted) - { - B2 = CHOLMOD(copy) (B, B->stype, mode, Common) ; - RETURN_IF_ERROR ; - CHOLMOD(sort) (B2, Common) ; - RETURN_IF_ERROR ; - B = B2 ; - } - - } - else - { - - //---------------------------------------------------------------------- - // the stype of A and B differ, so make both unsymmetric and sorted - //---------------------------------------------------------------------- - - if (!(A->stype == 0 && A->sorted)) - { - // A2 = sorted unsymmetric copy of A with stype of zero - A2 = CHOLMOD(copy) (A, 0, mode, Common) ; - RETURN_IF_ERROR ; - if (!A2->sorted) - { - CHOLMOD(sort) (A2, Common) ; - RETURN_IF_ERROR ; - } - A = A2 ; - } - - if (!(B->stype == 0 && B->sorted)) - { - // B2 = sorted unsymmetric copy of A with stype of zero - B2 = CHOLMOD(copy) (B, 0, mode, Common) ; - RETURN_IF_ERROR ; - if (!B2->sorted) - { - CHOLMOD(sort) (B2, Common) ; - RETURN_IF_ERROR ; - } - B = B2 ; - } - } - - // C, A, and B now all have the same stype, and are sorted - ASSERT (A->stype == B->stype) ; - ASSERT (A->sorted) ; - ASSERT (B->sorted) ; - - //-------------------------------------------------------------------------- - // allocate C - //-------------------------------------------------------------------------- - - size_t nzmax = CHOLMOD(nnz) (A, Common) + CHOLMOD(nnz) (B, Common) ; - C = CHOLMOD(allocate_sparse) (A->nrow, A->ncol, nzmax, - /* C is sorted: */ TRUE, /* C is packed: */ TRUE, - A->stype, xtype + dtype, Common) ; - RETURN_IF_ERROR ; - - //-------------------------------------------------------------------------- - // C = alpha*A + beta*B - //-------------------------------------------------------------------------- - - switch ((xtype + dtype) % 8) - { - default: - p_cholmod_add_worker (C, A, B, alpha, beta, Common) ; - break ; - - case CHOLMOD_SINGLE + CHOLMOD_REAL: - r_s_cholmod_add_worker (C, A, B, alpha, beta, Common) ; - break ; - - case CHOLMOD_SINGLE + CHOLMOD_COMPLEX: - c_s_cholmod_add_worker (C, A, B, alpha, beta, Common) ; - break ; - - case CHOLMOD_SINGLE + CHOLMOD_ZOMPLEX: - z_s_cholmod_add_worker (C, A, B, alpha, beta, Common) ; - break ; - - case CHOLMOD_DOUBLE + CHOLMOD_REAL: - r_cholmod_add_worker (C, A, B, alpha, beta, Common) ; - break ; - - case CHOLMOD_DOUBLE + CHOLMOD_COMPLEX: - c_cholmod_add_worker (C, A, B, alpha, beta, Common) ; - break ; - - case CHOLMOD_DOUBLE + CHOLMOD_ZOMPLEX: - z_cholmod_add_worker (C, A, B, alpha, beta, Common) ; - break ; - } - - //-------------------------------------------------------------------------- - // free temporary copies of A and B, if created - //-------------------------------------------------------------------------- - - CHOLMOD(free_sparse) (&A2, Common) ; - CHOLMOD(free_sparse) (&B2, Common) ; - - //-------------------------------------------------------------------------- - // compact the space of C - //-------------------------------------------------------------------------- - - size_t cnz = CHOLMOD(nnz) (C, Common) ; - CHOLMOD(reallocate_sparse) (cnz, C, Common) ; - RETURN_IF_ERROR ; - - //-------------------------------------------------------------------------- - // return result - //-------------------------------------------------------------------------- - - ASSERT (CHOLMOD(dump_sparse) (C, "add:C", Common) >= 0) ; - return (C) ; -} - diff --git a/CHOLMOD/Utility/t_cholmod_add_size_t.c b/CHOLMOD/Utility/t_cholmod_add_size_t.c deleted file mode 100644 index a728b15000..0000000000 --- a/CHOLMOD/Utility/t_cholmod_add_size_t.c +++ /dev/null @@ -1,38 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/t_cholmod_add_size_t: add two size_t values -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -#include "cholmod_internal.h" - -size_t CHOLMOD(add_size_t) (size_t a, size_t b, int *ok) -{ - - //-------------------------------------------------------------------------- - // add a and b - //-------------------------------------------------------------------------- - - size_t s = a + b ; - - //-------------------------------------------------------------------------- - // check for size_t overflow - //-------------------------------------------------------------------------- - - if (s < a || s < b) - { - (*ok) = FALSE ; - s = 0 ; - } - - //-------------------------------------------------------------------------- - // return result - //-------------------------------------------------------------------------- - - return (s) ; -} - diff --git a/CHOLMOD/Utility/t_cholmod_add_worker.c b/CHOLMOD/Utility/t_cholmod_add_worker.c deleted file mode 100644 index f73557aa6c..0000000000 --- a/CHOLMOD/Utility/t_cholmod_add_worker.c +++ /dev/null @@ -1,158 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/t_cholmod_add_worker: C = alpha*A + beta*B -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -#include "cholmod_template.h" - -//------------------------------------------------------------------------------ -// cholmod_add: C = alpha*A + beta*B -//------------------------------------------------------------------------------ - -static void TEMPLATE (cholmod_add_worker) -( - cholmod_sparse *C, - cholmod_sparse *A, - cholmod_sparse *B, - double alpha [2], - double beta [2], - cholmod_common *Common -) -{ - - //-------------------------------------------------------------------------- - // get inputs - //-------------------------------------------------------------------------- - - ASSERT (A->sorted) ; - ASSERT (B->sorted) ; - ASSERT (C->sorted) ; - ASSERT (A->stype == B->stype) ; - ASSERT (A->stype == C->stype) ; - ASSERT (C->packed) ; - - bool upper = (A->stype > 0) ; - bool lower = (A->stype < 0) ; - - Int *Ap = (Int *) A->p ; - Int *Anz = (Int *) A->nz ; - Int *Ai = (Int *) A->i ; - bool apacked = A->packed ; - size_t ncol = A->ncol ; - - Int *Bp = (Int *) B->p ; - Int *Bnz = (Int *) B->nz ; - Int *Bi = (Int *) B->i ; - bool bpacked = B->packed ; - - Int *Cp = (Int *) C->p ; - Int *Ci = (Int *) C->i ; - - #ifndef PATTERN - Real *Ax = (Real *) A->x ; - Real *Bx = (Real *) B->x ; - Real *Cx = (Real *) C->x ; - Real alphax [2], betax [2] ; - alphax [0] = (Real) alpha [0] ; - betax [0] = (Real) beta [0] ; - #endif - - #ifdef COMPLEX - alphax [1] = (Real) alpha [1] ; - betax [1] = (Real) beta [1] ; - #endif - - #ifdef ZOMPLEX - Real *Az = (Real *) A->z ; - Real *Bz = (Real *) B->z ; - Real *Cz = (Real *) C->z ; - Real alphaz [1], betaz [1] ; - alphaz [0] = (Real) alpha [1] ; - betaz [0] = (Real) beta [1] ; - #endif - - //-------------------------------------------------------------------------- - // C = alpha*A + beta*B - //-------------------------------------------------------------------------- - - Int cnz = 0 ; - - for (Int j = 0 ; j < ncol ; j++) - { - - //---------------------------------------------------------------------- - // log the start of the jth column of C - //---------------------------------------------------------------------- - - Cp [j] = cnz ; - - //---------------------------------------------------------------------- - // get A(:,j) and B(:,j) - //---------------------------------------------------------------------- - - Int pa = Ap [j] ; - Int paend = (apacked) ? (Ap [j+1]) : (pa + Anz [j]) ; - - Int pb = Bp [j] ; - Int pbend = (bpacked) ? (Bp [j+1]) : (pb + Bnz [j]) ; - - //---------------------------------------------------------------------- - // C(:,j) = alpha*A(:,j) + beta*B(:,j) - //---------------------------------------------------------------------- - - while (pa < paend || pb < pbend) - { - // get A(i,j) - Int iA = (pa < paend) ? Ai [pa] : Int_max ; - - // get B(i,j) - Int iB = (pb < pbend) ? Bi [pb] : Int_max ; - - // skip if C(i,j) is in the ignored part of the matrix - Int i = MIN (iA, iB) ; - if ((upper && i > j) || (lower && i < j)) continue ; - - // compute C(i,j) - ASSERT (cnz < C->nzmax) ; - Ci [cnz] = i ; - if (iA < iB) - { - // B(:,j) is not present, so C(i,j) = alpha*A(i,j) - MULT (Cx, Cz, cnz, alphax, alphaz, 0, Ax, Az, pa) ; - pa++ ; - } - else if (iA > iB) - { - // A(:,j) is not present, so C(i,j) = beta*B(i,j) - MULT (Cx, Cz, cnz, betax, betaz, 0, Bx, Bz, pb) ; - pb++ ; - } - else - { - // C(i,j) = alpha*A(i,j) + beta*B(i,j) - MULT (Cx, Cz, cnz, alphax, alphaz, 0, Ax, Az, pa) ; - MULTADD (Cx, Cz, cnz, betax, betaz, 0, Bx, Bz, pb) ; - pa++ ; - pb++ ; - } - cnz++ ; - } - } - - //-------------------------------------------------------------------------- - // log the end of the last column of C - //-------------------------------------------------------------------------- - - Cp [ncol] = cnz ; -} - -#undef PATTERN -#undef REAL -#undef COMPLEX -#undef ZOMPLEX - diff --git a/CHOLMOD/Utility/t_cholmod_alloc_factor.c b/CHOLMOD/Utility/t_cholmod_alloc_factor.c deleted file mode 100644 index 58a68e52d1..0000000000 --- a/CHOLMOD/Utility/t_cholmod_alloc_factor.c +++ /dev/null @@ -1,97 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/t_cholmod_alloc_factor: allocate a simplicial factor -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -// Allocates a simplicial symbolic factor, with only L->Perm and L->ColCount -// created and set to empty values (L->Perm is the identity permutation, and -// ColCount is all 1's). L is pattern. Unlike cholmod_allocate_factor, the -// factor can be either single or double precision. L->xtype is -// CHOLMOD_PATTERN. - -#include "cholmod_internal.h" - -#define RETURN_IF_ERROR \ - if (Common->status < CHOLMOD_OK) \ - { \ - CHOLMOD(free_factor) (&L, Common) ; \ - return (NULL) ; \ - } - -cholmod_factor *CHOLMOD(alloc_factor) // return the new factor L -( - size_t n, // L is factorization of an n-by-n matrix - int dtype, // CHOLMOD_SINGLE or CHOLMOD_DOUBLE - cholmod_common *Common -) -{ - - //-------------------------------------------------------------------------- - // check inputs - //-------------------------------------------------------------------------- - - RETURN_IF_NULL_COMMON (FALSE) ; - Common->status = CHOLMOD_OK ; - - if ((int64_t) n >= Int_max) - { - ERROR (CHOLMOD_TOO_LARGE, "problem too large") ; - return (NULL) ; - } - - //-------------------------------------------------------------------------- - // get the dtype - //-------------------------------------------------------------------------- - - dtype = dtype & 4 ; // double or single - - //-------------------------------------------------------------------------- - // allocate the header for L - //-------------------------------------------------------------------------- - - cholmod_factor *L = CHOLMOD(calloc) (1, sizeof (cholmod_factor), Common) ; - RETURN_IF_ERROR ; - - //-------------------------------------------------------------------------- - // fill the header - //-------------------------------------------------------------------------- - - L->n = n ; // # of rows and columns - L->itype = ITYPE ; // integer type - L->dtype = dtype ; // double or single - L->is_monotonic = TRUE ; // columns of L appear in order 0..n-1 - L->minor = n ; // L has not been factorized - - //-------------------------------------------------------------------------- - // allocate Perm and ColCount - //-------------------------------------------------------------------------- - - L->Perm = CHOLMOD(malloc) (n, sizeof (Int), Common) ; - L->ColCount = CHOLMOD(malloc) (n, sizeof (Int), Common) ; - RETURN_IF_ERROR ; - - //-------------------------------------------------------------------------- - // initialize Perm and and ColCount - //-------------------------------------------------------------------------- - - Int *Perm = (Int *) L->Perm ; - Int *ColCount = (Int *) L->ColCount ; - - for (Int j = 0 ; j < n ; j++) - { - Perm [j] = j ; - ColCount [j] = 1 ; - } - - //-------------------------------------------------------------------------- - // return result - //-------------------------------------------------------------------------- - - return (L) ; -} - diff --git a/CHOLMOD/Utility/t_cholmod_alloc_work.c b/CHOLMOD/Utility/t_cholmod_alloc_work.c deleted file mode 100644 index d45e3549d2..0000000000 --- a/CHOLMOD/Utility/t_cholmod_alloc_work.c +++ /dev/null @@ -1,116 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/t_cholmod_alloc_work: double/single int32/64 workspace -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -// Allocates and initializes CHOLMOD workspace in Common, or increases the size -// of the workspace if already allocated. If the required workspace is already -// allocated, no action is taken. - -#include "cholmod_internal.h" - -#define RETURN_IF_ERROR \ - if (Common->status < CHOLMOD_OK) \ - { \ - CHOLMOD(free_work) (Common) ; \ - return (FALSE) ; \ - } - -#define RETURN_IF_ALLOC_NOT_ALLOWED \ - if (Common->no_workspace_reallocate) \ - { \ - Common->status = CHOLMOD_INVALID ; \ - return (FALSE) ; \ - } - -int CHOLMOD(alloc_work) -( - size_t nrow, // # of rows in the matrix A - size_t iworksize, // size of Iwork (# of integers, int32 or int64) - size_t xworksize, // size of Xwork (in # of entries, double or single) - int dtype, // CHOLMOD_DOUBLE or CHOLMOD_SINGLE - cholmod_common *Common -) -{ - - //-------------------------------------------------------------------------- - // check inputs - //-------------------------------------------------------------------------- - - RETURN_IF_NULL_COMMON (FALSE) ; - Common->status = CHOLMOD_OK ; - - //-------------------------------------------------------------------------- - // allocate Flag (of size nrow Ints) and Head (of size nrow+1 Ints) - //-------------------------------------------------------------------------- - - // ensure at least 1 entry allocated, and check for size_t overflow - nrow = MAX (1, nrow) ; - size_t nrow1 = nrow + 1 ; - if (nrow1 < nrow) Common->status = CHOLMOD_TOO_LARGE ; - RETURN_IF_ERROR ; - - if (nrow > Common->nrow) - { - RETURN_IF_ALLOC_NOT_ALLOWED ; - Common->Flag = CHOLMOD(free) (Common->nrow, sizeof (Int), - Common->Flag, Common) ; - Common->Head = CHOLMOD(free) (Common->nrow+1, sizeof (Int), - Common->Head, Common) ; - Common->nrow = nrow ; - Common->Flag = CHOLMOD(malloc) (nrow, sizeof (Int), Common) ; - Common->Head = CHOLMOD(malloc) (nrow1, sizeof (Int), Common) ; - RETURN_IF_ERROR ; - // clear the Flag and Head workspace - Common->mark = 0 ; - CHOLMOD(set_empty) (Common->Flag, nrow) ; - CHOLMOD(set_empty) (Common->Head, nrow+1) ; - } - - //-------------------------------------------------------------------------- - // allocate Iwork (of size iworksize Ints) - //-------------------------------------------------------------------------- - - iworksize = MAX (1, iworksize) ; - if (iworksize > Common->iworksize) - { - RETURN_IF_ALLOC_NOT_ALLOWED ; - CHOLMOD(free) (Common->iworksize, sizeof (Int), Common->Iwork, Common) ; - Common->iworksize = iworksize ; - Common->Iwork = CHOLMOD(malloc) (iworksize, sizeof (Int), Common) ; - RETURN_IF_ERROR ; - } - - //-------------------------------------------------------------------------- - // allocate Xwork (xworksize) and set it to 0 - //-------------------------------------------------------------------------- - - // make sure xworksize is >= 2 - xworksize = MAX (2, xworksize) ; - - size_t e = (dtype == CHOLMOD_SINGLE) ? sizeof (float) : sizeof (double) ; - - if (xworksize > Common->xworkbytes / e) - { - RETURN_IF_ALLOC_NOT_ALLOWED ; - CHOLMOD(free) (Common->xworkbytes, sizeof (uint8_t), Common->Xwork, - Common) ; - Common->Xwork = CHOLMOD(malloc) (xworksize, e, Common) ; - RETURN_IF_ERROR ; - // clear the Xwork workspace - Common->xworkbytes = xworksize * e ; - memset (Common->Xwork, 0, Common->xworkbytes) ; - } - - //-------------------------------------------------------------------------- - // return result - //-------------------------------------------------------------------------- - - return (TRUE) ; -} - diff --git a/CHOLMOD/Utility/t_cholmod_allocate_dense.c b/CHOLMOD/Utility/t_cholmod_allocate_dense.c deleted file mode 100644 index b0da190f27..0000000000 --- a/CHOLMOD/Utility/t_cholmod_allocate_dense.c +++ /dev/null @@ -1,97 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/t_cholmod_allocate_dense: allocate dense matrix -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -// Allocate a dense matrix. The space is not initialized. - -#include "cholmod_internal.h" - -#define RETURN_IF_ERROR \ - if (Common->status < CHOLMOD_OK) \ - { \ - CHOLMOD(free_dense) (&X, Common) ; \ - return (NULL) ; \ - } - -cholmod_dense *CHOLMOD(allocate_dense) -( - size_t nrow, // # of rows - size_t ncol, // # of columns - size_t d, // leading dimension - int xdtype, // xtype + dtype of the matrix: - // (CHOLMOD_DOUBLE, _SINGLE) + - // (CHOLMOD_REAL, _COMPLEX, or _ZOMPLEX) - cholmod_common *Common -) -{ - - //-------------------------------------------------------------------------- - // check inputs - //-------------------------------------------------------------------------- - - RETURN_IF_NULL_COMMON (NULL) ; - Common->status = CHOLMOD_OK ; - - //-------------------------------------------------------------------------- - // get the xtype and dtype - //-------------------------------------------------------------------------- - - int xtype = xdtype & 3 ; // real, complex, or zomplex (not pattern) - int dtype = xdtype & 4 ; // double or single - - if (xtype == CHOLMOD_PATTERN) - { - ERROR (CHOLMOD_INVALID, "xtype invalid") ; - return (NULL) ; - } - - d = MAX (d, nrow) ; // leading dimension d must be >= nrow - - int ok = TRUE ; - size_t nzmax = CHOLMOD(mult_size_t) (d, ncol, &ok) ; - if (!ok || nzmax >= Int_max) - { - ERROR (CHOLMOD_TOO_LARGE, "problem too large") ; - return (NULL) ; - } - - //-------------------------------------------------------------------------- - // allocate the header - //-------------------------------------------------------------------------- - - cholmod_dense *X = CHOLMOD(calloc) (1, sizeof (cholmod_dense), Common) ; - RETURN_IF_ERROR ; - - //-------------------------------------------------------------------------- - // fill the header - //-------------------------------------------------------------------------- - - X->nrow = nrow ; // # rows - X->ncol = ncol ; // # columns - X->xtype = xtype ; // real, complex, or zomplex - X->dtype = dtype ; // double or single - X->d = d ; // leading dimension - - //-------------------------------------------------------------------------- - // reallocate the dense matrix to change X->nzmax from 0 to nzmax - //-------------------------------------------------------------------------- - - CHOLMOD(realloc_multiple) (nzmax, /* nint: */ 0, xtype + dtype, - /* I not used: */ NULL, /* J not used: */ NULL, &(X->x), &(X->z), - &(X->nzmax), Common) ; - RETURN_IF_ERROR ; - - //-------------------------------------------------------------------------- - // return result - //-------------------------------------------------------------------------- - -// ASSERT (CHOLMOD(dump_dense) (X, "allocate_dense:X", Common) >= 0) ; - return (X) ; -} - diff --git a/CHOLMOD/Utility/t_cholmod_allocate_sparse.c b/CHOLMOD/Utility/t_cholmod_allocate_sparse.c deleted file mode 100644 index ca38c9f72b..0000000000 --- a/CHOLMOD/Utility/t_cholmod_allocate_sparse.c +++ /dev/null @@ -1,105 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/t_cholmod_allocate_sparse: allocate a sparse matrix -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -// Allocate a sparse matrix. The contents A->i, A->x, and A->z (if zomplex) -// exist but are not initialized. A->p and A->nz (if unpacked) are set to -// zero, giving a valid sparse matrix with no entries. - -#include "cholmod_internal.h" - -#define RETURN_IF_ERROR \ - if (Common->status < CHOLMOD_OK) \ - { \ - CHOLMOD(free_sparse) (&A, Common) ; \ - return (NULL) ; \ - } - -cholmod_sparse *CHOLMOD(allocate_sparse) -( - size_t nrow, // # of rows - size_t ncol, // # of columns - size_t nzmax, // max # of entries the matrix can hold - int sorted, // true if columns are sorted - int packed, // true if A is be packed (A->nz NULL), false if unpacked - int stype, // the stype of the matrix (unsym, tril, or triu) - int xdtype, // xtype + dtype of the matrix: - // (CHOLMOD_DOUBLE, _SINGLE) + - // (CHOLMOD_PATTERN, _REAL, _COMPLEX, or _ZOMPLEX) - cholmod_common *Common -) -{ - - //-------------------------------------------------------------------------- - // check inputs - //-------------------------------------------------------------------------- - - RETURN_IF_NULL_COMMON (NULL) ; - Common->status = CHOLMOD_OK ; - - if (stype != 0 && nrow != ncol) - { - ERROR (CHOLMOD_INVALID, "rectangular matrix with stype != 0 invalid") ; - return (NULL) ; - } - - //-------------------------------------------------------------------------- - // get the xtype and dtype - //-------------------------------------------------------------------------- - - int xtype = xdtype & 3 ; // pattern, real, complex, or zomplex - int dtype = xdtype & 4 ; // double or single - - //-------------------------------------------------------------------------- - // allocate the header for A - //-------------------------------------------------------------------------- - - cholmod_sparse *A = CHOLMOD(calloc) (1, sizeof (cholmod_sparse), Common) ; - RETURN_IF_ERROR ; - - //-------------------------------------------------------------------------- - // fill the header - //-------------------------------------------------------------------------- - - A->nrow = nrow ; // # rows - A->ncol = ncol ; // # columns - A->stype = stype ; // symmetry type - A->itype = ITYPE ; // integer type - A->xtype = xtype ; // pattern, real, complex, or zomplex - A->dtype = dtype ; // double or single - - A->packed = packed ; // packed or unpacked - A->sorted = sorted ; // columns sorted or unsorted - - //-------------------------------------------------------------------------- - // allocate and clear A->p and A->nz - //-------------------------------------------------------------------------- - - A->p = CHOLMOD(calloc) (ncol+1, sizeof (Int), Common) ; - if (!packed) - { - A->nz = CHOLMOD(calloc) (ncol, sizeof (Int), Common) ; - } - RETURN_IF_ERROR ; - - //-------------------------------------------------------------------------- - // reallocate the sparse matrix to change A->nzmax from 0 to nzmax - //-------------------------------------------------------------------------- - - CHOLMOD(reallocate_sparse) (nzmax, A, Common) ; - RETURN_IF_ERROR ; - - //-------------------------------------------------------------------------- - // return result - //-------------------------------------------------------------------------- - - ASSERT (CHOLMOD(dump_sparse) (A, "allocate_sparse:A", Common) >= 0) ; - return (A) ; -} - diff --git a/CHOLMOD/Utility/t_cholmod_allocate_triplet.c b/CHOLMOD/Utility/t_cholmod_allocate_triplet.c deleted file mode 100644 index 55572ff7c8..0000000000 --- a/CHOLMOD/Utility/t_cholmod_allocate_triplet.c +++ /dev/null @@ -1,88 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/t_cholmod_allocate_triplet: allocate triplet matrix -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -// Allocate an empty triplet matrix, with space to hold a given max # of -// entries. The contents of T->i, T->j, T->x, and T->z are not initialized. - -#include "cholmod_internal.h" - -#define RETURN_IF_ERROR \ - if (Common->status < CHOLMOD_OK) \ - { \ - CHOLMOD(free_triplet) (&T, Common) ; \ - return (NULL) ; \ - } - -cholmod_triplet *CHOLMOD(allocate_triplet) // return triplet matrix T -( - size_t nrow, // # of rows - size_t ncol, // # of columns - size_t nzmax, // max # of entries the matrix can hold - int stype, // the stype of the matrix (unsym, tril, or triu) - int xdtype, // xtype + dtype of the matrix: - // (CHOLMOD_DOUBLE, _SINGLE) + - // (CHOLMOD_PATTERN, _REAL, _COMPLEX, or _ZOMPLEX) - cholmod_common *Common -) -{ - - //-------------------------------------------------------------------------- - // check inputs - //-------------------------------------------------------------------------- - - RETURN_IF_NULL_COMMON (NULL) ; - Common->status = CHOLMOD_OK ; - - if (stype != 0 && nrow != ncol) - { - ERROR (CHOLMOD_INVALID, "rectangular matrix with stype != 0 invalid") ; - return (NULL) ; - } - - //-------------------------------------------------------------------------- - // get the xtype and dtype - //-------------------------------------------------------------------------- - - int xtype = xdtype & 3 ; // pattern, real, complex, or zomplex - int dtype = xdtype & 4 ; // double or single - - //-------------------------------------------------------------------------- - // allocate the header for T - //-------------------------------------------------------------------------- - - cholmod_triplet *T = CHOLMOD(calloc) (1, sizeof (cholmod_triplet), Common) ; - RETURN_IF_ERROR ; - - //-------------------------------------------------------------------------- - // fill the header - //-------------------------------------------------------------------------- - - T->nrow = nrow ; // # rows - T->ncol = ncol ; // # columns - T->stype = stype ; // symmetry type - T->itype = ITYPE ; // integer type - T->xtype = xtype ; // pattern, real, complex, or zomplex - T->dtype = dtype ; // double or single - - //-------------------------------------------------------------------------- - // reallocate the triplet matrix to change T->nzmax from 0 to nzmax - //-------------------------------------------------------------------------- - - CHOLMOD(reallocate_triplet) (nzmax, T, Common) ; - RETURN_IF_ERROR ; - - //-------------------------------------------------------------------------- - // return result - //-------------------------------------------------------------------------- - - ASSERT (CHOLMOD(dump_triplet) (T, "allocate_triplet:T", Common) >= 0) ; - return (T) ; -} - diff --git a/CHOLMOD/Utility/t_cholmod_band.c b/CHOLMOD/Utility/t_cholmod_band.c deleted file mode 100644 index 1fd981c261..0000000000 --- a/CHOLMOD/Utility/t_cholmod_band.c +++ /dev/null @@ -1,226 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/t_cholmod_band: extract the band of a sparse matrix -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -// Construct a sparse matrix C that contains entries in bands k1:k2 of an input -// sparse matrix A. A can have any xtype, stype, or dtype. C is sorted if and -// only if A is sorted. - -// A can be constructed in place, but only if it is in packed form. -// The diagonal can be ignored, if the ignore_diag flag is true. -// C can optionally be constructed as a pattern matrix. - -#include "cholmod_internal.h" - -#define RETURN_IF_ERROR \ - if (Common->status < CHOLMOD_OK) \ - { \ - CHOLMOD(free_sparse) (&C2, Common) ; \ - return (NULL) ; \ - } - -//------------------------------------------------------------------------------ -// t_cholmod_band_worker template -//------------------------------------------------------------------------------ - -#define PATTERN -#include "t_cholmod_band_worker.c" - -#define DOUBLE -#define REAL -#include "t_cholmod_band_worker.c" -#define COMPLEX -#include "t_cholmod_band_worker.c" -#define ZOMPLEX -#include "t_cholmod_band_worker.c" - -#undef DOUBLE -#define SINGLE -#define REAL -#include "t_cholmod_band_worker.c" -#define COMPLEX -#include "t_cholmod_band_worker.c" -#define ZOMPLEX -#include "t_cholmod_band_worker.c" - -//------------------------------------------------------------------------------ -// band_helper -//------------------------------------------------------------------------------ - -static cholmod_sparse *band_helper -( - cholmod_sparse *A, - int64_t k1, // count entries in k1:k2 diagonals - int64_t k2, - bool values, // if true and A numerical, C is numerical - bool inplace, // if true, convert A in place (A cannot be packed) - bool ignore_diag, // if true, ignore diagonal - cholmod_common *Common -) -{ - - //-------------------------------------------------------------------------- - // check inputs - //-------------------------------------------------------------------------- - - RETURN_IF_NULL_COMMON (NULL) ; - RETURN_IF_SPARSE_MATRIX_INVALID (A, NULL) ; - Common->status = CHOLMOD_OK ; - - //-------------------------------------------------------------------------- - // get inputs - //-------------------------------------------------------------------------- - - Int nrow = A->nrow ; - Int ncol = A->ncol ; - - if (A->stype > 0 && k1 < 0) - { - // A is symmetric with the strictly lower triangular part ignored - k1 = 0 ; - } - else if (A->stype < 0 && k2 > 0) - { - // A is symmetric with the strictly upper triangular part ignored - k2 = 0 ; - } - - // ensure k1 and k2 are in range -nrow:ncol - k1 = RANGE (k1, -nrow, ncol) ; - k2 = RANGE (k2, -nrow, ncol) ; - - values = values && (A->xtype != CHOLMOD_PATTERN) ; - - //-------------------------------------------------------------------------- - // allocate new matrix C, or operate on A in place - //-------------------------------------------------------------------------- - - cholmod_sparse *C, *C2 = NULL ; - if (inplace) - { - // convert A in place - if (!values) - { - // change A to pattern - CHOLMOD(sparse_xtype) (CHOLMOD_PATTERN + A->dtype, A, Common) ; - } - C = A ; - } - else - { - // count # of entries in C and allocate it - int64_t cnz = CHOLMOD(band_nnz) (A, k1, k2, ignore_diag, Common) ; - int cxtype = values ? A->xtype : CHOLMOD_PATTERN ; - C2 = CHOLMOD(allocate_sparse) (nrow, ncol, cnz, A->sorted, - /* C is packed: */ TRUE, A->stype, cxtype + A->dtype, Common) ; - C = C2 ; - } - RETURN_IF_ERROR ; - - //-------------------------------------------------------------------------- - // C = band (A) - //-------------------------------------------------------------------------- - - switch ((C->xtype + C->dtype) % 8) - { - default: - p_cholmod_band_worker (C, A, k1, k2, ignore_diag) ; - break ; - - case CHOLMOD_SINGLE + CHOLMOD_REAL: - r_s_cholmod_band_worker (C, A, k1, k2, ignore_diag) ; - break ; - - case CHOLMOD_SINGLE + CHOLMOD_COMPLEX: - c_s_cholmod_band_worker (C, A, k1, k2, ignore_diag) ; - break ; - - case CHOLMOD_SINGLE + CHOLMOD_ZOMPLEX: - z_s_cholmod_band_worker (C, A, k1, k2, ignore_diag) ; - break ; - - case CHOLMOD_DOUBLE + CHOLMOD_REAL: - r_cholmod_band_worker (C, A, k1, k2, ignore_diag) ; - break ; - - case CHOLMOD_DOUBLE + CHOLMOD_COMPLEX: - c_cholmod_band_worker (C, A, k1, k2, ignore_diag) ; - break ; - - case CHOLMOD_DOUBLE + CHOLMOD_ZOMPLEX: - z_cholmod_band_worker (C, A, k1, k2, ignore_diag) ; - break ; - } - - //-------------------------------------------------------------------------- - // shrink A if computed in-place - //-------------------------------------------------------------------------- - - if (inplace) - { - int64_t anz = CHOLMOD(nnz) (A, Common) ; - CHOLMOD(reallocate_sparse) (anz, A, Common) ; - RETURN_IF_ERROR ; - } - - //-------------------------------------------------------------------------- - // return result - //-------------------------------------------------------------------------- - - DEBUG (int64_t nzdiag = CHOLMOD(dump_sparse) (C, "band:C", Common)) ; - ASSERT (nzdiag >= 0) ; - ASSERT (IMPLIES (ignore_diag, nzdiag == 0)) ; - return (C) ; -} - -//------------------------------------------------------------------------------ -// cholmod_band -//------------------------------------------------------------------------------ - -cholmod_sparse *CHOLMOD(band) // return a new matrix C -( - cholmod_sparse *A, // input matrix - int64_t k1, // count entries in k1:k2 diagonals - int64_t k2, - int mode, // >0: numerical, 0: pattern, <0: pattern (no diag) - cholmod_common *Common -) -{ - bool values = (mode > 0) ; - bool inplace = FALSE ; - bool ignore_diag = (mode < 0) ; - return (band_helper (A, k1, k2, values, inplace, ignore_diag, Common)) ; -} - -//------------------------------------------------------------------------------ -// cholmod_band_inplace -//------------------------------------------------------------------------------ - -int CHOLMOD(band_inplace) -( - int64_t k1, // count entries in k1:k2 diagonals - int64_t k2, - int mode, // >0: numerical, 0: pattern, <0: pattern (no diag) - cholmod_sparse *A, // input/output matrix - cholmod_common *Common -) -{ - bool values = (mode > 0) ; - bool inplace = TRUE ; - bool ignore_diag = (mode < 0) ; - if (A != NULL && !(A->packed)) - { - /* cannot operate on an unpacked matrix in place */ - ERROR (CHOLMOD_INVALID, "cannot operate on unpacked matrix in-place") ; - return (FALSE) ; - } - return (band_helper (A, k1, k2, values, inplace, ignore_diag, Common) - != NULL) ; -} - diff --git a/CHOLMOD/Utility/t_cholmod_band_nnz.c b/CHOLMOD/Utility/t_cholmod_band_nnz.c deleted file mode 100644 index 0f3d0d3e31..0000000000 --- a/CHOLMOD/Utility/t_cholmod_band_nnz.c +++ /dev/null @@ -1,93 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/t_cholmod_band_nnz: # of entries in a band of sparse matrix -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -// Counts the # of entries with diagonals k1 to k2 of a sparse matrix. -// For example, to count entries in the tridagonal part, use k1=-1 and k2=1. -// To include the diagonal (k = 0), use ignore_diag = false; to exclude it, use -// ignore_diag = true. - -#include "cholmod_internal.h" - -int64_t CHOLMOD(band_nnz) // return # of entries in a band (-1 if error) -( - cholmod_sparse *A, // matrix to examine - int64_t k1, // count entries in k1:k2 diagonals - int64_t k2, - bool ignore_diag, // if true, exclude any diagonal entries - cholmod_common *Common -) -{ - - //-------------------------------------------------------------------------- - // check inputs - //-------------------------------------------------------------------------- - - RETURN_IF_NULL_COMMON (EMPTY) ; - RETURN_IF_SPARSE_MATRIX_INVALID (A, EMPTY) ; - - //-------------------------------------------------------------------------- - // get inputs - //-------------------------------------------------------------------------- - - Int *Ap = (Int *) A->p ; - Int *Ai = (Int *) A->i ; - Int *Anz = (Int *) A->nz ; - bool packed = (bool) A->packed ; - Int nrow = A->nrow ; - Int ncol = A->ncol ; - - if (A->stype > 0 && k1 < 0) - { - // A is symmetric with the strictly lower triangular part ignored - k1 = 0 ; - } - else if (A->stype < 0 && k2 > 0) - { - // A is symmetric with the strictly upper triangular part ignored - k2 = 0 ; - } - - // ensure k1 and k2 are in range -nrow:ncol - k1 = RANGE (k1, -nrow, ncol) ; - k2 = RANGE (k2, -nrow, ncol) ; - - // check for quick return - if (k1 > k2) return (0) ; - - // columns outside of j1:j2 have no entries in diagonals k1:k2 - Int j1 = MAX (k1, 0) ; - Int j2 = MIN (k2+nrow, ncol) ; - - //-------------------------------------------------------------------------- - // count entries within the k1:k2 band - //-------------------------------------------------------------------------- - - int64_t bnz = 0 ; - for (Int j = j1 ; j < j2 ; j++) - { - Int p = Ap [j] ; - Int pend = (packed) ? (Ap [j+1]) : (p + Anz [j]) ; - for ( ; p < pend ; p++) - { - // A(i,j) is in the kth diagonal, where k = j-i - Int k = j - Ai [p] ; - // check if k is in range k1:k2; if k is zero and diagonal is - // ignored, then skip this entry - bnz += ((k >= k1) && (k <= k2) && !(k == 0 && ignore_diag)) ; - } - } - - //-------------------------------------------------------------------------- - // return result - //-------------------------------------------------------------------------- - - return (bnz) ; -} - diff --git a/CHOLMOD/Utility/t_cholmod_band_worker.c b/CHOLMOD/Utility/t_cholmod_band_worker.c deleted file mode 100644 index 2729ed5f75..0000000000 --- a/CHOLMOD/Utility/t_cholmod_band_worker.c +++ /dev/null @@ -1,103 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/t_cholmod_band_worker: extract the band of a sparse matrix -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -#include "cholmod_template.h" - -static void TEMPLATE (cholmod_band_worker) -( - cholmod_sparse *C, - cholmod_sparse *A, - int64_t k1, // keep entries in k1:k2 diagonals - int64_t k2, - bool ignore_diag // if true, exclude any diagonal entries -) -{ - - //-------------------------------------------------------------------------- - // get inputs - //-------------------------------------------------------------------------- - - Int nrow = A->nrow ; - Int ncol = A->ncol ; - - Int *Ap = (Int *) A->p ; - Int *Anz = (Int *) A->nz ; - Int *Ai = (Int *) A->i ; - Real *Ax = (Real *) A->x ; - Real *Az = (Real *) A->x ; - bool packed = A->packed ; - - Int *Cp = (Int *) C->p ; - Int *Ci = (Int *) C->i ; - Real *Cx = (Real *) C->x ; - Real *Cz = (Real *) C->z ; - - // columns outside of j1:j2 have no entries in diagonals k1:k2 - Int j1 = MAX (k1, 0) ; - Int j2 = MIN (k2+nrow, ncol) ; - - //-------------------------------------------------------------------------- - // columns 0 to j1-1 are empty - //-------------------------------------------------------------------------- - - memset (Cp, 0, j1 * sizeof (Int)) ; - - //-------------------------------------------------------------------------- - // handle columns j1:j2-1 - //-------------------------------------------------------------------------- - - Int cnz = 0 ; - for (Int j = j1 ; j < j2 ; j++) - { - - //---------------------------------------------------------------------- - // get A(:,j) and log the start of C(:,j) - //---------------------------------------------------------------------- - - // NOTE: C and A can be aliased - Int p = Ap [j] ; - Int pend = (packed) ? (Ap [j+1]) : (p + Anz [j]) ; - Cp [j] = cnz ; - - //---------------------------------------------------------------------- - // extract entries in the band of A(:,j) - //---------------------------------------------------------------------- - - for ( ; p < pend ; p++) - { - // A(i,j) is in the kth diagonal, where k = j-i - Int i = Ai [p] ; - Int k = j - i ; - // check if k is in range k1:k2; if k is zero and diagonal is - // ignored, then skip this entry - if ((k >= k1) && (k <= k2) && !(k == 0 && ignore_diag)) - { - // C(i,j) = A(i,j) - ASSIGN (Cx, Cz, cnz, Ax, Az, p) ; - Ci [cnz++] = i ; - } - } - } - - //-------------------------------------------------------------------------- - // columns j2 to ncol-1 are empty - //-------------------------------------------------------------------------- - - for (Int j = j2 ; j <= ncol ; j++) - { - Cp [j] = cnz ; - } -} - -#undef PATTERN -#undef REAL -#undef COMPLEX -#undef ZOMPLEX - diff --git a/CHOLMOD/Utility/t_cholmod_bound.c b/CHOLMOD/Utility/t_cholmod_bound.c deleted file mode 100644 index 7045068e4d..0000000000 --- a/CHOLMOD/Utility/t_cholmod_bound.c +++ /dev/null @@ -1,79 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/t_cholmod_bound: bound diagonal of LDL -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -#include "cholmod_internal.h" - -// Template for creating the following functions: -// cholmod_dbound double, int32, using Common->dbound and ndbounds_hit -// cholmod_l_dbound double, int64, using Common->dbound and ndbounds_hit -// cholmod_sbound single, int32, using Common->sbound and nsbounds_hit -// cholmod_l_sbound single, int64, using Common->sbound and nsbounds_hit - -// This method ensures that the absolute value of D(j,j) is greater than dbound -// (for double) or sbound (for single), for LDL' factorization and -// update/downdate. It is not used for supernodal factorization. - -Real CHOLMOD_BOUND_FUNCTION // returns modified diagonal entry D(j,j) -( - Real djj, // input diagonal entry D(j,j) - cholmod_common *Common -) -{ - - //-------------------------------------------------------------------------- - // check inputs - //-------------------------------------------------------------------------- - - RETURN_IF_NULL_COMMON (0) ; - if (isnan (djj)) return (djj) ; // no change if D(j,j) is NaN - - //-------------------------------------------------------------------------- - // check the bound - //-------------------------------------------------------------------------- - - bool hit ; - Real bound ; - if (djj >= 0) - { - // D(j,j) is positive: check if djj in range [0,Common->bound] - bound = COMMON_BOUND ; - hit = (djj < bound) ; - } - else - { - // D(j,j) is negative: check if djj in range [-Common->bound,0] - bound = -COMMON_BOUND ; - hit = (djj > bound) ; - } - - //-------------------------------------------------------------------------- - // record the hit - //-------------------------------------------------------------------------- - - if (hit) - { - // bound the diagonal entry - djj = bound ; - // record the # of times the bound was hit - COMMON_BOUNDS_HIT++ ; - // set an error flag, if not already set - if (Common->status == CHOLMOD_OK) - { - ERROR (CHOLMOD_DSMALL, "diagonal entry is below threshold") ; - } - } - - //-------------------------------------------------------------------------- - // return result - //-------------------------------------------------------------------------- - - return (djj) ; -} - diff --git a/CHOLMOD/Utility/t_cholmod_change_factor.c b/CHOLMOD/Utility/t_cholmod_change_factor.c deleted file mode 100644 index 2d88b417bb..0000000000 --- a/CHOLMOD/Utility/t_cholmod_change_factor.c +++ /dev/null @@ -1,1288 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/t_cholmod_change_factor: change format of a factor object -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -// The cholmod_factor object holds a sparse Cholesky factorization in one of -// many formats. It can be numeric or symbolic, L*L' or L*D*L', simplicial -// or supernodal, packed or unpacked, and its columns can appear in order -// (monotonic) or not (non-monotonic). Not all combinations are possible. - -// The L->xtype field describes the type of the entries: - -// CHOLMOD_PATTERN: L->x and L->z are NULL, no values are stored. -// CHOLMOD_REAL: L->x is float or double, and L->z is NULL. The numeric -// value of the (p)th entry is L->x [p]. -// CHOLMOD_COMPLEX: L->x is float or double, the matrix is complex, -// where the value of (p)th entry is L->x [2*p] (the real part), -// and L->x [2*p+1] (the imaginary part). L->z is NULL. -// CHOLMOD_ZOMPLEX: L->x and L->z are float or double. The matrix is -// "zomplex", which means the matrix is mathematically complex, but -// the real and imaginary parts are held in two separate arrays. -// The value of the (p)th entry is L->x [p] (the real part), and -// L->z [p] (the imaginary part). Supernodal factors are never -// zomplex. - -// This method can change the L->xtype of a factor object L, but only to -// convert it to CHOLMOD_PATTERN (thus freeing all numeric values), or by -// changing a factor of xtype CHOLMOD_PATTERN to any of the three other types -// (thus allocating empty space, or placing a placeholder value of an -// identitity matrix. - -// The L->dtype field, just like the CHOLMOD sparse matrix, triplet matrix, and -// dense matrix formats, defines the underlying floating point type: single -// (float) or double, as CHOLMOD_SINGLE or CHOLMOD_DOUBLE. Matrices of -// different dtypes cannot be mixed. To convert the xtype and dtype of an -// object, use the cholmod_*_xtype methods (named "_xtype" for backward -// compatibility with CHOLMOD v4 and earlier). That method will preserve the -// values of the factor L. - -// CHOLMOD has the following basic kinds of factor formats: -// -// (1) simplicial symbolic: this consists of just two arrays of size n. -// L->Perm contains the fill-reducing ordering, and L->ColCount is an -// array containing the # of entries in each column of L. All of the other -// factor objects contain this information as well. The simplicial -// symbolic format does not hold the pattern of the matrix L itself. -// -// (2) simplicial numeric: this can hold either an LL' or LDL' factorization. -// -// LDL': The numeric L matrix itself is unit-diagonal, and the diagonal -// entries of L are not stored. The jth column appears in positions -// L->p [j] to L->p [j] + L->nz [j], in the arrays L->i, L->x, and (if -// zomplex), L->z. Thus, L->nz [j] is the # of entries in the jth column, -// which includes the entry D(j,j) as the first entry held in that column. -// The columns of L need not appear in order 0, 1, ... n-1 in L->(i,x,z). -// Instead, a doubly-link list is used (with L->prev and L->next). -// The value D(j,j) can be negative (that is, the matrix being factorized -// can be symmetric indefinite but with all principal minor matrices being -// full rank). -// -// LL': this is the same format as LL', except the first entry in each -// column is L(j,j). The diagonal matrix D is not preset. -// -// (3) supernodal symbolic: this represents the nonzero pattern of the -// supernodes for a supernodal factorization, with L->nsuper supernodes. -// The kth supernode contains columns L->super [k] to L->super [k+1]-1. -// Its row indices are held in L->s [L->pi [k] ... L->pi [k+1]-1]. -// L->x is not allocated, and is NULL. -// -// (4) supernodal numeric: This is always an LL' factorization (not LDL'). -// L->x holds then numeric values of each supernode. The values of -// the kth supernode (for the real case) are held in -// L->x [L->px [k] ... L->px [k+1]-1]. The factor can be complex but -// not zomplex (L->z is never used for a supernodal numeric factor). -// -// Within each column, or which each supernode, the row indices in L->i -// (simplicial) or L->s (supernodal) are kept sorted, from low to high. -// -// This function, cholmod_change_factor and cholmod_l_change_factor, converts -// a factor object between these representations, with some limitations: -// -// (a) a simplicial numeric factor cannot be converted to supernodal. -// -// (b) only a symbolic factor (simplicial or supernodal) can be converted -// into a supernodal numeric factor. -// -// (c) L->dtype is not changed (single or double precision). -// -// (d) L->xtype can be changed but the numeric contents of L are discarded. -// -// Some of these conversions are only meant for internal use by CHOLMOD itself, -// and they allocate space whose contents are not defined: simplicial -// symbolic to supernodal symbolic, and converting any factor to supernodal -// numeric. CHOLMOD performs these conversions just before it does its -// numeric factorization. - -#include "cholmod_internal.h" - -#define RETURN_IF_ERROR(result) \ -{ \ - if (Common->status < CHOLMOD_OK) \ - { \ - return result ; \ - } \ -} - -//------------------------------------------------------------------------------ -// grow_column: increase the space for a single column of L -//------------------------------------------------------------------------------ - -static Int grow_column (Int len, double grow1, double grow2, Int maxlen) -{ - double xlen = (double) len ; - xlen = grow1 * xlen + grow2 ; - xlen = MIN (xlen, maxlen) ; - len = (Int) xlen ; - len = MAX (1, len) ; - len = MIN (len, maxlen) ; - return (len) ; -} - -//------------------------------------------------------------------------------ -// grow_L: grow the space at the end of L -//------------------------------------------------------------------------------ - -static Int grow_L (Int lnz, double grow0, Int n) -{ - double xlnz = (double) lnz ; - xlnz *= grow0 ; - xlnz = MIN (xlnz, (double) SIZE_MAX) ; - double d = (double) n ; - d = (d*d + d) / 2 ; - xlnz = MIN (xlnz, d) ; - lnz = (Int) xlnz ; - return (lnz) ; -} - -//------------------------------------------------------------------------------ -// t_cholmod_change_factor_*_worker -//------------------------------------------------------------------------------ - -#define DOUBLE - - #define REAL - #include "t_cholmod_change_factor_1_worker.c" - #include "t_cholmod_change_factor_2_worker.c" - #include "t_cholmod_change_factor_3_worker.c" - #undef REAL - - #define COMPLEX - #include "t_cholmod_change_factor_1_worker.c" - #include "t_cholmod_change_factor_2_worker.c" - #include "t_cholmod_change_factor_3_worker.c" - #undef COMPLEX - - #define ZOMPLEX - #include "t_cholmod_change_factor_1_worker.c" - #include "t_cholmod_change_factor_2_worker.c" - #undef ZOMPLEX - -#undef DOUBLE -#define SINGLE - - #define REAL - #include "t_cholmod_change_factor_1_worker.c" - #include "t_cholmod_change_factor_2_worker.c" - #include "t_cholmod_change_factor_3_worker.c" - #undef REAL - - #define COMPLEX - #include "t_cholmod_change_factor_1_worker.c" - #include "t_cholmod_change_factor_2_worker.c" - #include "t_cholmod_change_factor_3_worker.c" - #undef COMPLEX - - #define ZOMPLEX - #include "t_cholmod_change_factor_1_worker.c" - #include "t_cholmod_change_factor_2_worker.c" - #undef ZOMPLEX - -//------------------------------------------------------------------------------ -// natural list: create a doubly-link list of columns, in ordering 0 to n-1 -//------------------------------------------------------------------------------ - -// The head of the link list is always n+1, and the tail is always n, where -// n = L->n. The actual columns of L are in range 0 to L->n. - -static void natural_list (cholmod_factor *L) -{ - // get inputs - Int *Lnext = (Int *) L->next ; - Int *Lprev = (Int *) L->prev ; - ASSERT (Lprev != NULL && Lnext != NULL) ; - Int n = L->n ; - - // create the head node - Int head = n+1 ; - Lnext [head] = 0 ; - Lprev [head] = EMPTY ; - - // create the tail node - Int tail = n ; - Lnext [tail] = EMPTY ; - Lprev [tail] = n-1 ; - - // link columns 0 to n-1 in increasing order: 0, 1, 2, ... n-1 - for (Int j = 0 ; j < n ; j++) - { - Lnext [j] = j+1 ; - Lprev [j] = j-1 ; - } - - // the prev node of the first coumn 0 is n+1 - Lprev [0] = head ; - - // the columns appear in order 0, 1, 2, ... n-1 in the link list - L->is_monotonic = TRUE ; -} - - -//------------------------------------------------------------------------------ -// L_is_packed: return true if no column of L has any extra space after it -//------------------------------------------------------------------------------ - -// This method is used for debugging only. - -#ifndef NDEBUG -static int L_is_packed (cholmod_factor *L, cholmod_common *Common) -{ - Int *Lnz = (Int *) L->nz ; - Int *Lp = (Int *) L->p ; - Int n = L->n ; - - if (Lnz == NULL || Lp == NULL || L->xtype == CHOLMOD_PATTERN || L->is_super) - { - // nothing to check: L is intrinsically packed - return (TRUE) ; - } - - if (!L->is_monotonic) - { - // L is not packed, by definition - return (FALSE) ; - } - - for (Int j = 0 ; j < n ; j++) - { - PRINT3 (("j: "ID" Lnz "ID" Lp[j+1] "ID" Lp[j] "ID"\n", j, Lnz [j], - Lp [j+1], Lp [j])) ; - Int total_space_for_column_j = Lp [j+1] - Lp [j] ; - Int entries_in_column_j = Lnz [j] ; - if (entries_in_column_j != total_space_for_column_j) - { - // L(:,j) has extra slack space at the end of the column - PRINT2 (("L is not packed\n")) ; - return (FALSE) ; - } - } - - // L is packed - return (TRUE) ; -} -#endif - -//------------------------------------------------------------------------------ -// alloc_simplicial_num: allocate size-n arrays for simplicial numeric -//------------------------------------------------------------------------------ - -// Does not allocate L->i, L->x, or L->z, which are larger. -// See also cholmod_alloc_factor, which allocates L->Perm and L->ColCount. - -static int alloc_simplicial_num -( - cholmod_factor *L, - cholmod_common *Common -) -{ - - //-------------------------------------------------------------------------- - // check inputs - //-------------------------------------------------------------------------- - - ASSERT (L->xtype == CHOLMOD_PATTERN || L->is_super) ; - ASSERT (L->p == NULL) ; - ASSERT (L->nz == NULL) ; - ASSERT (L->prev == NULL) ; - ASSERT (L->next == NULL) ; - - size_t n = L->n ; - - //-------------------------------------------------------------------------- - // allocate the four arrays - //-------------------------------------------------------------------------- - - Int *Lp = CHOLMOD(malloc) (n+1, sizeof (Int), Common) ; - Int *Lnz = CHOLMOD(malloc) (n, sizeof (Int), Common) ; - Int *Lprev = CHOLMOD(malloc) (n+2, sizeof (Int), Common) ; - Int *Lnext = CHOLMOD(malloc) (n+2, sizeof (Int), Common) ; - - //-------------------------------------------------------------------------- - // check if out of memory - //-------------------------------------------------------------------------- - - if (Common->status < CHOLMOD_OK) - { - // out of memory - CHOLMOD(free) (n+1, sizeof (Int), Lp, Common) ; - CHOLMOD(free) (n, sizeof (Int), Lnz, Common) ; - CHOLMOD(free) (n+2, sizeof (Int), Lprev, Common) ; - CHOLMOD(free) (n+2, sizeof (Int), Lnext, Common) ; - return (FALSE) ; - } - - //-------------------------------------------------------------------------- - // place the arrays in L - //-------------------------------------------------------------------------- - - L->p = Lp ; - L->nz = Lnz ; - L->prev = Lprev ; - L->next = Lnext ; - - //-------------------------------------------------------------------------- - // initialize the link list of the columns of L - //-------------------------------------------------------------------------- - - natural_list (L) ; - return (TRUE) ; -} - -//------------------------------------------------------------------------------ -// simplicial_sym_to_super_sym: converts simplicial symbolic to super -//------------------------------------------------------------------------------ - -// converts a simplicial symbolic factor to supernodal symbolic. The space -// is allocated but not initialized. - -static int simplicial_sym_to_super_sym -( - cholmod_factor *L, - cholmod_common *Common -) -{ - - //-------------------------------------------------------------------------- - // check inputs - //-------------------------------------------------------------------------- - - ASSERT (L->xtype == CHOLMOD_PATTERN && !(L->is_super)) ; - - //-------------------------------------------------------------------------- - // allocate L->super, L->pi, L->px, and L->s - //-------------------------------------------------------------------------- - - Int *Lsuper = CHOLMOD(malloc) (L->nsuper+1, sizeof (Int), Common) ; - Int *Lpi = CHOLMOD(malloc) (L->nsuper+1, sizeof (Int), Common) ; - Int *Lpx = CHOLMOD(malloc) (L->nsuper+1, sizeof (Int), Common) ; - Int *Ls = CHOLMOD(malloc) (L->ssize, sizeof (Int), Common) ; - - //-------------------------------------------------------------------------- - // check if out of memory - //-------------------------------------------------------------------------- - - if (Common->status < CHOLMOD_OK) - { - // out of memory - CHOLMOD(free) (L->nsuper+1, sizeof (Int), Lsuper, Common) ; - CHOLMOD(free) (L->nsuper+1, sizeof (Int), Lpi, Common) ; - CHOLMOD(free) (L->nsuper+1, sizeof (Int), Lpx, Common) ; - CHOLMOD(free) (L->ssize, sizeof (Int), Ls, Common) ; - return (FALSE) ; - } - - //-------------------------------------------------------------------------- - // place the arrays in L - //-------------------------------------------------------------------------- - - L->super = Lsuper ; - L->pi = Lpi ; - L->px = Lpx ; - L->s = Ls ; - - //-------------------------------------------------------------------------- - // revise the header of L (L->dtype is not changed) - //-------------------------------------------------------------------------- - - L->xtype = CHOLMOD_PATTERN ; // L is symbolic (no L->x, L->i, L->z) - L->is_super = TRUE ; // L is now supernodal - Ls [0] = EMPTY ; // contents of supernodal pattern undefined - L->is_ll = TRUE ; // L is a supernodal LL' factorization - L->maxcsize = 0 ; // size of largest update matrix - L->maxesize = 0 ; // max rows in any supernode excl tri. part) - L->minor = L->n ; // see cholmod.h for a description - return (TRUE) ; -} - -//------------------------------------------------------------------------------ -// super_num_to_super_sym: convert numeric supernodal to symbolic -//------------------------------------------------------------------------------ - -// This method converts a supernodal numeric factor L to supernodal symbolic, -// by freeing the numeric values of all the supernodes. The supernodal -// pattern (L->s) is kept. - -static void super_num_to_super_sym -( - cholmod_factor *L, - cholmod_common *Common -) -{ - - //-------------------------------------------------------------------------- - // check inputs - //-------------------------------------------------------------------------- - - ASSERT (L->xtype != CHOLMOD_PATTERN) ; - ASSERT (L->xtype != CHOLMOD_ZOMPLEX) ; - ASSERT (L->is_super) ; - ASSERT (L->is_ll) ; - DEBUG (CHOLMOD(dump_factor) (L, "supernum to supersym:L input", Common)) ; - - //-------------------------------------------------------------------------- - // free L->x only - //-------------------------------------------------------------------------- - - size_t e = (L->dtype == CHOLMOD_SINGLE) ? sizeof (float) : sizeof (double) ; - size_t ex = e * ((L->xtype == CHOLMOD_PATTERN) ? 0 : - ((L->xtype == CHOLMOD_COMPLEX) ? 2 : 1)) ; - - L->x = CHOLMOD(free) (L->xsize, ex, L->x, Common) ; - - //-------------------------------------------------------------------------- - // change the header contents to reflect the supernodal symbolic status - //-------------------------------------------------------------------------- - - L->xtype = CHOLMOD_PATTERN ; // L is symbolic - L->minor = L->n ; // see cholmod.h - L->is_ll = TRUE ; // supernodal factor is always LL', not LDL' - DEBUG (CHOLMOD(dump_factor) (L, "supernum to supersym:L output", Common)) ; -} - -//------------------------------------------------------------------------------ -// simplicial_sym_to_simplicial_num: convert simplicial numeric to symbolic -//------------------------------------------------------------------------------ - -// This methods allocates space and converts a simplicial symbolic L to -// simplicial numeric. L is set to the identity matrix, except in one case -// where the contents of L are not initialized (packed < 0 case). - -static void simplicial_sym_to_simplicial_num -( - cholmod_factor *L, // factor to modify - int to_ll, // if true, convert to LL. if false: to LDL' - int packed, // if > 0: L is packed, if 0: L is unpacked, - // if < 0: L is packed but contents are not initialized - int to_xtype, // the L->xtype (real, complex, or zomplex) - cholmod_common *Common -) -{ - - //-------------------------------------------------------------------------- - // check inputs - //-------------------------------------------------------------------------- - - ASSERT (L->xtype == CHOLMOD_PATTERN && !(L->is_super)) ; - - //-------------------------------------------------------------------------- - // allocate space for the simplicial numeric factor (except L->(i,x,z)) - //-------------------------------------------------------------------------- - - if (!alloc_simplicial_num (L, Common)) - { - // out of memory; error status is already in Common->status - return ; - } - - //-------------------------------------------------------------------------- - // get inputs - //-------------------------------------------------------------------------- - - Int n = L->n ; - Int *Lp = L->p ; - Int *Lnz = L->nz ; - Int *ColCount = L->ColCount ; - - //-------------------------------------------------------------------------- - // initialize L->p and L->nz - //-------------------------------------------------------------------------- - - bool ok = true ; - Int lnz = 0 ; - - if (packed < 0) - { - - //---------------------------------------------------------------------- - // do not initialize the space - //---------------------------------------------------------------------- - - lnz = L->nzmax ; - L->nzmax = 0 ; - - } - else if (packed > 0) - { - - //---------------------------------------------------------------------- - // initialize the packed LL' or LDL' case (L is identity) - //---------------------------------------------------------------------- - - for (Int j = 0 ; j < n ; j++) - { - // ensure ColCount [j] is in the range 1 to n-j - Int len = ColCount [j] ; - len = MAX (1, len) ; - len = MIN (len, n-j) ; - lnz += len ; - ok = (lnz >= 0) ; - if (!ok) break ; - } - // each column L(:,j) holds a single diagonal entry - for (Int j = 0 ; j <= n ; j++) - { - Lp [j] = j ; - } - for (Int j = 0 ; j < n ; j++) - { - Lnz [j] = 1 ; - } - - } - else - { - - //---------------------------------------------------------------------- - // initialize the unpacked LL' or LDL' case (L is identity) - //---------------------------------------------------------------------- - - // slack space will be added to L below - double grow0 = Common->grow0 ; - double grow1 = Common->grow1 ; - double grow2 = (double) Common->grow2 ; - grow0 = isnan (grow0) ? 1 : grow0 ; - grow1 = isnan (grow1) ? 1 : grow1 ; - Int grow = (grow0 >= 1.0) && (grow1 >= 1.0) && (grow2 > 0) ; - - for (Int j = 0 ; j < n ; j++) - { - - //------------------------------------------------------------------ - // log the start of L(:,j), containing a single entry - //------------------------------------------------------------------ - - Lp [j] = lnz ; - Lnz [j] = 1 ; - - //------------------------------------------------------------------ - // ensure ColCount [j] is in the range 1 to n-j - //------------------------------------------------------------------ - - Int len = ColCount [j] ; - len = MAX (1, len) ; - len = MIN (len, n-j) ; - - //------------------------------------------------------------------ - // add some slack space to L(:,j) - //------------------------------------------------------------------ - - if (grow) - { - len = grow_column (len, grow1, grow2, n-j) ; - } - lnz += len ; - ok = (lnz >= 0) ; - if (!ok) break ; - } - - //---------------------------------------------------------------------- - // add slack space at the end of L - //---------------------------------------------------------------------- - - if (ok) - { - Lp [n] = lnz ; - if (grow) - { - lnz = grow_L (lnz, grow0, n) ; - } - } - } - - //-------------------------------------------------------------------------- - // allocate L->i, L->x, and L->z with the new xtype and existing dtype - //-------------------------------------------------------------------------- - - ASSERT (L->nzmax == 0) ; - lnz = MAX (1, lnz) ; - int nint = 1 ; - if (!ok || !CHOLMOD(realloc_multiple) (lnz, nint, to_xtype + L->dtype, - &(L->i), NULL, &(L->x), &(L->z), &(L->nzmax), Common)) - { - // out of memory: convert L back to simplicial symbolic - CHOLMOD(to_simplicial_sym) (L, to_ll, Common) ; - return ; - } - - L->xtype = to_xtype ; - L->minor = n ; - - //-------------------------------------------------------------------------- - // set L to the identity matrix, if requested - //-------------------------------------------------------------------------- - - if (packed >= 0) - { - - switch ((L->xtype + L->dtype) % 8) - { - case CHOLMOD_SINGLE + CHOLMOD_REAL: - r_s_cholmod_change_factor_1_worker (L) ; - break ; - - case CHOLMOD_SINGLE + CHOLMOD_COMPLEX: - c_s_cholmod_change_factor_1_worker (L) ; - break ; - - case CHOLMOD_SINGLE + CHOLMOD_ZOMPLEX: - z_s_cholmod_change_factor_1_worker (L) ; - break ; - - case CHOLMOD_DOUBLE + CHOLMOD_REAL: - r_cholmod_change_factor_1_worker (L) ; - break ; - - case CHOLMOD_DOUBLE + CHOLMOD_COMPLEX: - c_cholmod_change_factor_1_worker (L) ; - break ; - - case CHOLMOD_DOUBLE + CHOLMOD_ZOMPLEX: - z_cholmod_change_factor_1_worker (L) ; - break ; - } - } - - L->is_ll = to_ll ; -} - -//------------------------------------------------------------------------------ -// change_simplicial_num: change LL' to LDL' or LDL' to LL' -//------------------------------------------------------------------------------ - -// L must be simplicial numeric. -// -// to_ll: if true, L is converted to LL'; if false, to LDL' -// to_packed: if true, L is converted to packed and monotonic -// (to_monotonic is treated as true) -// -// to_monotonoic: if true but to_packed is false, L is converted to monotonic -// but the columns are not packed. Slack space is left in -// the columns of L. -// -// If both to_packed and to_monotonic are false: the columns of L are -// converted in place, and neither packed nor made monotonic. -// -// To convert LDL' to LL', columns with D(j,j) <= 0 are left as-is, but L is -// not numerically valid. The column L(:,j) is unchanged. If converted back -// to LDL', the column is also left as-is, so that the LDL' can be recovered. -// L->minor is set to the first j where D(j,j) <= 0. - -static void change_simplicial_num -( - cholmod_factor *L, // factor to modify - int to_ll, // if true: convert to LL'; else LDL' - int to_packed, // if true: pack the columns of L - int to_monotonic, // if true: make columns of L monotonic - cholmod_common *Common -) -{ - - //-------------------------------------------------------------------------- - // check inputs - //-------------------------------------------------------------------------- - - ASSERT (Common != NULL) ; - DEBUG (CHOLMOD(dump_factor) (L, "change simplnum:L input", Common)) ; - ASSERT (L->xtype != CHOLMOD_PATTERN) ; - ASSERT (!L->is_super) ; - - //-------------------------------------------------------------------------- - // get inputs - //-------------------------------------------------------------------------- - - bool out_of_place = ((to_packed || to_monotonic) && !(L->is_monotonic)) ; - bool make_ll = (to_ll && !(L->is_ll)) ; - bool make_ldl = (!to_ll && L->is_ll) ; - - Int n = L->n ; - Int *Lp = (Int *) L->p ; - Int *Li = (Int *) L->i ; - Int *Lnz = (Int *) L->nz ; - - bool grow = false ; - double grow0 = Common->grow0 ; - double grow1 = Common->grow1 ; - double grow2 = (double) Common->grow2 ; - grow0 = isnan (grow0) ? 1 : grow0 ; - grow1 = isnan (grow1) ? 1 : grow1 ; - - void *Li2 = NULL ; - void *Lx2 = NULL ; - void *Lz2 = NULL ; - - size_t ei = sizeof (Int) ; - size_t e = (L->dtype == CHOLMOD_SINGLE) ? sizeof (float) : sizeof (double) ; - size_t ex = e * ((L->xtype == CHOLMOD_COMPLEX) ? 2 : 1) ; - size_t ez = e * ((L->xtype == CHOLMOD_ZOMPLEX) ? 1 : 0) ; - - //-------------------------------------------------------------------------- - // resize if changing to monotonic and/or packed and not already monotonic - //-------------------------------------------------------------------------- - - Int lnz = 0 ; - - if (out_of_place) - { - - //---------------------------------------------------------------------- - // out-of-place: construct L in new space (Li2, Lx2, and Lz2) - //---------------------------------------------------------------------- - - // The columns of L are out of order (not monotonic), but L is being - // changed to being either monotonic, or packed, or both. Thus, L - // needs to be resized, in newly allocated space (Li2, Lx2, and Lz2). - - //---------------------------------------------------------------------- - // determine if L should grow - //---------------------------------------------------------------------- - - if (!to_packed) - { - grow = (grow0 >= 1.0) && (grow1 >= 1.0) && (grow2 > 0) ; - } - - //---------------------------------------------------------------------- - // compute the new space for each column of L - //---------------------------------------------------------------------- - - for (Int j = 0 ; j < n ; j++) - { - Int len = Lnz [j] ; - ASSERT (len >= 1 && len <= n-j) ; - if (grow) - { - len = grow_column (len, grow1, grow2, n-j) ; - } - ASSERT (len >= Lnz [j] && len <= n-j) ; - lnz += len ; - if (lnz <= 0) - { - ERROR (CHOLMOD_TOO_LARGE, "problem too large") ; - return ; - } - } - - //---------------------------------------------------------------------- - // add additional space at the end of L, if requested - //---------------------------------------------------------------------- - - if (grow) - { - lnz = grow_L (lnz, grow0, n) ; - } - - //---------------------------------------------------------------------- - // allocate Li2, Lx2, and Lz2 (as newly allocated space) - //---------------------------------------------------------------------- - - lnz = MAX (1, lnz) ; - int nint = 1 ; - size_t nzmax0 = 0 ; - CHOLMOD(realloc_multiple) (lnz, nint, L->xtype + L->dtype, &Li2, - NULL, &Lx2, &Lz2, &nzmax0, Common) ; - RETURN_IF_ERROR () ; - } - - //-------------------------------------------------------------------------- - // convert the simplicial L - //-------------------------------------------------------------------------- - - switch ((L->xtype + L->dtype) % 8) - { - case CHOLMOD_SINGLE + CHOLMOD_REAL: - r_s_cholmod_change_factor_2_worker (L, to_packed, Li2, Lx2, Lz2, - lnz, grow, grow1, grow2, make_ll, out_of_place, make_ldl, - Common) ; - break ; - - case CHOLMOD_SINGLE + CHOLMOD_COMPLEX: - c_s_cholmod_change_factor_2_worker (L, to_packed, Li2, Lx2, Lz2, - lnz, grow, grow1, grow2, make_ll, out_of_place, make_ldl, - Common) ; - break ; - - case CHOLMOD_SINGLE + CHOLMOD_ZOMPLEX: - z_s_cholmod_change_factor_2_worker (L, to_packed, Li2, Lx2, Lz2, - lnz, grow, grow1, grow2, make_ll, out_of_place, make_ldl, - Common) ; - break ; - - case CHOLMOD_DOUBLE + CHOLMOD_REAL: - r_cholmod_change_factor_2_worker (L, to_packed, Li2, Lx2, Lz2, - lnz, grow, grow1, grow2, make_ll, out_of_place, make_ldl, - Common) ; - break ; - - case CHOLMOD_DOUBLE + CHOLMOD_COMPLEX: - c_cholmod_change_factor_2_worker (L, to_packed, Li2, Lx2, Lz2, - lnz, grow, grow1, grow2, make_ll, out_of_place, make_ldl, - Common) ; - break ; - - case CHOLMOD_DOUBLE + CHOLMOD_ZOMPLEX: - z_cholmod_change_factor_2_worker (L, to_packed, Li2, Lx2, Lz2, - lnz, grow, grow1, grow2, make_ll, out_of_place, make_ldl, - Common) ; - break ; - } - - //-------------------------------------------------------------------------- - // finalize the result L - //-------------------------------------------------------------------------- - - L->is_ll = to_ll ; - - if (out_of_place) - { - - //---------------------------------------------------------------------- - // free the old space and move the new space into L - //---------------------------------------------------------------------- - - CHOLMOD(free) (L->nzmax, ei, L->i, Common) ; - CHOLMOD(free) (L->nzmax, ex, L->x, Common) ; - CHOLMOD(free) (L->nzmax, ez, L->z, Common) ; - - L->i = Li2 ; - L->x = Lx2 ; - L->z = Lz2 ; - L->nzmax = lnz ; - - //---------------------------------------------------------------------- - // revise the link list (columns 0 to n-1 now in natural order) - //---------------------------------------------------------------------- - - natural_list (L) ; - } - - DEBUG (CHOLMOD(dump_factor) (L, "change simplnum:L output", Common)) ; -} - -//------------------------------------------------------------------------------ -// super_num_to_simplicial_num: convert supernodal numeric to simplicial numeric -//------------------------------------------------------------------------------ - -static void super_num_to_simplicial_num -( - cholmod_factor *L, - int to_packed, - int to_ll, - cholmod_common *Common -) -{ - - //-------------------------------------------------------------------------- - // check inputs - //-------------------------------------------------------------------------- - - ASSERT (L != NULL) ; - ASSERT (Common != NULL) ; - DEBUG (CHOLMOD(dump_factor) (L, "supernum to simplnum:L input", Common)) ; - ASSERT (L->xtype != CHOLMOD_PATTERN) ; - ASSERT (L->xtype != CHOLMOD_ZOMPLEX) ; - ASSERT (L->is_ll) ; - ASSERT (L->is_super) ; - ASSERT (L->x != NULL) ; - ASSERT (L->i == NULL) ; - ASSERT (L->z == NULL) ; - - //-------------------------------------------------------------------------- - // get inputs - //-------------------------------------------------------------------------- - - Int n = L->n ; - Int nsuper = L->nsuper ; - Int *Lpi = (Int *) L->pi ; - Int *Lpx = (Int *) L->px ; - Int *Ls = (Int *) L->s ; - Int *Super = (Int *) L->super ; - - size_t ei = sizeof (Int) ; - size_t e = (L->dtype == CHOLMOD_SINGLE) ? sizeof (float) : sizeof (double) ; - size_t ex = e * ((L->xtype == CHOLMOD_COMPLEX) ? 2 : 1) ; - - //-------------------------------------------------------------------------- - // determine the size of L after conversion to simplicial numeric - //-------------------------------------------------------------------------- - - Int lnz = 0 ; - - if (to_packed) - { - - //---------------------------------------------------------------------- - // count the # of nonzeros in all supernodes of L - //---------------------------------------------------------------------- - - // Each supernode is lower trapezoidal, with a top part that is lower - // triangular (with diagonal present) and a bottom part that is - // rectangular. In this example below, nscol = 5, so the supernode - // represents 5 columns of L, and nsrow = 8, which means that the - // first column of the supernode has 8 entries, including the - // diagonal. - // - // x . . . . - // x x . . . - // x x x . . - // x x x x . - // x x x x x - // x x x x x - // x x x x x - // x x x x x - // - // The '.' entries above are in the data structure but not used, and - // are not copied into the simplicial factor L. The 'x' entries are - // used, but some might be exactly equal to zero. Some of these zeros - // come from relaxed supernodal algamation, and some come from exact - // numeric cancellation. These entries appear in the final - // simplicial factor L. - - for (Int s = 0 ; s < nsuper ; s++) - { - - //------------------------------------------------------------------ - // get the supernode - //------------------------------------------------------------------ - - Int k1 = Super [s] ; // L(:,k1) is 1st col in supernode s - Int k2 = Super [s+1] ; // L(:,k2) is 1st col in supernode s+1 - Int psi = Lpi [s] ; // start of pattern in Ls of supernode s - Int psend = Lpi [s+1] ; // start of pattern in Ls of s+1 - Int nsrow = psend - psi ; // # entries in 1st col of supernode s - Int nscol = k2 - k1 ; // # of columns in supernode - ASSERT (nsrow >= nscol) ; - Int erows = nsrow - nscol ; // # of rows below triangular part - - //------------------------------------------------------------------ - // count the entries in the supernode, including any exact zeros - //------------------------------------------------------------------ - - // lower triangular part - lnz += nscol * (nscol+1) / 2 ; - - // rectangular part - lnz += nscol * erows ; - } - - } - else - { - - //---------------------------------------------------------------------- - // the supernodal L will not be packed - //---------------------------------------------------------------------- - - // L->x holds all numeric values of the supernodes, and these entries - // will remain in place. L->x will not be decreased in size, so Li - // will have the same size as L->x. - - lnz = L->xsize ; - } - - ASSERT (lnz >= 0 && lnz <= (Int) (L->xsize)) ; - - //-------------------------------------------------------------------------- - // allocate Li for the pattern L->i of the simplicial factor of L - //-------------------------------------------------------------------------- - - Int *Li = CHOLMOD(malloc) (lnz, ei, Common) ; - RETURN_IF_ERROR () ; - - //-------------------------------------------------------------------------- - // allocate the size-n arrays for L: L->p, L->nz, L->prev, and L->nex - //-------------------------------------------------------------------------- - - if (!alloc_simplicial_num (L, Common)) - { - // out of memory - CHOLMOD(free) (lnz, ei, Li, Common) ; - return ; - } - - //-------------------------------------------------------------------------- - // convert the supernodal numeric L into a simplicial numeric L - //-------------------------------------------------------------------------- - - L->i = Li ; - L->nzmax = lnz ; - - switch ((L->xtype + L->dtype) % 8) - { - case CHOLMOD_SINGLE + CHOLMOD_REAL: - r_s_cholmod_change_factor_3_worker (L, to_packed, to_ll, Common) ; - break ; - - case CHOLMOD_SINGLE + CHOLMOD_COMPLEX: - c_s_cholmod_change_factor_3_worker (L, to_packed, to_ll, Common) ; - break ; - - case CHOLMOD_DOUBLE + CHOLMOD_REAL: - r_cholmod_change_factor_3_worker (L, to_packed, to_ll, Common) ; - break ; - - case CHOLMOD_DOUBLE + CHOLMOD_COMPLEX: - c_cholmod_change_factor_3_worker (L, to_packed, to_ll, Common) ; - break ; - } - - //-------------------------------------------------------------------------- - // reduce the size of L->x to match L->i (this cannot fail) - //-------------------------------------------------------------------------- - - L->x = CHOLMOD(realloc) (lnz, ex, L->x, &(L->xsize), Common) ; - Common->status = CHOLMOD_OK ; - - //-------------------------------------------------------------------------- - // free the supernodal parts of L and return result - //-------------------------------------------------------------------------- - - L->is_super = FALSE ; // L is now simplicial - L->is_ll = to_ll ; // L is LL' or LDL', according to to_ll - L->pi = CHOLMOD(free) (nsuper+1, ei, L->pi, Common) ; - L->px = CHOLMOD(free) (nsuper+1, ei, L->px, Common) ; - L->super = CHOLMOD(free) (nsuper+1, ei, L->super, Common) ; - L->s = CHOLMOD(free) (L->ssize, ei, L->s, Common) ; - L->ssize = 0 ; // L->s is not present - L->xsize = 0 ; // L->x is not present - L->nsuper = 0 ; // no supernodes - L->maxesize = 0 ; // no rows in any supernodes - L->maxcsize = 0 ; // largest update matrix is size zero - - DEBUG (CHOLMOD(dump_factor) (L, "supernum to simplnum:L output", Common)) ; -} - -//------------------------------------------------------------------------------ -// super_sym_to_super_num: convert supernodal symbolic to numeric -//------------------------------------------------------------------------------ - -static int super_sym_to_super_num -( - int to_xtype, - cholmod_factor *L, - cholmod_common *Common -) -{ - - //-------------------------------------------------------------------------- - // check inputs - //-------------------------------------------------------------------------- - - ASSERT (L != NULL) ; - ASSERT (Common != NULL) ; - ASSERT (L->xtype == CHOLMOD_PATTERN) ; - ASSERT (L->is_super) ; - ASSERT (L->x == NULL) ; - ASSERT (to_xtype == CHOLMOD_REAL || to_xtype == CHOLMOD_COMPLEX) ; - - //-------------------------------------------------------------------------- - // get the sizes of the entries - //-------------------------------------------------------------------------- - - size_t ei = sizeof (Int) ; - size_t e = (L->dtype == CHOLMOD_SINGLE) ? sizeof (float) : sizeof (double) ; - size_t ex = e * ((to_xtype == CHOLMOD_COMPLEX) ? 2 : 1) ; - size_t xs = L->xsize ; - - //-------------------------------------------------------------------------- - // allocate the space - //-------------------------------------------------------------------------- - - double *Lx = CHOLMOD(malloc) (xs, ex, Common) ; - RETURN_IF_ERROR ((FALSE)) ; - - //-------------------------------------------------------------------------- - // finalize L and return result - //-------------------------------------------------------------------------- - - // clear the first few entries so valgrind is satisfied - memset (Lx, 0, MIN (2 * sizeof (double), xs*ex)) ; - L->x = Lx ; // new space for numeric values - L->xtype = to_xtype ; // real or complex - L->minor = L->n ; - return (TRUE) ; -} - -//============================================================================== -// cholmod_change_factor -//============================================================================== - -// Convert a factor L. Some conversions simply allocate uninitialized space -// that is meant to be filled later. - -int CHOLMOD(change_factor) -( - int to_xtype, // CHOLMOD_PATTERN, _REAL, _COMPLEX, or _ZOMPLEX - int to_ll, // if true: convert to LL'; else to LDL' - int to_super, // if true: convert to supernodal; else to simplicial - int to_packed, // if true: pack simplicial columns' else: do not pack - int to_monotonic, // if true, put simplicial columns in order - cholmod_factor *L, // factor to change - cholmod_common *Common -) -{ - - //-------------------------------------------------------------------------- - // check inputs - //-------------------------------------------------------------------------- - - RETURN_IF_NULL_COMMON (FALSE) ; - RETURN_IF_NULL (L, FALSE) ; - RETURN_IF_XTYPE_INVALID (L, CHOLMOD_PATTERN, CHOLMOD_ZOMPLEX, FALSE) ; - Common->status = CHOLMOD_OK ; - - to_xtype = to_xtype & 3 ; - to_ll = to_ll ? 1 : 0 ; - if (to_super && (to_xtype == CHOLMOD_ZOMPLEX)) - { - ERROR (CHOLMOD_INVALID, "supernodal zomplex L not supported") ; - return (FALSE) ; - } - - PRINT1 (("-----convert from (%d,%d,%d,%d,%d) to (%d,%d,%d,%d,%d)\n", - L->xtype, L->is_ll, L->is_super, L_is_packed (L, Common), L->is_monotonic, - to_xtype, to_ll, to_super, to_packed, to_monotonic)) ; - - //-------------------------------------------------------------------------- - // convert the factor L - //-------------------------------------------------------------------------- - - if (to_xtype == CHOLMOD_PATTERN) - { - - //---------------------------------------------------------------------- - // convert to symbolic - //---------------------------------------------------------------------- - - if (!to_super) - { - - //------------------------------------------------------------------ - // convert to simplicial symbolic factor (this cannot fail) - //------------------------------------------------------------------ - - CHOLMOD(to_simplicial_sym) (L, to_ll, Common) ; - - } - else - { - - //------------------------------------------------------------------ - // convert to supernodal symbolic factor - //------------------------------------------------------------------ - - if (L->xtype != CHOLMOD_PATTERN && L->is_super) - { - // convert supernodal numeric to supernodal symbolic, - // keeping the pattern but freeing the numeric values. - super_num_to_super_sym (L, Common) ; - } - else if (L->xtype == CHOLMOD_PATTERN && !(L->is_super)) - { - // convert simplicial symbolic to supernodal symbolic, - // only meant for use internally to CHOLMOD. - simplicial_sym_to_super_sym (L, Common) ; - } - else - { - // can't convert simplicial numeric to supernodal symbolic - ERROR (CHOLMOD_INVALID, "failed to change L") ; - return (FALSE) ; - } - } - - } - else - { - - //---------------------------------------------------------------------- - // convert to numeric - //---------------------------------------------------------------------- - - if (to_super) - { - - //------------------------------------------------------------------ - // convert to supernodal numeric factor - //------------------------------------------------------------------ - - if (L->xtype == CHOLMOD_PATTERN) - { - if (L->is_super) - { - // convert supernodal symbolic to supernodal numeric, - // only meant for use internally to CHOLMOD. - super_sym_to_super_num (to_xtype, L, Common) ; - } - else - { - // convert simplicial symbolic to supernodal numeric, - // only meant for use internally to CHOLMOD. - if (!simplicial_sym_to_super_sym (L, Common)) - { - // failure, convert back to simplicial symbolic - CHOLMOD(to_simplicial_sym) (L, to_ll, Common) ; - return (FALSE) ; - } - // convert supernodal symbolic to supernodal numeric - super_sym_to_super_num (to_xtype, L, Common) ; - } - } - else - { - // nothing to do if already supernodal numeric - if (!(L->is_super)) - { - ERROR (CHOLMOD_INVALID, "failed to change L") ; - return (FALSE) ; - } - } - - } - else - { - - //------------------------------------------------------------------ - // convert any factor to simplicial numeric - //------------------------------------------------------------------ - - if (L->xtype == CHOLMOD_PATTERN && !(L->is_super)) - { - // convert simplicial symbolic to simplicial numeric (L=D=I) - simplicial_sym_to_simplicial_num (L, to_ll, to_packed, - to_xtype, Common) ; - } - else if (L->xtype != CHOLMOD_PATTERN && L->is_super) - { - // convert a supernodal LL' to simplicial numeric - super_num_to_simplicial_num (L, to_packed, to_ll, Common) ; - } - else if (L->xtype == CHOLMOD_PATTERN && L->is_super) - { - // convert a supernodal symbolic to simplicial numeric (L=D=I) - CHOLMOD(to_simplicial_sym) (L, to_ll, Common) ; - simplicial_sym_to_simplicial_num (L, to_ll, to_packed, - to_xtype, Common) ; - } - else - { - // change a simplicial numeric factor: change LL' to LDL', LDL' - // to LL', or leave as-is. pack the columns of L, or leave - // as-is. Ensure the columns are monotonic, or leave as-is. - change_simplicial_num (L, to_ll, to_packed, to_monotonic, - Common) ; - } - } - } - - //-------------------------------------------------------------------------- - // return result - //-------------------------------------------------------------------------- - - return (Common->status >= CHOLMOD_OK) ; -} - diff --git a/CHOLMOD/Utility/t_cholmod_change_factor_1_worker.c b/CHOLMOD/Utility/t_cholmod_change_factor_1_worker.c deleted file mode 100644 index eb64b05f20..0000000000 --- a/CHOLMOD/Utility/t_cholmod_change_factor_1_worker.c +++ /dev/null @@ -1,57 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/t_cholmod_change_factor_1_worker: change factor to identity -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -#include "cholmod_template.h" - -//------------------------------------------------------------------------------ -// t_cholmod_change_factor_1_worker: set L to the identity matrix -//------------------------------------------------------------------------------ - -// L is simplicial numeric. - -static void TEMPLATE (cholmod_change_factor_1_worker) -( - cholmod_factor *L -) -{ - - //-------------------------------------------------------------------------- - // check inputs - //-------------------------------------------------------------------------- - - ASSERT (L->xtype != CHOLMOD_PATTERN) ; - ASSERT (!L->is_super) ; - - //-------------------------------------------------------------------------- - // get inputs - //-------------------------------------------------------------------------- - - Int *Lp = (Int *) L->p ; - Int *Li = (Int *) L->i ; - Real *Lx = (Real *) L->x ; - Real *Lz = (Real *) L->z ; - Int n = L->n ; - - //-------------------------------------------------------------------------- - // set L to the identity matrix - //-------------------------------------------------------------------------- - - Real onex [2] = {1,0} ; - Real onez [1] = {0} ; - - for (Int j = 0 ; j < n ; j++) - { - Int p = Lp [j] ; - ASSERT (p < Lp [j+1]) ; - Li [p] = j ; - ASSIGN (Lx, Lz, p, onex, onez, 0) ; - } -} - diff --git a/CHOLMOD/Utility/t_cholmod_change_factor_2_template.c b/CHOLMOD/Utility/t_cholmod_change_factor_2_template.c deleted file mode 100644 index 1e5988eb7f..0000000000 --- a/CHOLMOD/Utility/t_cholmod_change_factor_2_template.c +++ /dev/null @@ -1,273 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/t_cholmod_change_factor_2_template -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -// Converts a simplicial numeric factor: to/from LL' and LDL', either -// out-of-place or in-place. - -#ifdef OUT_OF_PLACE - // the new L is created in new space: Li2, Lx2, Lz2 - #define Li_NEW Li2 - #define Lx_NEW Lx2 - #define Lz_NEW Lx2 -#else - // L is modified in its existing space: Li, Lx, and Lz - #define Li_NEW Li - #define Lx_NEW Lx - #define Lz_NEW Lz -#endif - -#ifdef IN_PLACE - // Li is not modified. Entries in Lx and Lz are changed but not moved - // to a different place in Lx and Lz - #define p_NEW p -#else - #define p_NEW pnew -#endif - -//------------------------------------------------------------------------------ - -{ - Int pnew = 0 ; - - if (make_ll) - { - - //---------------------------------------------------------------------- - // convert an LDL' factorization to LL' - //---------------------------------------------------------------------- - - for (Int j = 0 ; j < n ; j++) - { - - //------------------------------------------------------------------ - // get column L(:,j) - //------------------------------------------------------------------ - - Int p = Lp [j] ; - Int len = Lnz [j] ; - - // get the diagonal entry, djj = D(j,j) - Real djj [1] ; - ASSIGN_REAL (djj, 0, Lx, p) ; - - if (djj [0] <= 0) - { - - //-------------------------------------------------------------- - // the matrix is not positive definite - //-------------------------------------------------------------- - - // The matrix is not postive-definite and cannot be converted - // to LL'. The column L(:,j) is moved to its new space but not - // numerically modified so it can be converted back to a valid - // LDL' factorization. - - if (L->minor == (size_t) n) - { - ERROR (CHOLMOD_NOT_POSDEF, "L not positive definite") ; - L->minor = j ; - } - - #ifndef IN_PLACE - for (Int k = 0 ; k < len ; k++) - { - Li_NEW [p_NEW+k] = Li [p+k] ; - ASSIGN (Lx_NEW, Lz_NEW, p_NEW+k, Lx, Lz, p+k) ; - } - #endif - - } - else - { - - //-------------------------------------------------------------- - // convert L(:,j) from an LDL' factorization to LL' - //-------------------------------------------------------------- - - // L(j,j) = sqrt (D(j,j)) - Real ljj [1] ; - ljj [0] = sqrt (djj [0]) ; - #ifndef IN_PLACE - Li_NEW [p_NEW] = j ; - #endif - ASSIGN_REAL (Lx_NEW, p_NEW, ljj, 0) ; - CLEAR_IMAG (Lx_NEW, Lz_NEW, p_NEW) ; - - // L(j+1:n,j) = L(j+1:n,j) * L(j,j) - for (Int k = 1 ; k < len ; k++) - { - #ifndef IN_PLACE - Li_NEW [p_NEW+k] = Li [p+k] ; - #endif - MULT_REAL (Lx_NEW, Lz_NEW, p_NEW+k, Lx, Lz, p+k, ljj, 0) ; - } - } - - //------------------------------------------------------------------ - // grow column L(:,j) if requested, and advance to column j+1 - //------------------------------------------------------------------ - - #ifndef IN_PLACE - Lp [j] = p_NEW ; - #ifdef OUT_OF_PLACE - if (grow) len = grow_column (len, grow1, grow2, n-j) ; - #endif - p_NEW += len ; - #endif - } - - // log the end of the last column - #ifndef IN_PLACE - Lp [n] = p_NEW ; - #endif - - } - else if (make_ldl) - { - - //---------------------------------------------------------------------- - // convert an LL' factorization to LDL' - //---------------------------------------------------------------------- - - for (Int j = 0 ; j < n ; j++) - { - - //------------------------------------------------------------------ - // get column L(:,j) - //------------------------------------------------------------------ - - Int len = Lnz [j] ; - Int p = Lp [j] ; - - // get the diagonal entry, ljj = L(j,j) - Real ljj [1] ; - ASSIGN_REAL (ljj, 0, Lx, p) ; - - if (ljj [0] <= 0) - { - - //-------------------------------------------------------------- - // the matrix is not positive definite - //-------------------------------------------------------------- - - // do not modify L(:,j), just copy it to its new place - - #ifndef IN_PLACE - for (Int k = 0 ; k < len ; k++) - { - Li_NEW [p_NEW+k] = Li [p+k] ; - ASSIGN (Lx_NEW, Lz_NEW, p_NEW+k, Lx, Lz, p+k) ; - } - #endif - - } - else - { - - //-------------------------------------------------------------- - // convert L(:,j) from an LL' factorization to LDL' - //-------------------------------------------------------------- - - // D(j,j) = L(j,j)^2 - #ifndef IN_PLACE - Li_NEW [p_NEW] = j ; - #endif - Real djj [1] ; - djj [0] = ljj [0] * ljj [0] ; - ASSIGN_REAL (Lx_NEW, p_NEW, djj, 0) ; - CLEAR_IMAG (Lx_NEW, Lz_NEW, p_NEW) ; - - // L(j+1:n) = L(j+1:n) / L(j,j) - for (Int k = 1 ; k < len ; k++) - { - #ifndef IN_PLACE - Li_NEW [p_NEW+k] = Li [p+k] ; - #endif - DIV_REAL (Lx_NEW, Lz_NEW, p_NEW+k, Lx, Lz, p+k, ljj, 0) ; - } - } - - //------------------------------------------------------------------ - // grow column L(:,j) if requested, and advance to column j+1 - //------------------------------------------------------------------ - - #ifndef IN_PLACE - Lp [j] = p_NEW ; - #ifdef OUT_OF_PLACE - if (grow) len = grow_column (len, grow1, grow2, n-j) ; - #endif - p_NEW += len ; - #endif - } - - // log the end of the last column - #ifndef IN_PLACE - Lp [n] = p_NEW ; - #endif - - } - else - { - - //---------------------------------------------------------------------- - // factorization remains as is, but space may be revised - //---------------------------------------------------------------------- - - #ifndef IN_PLACE - for (Int j = 0 ; j < n ; j++) - { - - //------------------------------------------------------------------ - // get column L(:,j) - //------------------------------------------------------------------ - - Int len = Lnz [j] ; - Int p = Lp [j] ; - - //------------------------------------------------------------------ - // move L(:,j) to its new position - //------------------------------------------------------------------ - - #ifdef TO_PACKED - if (p_NEW < p) - #endif - { - for (Int k = 0 ; k < len ; k++) - { - Li_NEW [p_NEW+k] = Li [p+k] ; - ASSIGN (Lx_NEW, Lz_NEW, p_NEW+k, Lx, Lz, p+k) ; - } - Lp [j] = p_NEW ; - } - - //------------------------------------------------------------------ - // grow column L(:,j) if requested, and advance to column j+1 - //------------------------------------------------------------------ - - #ifdef OUT_OF_PLACE - if (grow) len = grow_column (len, grow1, grow2, n-j) ; - #endif - p_NEW += len ; - } - - // log the end of the last column - Lp [n] = p_NEW ; - #endif - } -} - -#undef OUT_OF_PLACE -#undef TO_PACKED -#undef IN_PLACE -#undef Li_NEW -#undef Lx_NEW -#undef Lz_NEW -#undef p_NEW - diff --git a/CHOLMOD/Utility/t_cholmod_change_factor_2_worker.c b/CHOLMOD/Utility/t_cholmod_change_factor_2_worker.c deleted file mode 100644 index 0844e2e088..0000000000 --- a/CHOLMOD/Utility/t_cholmod_change_factor_2_worker.c +++ /dev/null @@ -1,118 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/t_cholmod_change_factor_2_worker: change format of a factor -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -#include "cholmod_template.h" - -//------------------------------------------------------------------------------ -// t_cholmod_change_factor_2_worker: changes a simplicial numeric factor -//------------------------------------------------------------------------------ - -// The contents of the old L->(i,x,z) is copied/converted into Li2, Lx2, and -// Lz2. - -static void TEMPLATE (cholmod_change_factor_2_worker) -( - cholmod_factor *L, // factor to modify - int to_packed, // if true: convert L to packed - Int *Li2, // new space for L->i (if out_of_place is true) - Real *Lx2, // new space for L->x (if out_of_place is true) - Real *Lz2, // new space for L->z (if out_of_place is true) - Int lnz, // max # of entries that Li2, Lx2, Lz2 can hold - bool grow, // if true: add slack space to the new columns of L - double grow1, // growth factor for each column - double grow2, // growth factor for each column - bool make_ll, // if true: convert LDL' to LL' - bool out_of_place, // if true: convert L out-of-place using Li2, Lx2, Lz2 - bool make_ldl, // if true: convert LL' to LDL' - cholmod_common *Common -) -{ - - //-------------------------------------------------------------------------- - // check inputs - //-------------------------------------------------------------------------- - - ASSERT (!L->is_super) ; - ASSERT (L->xtype != CHOLMOD_PATTERN) ; - - //-------------------------------------------------------------------------- - // get inputs - //-------------------------------------------------------------------------- - - Int n = L->n ; - Int *Lp = (Int *) L->p ; - Int *Li = (Int *) L->i ; - Real *Lx = (Real *) L->x ; - Real *Lz = (Real *) L->z ; - Int *Lnz = (Int *) L->nz ; - - //-------------------------------------------------------------------------- - // initialize L->minor; will be set below to the min j where D(j,j) <= 0 - //-------------------------------------------------------------------------- - - if (make_ll) - { - L->minor = n ; - } - - //-------------------------------------------------------------------------- - // convert the simplicial numeric L - //-------------------------------------------------------------------------- - - if (out_of_place) - { - - //---------------------------------------------------------------------- - // L must be converted out of place - //---------------------------------------------------------------------- - - // L is converted out-of-place, into the newly allocate space Li2, Lx2, - // and Lz2. This occurs if L is to be packed and/or made monotonic, - // but L is not already monotonic. - - ASSERT (Li2 != NULL) ; - ASSERT (Lx2 != NULL) ; - ASSERT (IMPLIES (L->xtype == CHOLMOD_ZOMPLEX, Lz2 != NULL)) ; - - #define OUT_OF_PLACE - #include "t_cholmod_change_factor_2_template.c" - - } - else if (to_packed) - { - - //---------------------------------------------------------------------- - // pack L, removing all slack space, in existing Li, Lx, and Lz space - //---------------------------------------------------------------------- - - ASSERT (Li2 == NULL) ; - ASSERT (Lx2 == NULL) ; - ASSERT (Lz2 == NULL) ; - - #define TO_PACKED - #include "t_cholmod_change_factor_2_template.c" - - } - else - { - - //---------------------------------------------------------------------- - // in-place conversion of L: no entries are moved - //---------------------------------------------------------------------- - - ASSERT (Li2 == NULL) ; - ASSERT (Lx2 == NULL) ; - ASSERT (Lz2 == NULL) ; - - #define IN_PLACE - #include "t_cholmod_change_factor_2_template.c" - } -} - diff --git a/CHOLMOD/Utility/t_cholmod_change_factor_3_template.c b/CHOLMOD/Utility/t_cholmod_change_factor_3_template.c deleted file mode 100644 index e3bb492e90..0000000000 --- a/CHOLMOD/Utility/t_cholmod_change_factor_3_template.c +++ /dev/null @@ -1,117 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/t_cholmod_change_factor_3_template -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -{ - Int p = 0 ; // current position in simplicial L - - for (Int s = 0 ; s < nsuper ; s++) - { - - //------------------------------------------------------------------ - // get the Supernode (0:nsrow-1, 0:nscol-1) - //------------------------------------------------------------------ - - Int k1 = Super [s] ; // 1st column of supernode s - Int k2 = Super [s+1] ; // k2-1 is last column of supernode s - Int psi = Lpi [s] ; // Ls [psi:psend-1]: pattern of s - Int psend = Lpi [s+1] ; - Int psx = Lpx [s] ; // Lx [psx:..]: values of supernode s - Int nsrow = psend - psi ; // # of rows in 1st column of s - Int nscol = k2 - k1 ; // # of cols in the supernode - - //------------------------------------------------------------------ - // convert the Supernode to the simplicial L (k1,k2-1) - //------------------------------------------------------------------ - - for (Int jj = 0 ; jj < nscol ; jj++) - { - - //-------------------------------------------------------------- - // convert L(:,j) from Supernode (:,jj) - //-------------------------------------------------------------- - - Int j = jj + k1 ; // L(:,j) is Supernode column jj - Lnz [j] = nsrow - jj ; // # entries in L(:,j) - - //-------------------------------------------------------------- - // log the start of L(:,j) in the simplicial form of L - //-------------------------------------------------------------- - - Int ii = jj ; - Int q = psx + jj + jj*nsrow ; - Lp [j] = TO_PACKED ? p:q ; - - //-------------------------------------------------------------- - // handle the diagonal for LDL' - //-------------------------------------------------------------- - - Real ljj [1] ; - if (!TO_LL) - { - // create the row index for L(j,j) - Li [TO_PACKED ? p:q] = j ; - - // compute D(j,j) - ASSIGN_REAL (ljj, 0, Lx, q) ; - if (ljj [0] <= 0) - { - // not positive definite: values of L(:,j) not changed - ASSIGN_REAL (Lx, TO_PACKED ? p:q, ljj, 0) ; - CLEAR_IMAG (Lx, , TO_PACKED ? p:q) ; - ljj [0] = 1 ; - } - else - { - // D(j,j) = L (j,j)^2 - Real djj [1] ; - djj [0] = ljj [0] * ljj [0] ; - ASSIGN_REAL (Lx, TO_PACKED ? p:q, djj, 0) ; - CLEAR_IMAG (Lx, , TO_PACKED ? p:q) ; - } - - // advance to the first off-diagonal entry of L(:,j) - ii++ ; - p++ ; - } - - //-------------------------------------------------------------- - // convert the remainder of L(:,j) - //-------------------------------------------------------------- - - for ( ; ii < nsrow ; ii++, p++) - { - // create the row index for L(i,j) - q = psx + ii + jj*nsrow ; - Li [TO_PACKED ? p:q] = Ls [psi + ii] ; - // revise the numeric value of L(i,j) - if (TO_LL) - { - // for LL': L(i,j) is unchanged; move to new position - if (TO_PACKED) - { - ASSIGN (Lx, , p, Lx, , q) ; - } - } - else - { - // for LDL': L(i,j) = L(i,j) / L(j,j) - DIV_REAL (Lx, , TO_PACKED ? p:q, Lx, , q, ljj, 0) ; - } - } - } - } - - // log the end of the last column in L - Lp [n] = TO_PACKED ? p : Lpx [nsuper] ; -} - -#undef TO_PACKED -#undef TO_LL - diff --git a/CHOLMOD/Utility/t_cholmod_change_factor_3_worker.c b/CHOLMOD/Utility/t_cholmod_change_factor_3_worker.c deleted file mode 100644 index 3cd76f3e71..0000000000 --- a/CHOLMOD/Utility/t_cholmod_change_factor_3_worker.c +++ /dev/null @@ -1,144 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/t_cholmod_change_factor_3_worker: change format of a factor -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -// Converts a supernodal numeric L into a simplicial numeric L. The factor is -// modified in place in Lx. - -// If to_packed is false, entries in Lx stay in the same position they had in -// the supernode, and Li is created to hold the pattern of all those entries. -// Gaps will naturally appear because of the unused space in each supernode. -// -// Consider the following example: -// -// Each supernode is lower trapezoidal, with a top part that is lower -// triangular (with diagonal present) and a bottom part that is rectangular. -// In this example below, nscol = 5, so the supernode represents 5 columns of -// L, and nsrow = 8, which means that the first column of the supernode has 8 -// entries, including the diagonal. -// -// x 1 2 3 4 -// x x 2 3 4 -// x x x 3 4 -// x x x x 4 -// x x x x x -// x x x x x -// x x x x x -// x x x x x -// -// If the entries in the supernode are not moved, the first column will have a -// single entry of slack space at the end of the space (the "1" above). The -// 2nd column has 2 entries of slack space ("2"). The 3rd column has 3 entries -// of slack space ("3"), and so on. The last column (5th) has no slack space -// since it is followed by the next supenode. - -// If to_packed is true, the space is compressed and the unused entries above -// the diagonal of each supernode are removed. That is, in this example, the -// supernode takes up 40 entries in Lx in supernodal form. In the simplicial -// form, there is no slack space, and the total space becomes 8 + 7 + 6 + 5 + 4 -// = 30. The first column starts at position Lpx [s] in Lx for supernode s, -// and is moved to the 'left', starting at position Lp [j] if the first column -// is j = L->super [s]. Since space is being compacted, Lp [j] <= Lpx [s] -// holds, and thus Lx can be compacted in place when to_packed is true. -// -// x -// x x -// x x x -// x x x x -// x x x x x -// x x x x x -// x x x x x -// x x x x x - -// The factor is either real or complex (not pattern nor complex). Thus, -// L->x is always non-NULL, and L->z is NULL and not used. Instead of Lz, -// a blank appears in the macros that access the values of L below. - -#include "cholmod_template.h" - -//------------------------------------------------------------------------------ -// t_cholmod_change_factor_3_worker: convert supernodal numeric L to simplicial -//------------------------------------------------------------------------------ - -static void TEMPLATE (cholmod_change_factor_3_worker) -( - cholmod_factor *L, // factor to modify - int to_packed, // if true: convert L to packed - int to_ll, // if true, convert to LL. if false: to LDL' - cholmod_common *Common -) -{ - - //-------------------------------------------------------------------------- - // check inputs - //-------------------------------------------------------------------------- - - ASSERT (L->is_super) ; - ASSERT (L->xtype == CHOLMOD_REAL || L->xtype == CHOLMOD_COMPLEX) ; - - //-------------------------------------------------------------------------- - // get inputs - //-------------------------------------------------------------------------- - - Int n = L->n ; // L is n-by-n - Int nsuper = L->nsuper ; // # of supernodes - Int *Lpi = (Int *) L->pi ; // index into L->s for supernode pattern - Int *Lpx = (Int *) L->px ; // index into L->x for supernode values - Int *Ls = (Int *) L->s ; // pattern of supernodes - Int *Super = (Int *) L->super ; // 1st column in each supernode - - // Lx holds supernode values on input; simplicial values on output: - Real *Lx = (Real *) L->x ; // numerical values (real or complex) - - // the simplicial space is allocated but not initialized on input: - Int *Lp = (Int *) L->p ; // simplicial col pointers - Int *Li = (Int *) L->i ; // simplicial row indices - Int *Lnz = (Int *) L->nz ; // simplicial column counts - Int lnz = L->nzmax ; // size of Li, Lp, and Lx - - //---------------------------------------------------------------------- - // convert supernodal LL' to simplicial LL' or LDL' (packed/unpacked) - //---------------------------------------------------------------------- - - if (to_packed) - { - if (to_ll) - { - // convert to simplicial packed LL' - #define TO_PACKED true - #define TO_LL true - #include "t_cholmod_change_factor_3_template.c" - } - else - { - // convert to simplicial packed LDL' - #define TO_PACKED true - #define TO_LL false - #include "t_cholmod_change_factor_3_template.c" - } - } - else - { - if (to_ll) - { - // convert to simplicial unpacked LL' - #define TO_PACKED false - #define TO_LL true - #include "t_cholmod_change_factor_3_template.c" - } - else - { - // convert to simplicial unpacked LDL' - #define TO_PACKED false - #define TO_LL false - #include "t_cholmod_change_factor_3_template.c" - } - } -} - diff --git a/CHOLMOD/Utility/t_cholmod_change_xdtype.c b/CHOLMOD/Utility/t_cholmod_change_xdtype.c deleted file mode 100644 index 8aaf8d23de..0000000000 --- a/CHOLMOD/Utility/t_cholmod_change_xdtype.c +++ /dev/null @@ -1,221 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/t_cholmod_xtype: change xtype and/or dtype of an object -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -#include "cholmod_internal.h" - -//------------------------------------------------------------------------------ -// t_change_xdtype_template -//------------------------------------------------------------------------------ - -#define CHANGE_XDTYPE2 change_xdtype_d2d -#define Real_IN double -#define Real_OUT double -#include "t_cholmod_change_xdtype_template.c" - -#define CHANGE_XDTYPE2 change_xdtype_d2s -#define Real_IN double -#define Real_OUT float -#include "t_cholmod_change_xdtype_template.c" - -#define CHANGE_XDTYPE2 change_xdtype_s2d -#define Real_IN float -#define Real_OUT double -#include "t_cholmod_change_xdtype_template.c" - -#define CHANGE_XDTYPE2 change_xdtype_s2s -#define Real_IN float -#define Real_OUT float -#include "t_cholmod_change_xdtype_template.c" - -//------------------------------------------------------------------------------ -// change_xdtype: change the xtype and/or dtype of an array -//------------------------------------------------------------------------------ - -static int change_xdtype -( - Int nz, // # of entries - int *input_xtype, // xtype of input: pattern, real, complex, zomplex - int output_xtype, // xtype of output: pattern, real, complex, zomplex - int *input_dtype, // dtype of input: double or single - int output_dtype, // dtype of output: double or single - void **X, // X array for real, complex, zomplex cases - void **Z, // Z array for zomplex case - cholmod_common *Common -) -{ - if (*input_dtype == CHOLMOD_DOUBLE) - { - if (output_dtype == CHOLMOD_DOUBLE) - { - // double to double - return (change_xdtype_d2d (nz, input_xtype, output_xtype, - input_dtype, output_dtype, X, Z, Common)) ; - } - else - { - // double to single - return (change_xdtype_d2s (nz, input_xtype, output_xtype, - input_dtype, output_dtype, X, Z, Common)) ; - } - } - else - { - if (output_dtype == CHOLMOD_DOUBLE) - { - // single to double - return (change_xdtype_s2d (nz, input_xtype, output_xtype, - input_dtype, output_dtype, X, Z, Common)) ; - } - else - { - // single to single - return (change_xdtype_s2s (nz, input_xtype, output_xtype, - input_dtype, output_dtype, X, Z, Common)) ; - } - } -} - -//------------------------------------------------------------------------------ -// cholmod_sparse_xtype: change xtype and/or dtype of a sparse matrix -//------------------------------------------------------------------------------ - -int CHOLMOD(sparse_xtype) -( - int to_xdtype, // requested xtype and dtype - cholmod_sparse *A, // sparse matrix to change - cholmod_common *Common -) -{ - - //-------------------------------------------------------------------------- - // check inputs - //-------------------------------------------------------------------------- - - RETURN_IF_NULL_COMMON (FALSE) ; - RETURN_IF_SPARSE_MATRIX_INVALID (A, FALSE) ; - - //-------------------------------------------------------------------------- - // change the xtype and/or dtype - //-------------------------------------------------------------------------- - - int output_xtype = to_xdtype & 3 ; // pattern, real, complex, or zomplex - int output_dtype = to_xdtype & 4 ; // double or single - - return (change_xdtype (A->nzmax, &(A->xtype), output_xtype, - &(A->dtype), output_dtype, &(A->x), &(A->z), Common)) ; -} - -//------------------------------------------------------------------------------ -// cholmod_triplet_xtype: change xtype and/or dtype of a triplet matrix -//------------------------------------------------------------------------------ - -int CHOLMOD(triplet_xtype) -( - int to_xdtype, // requested xtype and dtype - cholmod_triplet *T, // triplet matrix to change - cholmod_common *Common -) -{ - - //-------------------------------------------------------------------------- - // check inputs - //-------------------------------------------------------------------------- - - RETURN_IF_NULL_COMMON (FALSE) ; - RETURN_IF_TRIPLET_MATRIX_INVALID (T, FALSE) ; - - //-------------------------------------------------------------------------- - // change the xtype and/or dtype - //-------------------------------------------------------------------------- - - int output_xtype = to_xdtype & 3 ; // pattern, real, complex, or zomplex - int output_dtype = to_xdtype & 4 ; // double or single - - return (change_xdtype (T->nzmax, &(T->xtype), output_xtype, - &(T->dtype), output_dtype, &(T->x), &(T->z), Common)) ; -} - -//------------------------------------------------------------------------------ -// cholmod_dense_xtype: change xtype and/or dtype of a dense matrix -//------------------------------------------------------------------------------ - -int CHOLMOD(dense_xtype) -( - int to_xdtype, // requested xtype and dtype - cholmod_dense *X, // dense matrix to change - cholmod_common *Common -) -{ - - //-------------------------------------------------------------------------- - // check inputs - //-------------------------------------------------------------------------- - - RETURN_IF_NULL_COMMON (FALSE) ; - RETURN_IF_DENSE_MATRIX_INVALID (X, FALSE) ; - - //-------------------------------------------------------------------------- - // change the xtype and/or dtype - //-------------------------------------------------------------------------- - - int output_xtype = to_xdtype & 3 ; // real, complex, or zomplex - int output_dtype = to_xdtype & 4 ; // double or single - - if (output_xtype <= CHOLMOD_PATTERN) - { - // output_xtype not supported - ERROR (CHOLMOD_INVALID, "invalid xtype") ; - return (FALSE) ; - } - - return (change_xdtype (X->nzmax, &(X->xtype), output_xtype, - &(X->dtype), output_dtype, &(X->x), &(X->z), Common)) ; -} - -//------------------------------------------------------------------------------ -// cholmod_factor_xtype: change xtype and/or dtype of a factor -//------------------------------------------------------------------------------ - -int CHOLMOD(factor_xtype) -( - int to_xdtype, // requested xtype and dtype - cholmod_factor *L, // factor to change - cholmod_common *Common -) -{ - - //-------------------------------------------------------------------------- - // check inputs - //-------------------------------------------------------------------------- - - RETURN_IF_NULL_COMMON (FALSE) ; - RETURN_IF_FACTOR_INVALID (L, FALSE) ; - - //-------------------------------------------------------------------------- - // change the xtype and/or dtype - //-------------------------------------------------------------------------- - - int output_xtype = to_xdtype & 3 ; // real, complex, or zomplex - int output_dtype = to_xdtype & 4 ; // double or single - - if (output_xtype <= CHOLMOD_PATTERN || - L->is_super && output_xtype == CHOLMOD_ZOMPLEX) - { - // output_xtype not supported - ERROR (CHOLMOD_INVALID, "invalid xtype") ; - return (FALSE) ; - } - - Int nzmax = L->is_super ? L->xsize : L->nzmax ; - - return (change_xdtype (nzmax, &(L->xtype), output_xtype, - &(L->dtype), output_dtype, &(L->x), &(L->z), Common)) ; -} - diff --git a/CHOLMOD/Utility/t_cholmod_change_xdtype_template.c b/CHOLMOD/Utility/t_cholmod_change_xdtype_template.c deleted file mode 100644 index a3707fb511..0000000000 --- a/CHOLMOD/Utility/t_cholmod_change_xdtype_template.c +++ /dev/null @@ -1,255 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/t_cholmod_change_xdtype_template: change xtype and/or dtype -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -// Changes the xtype and/or dtype of X and Z. -// X and Z are arrays of size 0, nz, 2*nz, and are modified (in/out). - -#include "cholmod_internal.h" - -#define TRY(statement) \ - { \ - statement ; \ - if (Common->status < CHOLMOD_OK) \ - { \ - CHOLMOD(free) (nz, exout, X_output, Common) ; \ - CHOLMOD(free) (nz, ezout, Z_output, Common) ; \ - return (FALSE) ; \ - } \ - } - -//------------------------------------------------------------------------------ - -static int CHANGE_XDTYPE2 -( - Int nz, // # of entries in X and/or Z - - int *input_xtype, // changed to output_xtype on output - // CHOLMOD_PATTERN: X and Z are NULL on input - // CHOLMOD_REAL: X is size nz, and Z is NULL on input - // CHOLMOD_COMPLEX: X is size 2*nz, and Z is NULL on input - // CHOLMOD_ZOMPLEX: X and Z are size nz on input - - int output_xtype, - // CHOLMOD_PATTERN: X and Z are NULL on output - // CHOLMOD_REAL: X is size nz, and Z is NULL on output - // CHOLMOD_COMPLEX: X is size 2*nz, and Z is NULL on output - // CHOLMOD_ZOMPLEX: X and Z are size nz on output - - int *input_dtype, // changed to output_dtype on output - int output_dtype, - - // input/output: - void **X, // &X on input, reallocated on output - void **Z, // &Z on input, reallocated on output - - cholmod_common *Common -) -{ - - //-------------------------------------------------------------------------- - // check inputs - //-------------------------------------------------------------------------- - - Common->status = CHOLMOD_OK ; - if (*input_xtype == output_xtype && sizeof (Real_IN) == sizeof (Real_OUT)) - { - // nothing to do - return (TRUE) ; - } - - //-------------------------------------------------------------------------- - // get the entry sizes of the input and output - //-------------------------------------------------------------------------- - - size_t ein = sizeof (Real_IN) ; - size_t exin = ein * (((*input_xtype) == CHOLMOD_PATTERN) ? 0 : - (((*input_xtype) == CHOLMOD_COMPLEX) ? 2 : 1)) ; - size_t ezin = ein * (((*input_xtype) == CHOLMOD_ZOMPLEX) ? 1 : 0) ; - - size_t eout = sizeof (Real_OUT) ; - size_t exout = eout * (((output_xtype) == CHOLMOD_PATTERN) ? 0 : - (((output_xtype) == CHOLMOD_COMPLEX) ? 2 : 1)) ; - size_t ezout = eout * (((output_xtype) == CHOLMOD_ZOMPLEX) ? 1 : 0) ; - - //-------------------------------------------------------------------------- - // convert the array - //-------------------------------------------------------------------------- - - Real_IN *X_input = (Real_IN *) *X ; - Real_IN *Z_input = (Real_IN *) *Z ; - Real_OUT *X_output = NULL ; - Real_OUT *Z_output = NULL ; - - switch (output_xtype) - { - - //---------------------------------------------------------------------- - case CHOLMOD_PATTERN: // convert any xtype to pattern - //---------------------------------------------------------------------- - - break ; - - //---------------------------------------------------------------------- - case CHOLMOD_REAL: // convert any xtype to real - //---------------------------------------------------------------------- - - TRY (X_output = CHOLMOD(malloc) (nz, exout, Common)) ; - - switch (*input_xtype) - { - - case CHOLMOD_PATTERN: // pattern to real - - for (Int k = 0 ; k < nz ; k++) - { - X_output [k] = 1 ; - } - break ; - - case CHOLMOD_REAL: // real to real - - for (Int k = 0 ; k < nz ; k++) - { - X_output [k] = (Real_OUT) X_input [k] ; - } - break ; - - case CHOLMOD_COMPLEX: // complex to real - - for (Int k = 0 ; k < nz ; k++) - { - X_output [k] = (Real_OUT) X_input [2*k] ; - } - break ; - - case CHOLMOD_ZOMPLEX: // zomplex to real - - for (Int k = 0 ; k < nz ; k++) - { - X_output [k] = (Real_OUT) X_input [k] ; - } - break ; - - } - break ; - - //---------------------------------------------------------------------- - case CHOLMOD_COMPLEX: // convert any xtype to complex - //---------------------------------------------------------------------- - - TRY (X_output = CHOLMOD(malloc) (nz, exout, Common)) ; - - switch (*input_xtype) - { - - case CHOLMOD_PATTERN: // pattern to complex - - for (Int k = 0 ; k < nz ; k++) - { - X_output [2*k ] = 1 ; - X_output [2*k+1] = 0 ; - } - break ; - - case CHOLMOD_REAL: // real to complex - - for (Int k = 0 ; k < nz ; k++) - { - X_output [2*k ] = (Real_OUT) X_input [k] ; - X_output [2*k+1] = 0 ; - } - break ; - - case CHOLMOD_COMPLEX: // complex to complex - - for (Int k = 0 ; k < 2*nz ; k++) - { - X_output [k] = (Real_OUT) X_input [k] ; - } - break ; - - case CHOLMOD_ZOMPLEX: // zomplex to complex - - for (Int k = 0 ; k < nz ; k++) - { - X_output [2*k ] = (Real_OUT) X_input [k] ; - X_output [2*k+1] = (Real_OUT) Z_input [k] ; - } - break ; - } - break ; - - //---------------------------------------------------------------------- - case CHOLMOD_ZOMPLEX: // convert any xtype to zomplex - //---------------------------------------------------------------------- - - TRY (X_output = CHOLMOD(malloc) (nz, exout, Common)) ; - TRY (Z_output = CHOLMOD(malloc) (nz, ezout, Common)) ; - - switch (*input_xtype) - { - case CHOLMOD_PATTERN: // pattern to zomplex - - for (Int k = 0 ; k < nz ; k++) - { - X_output [k] = 1 ; - Z_output [k] = 0 ; - } - break ; - - case CHOLMOD_REAL: // real to zomplex - - for (Int k = 0 ; k < nz ; k++) - { - X_output [k] = (Real_OUT) X_input [k] ; - Z_output [k] = 0 ; - } - break ; - - case CHOLMOD_COMPLEX: // complex to zomplex - - for (Int k = 0 ; k < nz ; k++) - { - X_output [k] = (Real_OUT) X_input [2*k ] ; - Z_output [k] = (Real_OUT) X_input [2*k+1] ; - } - break ; - - case CHOLMOD_ZOMPLEX: // zomplex to zomplex - - for (Int k = 0 ; k < nz ; k++) - { - X_output [k] = (Real_OUT) X_input [k] ; - Z_output [k] = (Real_OUT) Z_input [k] ; - } - break ; - - } - break ; - - } - - //-------------------------------------------------------------------------- - // free the input arrays and return result - //-------------------------------------------------------------------------- - - CHOLMOD(free) (nz, exin, X_input, Common) ; - CHOLMOD(free) (nz, ezin, Z_input, Common) ; - (*X) = X_output ; - (*Z) = Z_output ; - (*input_xtype) = output_xtype ; - (*input_dtype) = output_dtype ; - return (TRUE) ; -} - -#undef CHANGE_XDTYPE2 -#undef Real_IN -#undef Real_OUT - diff --git a/CHOLMOD/Utility/t_cholmod_clear_flag.c b/CHOLMOD/Utility/t_cholmod_clear_flag.c deleted file mode 100644 index c0f7320f7c..0000000000 --- a/CHOLMOD/Utility/t_cholmod_clear_flag.c +++ /dev/null @@ -1,58 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/t_cholmod_clear_flag: clear Common->Flag -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -#include "cholmod_internal.h" - -// cholmod_clear_flag increments Common->mark to ensure -// Common->Flag [0..Common->nrow-1] < mark holds. If incrementing -// Common->mark results in integer overflow, Flag is set to EMPTY and -// Common->mark is set to zero. - -int64_t CHOLMOD(clear_flag) // returns the new Common->mark -( - cholmod_common *Common -) -{ - - //-------------------------------------------------------------------------- - // check inputs - //-------------------------------------------------------------------------- - - RETURN_IF_NULL_COMMON (EMPTY) ; - - //-------------------------------------------------------------------------- - // increment the mark - //-------------------------------------------------------------------------- - - Common->mark++ ; - - //-------------------------------------------------------------------------- - // check for int32 or int64 overflow - //-------------------------------------------------------------------------- - - bool overflow = (Common->mark <= 0) ; - #if defined ( CHOLMOD_INT32 ) - overflow = overflow || (Common->mark > INT32_MAX) ; - #endif - - if (overflow) - { - Common->mark = 0 ; - CHOLMOD(set_empty) (Common->Flag, Common->nrow) ; - } - - //-------------------------------------------------------------------------- - // return result - //-------------------------------------------------------------------------- - - ASSERT (check_flag (Common)) ; - return (Common->mark) ; -} - diff --git a/CHOLMOD/Utility/t_cholmod_copy.c b/CHOLMOD/Utility/t_cholmod_copy.c deleted file mode 100644 index d8b3784499..0000000000 --- a/CHOLMOD/Utility/t_cholmod_copy.c +++ /dev/null @@ -1,332 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/t_cholmod_copy: copy a sparse matrix (with change of stype) -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -// Create a copy (C) of a sparse matrix A, with change of stype. -// A has any xtype, dtype, and stype, and can be packed or unpacked. -// C has the same xtype and dtype, but any stype (unless A is rectangular, -// in which case C->stype must be zero). C is packed. - -// A->stype == 0: A is unsymmetric -// A->stype < 0: A is symmetric with lower triangular part stored. Any entries -// above the diagonal are ignored. -// A->stype > 0: A is symmetric with upper triangular part stored. Any entries -// below the diagonal are ignored. - -// C can be returned as numerical or pattern-only; and in the latter case, -// the diagonal entries can be ignored. - -// In MATLAB: Using cholmod_copy: -// --------- ---------------------------- -// C = A ; A unsymmetric, C unsymmetric -// C = tril (A) ; A unsymmetric, C sym lower -// C = triu (A) ; A unsymmetric, C sym upper -// U = triu (A) ; L = tril (U',-1) ; C = L+U ; A sym upper, C unsymmetric -// C = triu (A)' ; A sym upper, C sym lower -// C = triu (A) ; A sym upper, C sym upper -// L = tril (A) ; U = triu (L',1) ; C = L+U ; A sym lower, C unsymmetric -// C = tril (A) ; A sym lower, C sym lower -// C = tril (A)' ; A sym lower, C sym upper - -// If A is complex or zomplex, then U' or L' above can be computed as an -// array (non-conjugate) transpose, or a matrix (conjugate) transpose. - -// The mode parameter: -// 2 numerical, with conjugate transpose -// 1 numerical, with non-conjugate transpose -// 0 pattern, keeping the diagonal -// -1 pattern, remove the diagonal -// -2 pattern, and add 50% + n extra space to C -// as elbow room for AMD and CAMD, when converting -// a symmetric matrix A to an unsymmetric matrix C - -// workspace: Iwork (max (nrow,ncol)) - -#include "cholmod_internal.h" - -#define RETURN_IF_ERROR \ - if (Common->status < CHOLMOD_OK) \ - { \ - CHOLMOD(free_sparse) (&C, Common) ; \ - return (NULL) ; \ - } - -//------------------------------------------------------------------------------ -// t_cholmod_copy_worker template -//------------------------------------------------------------------------------ - -#define PATTERN -#include "t_cholmod_copy_worker.c" - -#define DOUBLE -#define REAL -#include "t_cholmod_copy_worker.c" - -#define COMPLEX -#include "t_cholmod_copy_worker.c" -#define COMPLEX -#define NCONJUGATE -#include "t_cholmod_copy_worker.c" - -#define ZOMPLEX -#include "t_cholmod_copy_worker.c" -#define ZOMPLEX -#define NCONJUGATE -#include "t_cholmod_copy_worker.c" - -#undef DOUBLE -#define SINGLE -#define REAL -#include "t_cholmod_copy_worker.c" - -#define COMPLEX -#include "t_cholmod_copy_worker.c" -#define COMPLEX -#define NCONJUGATE -#include "t_cholmod_copy_worker.c" - -#define ZOMPLEX -#include "t_cholmod_copy_worker.c" -#define ZOMPLEX -#define NCONJUGATE -#include "t_cholmod_copy_worker.c" - -//------------------------------------------------------------------------------ - -cholmod_sparse *CHOLMOD(copy) -( - cholmod_sparse *A, // input matrix, not modified - int stype, // stype of C - int mode, // 2: numerical (conj), 1: numerical (non-conj.), - // 0: pattern (with diag), -1: pattern (remove diag), - // -2: pattern (remove diag; add ~50% extra space in C) - cholmod_common *Common -) -{ - - //-------------------------------------------------------------------------- - // check inputs - //-------------------------------------------------------------------------- - - RETURN_IF_NULL_COMMON (NULL) ; - RETURN_IF_SPARSE_MATRIX_INVALID (A, NULL) ; - Common->status = CHOLMOD_OK ; - cholmod_sparse *C = NULL ; - - Int nrow = A->nrow ; - Int ncol = A->ncol ; - int astype = SIGN (A->stype) ; - stype = SIGN (stype) ; - if ((stype || astype) && nrow != ncol) - { - ERROR (CHOLMOD_INVALID, "matrix invalid") ; - return (NULL) ; - } - - //-------------------------------------------------------------------------- - // get inputs - //-------------------------------------------------------------------------- - - bool ignore_diag = (mode < 0) ; - bool up = (astype > 0) ; - bool lo = (astype < 0) ; - bool values = (mode > 0) && (A->xtype != CHOLMOD_PATTERN) ; - bool conj = (mode >= 2) ; - - //-------------------------------------------------------------------------- - // copy the matrix - //-------------------------------------------------------------------------- - - if (astype == stype) - { - - //---------------------------------------------------------------------- - // no change of stype, but possible remove of diagonal - //---------------------------------------------------------------------- - - C = CHOLMOD(band) (A, -nrow, ncol, mode, Common) ; - RETURN_IF_ERROR ; - - } - else if (astype == 0) - { - - //---------------------------------------------------------------------- - // A is unsymmetric; C is symmetric upper or lower - //---------------------------------------------------------------------- - - size_t nlo = (stype > 0) ? 0 : (-nrow) ; - size_t nup = (stype > 0) ? ncol : 0 ; - C = CHOLMOD(band) (A, nlo, nup, mode, Common) ; - RETURN_IF_ERROR ; - C->stype = stype ; - - } - else if (astype == -stype) - { - - //---------------------------------------------------------------------- - // both A and C are symmetric, but opposite, so a transpose is needed - //---------------------------------------------------------------------- - - C = CHOLMOD(transpose) (A, mode, Common) ; - RETURN_IF_ERROR ; - if (ignore_diag) - { - // remove diagonal, if requested - CHOLMOD(band_inplace) (-nrow, ncol, -1, C, Common) ; - RETURN_IF_ERROR ; - } - - } - else - { - - //---------------------------------------------------------------------- - // A is symmetric and C is unsymmetric - //---------------------------------------------------------------------- - - Int *Ap = (Int *) A->p ; - Int *Anz = (Int *) A->nz ; - Int *Ai = (Int *) A->i ; - bool packed = A->packed ; - - //---------------------------------------------------------------------- - // allocate workspace - //---------------------------------------------------------------------- - - ASSERT (nrow == ncol) ; - CHOLMOD(allocate_work) (0, ncol, 0, Common) ; - RETURN_IF_ERROR ; - Int *Wj = (Int *) Common->Iwork ; - - //---------------------------------------------------------------------- - // count entries in each column of C - //---------------------------------------------------------------------- - - memset (Wj, 0, ncol * sizeof (Int)) ; - size_t cnz = 0 ; - - for (Int j = 0 ; j < ncol ; j++) - { - Int p = Ap [j] ; - Int pend = (packed) ? (Ap [j+1]) : (p + Anz [j]) ; - for ( ; p < pend ; p++) - { - Int i = Ai [p] ; - if (i == j) - { - // diagonal entry A(i,i) - if (ignore_diag) continue ; - Wj [j]++ ; - cnz++ ; - } - else if ((up && i < j) || (lo && i > j)) - { - // A(i,j) is placed in both upper and lower part of C - Wj [j]++ ; - Wj [i]++ ; - cnz += 2 ; - } - } - } - - //---------------------------------------------------------------------- - // allocate C - //---------------------------------------------------------------------- - - size_t cnzmax = cnz + ((mode == -2) ? (cnz/2 + ncol) : 0) ; - C = CHOLMOD(allocate_sparse) (nrow, ncol, cnzmax, - /* C is sorted if A is sorted: */ A->sorted, - /* C is packed: */ TRUE, /* C stype: */ 0, - (values ? A->xtype : CHOLMOD_PATTERN) + A->dtype, Common) ; - RETURN_IF_ERROR ; - - //---------------------------------------------------------------------- - // Cp = cumsum of column counts (Wj), and then copy Cp back to Wj - //---------------------------------------------------------------------- - - Int *Cp = C->p ; - CHOLMOD(cumsum) (Cp, Wj, ncol) ; - memcpy (Wj, Cp, ncol * sizeof (Int)) ; - - //---------------------------------------------------------------------- - // construct C via the template function - //---------------------------------------------------------------------- - - switch ((C->xtype + C->dtype) % 8) - { - - default: - p_cholmod_copy_worker (C, A, ignore_diag, Common) ; - break ; - - case CHOLMOD_SINGLE + CHOLMOD_REAL: - r_s_cholmod_copy_worker (C, A, ignore_diag, Common) ; - break ; - - case CHOLMOD_SINGLE + CHOLMOD_COMPLEX: - if (conj) - { - c_s_cholmod_copy_worker (C, A, ignore_diag, Common) ; - } - else - { - ct_s_cholmod_copy_worker (C, A, ignore_diag, Common) ; - } - break ; - - case CHOLMOD_SINGLE + CHOLMOD_ZOMPLEX: - if (conj) - { - z_s_cholmod_copy_worker (C, A, ignore_diag, Common) ; - } - else - { - zt_s_cholmod_copy_worker (C, A, ignore_diag, Common) ; - } - break ; - - case CHOLMOD_DOUBLE + CHOLMOD_REAL: - r_cholmod_copy_worker (C, A, ignore_diag, Common) ; - break ; - - case CHOLMOD_DOUBLE + CHOLMOD_COMPLEX: - if (conj) - { - c_cholmod_copy_worker (C, A, ignore_diag, Common) ; - } - else - { - ct_cholmod_copy_worker (C, A, ignore_diag, Common) ; - } - break ; - - case CHOLMOD_DOUBLE + CHOLMOD_ZOMPLEX: - if (conj) - { - z_cholmod_copy_worker (C, A, ignore_diag, Common) ; - } - else - { - zt_cholmod_copy_worker (C, A, ignore_diag, Common) ; - } - break ; - } - } - - //-------------------------------------------------------------------------- - // return result - //-------------------------------------------------------------------------- - - DEBUG (size_t nnzdiag = CHOLMOD(dump_sparse) (C, "copy:C", Common)) ; - ASSERT (IMPLIES (ignore_diag, nnzdiag == 0)) ; - return (C) ; -} - diff --git a/CHOLMOD/Utility/t_cholmod_copy_dense.c b/CHOLMOD/Utility/t_cholmod_copy_dense.c deleted file mode 100644 index 137a1b2c12..0000000000 --- a/CHOLMOD/Utility/t_cholmod_copy_dense.c +++ /dev/null @@ -1,58 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/t_cholmod_dense: copy a dense matrix -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -// Copies a dense matrix X into a new dense matrix Y, with the same leading -// dimensions. - -#include "cholmod_internal.h" - -#define RETURN_IF_ERROR \ - if (Common->status < CHOLMOD_OK) \ - { \ - CHOLMOD(free_dense) (&Y, Common) ; \ - return (NULL) ; \ - } - -cholmod_dense *CHOLMOD(copy_dense) // returns new dense matrix -( - cholmod_dense *X, // input dense matrix - cholmod_common *Common -) -{ - - //-------------------------------------------------------------------------- - // check inputs - //-------------------------------------------------------------------------- - - RETURN_IF_NULL_COMMON (FALSE) ; - RETURN_IF_DENSE_MATRIX_INVALID (X, FALSE) ; - Common->status = CHOLMOD_OK ; - - //-------------------------------------------------------------------------- - // allocate the output matrix Y with same properties as X - //-------------------------------------------------------------------------- - - cholmod_dense *Y = CHOLMOD(allocate_dense) (X->nrow, X->ncol, X->d, - X->xtype + X->dtype, Common) ; - RETURN_IF_ERROR ; - - //-------------------------------------------------------------------------- - // copy X = Y - //-------------------------------------------------------------------------- - - CHOLMOD(copy_dense2) (X, Y, Common) ; - - //-------------------------------------------------------------------------- - // return result - //-------------------------------------------------------------------------- - - return (Y) ; -} - diff --git a/CHOLMOD/Utility/t_cholmod_copy_dense2.c b/CHOLMOD/Utility/t_cholmod_copy_dense2.c deleted file mode 100644 index c19b4f531a..0000000000 --- a/CHOLMOD/Utility/t_cholmod_copy_dense2.c +++ /dev/null @@ -1,131 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/t_cholmod_dense2: copy a dense matrix -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -// Copies a dense matrix X into another dense matrix Y, which must already -// be allocated on input. The dimensions, xtype, and dtype of X and Y must -// match, but X->d and Y->d can differ. - -#include "cholmod_internal.h" - -//------------------------------------------------------------------------------ -// t_cholmod_copy_dense2_worker template -//------------------------------------------------------------------------------ - -#define DOUBLE -#define REAL -#include "t_cholmod_copy_dense2_worker.c" -#define COMPLEX -#include "t_cholmod_copy_dense2_worker.c" -#define ZOMPLEX -#include "t_cholmod_copy_dense2_worker.c" - -#undef DOUBLE -#define SINGLE -#define REAL -#include "t_cholmod_copy_dense2_worker.c" -#define COMPLEX -#include "t_cholmod_copy_dense2_worker.c" -#define ZOMPLEX -#include "t_cholmod_copy_dense2_worker.c" - -//------------------------------------------------------------------------------ - -int CHOLMOD(copy_dense2) -( - cholmod_dense *X, // input dense matrix - cholmod_dense *Y, // output dense matrix (already allocated on input) - cholmod_common *Common -) -{ - - //-------------------------------------------------------------------------- - // check inputs - //-------------------------------------------------------------------------- - - RETURN_IF_NULL_COMMON (FALSE) ; - RETURN_IF_DENSE_MATRIX_INVALID (X, FALSE) ; - RETURN_IF_DENSE_MATRIX_INVALID (Y, FALSE) ; - Common->status = CHOLMOD_OK ; - - if (X->nrow != Y->nrow || - X->ncol != Y->ncol || - X->xtype != Y->xtype || - X->dtype != Y->dtype) - { - ERROR (CHOLMOD_INVALID, "X and Y: wrong dimensions or type") ; - return (FALSE) ; - } - - //-------------------------------------------------------------------------- - // get the sizes of the entries - //-------------------------------------------------------------------------- - - size_t e = (X->dtype == CHOLMOD_SINGLE) ? sizeof (float) : sizeof (double) ; - size_t ex = e * ((X->xtype == CHOLMOD_COMPLEX) ? 2 : 1) ; - size_t ez = e * ((X->xtype == CHOLMOD_ZOMPLEX) ? 1 : 0) ; - - //-------------------------------------------------------------------------- - // copy X = Y - //-------------------------------------------------------------------------- - - if (X->d == Y->d) - { - - //---------------------------------------------------------------------- - // no change of leading dimension: copy all of X and Y as-is - //---------------------------------------------------------------------- - - size_t nz = X->d * X->ncol ; - if (X->x != NULL) memcpy (Y->x, X->x, nz * ex) ; - if (X->z != NULL) memcpy (Y->z, X->z, nz * ez) ; - - } - else - { - - //---------------------------------------------------------------------- - // copy Y into X, with possible change of leading dimension - //---------------------------------------------------------------------- - - switch ((X->xtype + X->dtype) % 8) - { - case CHOLMOD_SINGLE + CHOLMOD_REAL: - r_s_cholmod_copy_dense2_worker (X, Y) ; - break ; - - case CHOLMOD_SINGLE + CHOLMOD_COMPLEX: - c_s_cholmod_copy_dense2_worker (X, Y) ; - break ; - - case CHOLMOD_SINGLE + CHOLMOD_ZOMPLEX: - z_s_cholmod_copy_dense2_worker (X, Y) ; - break ; - - case CHOLMOD_DOUBLE + CHOLMOD_REAL: - r_cholmod_copy_dense2_worker (X, Y) ; - break ; - - case CHOLMOD_DOUBLE + CHOLMOD_COMPLEX: - c_cholmod_copy_dense2_worker (X, Y) ; - break ; - - case CHOLMOD_DOUBLE + CHOLMOD_ZOMPLEX: - z_cholmod_copy_dense2_worker (X, Y) ; - break ; - } - } - - //-------------------------------------------------------------------------- - // return result - //-------------------------------------------------------------------------- - - return (TRUE) ; -} - diff --git a/CHOLMOD/Utility/t_cholmod_copy_dense2_worker.c b/CHOLMOD/Utility/t_cholmod_copy_dense2_worker.c deleted file mode 100644 index d4a0ace8a2..0000000000 --- a/CHOLMOD/Utility/t_cholmod_copy_dense2_worker.c +++ /dev/null @@ -1,84 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/t_cholmod_dense2_worker: copy a dense matrix -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -// Copies a dense matrix X into Y, with change of leading dimension. If the -// leading dimensions are the same, the copy is done in the caller, -// t_cholmod_copy_dense2. - -#include "cholmod_template.h" - -static void TEMPLATE (cholmod_copy_dense2_worker) -( - cholmod_dense *X, - cholmod_dense *Y -) -{ - - //-------------------------------------------------------------------------- - // check inputs - //-------------------------------------------------------------------------- - - ASSERT (X->d != Y->d) ; - ASSERT (X->nrow == Y->nrow) ; - ASSERT (X->ncol == Y->ncol) ; - ASSERT (X->dtype == Y->dtype) ; - ASSERT (X->xtype == Y->xtype) ; - - //-------------------------------------------------------------------------- - // get inputs - //-------------------------------------------------------------------------- - - Real *Xx = (Real *) X->x ; - Real *Xz = (Real *) X->z ; - Real *Yx = (Real *) Y->x ; - Real *Yz = (Real *) Y->z ; - size_t nrow = X->nrow ; - size_t ncol = X->ncol ; - size_t xd = X->d ; - size_t yd = Y->d ; - - //-------------------------------------------------------------------------- - // get the sizes of the entries - //-------------------------------------------------------------------------- - - size_t e = (X->dtype == CHOLMOD_SINGLE) ? sizeof (float) : sizeof (double) ; - size_t fx = ((X->xtype == CHOLMOD_COMPLEX) ? 2 : 1) ; - size_t fz = ((X->xtype == CHOLMOD_ZOMPLEX) ? 1 : 0) ; - size_t e_fx_nrow = e * fx * nrow ; - size_t e_fz_nrow = e * fz * nrow ; - - //-------------------------------------------------------------------------- - // copy X = Y - //-------------------------------------------------------------------------- - - for (size_t j = 0 ; j < ncol ; j++) - { - - //---------------------------------------------------------------------- - // Y (:,j) = X (:,j) - //---------------------------------------------------------------------- - - memcpy (Yx, Xx, e_fx_nrow) ; - Xx += xd * fx ; - Yx += yd * fx ; - - #if defined ( ZOMPLEX ) - memcpy (Yz, Xz, e_fz_nrow) ; - Xz += xd * fz ; - Yz += yd * fz ; - #endif - } -} - -#undef PATTERN -#undef REAL -#undef COMPLEX -#undef ZOMPLEX - diff --git a/CHOLMOD/Utility/t_cholmod_copy_factor.c b/CHOLMOD/Utility/t_cholmod_copy_factor.c deleted file mode 100644 index 9f4102fd0d..0000000000 --- a/CHOLMOD/Utility/t_cholmod_copy_factor.c +++ /dev/null @@ -1,193 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/t_cholmod_copy_factor: copy a factor -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -// Creates an exact copy of a sparse factorization object. - -#include "cholmod_internal.h" - -#define RETURN_IF_ERROR \ - if (Common->status < CHOLMOD_OK) \ - { \ - CHOLMOD(free_factor) (&H, Common) ; \ - return (NULL) ; \ - } - -//------------------------------------------------------------------------------ -// t_cholmod_copy_factor_worker template -//------------------------------------------------------------------------------ - -#define DOUBLE -#define REAL -#include "t_cholmod_copy_factor_worker.c" -#define COMPLEX -#include "t_cholmod_copy_factor_worker.c" -#define ZOMPLEX -#include "t_cholmod_copy_factor_worker.c" - -#undef DOUBLE -#define SINGLE -#define REAL -#include "t_cholmod_copy_factor_worker.c" -#define COMPLEX -#include "t_cholmod_copy_factor_worker.c" -#define ZOMPLEX -#include "t_cholmod_copy_factor_worker.c" - -//------------------------------------------------------------------------------ - -cholmod_factor *CHOLMOD(copy_factor) // return a copy of the factor -( - cholmod_factor *L, // factor to copy (not modified) - cholmod_common *Common -) -{ - - //-------------------------------------------------------------------------- - // check inputs - //-------------------------------------------------------------------------- - - RETURN_IF_NULL_COMMON (NULL) ; - RETURN_IF_FACTOR_INVALID (L, FALSE) ; - Common->status = CHOLMOD_OK ; - - DEBUG (CHOLMOD(dump_factor) (L, "copy_factor:L", Common)) ; - - //-------------------------------------------------------------------------- - // get inputs and sizes of entries - //-------------------------------------------------------------------------- - - size_t n = L->n ; - size_t ei = sizeof (Int) ; - size_t e = (L->dtype == CHOLMOD_SINGLE) ? sizeof (float) : sizeof (double) ; - size_t ex = e * ((L->xtype == CHOLMOD_PATTERN) ? 0 : - ((L->xtype == CHOLMOD_COMPLEX) ? 2 : 1)) ; - size_t ez = e * ((L->xtype == CHOLMOD_ZOMPLEX) ? 1 : 0) ; - - //-------------------------------------------------------------------------- - // allocate the new factor H, H->Perm, and H->ColCount - //-------------------------------------------------------------------------- - - cholmod_factor *H = CHOLMOD(allocate_factor) (n, Common) ; - RETURN_IF_ERROR ; - - //-------------------------------------------------------------------------- - // copy the symbolic contents (same for simplicial or supernodal) - //-------------------------------------------------------------------------- - - memcpy (H->Perm, L->Perm, n * ei) ; - memcpy (H->ColCount, L->ColCount, n * ei) ; - H->ordering = L->ordering ; - H->is_ll = L->is_ll ; - - //-------------------------------------------------------------------------- - // copy the rest of the factor - //-------------------------------------------------------------------------- - - if (L->is_super) - { - - //---------------------------------------------------------------------- - // L is a numerical supernodal factor; change H to supernodal - //---------------------------------------------------------------------- - - H->xsize = L->xsize ; - H->ssize = L->ssize ; - H->nsuper = L->nsuper ; - - CHOLMOD(change_factor) (L->xtype + L->dtype, /* to LL': */ TRUE, - /* to supernodal: */ TRUE, /* to packed: */ TRUE, - /* to monotonic: */ TRUE, H, Common) ; - RETURN_IF_ERROR ; - - //---------------------------------------------------------------------- - // copy the supernodal contents - //---------------------------------------------------------------------- - - H->maxcsize = L->maxcsize ; - H->maxesize = L->maxesize ; - - memcpy (H->super, L->super, (L->nsuper + 1) * ei) ; - memcpy (H->pi, L->pi, (L->nsuper + 1) * ei) ; - memcpy (H->px, L->px, (L->nsuper + 1) * ei) ; - memset (H->s, 0, ei) ; - memcpy (H->s, L->s, (L->ssize) * ei) ; - - if (L->xtype == CHOLMOD_REAL || L->xtype == CHOLMOD_COMPLEX) - { - memcpy (H->x, L->x, (L->xsize) * ex) ; - } - - } - else if (L->xtype != CHOLMOD_PATTERN) - { - - //---------------------------------------------------------------------- - // L is a numerical simplicial factor; change H to the same - //---------------------------------------------------------------------- - - H->nzmax = L->nzmax ; - CHOLMOD(change_factor) (L->xtype + L->dtype, L->is_ll, - /* to supernodal: */ FALSE, /* to packed: */ -1, - /* to monotonic: */ TRUE, H, Common) ; - RETURN_IF_ERROR ; - - //---------------------------------------------------------------------- - // copy the simplicial contents - //---------------------------------------------------------------------- - - H->xtype = L->xtype ; - H->dtype = L->dtype ; - - memcpy (H->p, L->p, (n+1) * ei) ; - memcpy (H->prev, L->prev, (n+2) * ei) ; - memcpy (H->next, L->next, (n+2) * ei) ; - memcpy (H->nz, L->nz, n * ei) ; - - switch ((L->xtype + L->dtype) % 8) - { - - case CHOLMOD_SINGLE + CHOLMOD_REAL: - r_s_cholmod_copy_factor_worker (L, H) ; - break ; - - case CHOLMOD_SINGLE + CHOLMOD_COMPLEX: - c_s_cholmod_copy_factor_worker (L, H) ; - break ; - - case CHOLMOD_SINGLE + CHOLMOD_ZOMPLEX: - z_s_cholmod_copy_factor_worker (L, H) ; - break ; - - case CHOLMOD_DOUBLE + CHOLMOD_REAL: - r_cholmod_copy_factor_worker (L, H) ; - break ; - - case CHOLMOD_DOUBLE + CHOLMOD_COMPLEX: - c_cholmod_copy_factor_worker (L, H) ; - break ; - - case CHOLMOD_DOUBLE + CHOLMOD_ZOMPLEX: - z_cholmod_copy_factor_worker (L, H) ; - break ; - } - } - - //-------------------------------------------------------------------------- - // finalize the copy and return result - //-------------------------------------------------------------------------- - - H->minor = L->minor ; - H->is_monotonic = L->is_monotonic ; - - DEBUG (CHOLMOD(dump_factor) (H, "copy_factor:H", Common)) ; - ASSERT (H->xtype == L->xtype && H->is_super == L->is_super) ; - return (H) ; -} - diff --git a/CHOLMOD/Utility/t_cholmod_copy_factor_worker.c b/CHOLMOD/Utility/t_cholmod_copy_factor_worker.c deleted file mode 100644 index 80c2c96c20..0000000000 --- a/CHOLMOD/Utility/t_cholmod_copy_factor_worker.c +++ /dev/null @@ -1,58 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/t_cholmod_copy_factor_worker: copy a factor -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -// Columns are copied individually, to avoid copying uninitialized space - -#include "cholmod_template.h" - -static void TEMPLATE (cholmod_copy_factor_worker) -( - cholmod_factor *L, // input factor to copy (not modified) - cholmod_factor *H // output factor -) -{ - - //-------------------------------------------------------------------------- - // get inputs - //-------------------------------------------------------------------------- - - size_t n = L->n ; - - Int *Lp = (Int *) L->p ; - Int *Li = (Int *) L->i ; - Int *Lnz = (Int *) L->nz ; - Real *Lx = (Real *) L->x ; - Real *Lz = (Real *) L->z ; - - Int *Hi = (Int *) H->i ; - Real *Hx = (Real *) H->x ; - Real *Hz = (Real *) H->z ; - - //-------------------------------------------------------------------------- - // copy each column - //-------------------------------------------------------------------------- - - for (Int j = 0 ; j < n ; j++) - { - Int p = Lp [j] ; - Int pend = p + Lnz [j] ; - for ( ; p < pend ; p++) - { - Hi [p] = Li [p] ; - ASSIGN (Hx, Hz, p, Lx, Lz, p) ; - } - } -} - -#undef PATTERN -#undef REAL -#undef COMPLEX -#undef ZOMPLEX - diff --git a/CHOLMOD/Utility/t_cholmod_copy_sparse.c b/CHOLMOD/Utility/t_cholmod_copy_sparse.c deleted file mode 100644 index 042bd2bbd8..0000000000 --- a/CHOLMOD/Utility/t_cholmod_copy_sparse.c +++ /dev/null @@ -1,144 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/t_cholmod_copy_sparse: copy a sparse matrix -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -// Creates an exact copy of a sparse matrix. For making a copy with a change -// of stype and/or copying the pattern of a numerical matrix, see cholmod_copy. -// For changing the xtype and/or dtype, see cholmod_sparse_xtype. - -#include "cholmod_internal.h" - -#define RETURN_IF_ERROR \ - if (Common->status < CHOLMOD_OK) \ - { \ - CHOLMOD(free_sparse) (&C, Common) ; \ - return (NULL) ; \ - } - -//------------------------------------------------------------------------------ -// t_cholmod_copy_sparse_worker template -//------------------------------------------------------------------------------ - -#define PATTERN -#include "t_cholmod_copy_sparse_worker.c" - -#define DOUBLE -#define REAL -#include "t_cholmod_copy_sparse_worker.c" -#define COMPLEX -#include "t_cholmod_copy_sparse_worker.c" -#define ZOMPLEX -#include "t_cholmod_copy_sparse_worker.c" - -#undef DOUBLE -#define SINGLE -#define REAL -#include "t_cholmod_copy_sparse_worker.c" -#define COMPLEX -#include "t_cholmod_copy_sparse_worker.c" -#define ZOMPLEX -#include "t_cholmod_copy_sparse_worker.c" - -cholmod_sparse *CHOLMOD(copy_sparse) // return new sparse matrix -( - cholmod_sparse *A, // sparse matrix to copy - cholmod_common *Common -) -{ - - //-------------------------------------------------------------------------- - // check inputs - //-------------------------------------------------------------------------- - - RETURN_IF_NULL_COMMON (NULL) ; - RETURN_IF_SPARSE_MATRIX_INVALID (A, NULL) ; - Common->status = CHOLMOD_OK ; - ASSERT (CHOLMOD(dump_sparse) (A, "copy_sparse:A", Common) >= 0) ; - - //-------------------------------------------------------------------------- - // allocate the copy C with the same characteristcs as A - //-------------------------------------------------------------------------- - - cholmod_sparse *C = CHOLMOD(allocate_sparse) (A->nrow, A->ncol, - A->nzmax, A->sorted, A->packed, A->stype, A->xtype + A->dtype, Common) ; - RETURN_IF_ERROR ; - - //-------------------------------------------------------------------------- - // get the sizes of the entries - //-------------------------------------------------------------------------- - - size_t ei = sizeof (Int) ; - size_t e = (A->dtype == CHOLMOD_SINGLE) ? sizeof (float) : sizeof (double) ; - size_t ex = e * ((A->xtype == CHOLMOD_PATTERN) ? 0 : - ((A->xtype == CHOLMOD_COMPLEX) ? 2 : 1)) ; - size_t ez = e * ((A->xtype == CHOLMOD_ZOMPLEX) ? 1 : 0) ; - - //-------------------------------------------------------------------------- - // copy the contents from A to C - //-------------------------------------------------------------------------- - - size_t ncol = A->ncol ; - - // copy A->p (both packed and unpacked cases) - memcpy (C->p, A->p, (ncol+1) * ei) ; - - if (A->packed) - { - // use memcpy when A is packed - int64_t anz = CHOLMOD(nnz) (A, Common) ; - if (A->i != NULL) memcpy (C->i, A->i, anz * ei) ; - if (A->x != NULL) memcpy (C->x, A->x, anz * ex) ; - if (A->z != NULL) memcpy (C->z, A->z, anz * ez) ; - } - else - { - // copy A->nz (for any xtype and dtype) - if (A->nz != NULL) memcpy (C->nz, A->nz, ncol * ei) ; - - // use a template worker when A is unpacked to copy A->i, A->x, and A->z - switch ((A->xtype + A->dtype) % 8) - { - default: - p_cholmod_copy_sparse_worker (C, A) ; - break ; - - case CHOLMOD_SINGLE + CHOLMOD_REAL: - r_s_cholmod_copy_sparse_worker (C, A) ; - break ; - - case CHOLMOD_SINGLE + CHOLMOD_COMPLEX: - c_s_cholmod_copy_sparse_worker (C, A) ; - break ; - - case CHOLMOD_SINGLE + CHOLMOD_ZOMPLEX: - z_s_cholmod_copy_sparse_worker (C, A) ; - break ; - - case CHOLMOD_DOUBLE + CHOLMOD_REAL: - r_cholmod_copy_sparse_worker (C, A) ; - break ; - - case CHOLMOD_DOUBLE + CHOLMOD_COMPLEX: - c_cholmod_copy_sparse_worker (C, A) ; - break ; - - case CHOLMOD_DOUBLE + CHOLMOD_ZOMPLEX: - z_cholmod_copy_sparse_worker (C, A) ; - break ; - } - } - - //-------------------------------------------------------------------------- - // return result - //-------------------------------------------------------------------------- - - ASSERT (CHOLMOD(dump_sparse) (C, "copy_sparse:C", Common) >= 0) ; - return (C) ; -} - diff --git a/CHOLMOD/Utility/t_cholmod_copy_sparse_worker.c b/CHOLMOD/Utility/t_cholmod_copy_sparse_worker.c deleted file mode 100644 index b101952c09..0000000000 --- a/CHOLMOD/Utility/t_cholmod_copy_sparse_worker.c +++ /dev/null @@ -1,63 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/t_cholmod_copy_sparse_worker: copy a sparse matrix -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -#include "cholmod_template.h" - -static void TEMPLATE (cholmod_copy_sparse_worker) -( - cholmod_sparse *C, // output sparse matrix - cholmod_sparse *A // sparse matrix to copy -) -{ - - //-------------------------------------------------------------------------- - // check inputs - //-------------------------------------------------------------------------- - - // This worker is only used for the unpacked case - ASSERT (!(A->packed)) ; - - //-------------------------------------------------------------------------- - // get the A and C matrices - //-------------------------------------------------------------------------- - - Int *Ap = (Int *) A->p ; - Int *Anz = (Int *) A->nz ; - Int *Ai = (Int *) A->i ; - Real *Ax = (Real *) A->x ; - Real *Az = (Real *) A->z ; - size_t ncol = A->ncol ; - - Int *Ci = (Int *) C->i ; - Real *Cx = (Real *) C->x ; - Real *Cz = (Real *) C->z ; - - //-------------------------------------------------------------------------- - // copy the contents from A to C - //-------------------------------------------------------------------------- - - for (Int j = 0 ; j < ncol ; j++) - { - Int p = Ap [j] ; - Int pend = p + Anz [j] ; - for ( ; p < pend ; p++) - { - // C(i,j) = A (i,j) - Ci [p] = Ai [p] ; - ASSIGN (Cx, Cz, p, Ax, Az, p) ; - } - } -} - -#undef PATTERN -#undef REAL -#undef COMPLEX -#undef ZOMPLEX - diff --git a/CHOLMOD/Utility/t_cholmod_copy_triplet.c b/CHOLMOD/Utility/t_cholmod_copy_triplet.c deleted file mode 100644 index 9acab33a86..0000000000 --- a/CHOLMOD/Utility/t_cholmod_copy_triplet.c +++ /dev/null @@ -1,70 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/t_cholmod_copy_triplet: copy a triplet matrix -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -#include "cholmod_internal.h" - -#define RETURN_IF_ERROR \ - if (Common->status < CHOLMOD_OK) \ - { \ - CHOLMOD(free_triplet) (&C, Common) ; \ - return (NULL) ; \ - } - -cholmod_triplet *CHOLMOD(copy_triplet) // return new triplet matrix -( - cholmod_triplet *T, // triplet matrix to copy - cholmod_common *Common -) -{ - - //-------------------------------------------------------------------------- - // check inputs - //-------------------------------------------------------------------------- - - RETURN_IF_NULL_COMMON (NULL) ; - RETURN_IF_TRIPLET_MATRIX_INVALID (T, NULL) ; - Common->status = CHOLMOD_OK ; - - //-------------------------------------------------------------------------- - // allocate the copy - //-------------------------------------------------------------------------- - - cholmod_triplet *C = CHOLMOD(allocate_triplet) (T->nrow, T->ncol, - T->nzmax, T->stype, T->xtype + T->dtype, Common) ; - RETURN_IF_ERROR ; - - //-------------------------------------------------------------------------- - // get the sizes of the entries - //-------------------------------------------------------------------------- - - size_t ei = sizeof (Int) ; - size_t e = (T->dtype == CHOLMOD_SINGLE) ? sizeof (float) : sizeof (double) ; - size_t ex = e * ((T->xtype == CHOLMOD_PATTERN) ? 0 : - ((T->xtype == CHOLMOD_COMPLEX) ? 2 : 1)) ; - size_t ez = e * ((T->xtype == CHOLMOD_ZOMPLEX) ? 1 : 0) ; - - //-------------------------------------------------------------------------- - // copy the contents from T to C - //-------------------------------------------------------------------------- - - C->nnz = T->nnz ; - if (T->i != NULL) memcpy (C->i, T->i, T->nnz * ei) ; - if (T->j != NULL) memcpy (C->j, T->j, T->nnz * ei) ; - if (T->x != NULL) memcpy (C->x, T->x, T->nnz * ex) ; - if (T->z != NULL) memcpy (C->z, T->z, T->nnz * ez) ; - - //-------------------------------------------------------------------------- - // return result - //-------------------------------------------------------------------------- - - ASSERT (CHOLMOD(dump_triplet) (C, "copy_triplet:C", Common)) ; - return (C) ; -} - diff --git a/CHOLMOD/Utility/t_cholmod_copy_worker.c b/CHOLMOD/Utility/t_cholmod_copy_worker.c deleted file mode 100644 index f125caf2a0..0000000000 --- a/CHOLMOD/Utility/t_cholmod_copy_worker.c +++ /dev/null @@ -1,148 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/t_cholmod_copy_worker: copy sparse matrix (change of stype) -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -// A is symmetric upper or lower, and C is unsymmetric. Both are square. - -#include "cholmod_template.h" - -static void TEMPLATE (cholmod_copy_worker) -( - cholmod_sparse *C, // output matrix - cholmod_sparse *A, // input matrix, not modified - bool ignore_diag, // if true, ignore diagonal - cholmod_common *Common -) -{ - - //-------------------------------------------------------------------------- - // check inputs - //-------------------------------------------------------------------------- - - Int n = A->ncol ; - ASSERT (A->stype != 0) ; - ASSERT (C->stype == 0) ; - ASSERT (n == A->ncol) ; - ASSERT (n == C->nrow) ; - ASSERT (n == C->ncol) ; - ASSERT (C->packed) ; - ASSERT (C->sorted == A->sorted) ; - ASSERT (C->dtype == A->dtype) ; - ASSERT (C->xtype == A->xtype || C->xtype == CHOLMOD_PATTERN) ; - - //-------------------------------------------------------------------------- - // get inputs - //-------------------------------------------------------------------------- - - Int *Wj = (Int *) Common->Iwork ; // size n integer workspace - - Int *Ap = (Int *) A->p ; - Int *Anz = (Int *) A->nz ; - Int *Ai = (Int *) A->i ; - Real *Ax = (Real *) A->x ; - Real *Az = (Real *) A->z ; - bool packed = A->packed ; - - Int *Cp = (Int *) C->p ; - Int *Ci = (Int *) C->i ; - Real *Cx = (Real *) C->x ; - Real *Cz = (Real *) C->z ; - bool keep_diag = !ignore_diag ; - - //-------------------------------------------------------------------------- - // create an unsymmetric matrix C from a symmetric matrix A - //-------------------------------------------------------------------------- - - // place A(i,j) in C(:,k) - #define ASSIGN_CIJ(i,j) \ - { \ - Int q = Wj [j]++ ; \ - ASSIGN (Cx, Cz, q, Ax, Az, p) ; \ - Ci [q] = i ; \ - } - - // place conj(A(i,j)) or A(i,j) in C(:,k) - #define ASSIGN_CIJ_CONJ_OR_NCONJ(i,j) \ - { \ - Int q = Wj [i]++ ; \ - ASSIGN_CONJ_OR_NCONJ (Cx, Cz, q, Ax, Az, p) ; \ - Ci [q] = j ; \ - } - - if (A->stype > 0) - { - - //---------------------------------------------------------------------- - // A is symmetric upper - //---------------------------------------------------------------------- - - for (Int j = 0 ; j < n ; j++) - { - Int p = Ap [j] ; - Int pend = (packed) ? (Ap [j+1]) : (p + Anz [j]) ; - for ( ; p < pend ; p++) - { - // get A(i,j) - Int i = Ai [p] ; - // skip entries in strictly lower part - if (i > j) continue ; - if (i == j) - { - // place diagonal entry A(i,i) in C(:,i) - if (keep_diag) ASSIGN_CIJ (i,i) ; - } - else - { - // place A(i,j) in C(:,j) and conj(A(i,j)) in C(:,i) - ASSIGN_CIJ (i,j) ; - ASSIGN_CIJ_CONJ_OR_NCONJ (i,j) ; - } - } - } - - } - else // A->stype < 0 - { - - //---------------------------------------------------------------------- - // A is symmetric lower - //---------------------------------------------------------------------- - - for (Int j = 0 ; j < n ; j++) - { - Int p = Ap [j] ; - Int pend = (packed) ? (Ap [j+1]) : (p + Anz [j]) ; - for ( ; p < pend ; p++) - { - // get A(i,j) - Int i = Ai [p] ; - // skip entries in strictly upper part - if (i < j) continue ; - if (i == j) - { - // place diagonal entry A(i,i) in C(:,i) - if (keep_diag) ASSIGN_CIJ (i,i) ; - } - else - { - // place A(i,j) in C(:,j) and conj(A(i,j)) in C(:,i) - ASSIGN_CIJ (i,j) ; - ASSIGN_CIJ_CONJ_OR_NCONJ (i,j) ; - } - } - } - } -} - -#undef PATTERN -#undef REAL -#undef COMPLEX -#undef ZOMPLEX -#undef NCONJUGATE - diff --git a/CHOLMOD/Utility/t_cholmod_cumsum.c b/CHOLMOD/Utility/t_cholmod_cumsum.c deleted file mode 100644 index 61ce582fef..0000000000 --- a/CHOLMOD/Utility/t_cholmod_cumsum.c +++ /dev/null @@ -1,46 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/t_cholmod_cumsum: cumulative sum -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -// Cp [0:n] = cumulative sum of Cnz [0:n-1]. Returns the total sum, or -1 -// if integer overflow has occurred. - -// Cp [0] = 0 -// Cp [1] = Cnz [0] -// Cp [2] = Cnz [0] + Cnz [1] ; -// Cp [3] = Cnz [0] + Cnz [1] + Cnz [2] ; -// ... -// Cp [k] = sum (Cnz [0 ... k-1]) -// ... -// Cp [n] = sum (Cnz [0 ... n-1]) - -#include "cholmod_internal.h" - -int64_t CHOLMOD(cumsum) -( - Int *Cp, // size n+1, output array, the cumsum of Cnz - Int *Cnz, // size n, input array - size_t n // size of Cp and Cnz -) -{ - Int p = 0 ; - for (Int k = 0 ; k < n ; k++) - { - Cp [k] = p ; - p += Cnz [k] ; - if (p < 0) - { - // integer overflow has occured - return (EMPTY) ; - } - } - Cp [n] = p ; - return ((int64_t) p) ; -} - diff --git a/CHOLMOD/Utility/t_cholmod_defaults.c b/CHOLMOD/Utility/t_cholmod_defaults.c deleted file mode 100644 index a6525a5686..0000000000 --- a/CHOLMOD/Utility/t_cholmod_defaults.c +++ /dev/null @@ -1,132 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/t_cholmod_defaults: set CHOLMOD defaults -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -#include "cholmod_internal.h" - -// Sets all CHOLMOD parameters to their default values. - -int CHOLMOD(defaults) (cholmod_common *Common) -{ - - //-------------------------------------------------------------------------- - // check inputs - //-------------------------------------------------------------------------- - - RETURN_IF_NULL_COMMON (FALSE) ; - - //-------------------------------------------------------------------------- - // set defaults - //-------------------------------------------------------------------------- - - Common->dbound = 0.0 ; // bound D for LDL' (double case) - Common->sbound = 0.0 ; // bound D for LDL' (single case) - Common->grow0 = 1.2 ; // how to grow L for simplicial method - Common->grow1 = 1.2 ; - Common->grow2 = 5 ; - Common->maxrank = 8 ; // max rank for update/downdate - - Common->final_asis = TRUE ; // leave L as-is - Common->final_super = TRUE ; // leave L supernodal - Common->final_ll = FALSE ; // leave factorization as LDL' - Common->final_pack = TRUE ; // pack columns when done - Common->final_monotonic = TRUE ; // sort columns when done - Common->final_resymbol = FALSE ; // do not resymbol when done - - Common->supernodal = CHOLMOD_AUTO ; // select supernodal automatically - Common->supernodal_switch = 40 ; // how to select super vs simpicial - - Common->prefer_zomplex = FALSE ; // use complex, not zomplex - Common->prefer_upper = TRUE ; // sym case: use upper not lower - Common->prefer_binary = FALSE ; // use 1's when converting from pattern - Common->quick_return_if_not_posdef = FALSE ; // return early if not posdef - - Common->metis_memory = 0.0 ; // metis memory control - Common->metis_nswitch = 3000 ; - Common->metis_dswitch = 0.66 ; - - Common->nrelax [0] = 4 ; // supernodal relaxation parameters - Common->nrelax [1] = 16 ; - Common->nrelax [2] = 48 ; - Common->zrelax [0] = 0.8 ; - Common->zrelax [1] = 0.1 ; - Common->zrelax [2] = 0.05 ; - - Common->print = 3 ; // print control - Common->precise = FALSE ; // print 5 digits - - //-------------------------------------------------------------------------- - // ordering methods - //-------------------------------------------------------------------------- - - Common->nmethods = 0 ; // use default strategy - Common->default_nesdis = FALSE ; // use METIS not NESDIS - Common->current = 0 ; // method being evaluated - Common->selected = EMPTY ; // final method chosen - Common->postorder = TRUE ; // use weighted postordering - - // defaults for all methods (revised below) - for (int i = 0 ; i <= CHOLMOD_MAXMETHODS ; i++) - { - Common->method [i].ordering = CHOLMOD_AMD ; // use AMD - Common->method [i].fl = EMPTY ; // no flop counts yet - Common->method [i].lnz = EMPTY ; // no lnz counts yet - Common->method [i].prune_dense = 10.0 ; // dense row/col parameter - Common->method [i].prune_dense2 = -1 ; // dense row/col parameter - Common->method [i].aggressive = TRUE ; // aggressive absorption - Common->method [i].order_for_lu = FALSE ; // order for chol, not lu - Common->method [i].nd_small = 200 ; // nesdis: small graph - Common->method [i].nd_compress = TRUE ; // nesdis: compression - Common->method [i].nd_camd = 1 ; // nesdis: use CAMD - Common->method [i].nd_components = FALSE ; // nesdis: use components - Common->method [i].nd_oksep = 1.0 ; // nesdis: for good sep - } - - // define the 9 methods: - // (0) given (skipped if no user permutation) - // (1) amd - // (2) metis - // (3) nesdis with defaults - // (4) natural - // (5) nesdis: stop at subgraphs of 20000 nodes - // (6) nesdis: stop at subgraphs of 4 nodes, do not use CAMD - // (7) nesdis: no pruning on of dense rows/cols - // (8) colamd - - Common->method [0].ordering = CHOLMOD_GIVEN ; - Common->method [2].ordering = CHOLMOD_METIS ; - Common->method [3].ordering = CHOLMOD_NESDIS ; - Common->method [4].ordering = CHOLMOD_NATURAL ; - Common->method [5].ordering = CHOLMOD_NESDIS ; - Common->method [5].nd_small = 20000 ; - Common->method [6].ordering = CHOLMOD_NESDIS ; - Common->method [6].nd_small = 4 ; - Common->method [6].nd_camd = 0 ; - Common->method [7].ordering = CHOLMOD_NESDIS ; - Common->method [7].prune_dense = -1. ; - Common->method [8].ordering = CHOLMOD_COLAMD ; - - //-------------------------------------------------------------------------- - // GPU - //-------------------------------------------------------------------------- - - #if defined ( CHOLMOD_INT64 ) - // only use the GPU for the int64 version - Common->useGPU = EMPTY ; - #else - Common->useGPU = 0 ; - #endif - - //-------------------------------------------------------------------------- - // return result - //-------------------------------------------------------------------------- - - return (TRUE) ; -} - diff --git a/CHOLMOD/Utility/t_cholmod_dense_nnz.c b/CHOLMOD/Utility/t_cholmod_dense_nnz.c deleted file mode 100644 index cc48defd74..0000000000 --- a/CHOLMOD/Utility/t_cholmod_dense_nnz.c +++ /dev/null @@ -1,95 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/t_cholmod_dense_nnz: # of nonzeros in a dense matrix -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -// Returns the # of nonzero entries in a dense matrix. - -#include "cholmod_internal.h" - -//------------------------------------------------------------------------------ -// t_cholmod_dense_nnz_worker template -//------------------------------------------------------------------------------ - -#define DOUBLE -#define REAL -#include "t_cholmod_dense_nnz_worker.c" -#define COMPLEX -#include "t_cholmod_dense_nnz_worker.c" -#define ZOMPLEX -#include "t_cholmod_dense_nnz_worker.c" - -#undef DOUBLE -#define SINGLE -#define REAL -#include "t_cholmod_dense_nnz_worker.c" -#define COMPLEX -#include "t_cholmod_dense_nnz_worker.c" -#define ZOMPLEX -#include "t_cholmod_dense_nnz_worker.c" - -//------------------------------------------------------------------------------ -// cholmod_dense_nnz -//------------------------------------------------------------------------------ - -int64_t CHOLMOD(dense_nnz) // return # of entries in the dense matrix -( - cholmod_dense *X, // input matrix - cholmod_common *Common -) -{ - - //-------------------------------------------------------------------------- - // check inputs - //-------------------------------------------------------------------------- - - RETURN_IF_NULL_COMMON (EMPTY) ; - RETURN_IF_DENSE_MATRIX_INVALID (X, EMPTY) ; - Common->status = CHOLMOD_OK ; - ASSERT (CHOLMOD(dump_dense) (X, "dense_nnz:X", Common) >= 0) ; - - //-------------------------------------------------------------------------- - // count the # of nonzero entries in X - //-------------------------------------------------------------------------- - - int xnz = 0 ; - switch ((X->xtype + X->dtype) % 8) - { - - case CHOLMOD_SINGLE + CHOLMOD_REAL: - xnz = r_s_cholmod_dense_nnz_worker (X) ; - break ; - - case CHOLMOD_SINGLE + CHOLMOD_COMPLEX: - xnz = c_s_cholmod_dense_nnz_worker (X) ; - break ; - - case CHOLMOD_SINGLE + CHOLMOD_ZOMPLEX: - xnz = z_s_cholmod_dense_nnz_worker (X) ; - break ; - - case CHOLMOD_DOUBLE + CHOLMOD_REAL: - xnz = r_cholmod_dense_nnz_worker (X) ; - break ; - - case CHOLMOD_DOUBLE + CHOLMOD_COMPLEX: - xnz = c_cholmod_dense_nnz_worker (X) ; - break ; - - case CHOLMOD_DOUBLE + CHOLMOD_ZOMPLEX: - xnz = z_cholmod_dense_nnz_worker (X) ; - break ; - } - - //-------------------------------------------------------------------------- - // return result - //-------------------------------------------------------------------------- - - return (xnz) ; -} - diff --git a/CHOLMOD/Utility/t_cholmod_dense_nnz_worker.c b/CHOLMOD/Utility/t_cholmod_dense_nnz_worker.c deleted file mode 100644 index 4338342534..0000000000 --- a/CHOLMOD/Utility/t_cholmod_dense_nnz_worker.c +++ /dev/null @@ -1,54 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/t_cholmod_dense_nnz: # of nonzeros in a dense matrix -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -#include "cholmod_template.h" - -static int64_t TEMPLATE (cholmod_dense_nnz_worker) -( - cholmod_dense *X // input dense matrix -) -{ - - //-------------------------------------------------------------------------- - // get inputs - //-------------------------------------------------------------------------- - - Real *Xx = (Real *) X->x ; - Real *Xz = (Real *) X->z ; - - Int nrow = (Int) X->nrow ; - Int ncol = (Int) X->ncol ; - Int d = (Int) X->d ; - - //-------------------------------------------------------------------------- - // count # of nonzeros in X - //-------------------------------------------------------------------------- - - int64_t xnz = 0 ; - for (Int j = 0, jx = 0 ; j < ncol ; j++, jx += d) - { - for (Int p = jx ; p < jx + nrow ; p++) - { - xnz += ENTRY_IS_NONZERO (Xx, Xz, p) ; - } - } - - //-------------------------------------------------------------------------- - // return result - //-------------------------------------------------------------------------- - - return (xnz) ; -} - -#undef PATTERN -#undef REAL -#undef COMPLEX -#undef ZOMPLEX - diff --git a/CHOLMOD/Utility/t_cholmod_dense_to_sparse.c b/CHOLMOD/Utility/t_cholmod_dense_to_sparse.c deleted file mode 100644 index 03267f3841..0000000000 --- a/CHOLMOD/Utility/t_cholmod_dense_to_sparse.c +++ /dev/null @@ -1,116 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/t_cholmod_dense_to_sparse: convert a dense matrix to sparse -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -// Converts a dense matrix X (as input) to a new sparse matrix C (as output). -// The xtype and dtype are preserved, except if values is false in which case -// C is returned as a pattern sparse matrix. - -#include "cholmod_internal.h" - -#define RETURN_IF_ERROR \ - if (Common->status < CHOLMOD_OK) \ - { \ - CHOLMOD(free_sparse) (&C, Common) ; \ - return (NULL) ; \ - } - -//------------------------------------------------------------------------------ -// t_cholmod_dense_to_sparse_worker template -//------------------------------------------------------------------------------ - -#define DOUBLE -#define REAL -#include "t_cholmod_dense_to_sparse_worker.c" -#define COMPLEX -#include "t_cholmod_dense_to_sparse_worker.c" -#define ZOMPLEX -#include "t_cholmod_dense_to_sparse_worker.c" - -#undef DOUBLE -#define SINGLE -#define REAL -#include "t_cholmod_dense_to_sparse_worker.c" -#define COMPLEX -#include "t_cholmod_dense_to_sparse_worker.c" -#define ZOMPLEX -#include "t_cholmod_dense_to_sparse_worker.c" - -//------------------------------------------------------------------------------ -// cholmod_dense_to_sparse -//------------------------------------------------------------------------------ - -cholmod_sparse *CHOLMOD(dense_to_sparse) // return a sparse matrix C -( - cholmod_dense *X, // input matrix - int values, // if true, copy the values; if false, C is pattern - cholmod_common *Common -) -{ - - //-------------------------------------------------------------------------- - // check inputs - //-------------------------------------------------------------------------- - - RETURN_IF_NULL_COMMON (NULL) ; - RETURN_IF_DENSE_MATRIX_INVALID (X, NULL) ; - Common->status = CHOLMOD_OK ; - ASSERT (CHOLMOD(dump_dense) (X, "dense_to_sparse:X", Common) >= 0) ; - - //-------------------------------------------------------------------------- - // allocate the sparse matrix result C - //-------------------------------------------------------------------------- - - int cnz = CHOLMOD(dense_nnz) (X, Common) ; - int cxtype = values ? X->xtype : CHOLMOD_PATTERN ; - cholmod_sparse *C = CHOLMOD(allocate_sparse) (X->nrow, X->ncol, cnz, - /* C is sorted: */ TRUE, /* C is packed: */ TRUE, /* C->stype: */ 0, - cxtype + X->dtype, Common) ; - RETURN_IF_ERROR ; - - //-------------------------------------------------------------------------- - // copy the nonzeros (or just their pattern) from X into C - //-------------------------------------------------------------------------- - - switch ((X->xtype + X->dtype) % 8) - { - - case CHOLMOD_SINGLE + CHOLMOD_REAL: - r_s_cholmod_dense_to_sparse_worker (C, X) ; - break ; - - case CHOLMOD_SINGLE + CHOLMOD_COMPLEX: - c_s_cholmod_dense_to_sparse_worker (C, X) ; - break ; - - case CHOLMOD_SINGLE + CHOLMOD_ZOMPLEX: - z_s_cholmod_dense_to_sparse_worker (C, X) ; - break ; - - case CHOLMOD_DOUBLE + CHOLMOD_REAL: - r_cholmod_dense_to_sparse_worker (C, X) ; - break ; - - case CHOLMOD_DOUBLE + CHOLMOD_COMPLEX: - c_cholmod_dense_to_sparse_worker (C, X) ; - break ; - - case CHOLMOD_DOUBLE + CHOLMOD_ZOMPLEX: - z_cholmod_dense_to_sparse_worker (C, X) ; - break ; - } - - //-------------------------------------------------------------------------- - // return result - //-------------------------------------------------------------------------- - - ASSERT (CHOLMOD(dump_sparse) (C, "sparse_to_dense:C", Common) >= 0) ; - return (C) ; -} - diff --git a/CHOLMOD/Utility/t_cholmod_dense_to_sparse_worker.c b/CHOLMOD/Utility/t_cholmod_dense_to_sparse_worker.c deleted file mode 100644 index 788818f0d7..0000000000 --- a/CHOLMOD/Utility/t_cholmod_dense_to_sparse_worker.c +++ /dev/null @@ -1,112 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/t_cholmod_dense_to_sparse_worker: dense to sparse matrix -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -#include "cholmod_template.h" - -static void TEMPLATE (cholmod_dense_to_sparse_worker) -( - cholmod_sparse *C, // output sparse matrix, already allocated - cholmod_dense *X // input dense matrix -) -{ - - //-------------------------------------------------------------------------- - // check inputs - //-------------------------------------------------------------------------- - - ASSERT (X->nrow == C->nrow) ; - ASSERT (X->ncol == C->ncol) ; - ASSERT (X->d >= X->nrow) ; - ASSERT (X->dtype == C->dtype) ; - ASSERT (C->packed) ; - ASSERT (C->sorted) ; - ASSERT (C->stype == 0) ; - - //-------------------------------------------------------------------------- - // get inputs - //-------------------------------------------------------------------------- - - Real *Xx = (Real *) X->x ; - Real *Xz = (Real *) X->z ; - Int nrow = X->nrow ; - Int ncol = X->ncol ; - Int d = X->d ; - - Int *Cp = (Int *) C->p ; - Int *Ci = (Int *) C->i ; - Real *Cx = (Real *) C->x ; - Real *Cz = (Real *) C->z ; - bool pattern = (C->xtype == CHOLMOD_PATTERN) ; - - //-------------------------------------------------------------------------- - // copy the dense matrix into the sparse matrix C - //-------------------------------------------------------------------------- - - Int p = 0 ; - - if (pattern) - { - - //---------------------------------------------------------------------- - // copy just the pattern of the nonzeros of X into C - //---------------------------------------------------------------------- - - for (Int j = 0, jx = 0 ; j < ncol ; j++, jx += d) - { - // log the start of C(:,j) - Cp [j] = p ; - // find the pattern of nonzeros in X(:,j) - for (Int i = 0, q = jx ; i < nrow ; i++, q++) - { - if (ENTRY_IS_NONZERO (Xx, Xz, q)) - { - Ci [p++] = i ; - } - } - } - - } - else - { - - //---------------------------------------------------------------------- - // copy the pattern and values of nonzeros in X into C - //---------------------------------------------------------------------- - - ASSERT (C->xtype == X->xtype) ; - - for (Int j = 0, jx = 0 ; j < ncol ; j++, jx += d) - { - // log the start of C(:,j) - Cp [j] = p ; - // find the pattern and values of nonzeros in X(:,j) - for (Int i = 0, q = jx ; i < nrow ; i++, q++) - { - if (ENTRY_IS_NONZERO (Xx, Xz, q)) - { - ASSIGN (Cx, Cz, p, Xx, Xz, q) ; - Ci [p++] = i ; - } - } - } - } - - //-------------------------------------------------------------------------- - // log the end of the last column of C - //-------------------------------------------------------------------------- - - Cp [ncol] = p ; -} - -#undef PATTERN -#undef REAL -#undef COMPLEX -#undef ZOMPLEX - diff --git a/CHOLMOD/Utility/t_cholmod_ensure_dense.c b/CHOLMOD/Utility/t_cholmod_ensure_dense.c deleted file mode 100644 index e375e8f297..0000000000 --- a/CHOLMOD/Utility/t_cholmod_ensure_dense.c +++ /dev/null @@ -1,100 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/t_cholmod_ensure_dense: ensure dense matrix has a given size -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -// Ensure a dense matrix has a given size, xtype, and dtype. If not, it is -// freed and reallocated. - -#include "cholmod_internal.h" - -#define RETURN_IF_ERROR \ - if (Common->status < CHOLMOD_OK) \ - { \ - CHOLMOD(free_dense) (X, Common) ; \ - return (NULL) ; \ - } - -cholmod_dense *CHOLMOD(ensure_dense) -( - cholmod_dense **X, // matrix to resize as needed (*X may be NULL) - size_t nrow, // # of rows - size_t ncol, // # of columns - size_t d, // leading dimension - int xdtype, // xtype + dtype of the matrix: - // (CHOLMOD_DOUBLE, _SINGLE) + - // (CHOLMOD_REAL, _COMPLEX, or _ZOMPLEX) - cholmod_common *Common -) -{ - - //-------------------------------------------------------------------------- - // check inputs - //-------------------------------------------------------------------------- - - RETURN_IF_NULL_COMMON (NULL) ; - RETURN_IF_NULL (X, NULL) ; - Common->status = CHOLMOD_OK ; - - //-------------------------------------------------------------------------- - // get the xtype and dtype - //-------------------------------------------------------------------------- - - int xtype = xdtype & 3 ; // real, complex, or zomplex (not pattern) - int dtype = xdtype & 4 ; // double or single - - if (xtype == CHOLMOD_PATTERN) - { - ERROR (CHOLMOD_INVALID, "xtype invalid") ; - return (NULL) ; - } - - //-------------------------------------------------------------------------- - // get the dimensions - //-------------------------------------------------------------------------- - - d = MAX (d, nrow) ; // leading dimension d must be >= nrow - int ok = TRUE ; - size_t nzmax_required = CHOLMOD(mult_size_t) (d, ncol, &ok) ; - if (!ok) - { - ERROR (CHOLMOD_INVALID, "problem too large") ; - return (NULL) ; - } - - //-------------------------------------------------------------------------- - // reshape or reallocate the matrix - //-------------------------------------------------------------------------- - - if ((*X) != NULL && nzmax_required <= (*X)->nzmax && xtype == (*X)->xtype - && dtype == (*X)->dtype) - { - // The required total size (nzmax_required) is ok, but the dimensions - // might not be. This allows an n-by-m matrix to be reconfigured in - // O(1) time into an m-by-n matrix. X->nzmax is not changed, so a - // matrix can be reduced in size in O(1) time, and then enlarged again - // back to the original size, also in O(1) time. - (*X)->nrow = nrow ; - (*X)->ncol = ncol ; - (*X)->d = d ; - RETURN_IF_DENSE_MATRIX_INVALID (*X, NULL) ; - } - else - { - // free the matrix and reallocate it with the right properties - CHOLMOD(free_dense) (X, Common) ; - (*X) = CHOLMOD(allocate_dense) (nrow, ncol, d, xdtype, Common) ; - } - - //-------------------------------------------------------------------------- - // return result - //-------------------------------------------------------------------------- - - return (*X) ; -} - diff --git a/CHOLMOD/Utility/t_cholmod_error.c b/CHOLMOD/Utility/t_cholmod_error.c deleted file mode 100644 index 4d27b980cc..0000000000 --- a/CHOLMOD/Utility/t_cholmod_error.c +++ /dev/null @@ -1,99 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/t_cholmod_error: CHOLMOD error handling -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -#include "cholmod_internal.h" - -//------------------------------------------------------------------------------ -// MESSAGE macro: print a message using the given printf function pointer -//------------------------------------------------------------------------------ - -#define MESSAGE(kind) \ -{ \ - printf_function ("CHOLMOD " kind ":") ; \ - if (message != NULL) printf_function (" %s.", message) ; \ - if (file != NULL) printf_function (" file: %s", file) ; \ - if (line > 0 ) printf_function (" line: %d", line) ; \ - printf_function ("\n") ; \ - fflush (stdout) ; \ - fflush (stderr) ; \ -} - -//------------------------------------------------------------------------------ -// cholmod_error -//------------------------------------------------------------------------------ - -int CHOLMOD(error) -( - int status, // Common->status - const char *file, // source file where error occurred - int line, // line number where error occurred - const char *message, // error message to print - cholmod_common *Common -) -{ - - //-------------------------------------------------------------------------- - // check inputs - //-------------------------------------------------------------------------- - - RETURN_IF_NULL_COMMON (FALSE) ; - - //-------------------------------------------------------------------------- - // set the error status - //-------------------------------------------------------------------------- - - Common->status = status ; - - //-------------------------------------------------------------------------- - // handle the error, unless we're inside a CHOLMOD try/catch block - //-------------------------------------------------------------------------- - - if (!(Common->try_catch)) - { - - //---------------------------------------------------------------------- - // print the error message, if permitted - //---------------------------------------------------------------------- - - #ifndef NPRINT - int (*printf_function) (const char *, ...) ; - printf_function = SuiteSparse_config_printf_func_get ( ) ; - if (printf_function != NULL) - { - if (status > 0 && Common->print > 1) - { - // print a warning message - MESSAGE ("warning") ; - } - else if (Common->print > 0) - { - // print an error message - MESSAGE ("error") ; - } - } - #endif - - //---------------------------------------------------------------------- - // call the user error handler, if present - //---------------------------------------------------------------------- - - if (Common->error_handler != NULL) - { - Common->error_handler (status, file, line, message) ; - } - } - - //-------------------------------------------------------------------------- - // return result - //-------------------------------------------------------------------------- - - return (TRUE) ; -} - diff --git a/CHOLMOD/Utility/t_cholmod_eye.c b/CHOLMOD/Utility/t_cholmod_eye.c deleted file mode 100644 index 9886a4866f..0000000000 --- a/CHOLMOD/Utility/t_cholmod_eye.c +++ /dev/null @@ -1,111 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/t_cholmod_eye: dense identity matrix -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -// Create a dense identity matrix, possibly rectangular, of any xtype or -// dtype. - -#include "cholmod_internal.h" - -#define RETURN_IF_ERROR \ - if (Common->status < CHOLMOD_OK) \ - { \ - CHOLMOD(free_dense) (&X, Common) ; \ - return (NULL) ; \ - } - -//------------------------------------------------------------------------------ -// t_cholmod_eye_worker template -//------------------------------------------------------------------------------ - -#define DOUBLE -#define REAL -#include "t_cholmod_eye_worker.c" -#define COMPLEX -#include "t_cholmod_eye_worker.c" -#define ZOMPLEX -#include "t_cholmod_eye_worker.c" - -#undef DOUBLE -#define SINGLE -#define REAL -#include "t_cholmod_eye_worker.c" -#define COMPLEX -#include "t_cholmod_eye_worker.c" -#define ZOMPLEX -#include "t_cholmod_eye_worker.c" - -//------------------------------------------------------------------------------ -// cholmod_eye: create a dense identity matrix -//------------------------------------------------------------------------------ - -cholmod_dense *CHOLMOD(eye) // return a dense identity matrix -( - size_t nrow, // # of rows - size_t ncol, // # of columns - int xdtype, // xtype + dtype of the matrix: - // (CHOLMOD_DOUBLE, _SINGLE) + - // (_REAL, _COMPLEX, or _ZOMPLEX) - cholmod_common *Common -) -{ - - //-------------------------------------------------------------------------- - // check inputs - //-------------------------------------------------------------------------- - - RETURN_IF_NULL_COMMON (NULL) ; - Common->status = CHOLMOD_OK ; - - //-------------------------------------------------------------------------- - // allocate the matrix and set it to all zero - //-------------------------------------------------------------------------- - - cholmod_dense *X = CHOLMOD(zeros) (nrow, ncol, xdtype, Common) ; - RETURN_IF_ERROR ; - - //-------------------------------------------------------------------------- - // fill the matrix with all 1's on the diagonal - //-------------------------------------------------------------------------- - - switch (xdtype % 8) - { - case CHOLMOD_SINGLE + CHOLMOD_REAL: - r_s_cholmod_eye_worker (X) ; - break ; - - case CHOLMOD_SINGLE + CHOLMOD_COMPLEX: - c_s_cholmod_eye_worker (X) ; - break ; - - case CHOLMOD_SINGLE + CHOLMOD_ZOMPLEX: - z_s_cholmod_eye_worker (X) ; - break ; - - case CHOLMOD_DOUBLE + CHOLMOD_REAL: - r_cholmod_eye_worker (X) ; - break ; - - case CHOLMOD_DOUBLE + CHOLMOD_COMPLEX: - c_cholmod_eye_worker (X) ; - break ; - - case CHOLMOD_DOUBLE + CHOLMOD_ZOMPLEX: - z_cholmod_eye_worker (X) ; - break ; - } - - //-------------------------------------------------------------------------- - // return result - //-------------------------------------------------------------------------- - - ASSERT (CHOLMOD(dump_dense) (X, "eye:X", Common) >= 0) ; - return (X) ; -} - diff --git a/CHOLMOD/Utility/t_cholmod_eye_worker.c b/CHOLMOD/Utility/t_cholmod_eye_worker.c deleted file mode 100644 index 4c66dcc4f7..0000000000 --- a/CHOLMOD/Utility/t_cholmod_eye_worker.c +++ /dev/null @@ -1,44 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/t_cholmod_eye_worker: dense identity matrix -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -#include "cholmod_template.h" - -static void TEMPLATE (cholmod_eye_worker) -( - cholmod_dense *X -) -{ - - //-------------------------------------------------------------------------- - // fill the matrix with all 1's on the diagonal - //-------------------------------------------------------------------------- - - Real *Xx = (Real *) X->x ; - Real *Xz = (Real *) X->z ; - - Int nrow = (Int) X->nrow ; - Int ncol = (Int) X->ncol ; - Int n = MIN (nrow, ncol) ; - - Real onex [2] = {1,0} ; - Real onez [1] = {0} ; - - for (Int k = 0 ; k < n ; k++) - { - // X(k,k) = 1 - ASSIGN (Xx, Xz, k + k*nrow, onex, onez, 0) ; - } -} - -#undef PATTERN -#undef REAL -#undef COMPLEX -#undef ZOMPLEX - diff --git a/CHOLMOD/Utility/t_cholmod_factor_to_sparse.c b/CHOLMOD/Utility/t_cholmod_factor_to_sparse.c deleted file mode 100644 index df786af4dc..0000000000 --- a/CHOLMOD/Utility/t_cholmod_factor_to_sparse.c +++ /dev/null @@ -1,98 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/t_cholmod_factor_to_sparse: convert factor to sparse matrix -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -// Creates a sparse matrix A from a factor L. The contents of L are -// transferred into A, and L is returned as a simplicial symbolic factor. - -#include "cholmod_internal.h" - -#define RETURN_IF_ERROR \ - if (Common->status < CHOLMOD_OK) \ - { \ - CHOLMOD(free_sparse) (&A, Common) ; \ - return (NULL) ; \ - } - -cholmod_sparse *CHOLMOD(factor_to_sparse) -( - cholmod_factor *L, // input: factor to convert; output: L is converted - // to a simplicial symbolic factor - cholmod_common *Common -) -{ - - //-------------------------------------------------------------------------- - // check inputs - //-------------------------------------------------------------------------- - - RETURN_IF_NULL_COMMON (NULL) ; - RETURN_IF_FACTOR_INVALID (L, NULL) ; - Common->status = CHOLMOD_OK ; - - DEBUG (CHOLMOD(dump_factor) (L, "factor_to_sparse:L input", Common)) ; - - if (L->xtype == CHOLMOD_PATTERN) - { - ERROR (CHOLMOD_INVALID, "L must be numerical on input") ; - return (NULL) ; - } - - cholmod_sparse *A = NULL ; - - //-------------------------------------------------------------------------- - // convert L in place - //-------------------------------------------------------------------------- - - CHOLMOD(change_factor) (L->xtype, L->is_ll, - /* L becomes simplicial: */ FALSE, - /* L becomes packed: */ TRUE, - /* L becomes monotonic: */ TRUE, L, Common) ; - RETURN_IF_ERROR ; - - //-------------------------------------------------------------------------- - // allocate the sparse matrix A - //-------------------------------------------------------------------------- - - A = CHOLMOD(calloc) (1, sizeof (cholmod_sparse), Common) ; - RETURN_IF_ERROR ; - - //-------------------------------------------------------------------------- - // move the contents of L into A, and make L pattern - //-------------------------------------------------------------------------- - - A->nrow = L->n ; - A->ncol = L->n ; - A->p = L->p ; L->p = NULL ; - A->i = L->i ; L->i = NULL ; - A->x = L->x ; L->x = NULL ; - A->z = L->z ; L->z = NULL ; - - A->stype = 0 ; - A->itype = L->itype ; - A->xtype = L->xtype ; L->xtype = CHOLMOD_PATTERN ; - A->dtype = L->dtype ; - - A->sorted = TRUE ; - A->packed = TRUE ; - A->nzmax = L->nzmax ; - - CHOLMOD(change_factor) (CHOLMOD_PATTERN, FALSE, FALSE, TRUE, TRUE, L, - Common) ; - RETURN_IF_ERROR ; - - //-------------------------------------------------------------------------- - // return result - //-------------------------------------------------------------------------- - - ASSERT (CHOLMOD(dump_sparse) (A, "factor to sparse:A", Common) >= 0) ; - DEBUG (CHOLMOD(dump_factor) (L, "factor_to_sparse:L input", Common)) ; - return (A) ; -} - diff --git a/CHOLMOD/Utility/t_cholmod_finish.c b/CHOLMOD/Utility/t_cholmod_finish.c deleted file mode 100644 index 596f566830..0000000000 --- a/CHOLMOD/Utility/t_cholmod_finish.c +++ /dev/null @@ -1,22 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/t_cholmod_finish: finish CHOLMOD (int32/int64 version) -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -#include "cholmod_internal.h" - -// cholmod_start or cholmod_l_start must be called once prior to calling any -// other CHOLMOD method. It contains workspace that must be freed by -// cholmod_finish or cholmod_l_finish (which is just another name for -// cholmod_free_work or cholmod_l_free_work, respetively), - -int CHOLMOD(finish) (cholmod_common *Common) -{ - return (CHOLMOD(free_work) (Common)) ; -} - diff --git a/CHOLMOD/Utility/t_cholmod_free.c b/CHOLMOD/Utility/t_cholmod_free.c deleted file mode 100644 index df473ee85b..0000000000 --- a/CHOLMOD/Utility/t_cholmod_free.c +++ /dev/null @@ -1,57 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/t_cholmod_free: free (int64/int32) -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -#include "cholmod_internal.h" - -void *CHOLMOD(free) // returns NULL to simplify its usage -( - size_t n, // number of items - size_t size, // size of each item - void *p, // memory to free - cholmod_common *Common -) -{ - - //-------------------------------------------------------------------------- - // check inputs - //-------------------------------------------------------------------------- - - RETURN_IF_NULL_COMMON (NULL) ; - if (p == NULL) return (NULL) ; // nothing to do (not an error) - - #ifndef NDEBUG - size_t size2 = CM_memtable_size (p) ; - ASSERT (n * size == size2) ; - #endif - - //-------------------------------------------------------------------------- - // free memory - //-------------------------------------------------------------------------- - - SuiteSparse_free (p) ; - - //-------------------------------------------------------------------------- - // log memory usage and return result - //-------------------------------------------------------------------------- - - Common->memory_inuse -= (n * size) ; - Common->malloc_count-- ; - - PRINTM (("cholmod_free %p %g cnt: %g inuse %g\n", - p, (double) n*size, (double) Common->malloc_count, - (double) Common->memory_inuse)) ; - - #ifndef NDEBUG - CM_memtable_remove (p) ; - #endif - - return (NULL) ; -} - diff --git a/CHOLMOD/Utility/t_cholmod_free_dense.c b/CHOLMOD/Utility/t_cholmod_free_dense.c deleted file mode 100644 index f682f47b49..0000000000 --- a/CHOLMOD/Utility/t_cholmod_free_dense.c +++ /dev/null @@ -1,55 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/t_cholmod_free_dense: free dense matrix -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -#include "cholmod_internal.h" - -int CHOLMOD(free_dense) -( - cholmod_dense **X, // handle of dense matrix to free - cholmod_common *Common -) -{ - - //-------------------------------------------------------------------------- - // check inputs - //-------------------------------------------------------------------------- - - RETURN_IF_NULL_COMMON (FALSE) ; - if (X == NULL || (*X) == NULL) - { - // X is already freed; nothing to do - return (TRUE) ; - } - - //-------------------------------------------------------------------------- - // get the sizes of the entries - //-------------------------------------------------------------------------- - - size_t e = ((*X)->dtype == CHOLMOD_SINGLE) ? - sizeof (float) : sizeof (double) ; - size_t ex = e * (((*X)->xtype == CHOLMOD_COMPLEX) ? 2 : 1) ; - size_t ez = e * (((*X)->xtype == CHOLMOD_ZOMPLEX) ? 1 : 0) ; - size_t nzmax = (*X)->nzmax ; - - //-------------------------------------------------------------------------- - // free the two arrays - //-------------------------------------------------------------------------- - - CHOLMOD(free) (nzmax, ex, (*X)->x, Common) ; - CHOLMOD(free) (nzmax, ez, (*X)->z, Common) ; - - //-------------------------------------------------------------------------- - // free the header and return result - //-------------------------------------------------------------------------- - - (*X) = CHOLMOD(free) (1, sizeof (cholmod_dense), (*X), Common) ; - return (TRUE) ; -} - diff --git a/CHOLMOD/Utility/t_cholmod_free_factor.c b/CHOLMOD/Utility/t_cholmod_free_factor.c deleted file mode 100644 index 4e1972d010..0000000000 --- a/CHOLMOD/Utility/t_cholmod_free_factor.c +++ /dev/null @@ -1,132 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/t_cholmod_free_factor: free a sparse factorization -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -#include "cholmod_internal.h" - -//------------------------------------------------------------------------------ -// cholmod_to_simplicial_sym -//------------------------------------------------------------------------------ - -// L is converted into a valid simplicial symbolic object, containing just -// L->Perm and L->ColCount. This method is used by cholmod_change_factor. L -// itself is not freed. This method is for internal use, not for the end-user -// (who should use cholmod_change_factor to access this functionality). - -int CHOLMOD(to_simplicial_sym) -( - cholmod_factor *L, // sparse factorization to modify - int to_ll, // change L to hold a LL' or LDL' factorization - cholmod_common *Common -) -{ - - //-------------------------------------------------------------------------- - // check inputs - //-------------------------------------------------------------------------- - - ASSERT (Common != NULL) ; - ASSERT (L != NULL) ; - - //-------------------------------------------------------------------------- - // get the sizes of the entries - //-------------------------------------------------------------------------- - - size_t ei = sizeof (Int) ; - size_t e = (L->dtype == CHOLMOD_SINGLE) ? sizeof (float) : sizeof (double) ; - size_t ex = e * ((L->xtype == CHOLMOD_PATTERN) ? 0 : - ((L->xtype == CHOLMOD_COMPLEX) ? 2 : 1)) ; - size_t ez = e * ((L->xtype == CHOLMOD_ZOMPLEX) ? 1 : 0) ; - - size_t nzmax = L->nzmax ; - size_t n = L->n ; - size_t s = L->nsuper + 1 ; - size_t xs = (L->is_super) ? L->xsize : nzmax ; - size_t ss = (L->ssize) ; - - //-------------------------------------------------------------------------- - // free the components of L - //-------------------------------------------------------------------------- - - // symbolic part of L (except for L->Perm and L->ColCount) - L->IPerm = CHOLMOD(free) (n, ei, L->IPerm, Common) ; - - // simplicial form of L - L->p = CHOLMOD(free) (n+1, ei, L->p, Common) ; - L->i = CHOLMOD(free) (nzmax, ei, L->i, Common) ; - L->nz = CHOLMOD(free) (n, ei, L->nz, Common) ; - L->next = CHOLMOD(free) (n+2, ei, L->next, Common) ; - L->prev = CHOLMOD(free) (n+2, ei, L->prev, Common) ; - - // supernodal form of L - L->pi = CHOLMOD(free) (s, ei, L->pi, Common) ; - L->px = CHOLMOD(free) (s, ei, L->px, Common) ; - L->super = CHOLMOD(free) (s, ei, L->super, Common) ; - L->s = CHOLMOD(free) (ss, ei, L->s, Common) ; - - // numerical part of L - L->x = CHOLMOD(free) (xs, ex, L->x, Common) ; - L->z = CHOLMOD(free) (xs, ez, L->z, Common) ; - - //-------------------------------------------------------------------------- - // change the header contents to reflect the simplicial symbolic status - //-------------------------------------------------------------------------- - - L->nzmax = 0 ; // no entries - L->is_super = FALSE ; // L is simplicial - L->xtype = CHOLMOD_PATTERN ; // L is symbolic - L->minor = n ; // see cholmod.h - L->is_ll = to_ll ? 1: 0 ; // L represents an LL' or LDL' factorization - L->ssize = 0 ; // L->s is not present - L->xsize = 0 ; // L->x is not present - L->nsuper = 0 ; // no supernodes - L->maxesize = 0 ; // no rows in any supernodes - L->maxcsize = 0 ; // largest update matrix is size zero -} - -//------------------------------------------------------------------------------ -// cholmod_free_factor -//------------------------------------------------------------------------------ - -int CHOLMOD(free_factor) -( - cholmod_factor **L, // handle of sparse factorization to free - cholmod_common *Common -) -{ - - //-------------------------------------------------------------------------- - // check inputs - //-------------------------------------------------------------------------- - - RETURN_IF_NULL_COMMON (FALSE) ; - if (L == NULL || (*L) == NULL) - { - // L is already freed; nothing to do - return (TRUE) ; - } - - //-------------------------------------------------------------------------- - // convert L to a simplicial symbolic LL' factorization - //-------------------------------------------------------------------------- - - CHOLMOD(to_simplicial_sym) (*L, 1, Common) ; - - //-------------------------------------------------------------------------- - // free the rest of L and return result - //-------------------------------------------------------------------------- - - size_t n = (*L)->n ; - size_t ei = sizeof (Int) ; - CHOLMOD(free) (n, ei, (*L)->Perm, Common) ; - CHOLMOD(free) (n, ei, (*L)->ColCount, Common) ; - (*L) = CHOLMOD(free) (1, sizeof (cholmod_factor), (*L), Common) ; - return (TRUE) ; -} - diff --git a/CHOLMOD/Utility/t_cholmod_free_sparse.c b/CHOLMOD/Utility/t_cholmod_free_sparse.c deleted file mode 100644 index 2fa15b6244..0000000000 --- a/CHOLMOD/Utility/t_cholmod_free_sparse.c +++ /dev/null @@ -1,62 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/t_cholmod_free_sparse: free sparse matrix -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -#include "cholmod_internal.h" - -int CHOLMOD(free_sparse) -( - cholmod_sparse **A, // handle of sparse matrix to free - cholmod_common *Common -) -{ - - //-------------------------------------------------------------------------- - // check inputs - //-------------------------------------------------------------------------- - - RETURN_IF_NULL_COMMON (FALSE) ; - if (A == NULL || (*A) == NULL) - { - // A is already freed; nothing to do - return (TRUE) ; - } - - //-------------------------------------------------------------------------- - // get the sizes of the entries - //-------------------------------------------------------------------------- - - size_t ei = sizeof (Int) ; - size_t e = ((*A)->dtype == CHOLMOD_SINGLE) ? - sizeof (float) : sizeof (double) ; - size_t ex = e * (((*A)->xtype == CHOLMOD_PATTERN) ? 0 : - (((*A)->xtype == CHOLMOD_COMPLEX) ? 2 : 1)) ; - size_t ez = e * (((*A)->xtype == CHOLMOD_ZOMPLEX) ? 1 : 0) ; - - size_t nzmax = (*A)->nzmax ; - size_t ncol = (*A)->ncol ; - - //-------------------------------------------------------------------------- - // free the five arrays - //-------------------------------------------------------------------------- - - CHOLMOD(free) (ncol+1, ei, (*A)->p, Common) ; - CHOLMOD(free) (ncol, ei, (*A)->nz, Common) ; - CHOLMOD(free) (nzmax, ei, (*A)->i, Common) ; - CHOLMOD(free) (nzmax, ex, (*A)->x, Common) ; - CHOLMOD(free) (nzmax, ez, (*A)->z, Common) ; - - //-------------------------------------------------------------------------- - // free the header and return result - //-------------------------------------------------------------------------- - - (*A) = CHOLMOD(free) (1, sizeof (cholmod_sparse), (*A), Common) ; - return (TRUE) ; -} - diff --git a/CHOLMOD/Utility/t_cholmod_free_triplet.c b/CHOLMOD/Utility/t_cholmod_free_triplet.c deleted file mode 100644 index 3783bbd167..0000000000 --- a/CHOLMOD/Utility/t_cholmod_free_triplet.c +++ /dev/null @@ -1,59 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/t_cholmod_free_triplet: free triplet matrix -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -#include "cholmod_internal.h" - -int CHOLMOD(free_triplet) -( - cholmod_triplet **T, // handle of triplet matrix to free - cholmod_common *Common -) -{ - - //-------------------------------------------------------------------------- - // check inputs - //-------------------------------------------------------------------------- - - RETURN_IF_NULL_COMMON (FALSE) ; - if (T == NULL || (*T) == NULL) - { - // T is already freed; nothing to do - return (TRUE) ; - } - - //-------------------------------------------------------------------------- - // get the sizes of the entries - //-------------------------------------------------------------------------- - - size_t ei = sizeof (Int) ; - size_t e = ((*T)->dtype == CHOLMOD_SINGLE) ? - sizeof (float) : sizeof (double) ; - size_t ex = e * (((*T)->xtype == CHOLMOD_PATTERN) ? 0 : - (((*T)->xtype == CHOLMOD_COMPLEX) ? 2 : 1)) ; - size_t ez = e * (((*T)->xtype == CHOLMOD_ZOMPLEX) ? 1 : 0) ; - size_t nz = (*T)->nzmax ; - - //-------------------------------------------------------------------------- - // free the four arrays - //-------------------------------------------------------------------------- - - CHOLMOD(free) (nz, ei, (*T)->i, Common) ; - CHOLMOD(free) (nz, ei, (*T)->j, Common) ; - CHOLMOD(free) (nz, ex, (*T)->x, Common) ; - CHOLMOD(free) (nz, ez, (*T)->z, Common) ; - - //-------------------------------------------------------------------------- - // free the header and return result - //-------------------------------------------------------------------------- - - (*T) = CHOLMOD(free) (1, sizeof (cholmod_triplet), (*T), Common) ; - return (TRUE) ; -} - diff --git a/CHOLMOD/Utility/t_cholmod_free_work.c b/CHOLMOD/Utility/t_cholmod_free_work.c deleted file mode 100644 index cda854bc29..0000000000 --- a/CHOLMOD/Utility/t_cholmod_free_work.c +++ /dev/null @@ -1,61 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/t_cholmod_free_work: free workspace in Common (int32/64) -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -#include "cholmod_internal.h" - -int CHOLMOD(free_work) (cholmod_common *Common) -{ - - //-------------------------------------------------------------------------- - // check inputs - //-------------------------------------------------------------------------- - - RETURN_IF_NULL_COMMON (FALSE) ; - - //-------------------------------------------------------------------------- - // free Flag and Head, of size nrow and nrow+1 Ints - //-------------------------------------------------------------------------- - - size_t nrow = Common->nrow ; - Common->Flag = CHOLMOD(free) (nrow, sizeof (Int), Common->Flag, Common) ; - Common->Head = CHOLMOD(free) (nrow+1, sizeof (Int), Common->Head, Common) ; - Common->nrow = 0 ; - - //-------------------------------------------------------------------------- - // free Iwork, of size iworksize Ints - //-------------------------------------------------------------------------- - - Common->Iwork = CHOLMOD(free) (Common->iworksize, - sizeof (Int), Common->Iwork, Common) ; - Common->iworksize = 0 ; - - //-------------------------------------------------------------------------- - // free Xwork, of size xworksize bytes - //-------------------------------------------------------------------------- - - Common->Xwork = CHOLMOD(free) (Common->xworkbytes, sizeof (uint8_t), - Common->Xwork, Common) ; - Common->xworkbytes = 0 ; - - //-------------------------------------------------------------------------- - // free GPU workspace - //-------------------------------------------------------------------------- - - #ifdef SUITESPARSE_CUDA - CHOLMOD(gpu_deallocate) (Common) ; - #endif - - //-------------------------------------------------------------------------- - // return result - //-------------------------------------------------------------------------- - - return (TRUE) ; -} - diff --git a/CHOLMOD/Utility/t_cholmod_malloc.c b/CHOLMOD/Utility/t_cholmod_malloc.c deleted file mode 100644 index 8c1b7b33f0..0000000000 --- a/CHOLMOD/Utility/t_cholmod_malloc.c +++ /dev/null @@ -1,62 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/t_cholmod_malloc: malloc/calloc (int64/int32) -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -#include "cholmod_internal.h" - -// This template creates 4 functions: -// cholmod_malloc int32, malloc, using SuiteSparse_malloc -// cholmod_l_malloc int64, malloc, using SuiteSparse_malloc -// cholmod_calloc int32, calloc, using SuiteSparse_calloc -// cholmod_l_calloc int64, calloc, using SuiteSparse_calloc - -void *CHOLMOD_ALLOC_FUNCTION // return pointer to newly allocated memory -( - size_t n, // number of items - size_t size, // size of each item - cholmod_common *Common -) -{ - - //-------------------------------------------------------------------------- - // check inputs - //-------------------------------------------------------------------------- - - RETURN_IF_NULL_COMMON (NULL) ; - - //-------------------------------------------------------------------------- - // allocate memory - //-------------------------------------------------------------------------- - - void *p = SUITESPARSE_ALLOC_FUNCTION (n, size) ; // malloc or calloc - - //-------------------------------------------------------------------------- - // log memory usage and return result - //-------------------------------------------------------------------------- - - if (p != NULL) - { - // success: log the change in memory usage - Common->memory_inuse += (n * size) ; - Common->memory_usage = MAX (Common->memory_usage, Common->memory_inuse); - Common->malloc_count++ ; - PRINTM (("cholmod_malloc %p %g cnt: %g inuse %g\n", - p, (double) n*size, (double) Common->malloc_count, - (double) Common->memory_inuse)) ; - #ifndef NDEBUG - CM_memtable_add (p, n*size) ; - #endif - } - else - { - ERROR (CHOLMOD_OUT_OF_MEMORY, "out of memory") ; - } - return (p) ; -} - diff --git a/CHOLMOD/Utility/t_cholmod_maxrank.c b/CHOLMOD/Utility/t_cholmod_maxrank.c deleted file mode 100644 index 508232ffe6..0000000000 --- a/CHOLMOD/Utility/t_cholmod_maxrank.c +++ /dev/null @@ -1,44 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/t_cholmod_maxrank: find valid value of Common->maxrank -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -#include "cholmod_internal.h" - -// Returns 0 on error, or 2, 4, or 8 otherwise. - -size_t CHOLMOD(maxrank) // return validated Common->maxrank -( - size_t n, // # of rows of L and A - cholmod_common *Common -) -{ - - //-------------------------------------------------------------------------- - // check inputs - //-------------------------------------------------------------------------- - - RETURN_IF_NULL_COMMON (0) ; - - //-------------------------------------------------------------------------- - // determine a valid value of maxrank - //-------------------------------------------------------------------------- - - size_t maxrank = Common->maxrank ; - if (n == 0) return (2) ; - - // guard against size_t overflow (very unlikely) - size_t max_maxrank = SIZE_MAX / (n * sizeof (float)) ; - maxrank = MIN (maxrank, max_maxrank) ; - - // maxrank of 2 or less: use 2 - // maxrank of 3 or 4: use 4 - // else use 8 - return ((maxrank <= 2) ? 2 : ((maxrank <= 4) ? 4 : 8)) ; -} - diff --git a/CHOLMOD/Utility/t_cholmod_mult_size_t.c b/CHOLMOD/Utility/t_cholmod_mult_size_t.c deleted file mode 100644 index 7bf6c70fda..0000000000 --- a/CHOLMOD/Utility/t_cholmod_mult_size_t.c +++ /dev/null @@ -1,21 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/t_cholmod_mult_size_t: multiply two size_t values -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -#include "cholmod_internal.h" - -// multiply two size_t values and safely check for integer overflow - -size_t CHOLMOD(mult_size_t) (size_t a, size_t b, int *ok) -{ - uint64_t x ; - (*ok) = cholmod_mult_uint64_t (&x, (uint64_t) a, (uint64_t) b) ; - return (((*ok) && x <= SIZE_MAX) ? ((size_t) x) : 0) ; -} - diff --git a/CHOLMOD/Utility/t_cholmod_nnz.c b/CHOLMOD/Utility/t_cholmod_nnz.c deleted file mode 100644 index d24931dca7..0000000000 --- a/CHOLMOD/Utility/t_cholmod_nnz.c +++ /dev/null @@ -1,54 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/t_cholmod_nnz: # of entries in a sparse matrix -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -// returns the # of entries held in a sparse matrix data structure. If A is -// symmetric and held in either upper/lower form, then only those entries -// in the upper/lower part are counted. - -#include "cholmod_internal.h" - -int64_t CHOLMOD(nnz) // return # of entries in the sparse matrix -( - cholmod_sparse *A, // sparse matrix to query - cholmod_common *Common -) -{ - - //-------------------------------------------------------------------------- - // check inputs - //-------------------------------------------------------------------------- - - RETURN_IF_NULL_COMMON (EMPTY) ; - RETURN_IF_SPARSE_MATRIX_INVALID (A, EMPTY) ; - Common->status = CHOLMOD_OK ; - - //-------------------------------------------------------------------------- - // get the # of entries - //-------------------------------------------------------------------------- - - if (!(A->packed)) - { - // A is held in unpacked form, so nnz(A) is sum (Anz [0..ncol-1]) - int64_t anz = 0 ; - int64_t ncol = A->ncol ; - Int *Anz = (Int *) A->nz ; - for (int64_t j = 0 ; j < ncol ; j++) - { - anz += (int64_t) Anz [j] ; - } - return (anz) ; - } - else - { - // A is held in packed form, so nnz(A) is just Ap [ncol] - return ((int64_t) ((Int *) A->p) [A->ncol]) ; - } -} - diff --git a/CHOLMOD/Utility/t_cholmod_ones.c b/CHOLMOD/Utility/t_cholmod_ones.c deleted file mode 100644 index d81f4b12b0..0000000000 --- a/CHOLMOD/Utility/t_cholmod_ones.c +++ /dev/null @@ -1,111 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/t_cholmod_ones: dense matrix of all ones -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -// Create a dense matrix with all entries equal to one, of any xtype or dtype. - -#include "cholmod_internal.h" - -#define RETURN_IF_ERROR \ - if (Common->status < CHOLMOD_OK) \ - { \ - CHOLMOD(free_dense) (&X, Common) ; \ - return (NULL) ; \ - } - -//------------------------------------------------------------------------------ -// t_cholmod_ones_worker template -//------------------------------------------------------------------------------ - -#define DOUBLE -#define REAL -#include "t_cholmod_ones_worker.c" -#define COMPLEX -#include "t_cholmod_ones_worker.c" -#define ZOMPLEX -#include "t_cholmod_ones_worker.c" - -#undef DOUBLE -#define SINGLE -#define REAL -#include "t_cholmod_ones_worker.c" -#define COMPLEX -#include "t_cholmod_ones_worker.c" -#define ZOMPLEX -#include "t_cholmod_ones_worker.c" - -//------------------------------------------------------------------------------ -// cholmod_ones: create a dense matrix all equal to 1 -//------------------------------------------------------------------------------ - -cholmod_dense *CHOLMOD(ones) -( - size_t nrow, // # of rows - size_t ncol, // # of columns - int xdtype, // xtype + dtype of the matrix: - // (CHOLMOD_DOUBLE, _SINGLE) + - // (_REAL, _COMPLEX, or _ZOMPLEX) - cholmod_common *Common -) -{ - - //-------------------------------------------------------------------------- - // check inputs - //-------------------------------------------------------------------------- - - RETURN_IF_NULL_COMMON (NULL) ; - Common->status = CHOLMOD_OK ; - - //-------------------------------------------------------------------------- - // allocate the matrix - //-------------------------------------------------------------------------- - - cholmod_dense *X = CHOLMOD(allocate_dense) (nrow, ncol, nrow, xdtype, - Common) ; - RETURN_IF_ERROR ; - - //-------------------------------------------------------------------------- - // fill the matrix with all 1's - //-------------------------------------------------------------------------- - - switch (xdtype % 8) - { - case CHOLMOD_SINGLE + CHOLMOD_REAL: - r_s_cholmod_ones_worker (X) ; - break ; - - case CHOLMOD_SINGLE + CHOLMOD_COMPLEX: - c_s_cholmod_ones_worker (X) ; - break ; - - case CHOLMOD_SINGLE + CHOLMOD_ZOMPLEX: - z_s_cholmod_ones_worker (X) ; - break ; - - case CHOLMOD_DOUBLE + CHOLMOD_REAL: - r_cholmod_ones_worker (X) ; - break ; - - case CHOLMOD_DOUBLE + CHOLMOD_COMPLEX: - c_cholmod_ones_worker (X) ; - break ; - - case CHOLMOD_DOUBLE + CHOLMOD_ZOMPLEX: - z_cholmod_ones_worker (X) ; - break ; - } - - //-------------------------------------------------------------------------- - // return result - //-------------------------------------------------------------------------- - - ASSERT (CHOLMOD(dump_dense) (X, "ones:X", Common) >= 0) ; - return (X) ; -} - diff --git a/CHOLMOD/Utility/t_cholmod_ones_worker.c b/CHOLMOD/Utility/t_cholmod_ones_worker.c deleted file mode 100644 index 50a8ebfcd4..0000000000 --- a/CHOLMOD/Utility/t_cholmod_ones_worker.c +++ /dev/null @@ -1,41 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/t_cholmod_ones_worker: dense matrix of all ones -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -#include "cholmod_template.h" - -static void TEMPLATE (cholmod_ones_worker) -( - cholmod_dense *X -) -{ - - //-------------------------------------------------------------------------- - // fill the matrix with all 1's - //-------------------------------------------------------------------------- - - Real *Xx = (Real *) X->x ; - Real *Xz = (Real *) X->z ; - size_t nzmax = X->nzmax ; - - Real onex [2] = {1,0} ; - Real onez [1] = {0} ; - - for (Int k = 0 ; k < nzmax ; k++) - { - // X(k) = 1 - ASSIGN (Xx, Xz, k, onex, onez, 0) ; - } -} - -#undef PATTERN -#undef REAL -#undef COMPLEX -#undef ZOMPLEX - diff --git a/CHOLMOD/Utility/t_cholmod_pack_factor.c b/CHOLMOD/Utility/t_cholmod_pack_factor.c deleted file mode 100644 index 244d57c119..0000000000 --- a/CHOLMOD/Utility/t_cholmod_pack_factor.c +++ /dev/null @@ -1,118 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/t_cholmod_pack_factor: pack a simplicial factorization -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -// The columns of simplicial factor L can have gaps between them, with empty -// space. This method removes the empty space, leaving all the empty space at -// the tail end of L->i and L->x. Each column of L is reduced in is size so -// that it has at most Common->grow2 empty space at the end of each column. - -// L must be simplicial and numerical (not symbolic). If L is supernodal, or -// symbolic, this method does nothing. - -// This method can be followed by a call to cholmod_reallocate_factor, to -// reduce the size of L->i and L->x. Or, the space can be left to accomodate -// future growth from updates/downdates. - -// The columns of L are not made to appear in monotonic order. For that, -// use cholmod_change_factor which can both pack the columns and make them -// monotonic. - -#include "cholmod_internal.h" - -//------------------------------------------------------------------------------ -// t_cholmod_pack_factor_worker template -//------------------------------------------------------------------------------ - -#define DOUBLE -#define REAL -#include "t_cholmod_pack_factor_worker.c" -#define COMPLEX -#include "t_cholmod_pack_factor_worker.c" -#define ZOMPLEX -#include "t_cholmod_pack_factor_worker.c" - -#undef DOUBLE -#define SINGLE -#define REAL -#include "t_cholmod_pack_factor_worker.c" -#define COMPLEX -#include "t_cholmod_pack_factor_worker.c" -#define ZOMPLEX -#include "t_cholmod_pack_factor_worker.c" - -//------------------------------------------------------------------------------ -// cholmod_pack_factor -//------------------------------------------------------------------------------ - -int CHOLMOD(pack_factor) -( - cholmod_factor *L, // factor to pack - cholmod_common *Common -) -{ - - //-------------------------------------------------------------------------- - // check inputs - //-------------------------------------------------------------------------- - - RETURN_IF_NULL_COMMON (FALSE) ; - RETURN_IF_FACTOR_INVALID (L, FALSE) ; - Common->status = CHOLMOD_OK ; - - DEBUG (CHOLMOD(dump_factor) (L, "pack:L input", Common)) ; - - if (L->xtype == CHOLMOD_PATTERN || L->is_super) - { - // nothing to do - return (TRUE) ; - } - - //-------------------------------------------------------------------------- - // pack - //-------------------------------------------------------------------------- - - switch ((L->xtype + L->dtype) % 8) - { - default: - break ; - - case CHOLMOD_SINGLE + CHOLMOD_REAL: - r_s_cholmod_pack_factor_worker (L, Common) ; - break ; - - case CHOLMOD_SINGLE + CHOLMOD_COMPLEX: - c_s_cholmod_pack_factor_worker (L, Common) ; - break ; - - case CHOLMOD_SINGLE + CHOLMOD_ZOMPLEX: - z_s_cholmod_pack_factor_worker (L, Common) ; - break ; - - case CHOLMOD_DOUBLE + CHOLMOD_REAL: - r_cholmod_pack_factor_worker (L, Common) ; - break ; - - case CHOLMOD_DOUBLE + CHOLMOD_COMPLEX: - c_cholmod_pack_factor_worker (L, Common) ; - break ; - - case CHOLMOD_DOUBLE + CHOLMOD_ZOMPLEX: - z_cholmod_pack_factor_worker (L, Common) ; - break ; - } - - //-------------------------------------------------------------------------- - // return result - //-------------------------------------------------------------------------- - - DEBUG (CHOLMOD(dump_factor) (L, "done pack", Common)) ; - return (TRUE) ; -} - diff --git a/CHOLMOD/Utility/t_cholmod_pack_factor_worker.c b/CHOLMOD/Utility/t_cholmod_pack_factor_worker.c deleted file mode 100644 index f4d5420bcb..0000000000 --- a/CHOLMOD/Utility/t_cholmod_pack_factor_worker.c +++ /dev/null @@ -1,97 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/t_cholmod_pack_factor_worker: pack a simplicial factorization -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -#include "cholmod_template.h" - -//------------------------------------------------------------------------------ -// cholmod_pack_factor_worker -//------------------------------------------------------------------------------ - -static void TEMPLATE (cholmod_pack_factor_worker) -( - cholmod_factor *L, // factor to pack - cholmod_common *Common -) -{ - - //-------------------------------------------------------------------------- - // get inputs - //-------------------------------------------------------------------------- - - Int n = L->n ; - Int *Lp = (Int *) L->p ; - Int *Li = (Int *) L->i ; - Real *Lx = (Real *) L->x ; - Real *Lz = (Real *) L->z ; - Int *Lnz = (Int *) L->nz ; - Int *Lnext = (Int *) L->next ; - - Int slack = Common->grow2 ; - - //-------------------------------------------------------------------------- - // pack, traversing the link list of columns of L - //-------------------------------------------------------------------------- - - Int j = Lnext [n+1] ; // first column in the list is Lnext [n+1] - Int pnew = 0 ; // next column can move to pnew - - while (j != n) // j=n is the fictious placeholder at end of list - { - - //---------------------------------------------------------------------- - // get column j, entries currently in Li and Lx [pold...pold+lnzj-1] - //---------------------------------------------------------------------- - - Int pold = Lp [j] ; // start of column j in L->i and L->j - Int lnzj = Lnz [j] ; // # of entries in column j - ASSERT (lnzj > 0) ; - - //---------------------------------------------------------------------- - // pack column j, if possible - //---------------------------------------------------------------------- - - if (pnew < pold) - { - // Li,Lx [pnew...pnew+lnz-1] = Li,Lx [pold...pold+lnz-1] - for (Int k = 0 ; k < lnzj ; k++) - { - // move L(i,j) from position pold+k to position pnew+k - Li [pnew + k] = Li [pold + k] ; - ASSIGN (Lx, Lz, pnew + k, Lx, Lz, pold + k) ; - } - // log the new position of the first entry of L(:,j) - Lp [j] = pnew ; - } - - //---------------------------------------------------------------------- - // add some empty space at the end of column j - //---------------------------------------------------------------------- - - Int desired_space = lnzj + slack ; // add slack space to column j - Int max_space = n - j ; // no need for more than this space - Int total_space = MIN (desired_space, max_space) ; - - //---------------------------------------------------------------------- - // next column will move to position pnew, if possible - //---------------------------------------------------------------------- - - Int jnext = Lnext [j] ; // jnext = next column in the list - Int pnext = Lp [jnext] ; // next column jnext starts here - Int pthis = Lp [j] + total_space ; // one past the end of column j - pnew = MIN (pthis, pnext) ; // next column can move to pnew - j = jnext ; // move to the next column - } -} - -#undef PATTERN -#undef REAL -#undef COMPLEX -#undef ZOMPLEX - diff --git a/CHOLMOD/Utility/t_cholmod_ptranspose.c b/CHOLMOD/Utility/t_cholmod_ptranspose.c deleted file mode 100644 index d81663cc0c..0000000000 --- a/CHOLMOD/Utility/t_cholmod_ptranspose.c +++ /dev/null @@ -1,113 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/t_cholmod_ptranspose: permuted transpose -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -// C = A' or A(p,p)' if A is symmetric. C = A', A(:,f)' or A(p,f)' if A is -// unsymmetric. -// -// workspace: at most nrow+ncol - -#include "cholmod_internal.h" - -#define RETURN_IF_ERROR \ - if (Common->status < CHOLMOD_OK) \ - { \ - CHOLMOD(free_sparse) (&C, Common) ; \ - return (NULL) ; \ - } - -cholmod_sparse *CHOLMOD(ptranspose) -( - cholmod_sparse *A, // input matrix - int mode, // 2: numerical (conj), 1: numerical (non-conj.), - // <= 0: pattern (with diag) - Int *Perm, // permutation for C=A(p,f)' or C=A(p,p)', or NULL - Int *fset, // a list of column indices in range 0:A->ncol-1 - size_t fsize, // # of entries in fset - cholmod_common *Common -) -{ - - //-------------------------------------------------------------------------- - // check inputs - //-------------------------------------------------------------------------- - - RETURN_IF_NULL_COMMON (NULL) ; - RETURN_IF_SPARSE_MATRIX_INVALID (A, NULL) ; - Common->status = CHOLMOD_OK ; - - //-------------------------------------------------------------------------- - // count # of entries in C - //-------------------------------------------------------------------------- - - Int cnz = 0 ; - if ((A->stype == 0) && (fset != NULL)) - { - // C = A(p,f)' or A(:,f)' where A is unsymmetric and fset is present - Int ncol = A->ncol ; - if (A->packed) - { - Int *Ap = (Int *) A->p ; - for (Int k = 0 ; k < fsize ; k++) - { - Int j = fset [k] ; - if (j < 0 || j >= ncol) continue ; - cnz += (Ap [j+1] - Ap [j]) ; - } - } - else - { - Int *Anz = (Int *) A->nz ; - for (Int k = 0 ; k < fsize ; k++) - { - Int j = fset [k] ; - if (j < 0 || j >= ncol) continue ; - cnz += Anz [j] ; - } - } - } - else - { - // C = A(p,p)' A is symmetric, or C=A' where A is any matrix - cnz = CHOLMOD(nnz) (A, Common) ; - } - - //-------------------------------------------------------------------------- - // allocate C - //-------------------------------------------------------------------------- - - cholmod_sparse *C = CHOLMOD(allocate_sparse) (A->ncol, A->nrow, cnz, - /* C is sorted: */ TRUE, /* C is packed */ TRUE, - /* C has the opposite stype as A: */ -(A->stype), - ((mode > 0) ? A->xtype : CHOLMOD_PATTERN) + A->dtype, Common) ; - RETURN_IF_ERROR ; - - //-------------------------------------------------------------------------- - // construct C - //-------------------------------------------------------------------------- - - if (A->stype != 0) - { - // C = A (p,p)' or A' when A is symmetric (upper or lower) - CHOLMOD(transpose_sym) (A, mode, Perm, C, Common) ; - } - else - { - // C = A (p,f)' or A(:,f)' when A is unsymmetric - CHOLMOD(transpose_unsym) (A, mode, Perm, fset, fsize, C, Common) ; - } - RETURN_IF_ERROR ; - - //-------------------------------------------------------------------------- - // return result - //-------------------------------------------------------------------------- - - return (C) ; -} - diff --git a/CHOLMOD/Utility/t_cholmod_realloc.c b/CHOLMOD/Utility/t_cholmod_realloc.c deleted file mode 100644 index e2cbe55920..0000000000 --- a/CHOLMOD/Utility/t_cholmod_realloc.c +++ /dev/null @@ -1,80 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/t_cholmod_realloc: realloc (int64/int32) -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -#include "cholmod_internal.h" - -void *CHOLMOD(realloc) // return newly reallocated block of memory -( - size_t nnew, // # of items in newly reallocate memory - size_t size, // size of each item - void *p, // pointer to memory to reallocate (may be NULL) - size_t *n, // # of items in p on input; nnew on output if success - cholmod_common *Common -) -{ - - //-------------------------------------------------------------------------- - // check inputs - //-------------------------------------------------------------------------- - - RETURN_IF_NULL_COMMON (NULL) ; - - //-------------------------------------------------------------------------- - // realloc the block - //-------------------------------------------------------------------------- - - int ok ; - bool newly_allocated = (p == NULL) ; - void *pold = p ; - size_t nold = (*n) ; - - p = SuiteSparse_realloc (nnew, *n, size, p, &ok) ; - - //-------------------------------------------------------------------------- - // log memory usage and return result - //-------------------------------------------------------------------------- - - if (ok) - { - // success: log the change in memory usage and update n to new # items - - if (!newly_allocated) - { - PRINTM (("cholmod_free %p %g cnt: %g inuse %g\n", - pold, (double) nold*size, (double) Common->malloc_count-1, - (double) (Common->memory_inuse - nold*size))) ; - #ifndef NDEBUG - size_t size2 = CM_memtable_size (pold) ; - ASSERT (nold * size == size2) ; - CM_memtable_remove (pold) ; - #endif - } - Common->memory_inuse += ((nnew-nold) * size) ; - Common->memory_usage = MAX (Common->memory_usage, Common->memory_inuse); - if (newly_allocated) - { - Common->malloc_count++ ; - } - PRINTM (("cholmod_malloc %p %g cnt: %g inuse %g\n", - p, (double) nnew*size, (double) Common->malloc_count, - (double) Common->memory_inuse)) ; - #ifndef NDEBUG - CM_memtable_add (p, nnew * size) ; - #endif - (*n) = nnew ; - } - else - { - // p is unchanged - ERROR (CHOLMOD_OUT_OF_MEMORY, "out of memory") ; - } - return (p) ; -} - diff --git a/CHOLMOD/Utility/t_cholmod_realloc_multiple.c b/CHOLMOD/Utility/t_cholmod_realloc_multiple.c deleted file mode 100644 index 49f84710d4..0000000000 --- a/CHOLMOD/Utility/t_cholmod_realloc_multiple.c +++ /dev/null @@ -1,130 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/t_cholmod_realloc_multiple: multiple realloc (int64/int32) -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -#include "cholmod_internal.h" - -int CHOLMOD(realloc_multiple) // returns true if successful, false otherwise -( - size_t nnew, // # of items in newly reallocate memory - int nint, // 0: do not allocate I or J, 1: just I, 2: both I and J - int xdtype, // xtype + dtype of the matrix: - // (CHOLMOD_DOUBLE, _SINGLE) + - // (CHOLMOD_PATTERN, _REAL, _COMPLEX, or _ZOMPLEX) - // input/output: - void **I, // integer block of memory (int32_t or int64_t) - void **J, // integer block of memory (int32_t or int64_t) - void **X, // real or complex, double or single, block - void **Z, // zomplex only: double or single block - size_t *n, // current size of I, J, X, and/or Z blocks on input, - // changed to nnew on output, if successful - cholmod_common *Common -) -{ - - //-------------------------------------------------------------------------- - // check inputs - //-------------------------------------------------------------------------- - - RETURN_IF_NULL_COMMON (FALSE) ; - - //-------------------------------------------------------------------------- - // get the xtype and dtype - //-------------------------------------------------------------------------- - - int xtype = xdtype & 3 ; // pattern, real, complex, or zomplex - int dtype = xdtype & 4 ; // double or single - - if (nint < 1 && xtype == CHOLMOD_PATTERN) - { - return (TRUE) ; // nothing to reallocate - } - - //-------------------------------------------------------------------------- - // get the problem size - //-------------------------------------------------------------------------- - - size_t ni = (*n) ; // size of I, if present - size_t nj = (*n) ; // size of J, if present - size_t nx = (*n) ; // size of X, if present - size_t nz = (*n) ; // size of Z, if present - - size_t ei = sizeof (Int) ; - size_t e = (dtype == CHOLMOD_SINGLE) ? sizeof (float) : sizeof (double) ; - size_t ex = e * ((xtype == CHOLMOD_PATTERN) ? 0 : - ((xtype == CHOLMOD_COMPLEX) ? 2 : 1)) ; - size_t ez = e * ((xtype == CHOLMOD_ZOMPLEX) ? 1 : 0) ; - - if ((nint > 0 && I == NULL) || - (nint > 1 && J == NULL) || - (ex > 0 && X == NULL) || - (ez > 0 && Z == NULL)) - { - if (Common->status != CHOLMOD_OUT_OF_MEMORY) - { - ERROR (CHOLMOD_INVALID, "argument missing") ; - } - return (FALSE) ; - } - - //-------------------------------------------------------------------------- - // reallocate all of the blocks - //-------------------------------------------------------------------------- - - if (nint > 0) (*I) = CHOLMOD(realloc) (nnew, ei, *I, &ni, Common) ; - if (nint > 1) (*J) = CHOLMOD(realloc) (nnew, ei, *J, &nj, Common) ; - if (ex > 0) (*X) = CHOLMOD(realloc) (nnew, ex, *X, &nx, Common) ; - if (ez > 0) (*Z) = CHOLMOD(realloc) (nnew, ez, *Z, &nz, Common) ; - - //-------------------------------------------------------------------------- - // handle any errors - //-------------------------------------------------------------------------- - - if (Common->status < CHOLMOD_OK) - { - if ((*n) == 0) - { - // free all blocks if they were just freshly allocated - if (nint > 0) (*I) = CHOLMOD(free) (ni, ei, *I, Common) ; - if (nint > 1) (*J) = CHOLMOD(free) (nj, ei, *J, Common) ; - if (ex > 0) (*X) = CHOLMOD(free) (nx, ex, *X, Common) ; - if (ez > 0) (*Z) = CHOLMOD(free) (nz, ez, *Z, Common) ; - } - else - { - // resize all blocks to their original size - if (nint > 0) (*I) = CHOLMOD(realloc) ((*n), ei, *I, &ni, Common) ; - if (nint > 1) (*J) = CHOLMOD(realloc) ((*n), ei, *J, &nj, Common) ; - if (ex > 0) (*X) = CHOLMOD(realloc) ((*n), ex, *X, &nx, Common) ; - if (ez > 0) (*Z) = CHOLMOD(realloc) ((*n), ez, *Z, &nz, Common) ; - } - return (FALSE) ; - } - - //-------------------------------------------------------------------------- - // clear the first entry of X and Z - //-------------------------------------------------------------------------- - - if ((*n) == 0) - { - // X and Z have been freshly allocated. Set their first entry to zero, - // so that valgrind doesn't complain about accessing uninitialized - // space in cholmod_*_xtype. - if (*X != NULL && ex > 0) memset (*X, 0, ex) ; - if (*Z != NULL && ez > 0) memset (*Z, 0, ez) ; - } - - //-------------------------------------------------------------------------- - // log the new size and return result - //-------------------------------------------------------------------------- - - (*n) = nnew ; - return (TRUE) ; -} - diff --git a/CHOLMOD/Utility/t_cholmod_reallocate_column.c b/CHOLMOD/Utility/t_cholmod_reallocate_column.c deleted file mode 100644 index fcbba8cee3..0000000000 --- a/CHOLMOD/Utility/t_cholmod_reallocate_column.c +++ /dev/null @@ -1,207 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/t_cholmod_reallocate_column: reallocate a column of a factor -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -// Expand the space for a single column L(:,j) of a simplicial factor. - -#include "cholmod_internal.h" - -#define RETURN_IF_ERROR \ - if (Common->status != CHOLMOD_OK) \ - { \ - /* out of memory; change L to simplicial symbolic */ \ - CHOLMOD(change_factor) (CHOLMOD_PATTERN + L->dtype, L->is_ll, \ - /* make L simplicial: */ FALSE, \ - /* make L packed */ TRUE, \ - /* make L monotonic: */ TRUE, L, Common) ; \ - ERROR (CHOLMOD_OUT_OF_MEMORY, "out of memory") ; \ - return (FALSE) ; \ - } - -//------------------------------------------------------------------------------ -// t_cholmod_reallocate_column_worker template -//------------------------------------------------------------------------------ - -#define DOUBLE -#define REAL -#include "t_cholmod_reallocate_column_worker.c" -#define COMPLEX -#include "t_cholmod_reallocate_column_worker.c" -#define ZOMPLEX -#include "t_cholmod_reallocate_column_worker.c" - -#undef DOUBLE -#define SINGLE -#define REAL -#include "t_cholmod_reallocate_column_worker.c" -#define COMPLEX -#include "t_cholmod_reallocate_column_worker.c" -#define ZOMPLEX -#include "t_cholmod_reallocate_column_worker.c" - -//------------------------------------------------------------------------------ -// cholmod_reallocate_column -//------------------------------------------------------------------------------ - -int CHOLMOD(reallocate_column) -( - size_t j, // reallocate L(:,j) - size_t need, // space in L(:,j) for this # of entries - cholmod_factor *L, // L factor modified, L(:,j) resized - cholmod_common *Common -) -{ - - //-------------------------------------------------------------------------- - // check inputs - //-------------------------------------------------------------------------- - - RETURN_IF_NULL_COMMON (FALSE) ; - RETURN_IF_FACTOR_INVALID (L, FALSE) ; - Common->status = CHOLMOD_OK ; - - DEBUG (CHOLMOD(dump_factor) (L, "realloc col:L input", Common)) ; - - Int n = L->n ; - if (L->xtype == CHOLMOD_PATTERN || L->is_super || j >= n) - { - ERROR (CHOLMOD_INVALID, "L not simplicial or j out of range") ; - return (FALSE) ; - } - - //-------------------------------------------------------------------------- - // ensure need is in range 1:(n-j) and add slack space - //-------------------------------------------------------------------------- - - need = MAX (need, 1) ; - double slack = MAX (Common->grow1, 1.0) * ((double) need) + Common->grow2 ; - slack = MIN (slack, (double) (n-j)) ; - size_t nslack = (size_t) floor (slack) ; - need = MAX (need, slack) ; - need = MAX (need, 1) ; - need = MIN (need, n-j) ; - - //-------------------------------------------------------------------------- - // quick return if L(:,j) already big enough - //-------------------------------------------------------------------------- - - Int *Lp = (Int *) L->p ; - Int *Lnext = (Int *) L->next ; - Int *Lprev = (Int *) L->prev ; - - size_t already_have = ((size_t) Lp [Lnext [j]] - (size_t) Lp [j]) ; - if (already_have >= need) - { - return (TRUE) ; - } - - //-------------------------------------------------------------------------- - // check if enough space at the end of L->i, L->x, and L->z - //-------------------------------------------------------------------------- - - Int tail = n ; - Int new_nzmax_required = need + Lp [tail] ; - if (new_nzmax_required > L->nzmax) - { - - //---------------------------------------------------------------------- - // out of space in L, so grow the entire factor to lnznew space - //---------------------------------------------------------------------- - - double grow0 = Common->grow0 ; - grow0 = (isnan (grow0) || grow0 < 1.2) ? 1.2 : grow0 ; - double xnz = grow0 * (((double) L->nzmax) + ((double) need) + 1) ; - size_t lnznew = (xnz > (double) SIZE_MAX) ? SIZE_MAX : (size_t) xnz ; - - CHOLMOD(reallocate_factor) (lnznew, L, Common) ; - RETURN_IF_ERROR ; - - //---------------------------------------------------------------------- - // count # of times any factor has been reallocated - //---------------------------------------------------------------------- - - Common->nrealloc_factor++ ; - - //---------------------------------------------------------------------- - // repack all columns so each column has some slack spce - //---------------------------------------------------------------------- - - CHOLMOD(pack_factor) (L, Common) ; - RETURN_IF_ERROR ; - } - - //-------------------------------------------------------------------------- - // move j to the end of the list - //-------------------------------------------------------------------------- - - L->is_monotonic = FALSE ; // L is no longer monotonic - Lnext [Lprev [j]] = Lnext [j] ; // remove j from is current place - Lprev [Lnext [j]] = Lprev [j] ; - Lnext [Lprev [tail]] = j ; // place it at the end of the list - Lprev [j] = Lprev [tail] ; - Lnext [j] = tail ; - Lprev [tail] = j ; - - //-------------------------------------------------------------------------- - // add space to L(:,j), now at the end of L - //-------------------------------------------------------------------------- - - Int psrc = Lp [j] ; - Int pdest = Lp [tail] ; - Lp [j] = pdest ; - Lp [tail] += need ; - - //-------------------------------------------------------------------------- - // move L(:,j) to its new space at the end of L - //-------------------------------------------------------------------------- - - switch ((L->xtype + L->dtype) % 8) - { - default: - break ; - - case CHOLMOD_SINGLE + CHOLMOD_REAL: - r_s_cholmod_reallocate_column_worker (L, j, pdest, psrc) ; - break ; - - case CHOLMOD_SINGLE + CHOLMOD_COMPLEX: - c_s_cholmod_reallocate_column_worker (L, j, pdest, psrc) ; - break ; - - case CHOLMOD_SINGLE + CHOLMOD_ZOMPLEX: - z_s_cholmod_reallocate_column_worker (L, j, pdest, psrc) ; - break ; - - case CHOLMOD_DOUBLE + CHOLMOD_REAL: - r_cholmod_reallocate_column_worker (L, j, pdest, psrc) ; - break ; - - case CHOLMOD_DOUBLE + CHOLMOD_COMPLEX: - c_cholmod_reallocate_column_worker (L, j, pdest, psrc) ; - break ; - - case CHOLMOD_DOUBLE + CHOLMOD_ZOMPLEX: - z_cholmod_reallocate_column_worker (L, j, pdest, psrc) ; - break ; - } - - //-------------------------------------------------------------------------- - // count # of times any L(:,j) has been reallocated - //-------------------------------------------------------------------------- - - Common->nrealloc_col++ ; - - //-------------------------------------------------------------------------- - // return result - //-------------------------------------------------------------------------- - - DEBUG (CHOLMOD(dump_factor) (L, "realloc col:L output", Common)) ; - return (TRUE) ; -} - diff --git a/CHOLMOD/Utility/t_cholmod_reallocate_column_worker.c b/CHOLMOD/Utility/t_cholmod_reallocate_column_worker.c deleted file mode 100644 index b6c5298ab7..0000000000 --- a/CHOLMOD/Utility/t_cholmod_reallocate_column_worker.c +++ /dev/null @@ -1,48 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/t_cholmod_reallocate_column_worker -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -#include "cholmod_template.h" - -static void TEMPLATE (cholmod_reallocate_column_worker) -( - cholmod_factor *L, // L factor modified, L(:,j) resized - Int j, // column L(:,j) to move - Int pdest, // place to move it to - Int psrc // place to move it from -) -{ - - //-------------------------------------------------------------------------- - // get inputs - //-------------------------------------------------------------------------- - - Int *Lnz = (Int *) L->nz ; - Int *Li = (Int *) L->i ; - Real *Lx = (Real *) L->x ; - Real *Lz = (Real *) L->z ; - Int len = Lnz [j] ; - - //-------------------------------------------------------------------------- - // move L(:,j) to its new position - //-------------------------------------------------------------------------- - - for (Int k = 0 ; k < len ; k++, pdest++, psrc++) - { - // move L(i,j) from position psrc to position pdest - Li [pdest] = Li [psrc] ; - ASSIGN (Lx, Lz, pdest, Lx, Lz, psrc) ; - } -} - -#undef PATTERN -#undef REAL -#undef COMPLEX -#undef ZOMPLEX - diff --git a/CHOLMOD/Utility/t_cholmod_reallocate_factor.c b/CHOLMOD/Utility/t_cholmod_reallocate_factor.c deleted file mode 100644 index aa1ffd4583..0000000000 --- a/CHOLMOD/Utility/t_cholmod_reallocate_factor.c +++ /dev/null @@ -1,55 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/t_cholmod_reallocate_factor: reallocate a factor -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -// Change the max # of nonzeros that can be held in a factor L. -// The factor must be simplicial. - -#include "cholmod_internal.h" - -int CHOLMOD(reallocate_factor) -( - size_t nznew, // new max # of nonzeros the factor matrix can hold - cholmod_factor *L, // factor to reallocate - cholmod_common *Common -) -{ - - //-------------------------------------------------------------------------- - // check inputs - //-------------------------------------------------------------------------- - - RETURN_IF_NULL_COMMON (FALSE) ; - RETURN_IF_NULL (L, FALSE) ; - RETURN_IF_XTYPE_IS_INVALID (L->xtype, CHOLMOD_PATTERN, CHOLMOD_ZOMPLEX, - FALSE) ; - if (L->is_super) - { - ERROR (CHOLMOD_INVALID, "L invalid") ; - return (FALSE) ; - } - Common->status = CHOLMOD_OK ; - - //-------------------------------------------------------------------------- - // reallocate the sparse matrix - //-------------------------------------------------------------------------- - - nznew = MAX (1, nznew) ; // ensure L can hold at least 1 entry - int nint = 1 ; // reallocate just L->i - - CHOLMOD(realloc_multiple) (nznew, nint, L->xtype + L->dtype, - &(L->i), NULL, &(L->x), &(L->z), &(L->nzmax), Common) ; - - //-------------------------------------------------------------------------- - // return result - //-------------------------------------------------------------------------- - - return (Common->status == CHOLMOD_OK) ; -} - diff --git a/CHOLMOD/Utility/t_cholmod_reallocate_sparse.c b/CHOLMOD/Utility/t_cholmod_reallocate_sparse.c deleted file mode 100644 index df74814515..0000000000 --- a/CHOLMOD/Utility/t_cholmod_reallocate_sparse.c +++ /dev/null @@ -1,48 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/t_cholmod_reallocate_sparse: reallocate sparse matrix -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -// Change the max # of nonzeros that can be held in a sparse matrix A. - -#include "cholmod_internal.h" - -int CHOLMOD(reallocate_sparse) -( - size_t nznew, // new max # of nonzeros the sparse matrix can hold - cholmod_sparse *A, // sparse matrix to reallocate - cholmod_common *Common -) -{ - - //-------------------------------------------------------------------------- - // check inputs - //-------------------------------------------------------------------------- - - RETURN_IF_NULL_COMMON (FALSE) ; - RETURN_IF_NULL (A, FALSE) ; - RETURN_IF_XTYPE_IS_INVALID (A->xtype, CHOLMOD_PATTERN, CHOLMOD_ZOMPLEX, - FALSE) ; - Common->status = CHOLMOD_OK ; - - //-------------------------------------------------------------------------- - // reallocate the sparse matrix - //-------------------------------------------------------------------------- - - nznew = MAX (1, nznew) ; // ensure A can hold at least 1 entry - int nint = 1 ; // reallocate just A->i - CHOLMOD(realloc_multiple) (nznew, nint, A->xtype + A->dtype, - &(A->i), NULL, &(A->x), &(A->z), &(A->nzmax), Common) ; - - //-------------------------------------------------------------------------- - // return result - //-------------------------------------------------------------------------- - - return (Common->status == CHOLMOD_OK) ; -} - diff --git a/CHOLMOD/Utility/t_cholmod_reallocate_triplet.c b/CHOLMOD/Utility/t_cholmod_reallocate_triplet.c deleted file mode 100644 index 5ffff9edf5..0000000000 --- a/CHOLMOD/Utility/t_cholmod_reallocate_triplet.c +++ /dev/null @@ -1,48 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/t_cholmod_reallocate_triplet: reallocate triplet matrix -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -// Change the max # of nonzeros that can be held in a triplet matrix T. - -#include "cholmod_internal.h" - -int CHOLMOD(reallocate_triplet) -( - size_t nznew, // new max # of nonzeros the triplet matrix can hold - cholmod_triplet *T, // triplet matrix to reallocate - cholmod_common *Common -) -{ - - //-------------------------------------------------------------------------- - // check inputs - //-------------------------------------------------------------------------- - - RETURN_IF_NULL_COMMON (FALSE) ; - RETURN_IF_NULL (T, FALSE) ; - RETURN_IF_XTYPE_IS_INVALID (T->xtype, CHOLMOD_PATTERN, CHOLMOD_ZOMPLEX, - FALSE) ; - Common->status = CHOLMOD_OK ; - - //-------------------------------------------------------------------------- - // reallocate the triplet matrix - //-------------------------------------------------------------------------- - - nznew = MAX (1, nznew) ; // ensure T can hold at least 1 entry - int nint = 2 ; // reallocate both T->i and T->j - CHOLMOD(realloc_multiple) (nznew, nint, T->xtype + T->dtype, - &(T->i), &(T->j), &(T->x), &(T->z), &(T->nzmax), Common) ; - - //-------------------------------------------------------------------------- - // return result - //-------------------------------------------------------------------------- - - return (Common->status == CHOLMOD_OK) ; -} - diff --git a/CHOLMOD/Utility/t_cholmod_score_comp.c b/CHOLMOD/Utility/t_cholmod_score_comp.c deleted file mode 100644 index 8f2aaa8758..0000000000 --- a/CHOLMOD/Utility/t_cholmod_score_comp.c +++ /dev/null @@ -1,21 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/t_cholmod_score_comp: for sorting supernodes -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -#include "cholmod_internal.h" - -int CHOLMOD(score_comp) -( - struct cholmod_descendant_score_t *i, - struct cholmod_descendant_score_t *j -) -{ - return ((i->score < j->score) ? 1 : -1) ; -} - diff --git a/CHOLMOD/Utility/t_cholmod_set_empty.c b/CHOLMOD/Utility/t_cholmod_set_empty.c deleted file mode 100644 index f757f8fc74..0000000000 --- a/CHOLMOD/Utility/t_cholmod_set_empty.c +++ /dev/null @@ -1,24 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/t_cholmod_set_empty: set an Int array to EMPTY -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -#include "cholmod_internal.h" - -void CHOLMOD(set_empty) -( - Int *S, // Int array of size n - size_t n -) -{ - for (size_t k = 0 ; k < n ; k++) - { - S [k] = EMPTY ; - } -} - diff --git a/CHOLMOD/Utility/t_cholmod_sort.c b/CHOLMOD/Utility/t_cholmod_sort.c deleted file mode 100644 index 9fe34a914d..0000000000 --- a/CHOLMOD/Utility/t_cholmod_sort.c +++ /dev/null @@ -1,132 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/t_cholmod_sort: sort a sparse matrix -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -// Sorts the entries in each column of a sparse matrix. - -#include "cholmod_internal.h" - -//------------------------------------------------------------------------------ -// random number generator for cm_qsort -//------------------------------------------------------------------------------ - -// return a random uint64_t, in range 0 to 2^60 -#define CM_RAND_MAX 32767 - -// return a random number between 0 and CM_RAND_MAX -static inline uint64_t cm_rand15 (uint64_t *seed) -{ - (*seed) = (*seed) * 1103515245 + 12345 ; - return (((*seed) / 65536) % (CM_RAND_MAX + 1)) ; -} - -// return a random uint64_t, in range 0 to 2^60 -static inline uint64_t cm_rand (uint64_t *seed) -{ - uint64_t i = cm_rand15 (seed) ; - i = CM_RAND_MAX * i + cm_rand15 (seed) ; - i = CM_RAND_MAX * i + cm_rand15 (seed) ; - i = CM_RAND_MAX * i + cm_rand15 (seed) ; - return (i) ; -} - -// swap two entries A [a] and A [b] -#define SWAP(type,A,a,b) \ -{ \ - type t = A [a] ; \ - A [a] = A [b] ; \ - A [b] = t ; \ -} - -//------------------------------------------------------------------------------ -// t_cholmod_sort_worker template -//------------------------------------------------------------------------------ - -#define PATTERN -#include "t_cholmod_sort_worker.c" - -#define DOUBLE -#define REAL -#include "t_cholmod_sort_worker.c" -#define COMPLEX -#include "t_cholmod_sort_worker.c" -#define ZOMPLEX -#include "t_cholmod_sort_worker.c" - -#undef DOUBLE -#define SINGLE -#define REAL -#include "t_cholmod_sort_worker.c" -#define COMPLEX -#include "t_cholmod_sort_worker.c" -#define ZOMPLEX -#include "t_cholmod_sort_worker.c" - -//------------------------------------------------------------------------------ -// cholmod_sort -//------------------------------------------------------------------------------ - -int CHOLMOD(sort) -( - cholmod_sparse *A, // input/output matrix to sort - cholmod_common *Common -) -{ - - //-------------------------------------------------------------------------- - // check inputs - //-------------------------------------------------------------------------- - - RETURN_IF_NULL_COMMON (FALSE) ; - RETURN_IF_SPARSE_MATRIX_INVALID (A, FALSE) ; - ASSERT (CHOLMOD(dump_sparse) (A, "sort:A input", Common) >= 0) ; - - //-------------------------------------------------------------------------- - // sort each column of A - //-------------------------------------------------------------------------- - - switch ((A->xtype + A->dtype) % 8) - { - default: - p_cholmod_sort_worker (A) ; - break ; - - case CHOLMOD_SINGLE + CHOLMOD_REAL: - r_s_cholmod_sort_worker (A) ; - break ; - - case CHOLMOD_SINGLE + CHOLMOD_COMPLEX: - c_s_cholmod_sort_worker (A) ; - break ; - - case CHOLMOD_SINGLE + CHOLMOD_ZOMPLEX: - z_s_cholmod_sort_worker (A) ; - break ; - - case CHOLMOD_DOUBLE + CHOLMOD_REAL: - r_cholmod_sort_worker (A) ; - break ; - - case CHOLMOD_DOUBLE + CHOLMOD_COMPLEX: - c_cholmod_sort_worker (A) ; - break ; - - case CHOLMOD_DOUBLE + CHOLMOD_ZOMPLEX: - z_cholmod_sort_worker (A) ; - break ; - } - - //-------------------------------------------------------------------------- - // return result - //-------------------------------------------------------------------------- - - ASSERT (CHOLMOD(dump_sparse) (A, "sort:A output", Common) >= 0) ; - return (TRUE) ; -} - diff --git a/CHOLMOD/Utility/t_cholmod_sort_worker.c b/CHOLMOD/Utility/t_cholmod_sort_worker.c deleted file mode 100644 index add2200a7b..0000000000 --- a/CHOLMOD/Utility/t_cholmod_sort_worker.c +++ /dev/null @@ -1,229 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/t_cholmod_sort_worker: sort all columns of a sparse matrix -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -#include "cholmod_template.h" - -//------------------------------------------------------------------------------ -// variants for each xtype: pattern, real, complex, and zomplex -//------------------------------------------------------------------------------ - -#if defined ( PATTERN ) - - #define CM_PART(Ai,Ax,Az,n,seed) TEMPLATE(cm_part) (Ai, n, seed) - #define CM_QSRT(Ai,Ax,Az,p,n,seed) TEMPLATE(cm_qsrt) (Ai+p, n, seed) - #define CM_SWAP(a,b) \ - { \ - SWAP (Int, Ai, a, b) ; \ - } - -#elif defined ( REAL ) - - #define CM_PART(Ai,Ax,Az,n,seed) TEMPLATE(cm_part) (Ai, Ax, n, seed) - #define CM_QSRT(Ai,Ax,Az,p,n,seed) TEMPLATE(cm_qsrt) (Ai+p, Ax+p, n, seed) - #define CM_SWAP(a,b) \ - { \ - SWAP (Int, Ai, a, b) ; \ - SWAP (Real, Ax, a, b) ; \ - } - -#elif defined ( COMPLEX ) - - #define CM_PART(Ai,Ax,Az,n,seed) TEMPLATE(cm_part) (Ai, Ax, n, seed) - #define CM_QSRT(Ai,Ax,Az,p,n,seed) TEMPLATE(cm_qsrt) (Ai+p,Ax+2*p,n,seed) - #define CM_SWAP(a,b) \ - { \ - SWAP (Int, Ai, a, b) ; \ - SWAP (Real, Ax, 2*(a), 2*(b)) ; \ - SWAP (Real, Ax, 2*(a)+1, 2*(b)+1) ; \ - } - -#else - - #define CM_PART(Ai,Ax,Az,n,seed) TEMPLATE(cm_part) (Ai, Ax, Az, n, seed) - #define CM_QSRT(Ai,Ax,Az,p,n,seed) TEMPLATE(cm_qsrt) (Ai+p,Ax+p,Az+p,n,seed) - #define CM_SWAP(a,b) \ - { \ - SWAP (Int, Ai, a, b) ; \ - SWAP (Real, Ax, a, b) ; \ - SWAP (Real, Az, a, b) ; \ - } - -#endif - -//------------------------------------------------------------------------------ -// cm_part: use a pivot to partition an array -//------------------------------------------------------------------------------ - -// C.A.R Hoare partition method, partitions an array in-place via a pivot. -// k = partition (A, n) partitions A [0:n-1] such that all entries in -// A [0:k] are <= all entries in A [k+1:n-1]. - -// Ai [0:n-1] is the sort key, and Ax,Az [0:n-1] are satelite data. - - -static inline Int TEMPLATE (cm_part) -( - Int *Ai, // Ai [0..n-1]: indices to sort - #if !defined ( PATTERN ) - Real *Ax, // Ax [0..n-1]: values of A(:,j) - #endif - #if defined ( ZOMPLEX ) - Real *Az, // Az [0..n-1] - #endif - const Int n, // length of Ai, Ax, Az - uint64_t *seed // random number seed, modified on output -) -{ - - // select a pivot at random - Int p = ((n < CM_RAND_MAX) ? cm_rand15 (seed) : cm_rand (seed)) % n ; - - // get the pivot value - Int pivot = Ai [p] ; - - // At the top of the while loop, A [left+1...right-1] is considered, and - // entries outside this range are in their proper place and not touched. - // Since the input specification of this function is to partition A - // [0..n-1], left must start at -1 and right must start at n. - Int left = -1 ; - Int right = n ; - - // keep partitioning until the left and right sides meet - while (true) - { - // loop invariant: A [0..left] < pivot and A [right..n-1] > pivot, - // so the region to be considered is A [left+1 ... right-1]. - - // increment left until finding an entry A [left] >= pivot - do { left++ ; } while (Ai [left] < pivot) ; - - // decrement right until finding an entry A [right] <= pivot - do { right-- ; } while (pivot < Ai [right]) ; - - // now A [0..left-1] < pivot and A [right+1..n-1] > pivot, but - // A [left] > pivot and A [right] < pivot, so these two entries - // are out of place and must be swapped. - - // However, if the two sides have met, the partition is finished. - if (left >= right) - { - // A has been partitioned into A [0:right] and A [right+1:n-1]. - // k = right+1, so A is split into A [0:k-1] and A [k:n-1]. - return (right + 1) ; - } - - // since A [left] > pivot and A [right] < pivot, swap them - CM_SWAP (left, right) ; - - // after the swap this condition holds: - // A [0..left] < pivot and A [right..n-1] > pivot - } -} - -//------------------------------------------------------------------------------ -// cm_qsrt: recursive single-threaded quicksort -//------------------------------------------------------------------------------ - -static void TEMPLATE (cm_qsrt) // sort A [0:n-1] -( - Int *Ai, // Ai [0..n-1]: indices to sort - #if !defined ( PATTERN ) - Real *Ax, // Ax [0..n-1]: values of A(:,j) - #endif - #if defined ( ZOMPLEX ) - Real *Az, // Az [0..n-1] - #endif - const Int n, // length of Ai, Ax, Az - uint64_t *seed // random number seed -) -{ - - if (n < 20) - { - // in-place insertion sort on A [0:n-1], where n is small - for (Int k = 1 ; k < n ; k++) - { - for (Int j = k ; j > 0 && Ai [j] < Ai [j-1] ; j--) - { - // swap A [j-1] and A [j] - CM_SWAP (j-1, j) ; - } - } - } - else - { - // partition A [0:n-1] into A [0:k-1] and A [k:n-1] - Int k = CM_PART (Ai, Ax, Az, n, seed) ; - - // sort each partition - CM_QSRT (Ai, Ax, Ax, 0, k, seed) ; // sort A [0:k-1] - CM_QSRT (Ai, Ax, Az, k, n-k, seed) ; // sort A [k+1:n-1] - } -} - -//------------------------------------------------------------------------------ -// t_cholmod_sort_worker -//------------------------------------------------------------------------------ - -static void TEMPLATE (cholmod_sort_worker) -( - cholmod_sparse *A // matrix to sort in-place -) -{ - - //-------------------------------------------------------------------------- - // get inputs - //-------------------------------------------------------------------------- - - Int *Ap = (Int *) A->p ; - Int *Ai = (Int *) A->i ; - Int *Anz = (Int *) A->nz ; - Real *Ax = (Real *) A->x ; - Real *Az = (Real *) A->z ; - Int ncol = A->ncol ; - bool packed = A->packed ; - uint64_t seed = 42 ; - - for (Int j = 0 ; j < ncol ; j++) - { - - //---------------------------------------------------------------------- - // sort A(:,j) according to its row indices - //---------------------------------------------------------------------- - - Int pa = Ap [j] ; - Int pend = (packed) ? (Ap [j+1]) : (pa + Anz [j]) ; - Int ilast = EMPTY ; - for (Int p = pa ; p < pend ; p++) - { - Int i = Ai [p] ; - if (i < ilast) - { - // sort Ai, Ax, Ax [pa:pend-1] according to row index Ai - Int jnz = pend - pa ; - CM_QSRT (Ai, Ax, Az, pa, pend - pa, &seed) ; - break ; - } - ilast = i ; - } - } - - A->sorted = TRUE ; -} - -#undef PATTERN -#undef REAL -#undef COMPLEX -#undef ZOMPLEX - -#undef CM_SWAP -#undef CM_PART -#undef CM_QSRT - diff --git a/CHOLMOD/Utility/t_cholmod_sparse_to_dense.c b/CHOLMOD/Utility/t_cholmod_sparse_to_dense.c deleted file mode 100644 index 5f05bc88b5..0000000000 --- a/CHOLMOD/Utility/t_cholmod_sparse_to_dense.c +++ /dev/null @@ -1,125 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/t_cholmod_sparse_to_dense: convert a sparse matrix to dense -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -// Converts a sparse matrix (as input) to a new dense matrix (as output). -// The xtype and dtype are preserved, except if A->xtype is pattern. In that -// case, the output matrix X has an xtype of real, and consists of 1's and 0's. - -#include "cholmod_internal.h" - -#define RETURN_IF_ERROR \ - if (Common->status < CHOLMOD_OK) \ - { \ - CHOLMOD(free_dense) (&X, Common) ; \ - return (NULL) ; \ - } - -//------------------------------------------------------------------------------ -// t_cholmod_sparse_to_dense_worker template -//------------------------------------------------------------------------------ - -#define DOUBLE -#define PATTERN -#include "t_cholmod_sparse_to_dense_worker.c" -#define REAL -#include "t_cholmod_sparse_to_dense_worker.c" -#define COMPLEX -#include "t_cholmod_sparse_to_dense_worker.c" -#define ZOMPLEX -#include "t_cholmod_sparse_to_dense_worker.c" - -#undef DOUBLE -#define SINGLE -#define PATTERN -#include "t_cholmod_sparse_to_dense_worker.c" -#define REAL -#include "t_cholmod_sparse_to_dense_worker.c" -#define COMPLEX -#include "t_cholmod_sparse_to_dense_worker.c" -#define ZOMPLEX -#include "t_cholmod_sparse_to_dense_worker.c" - -//------------------------------------------------------------------------------ -// cholmod_sparse_to_dense -//------------------------------------------------------------------------------ - -cholmod_dense *CHOLMOD(sparse_to_dense) // return a dense matrix -( - cholmod_sparse *A, // input matrix - cholmod_common *Common -) -{ - - //-------------------------------------------------------------------------- - // check inputs - //-------------------------------------------------------------------------- - - RETURN_IF_NULL_COMMON (NULL) ; - RETURN_IF_SPARSE_MATRIX_INVALID (A, NULL) ; - Common->status = CHOLMOD_OK ; - ASSERT (CHOLMOD(dump_sparse) (A, "sparse_to_dense:A", Common) >= 0) ; - - //-------------------------------------------------------------------------- - // allocate an all-zero dense matrix - //-------------------------------------------------------------------------- - - int xxtype = (A->xtype == CHOLMOD_PATTERN)? CHOLMOD_REAL : A->xtype ; - cholmod_dense *X = CHOLMOD(zeros) (A->nrow, A->ncol, xxtype + A->dtype, - Common) ; - RETURN_IF_ERROR ; - - //-------------------------------------------------------------------------- - // copy A into X - //-------------------------------------------------------------------------- - - switch ((A->xtype + A->dtype) % 8) - { - - case CHOLMOD_SINGLE + CHOLMOD_PATTERN: - p_s_cholmod_sparse_to_dense_worker (X, A) ; - break ; - - case CHOLMOD_SINGLE + CHOLMOD_REAL: - r_s_cholmod_sparse_to_dense_worker (X, A) ; - break ; - - case CHOLMOD_SINGLE + CHOLMOD_COMPLEX: - c_s_cholmod_sparse_to_dense_worker (X, A) ; - break ; - - case CHOLMOD_SINGLE + CHOLMOD_ZOMPLEX: - z_s_cholmod_sparse_to_dense_worker (X, A) ; - break ; - - case CHOLMOD_DOUBLE + CHOLMOD_PATTERN: - p_cholmod_sparse_to_dense_worker (X, A) ; - break ; - - case CHOLMOD_DOUBLE + CHOLMOD_REAL: - r_cholmod_sparse_to_dense_worker (X, A) ; - break ; - - case CHOLMOD_DOUBLE + CHOLMOD_COMPLEX: - c_cholmod_sparse_to_dense_worker (X, A) ; - break ; - - case CHOLMOD_DOUBLE + CHOLMOD_ZOMPLEX: - z_cholmod_sparse_to_dense_worker (X, A) ; - break ; - } - - //-------------------------------------------------------------------------- - // return result - //-------------------------------------------------------------------------- - - ASSERT (CHOLMOD(dump_dense) (X, "sparse_to_dense:X", Common) >= 0) ; - return (X) ; -} - diff --git a/CHOLMOD/Utility/t_cholmod_sparse_to_dense_worker.c b/CHOLMOD/Utility/t_cholmod_sparse_to_dense_worker.c deleted file mode 100644 index c0e6fc39ba..0000000000 --- a/CHOLMOD/Utility/t_cholmod_sparse_to_dense_worker.c +++ /dev/null @@ -1,124 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/t_cholmod_sparse_to_dense_worker: sparse to dense matrix -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -#include "cholmod_template.h" - -static void TEMPLATE (cholmod_sparse_to_dense_worker) -( - cholmod_dense *X, // output dense matrix, already allocated - cholmod_sparse *A // input sparse matrix -) -{ - - //-------------------------------------------------------------------------- - // check inputs - //-------------------------------------------------------------------------- - - ASSERT (X->d == X->nrow) ; - ASSERT (X->nrow == A->nrow) ; - ASSERT (X->ncol == A->ncol) ; - - //-------------------------------------------------------------------------- - // get inputs - //-------------------------------------------------------------------------- - - Real *Xx = (Real *) X->x ; - Real *Xz = (Real *) X->z ; - - Int *Ap = (Int *) A->p ; - Int *Ai = (Int *) A->i ; - Int *Anz = (Int *) A->nz ; - Real *Ax = (Real *) A->x ; - Real *Az = (Real *) A->z ; - - Int nrow = (Int) A->nrow ; - Int ncol = (Int) A->ncol ; - bool packed = (bool) A->packed ; - bool upper = (A->stype > 0) ; - bool lower = (A->stype < 0) ; - - //-------------------------------------------------------------------------- - // copy a sparse matrix A into a dense matrix X - //-------------------------------------------------------------------------- - - for (Int j = 0, jx = 0 ; j < ncol ; j++, jx += nrow) - { - - //---------------------------------------------------------------------- - // copy A(:,j) into X(:,j) - //---------------------------------------------------------------------- - - Int p = Ap [j] ; - Int pend = (packed) ? (Ap [j+1]) : (p + Anz [j]) ; - for ( ; p < pend ; p++) - { - - //------------------------------------------------------------------ - // get A(i,j) - //------------------------------------------------------------------ - - Int i = Ai [p] ; - Int q = i + jx ; - - if (upper) - { - - //-------------------------------------------------------------- - // A is symmetric with upper part stored - //-------------------------------------------------------------- - - if (i > j) continue ; - // X(i,j) = A(i,j) - ASSIGN2 (Xx, Xz, q, Ax, Az, p) ; - if (i < j) - { - // X(j,i) = conj (A(i,j)) - Int s = j + i*nrow ; - ASSIGN2_CONJ (Xx, Xz, s, Ax, Az, p) ; - } - - } - else if (lower) - { - - //-------------------------------------------------------------- - // A is symmetric with lower part stored - //-------------------------------------------------------------- - - if (i < j) continue ; - // X(i,j) = A(i,j) - ASSIGN2 (Xx, Xz, q, Ax, Az, p) ; - if (i > j) - { - // X(j,i) = conj (A(i,j)) - Int s = j + i*nrow ; - ASSIGN2_CONJ (Xx, Xz, s, Ax, Az, p) ; - } - - } - else - { - - //-------------------------------------------------------------- - // A and X are both unsymmetric - //-------------------------------------------------------------- - - // X(i,j) = A(i,j) - ASSIGN2 (Xx, Xz, q, Ax, Az, p) ; - } - } - } -} - -#undef PATTERN -#undef REAL -#undef COMPLEX -#undef ZOMPLEX - diff --git a/CHOLMOD/Utility/t_cholmod_sparse_to_triplet.c b/CHOLMOD/Utility/t_cholmod_sparse_to_triplet.c deleted file mode 100644 index 1ce6dc7d23..0000000000 --- a/CHOLMOD/Utility/t_cholmod_sparse_to_triplet.c +++ /dev/null @@ -1,111 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/t_cholmod_sparse_to_triplet: convert sparse to triplet -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -#include "cholmod_internal.h" - -//------------------------------------------------------------------------------ -// t_cholmod_sparse_to_triplet_worker template -//------------------------------------------------------------------------------ - -#define PATTERN -#include "t_cholmod_sparse_to_triplet_worker.c" - -#define DOUBLE -#define REAL -#include "t_cholmod_sparse_to_triplet_worker.c" -#define COMPLEX -#include "t_cholmod_sparse_to_triplet_worker.c" -#define ZOMPLEX -#include "t_cholmod_sparse_to_triplet_worker.c" - -#undef DOUBLE -#define SINGLE -#define REAL -#include "t_cholmod_sparse_to_triplet_worker.c" -#define COMPLEX -#include "t_cholmod_sparse_to_triplet_worker.c" -#define ZOMPLEX -#include "t_cholmod_sparse_to_triplet_worker.c" - -//------------------------------------------------------------------------------ -// cholmod_sparse_to_triplet: convert sparse matrix to triplet form -//------------------------------------------------------------------------------ - -cholmod_triplet *CHOLMOD(sparse_to_triplet) -( - cholmod_sparse *A, // matrix to copy into triplet form T - cholmod_common *Common -) -{ - - //-------------------------------------------------------------------------- - // check inputs - //-------------------------------------------------------------------------- - - RETURN_IF_NULL_COMMON (NULL) ; - RETURN_IF_SPARSE_MATRIX_INVALID (A, NULL) ; - Common->status = CHOLMOD_OK ; - ASSERT (CHOLMOD(dump_sparse) (A, "sparse_triplet:A", Common) >= 0) ; - - //-------------------------------------------------------------------------- - // allocate triplet matrix - //-------------------------------------------------------------------------- - - size_t nz = (size_t) CHOLMOD(nnz) (A, Common) ; - cholmod_triplet *T = CHOLMOD(allocate_triplet) (A->nrow, A->ncol, nz, - A->stype, A->xtype + A->dtype, Common) ; - if (Common->status < CHOLMOD_OK) - { - return (NULL) ; - } - - //-------------------------------------------------------------------------- - // copy a sparse matrix A to a triplet matrix T - //-------------------------------------------------------------------------- - - switch ((A->xtype + A->dtype) % 8) - { - default: - p_cholmod_sparse_to_triplet_worker (T, A) ; - break ; - - case CHOLMOD_SINGLE + CHOLMOD_REAL: - r_s_cholmod_sparse_to_triplet_worker (T, A) ; - break ; - - case CHOLMOD_SINGLE + CHOLMOD_COMPLEX: - c_s_cholmod_sparse_to_triplet_worker (T, A) ; - break ; - - case CHOLMOD_SINGLE + CHOLMOD_ZOMPLEX: - z_s_cholmod_sparse_to_triplet_worker (T, A) ; - break ; - - case CHOLMOD_DOUBLE + CHOLMOD_REAL: - r_cholmod_sparse_to_triplet_worker (T, A) ; - break ; - - case CHOLMOD_DOUBLE + CHOLMOD_COMPLEX: - c_cholmod_sparse_to_triplet_worker (T, A) ; - break ; - - case CHOLMOD_DOUBLE + CHOLMOD_ZOMPLEX: - z_cholmod_sparse_to_triplet_worker (T, A) ; - break ; - } - - //-------------------------------------------------------------------------- - // return result - //-------------------------------------------------------------------------- - - ASSERT (CHOLMOD(dump_triplet) (T, "sparse_to_triplet:T", Common)) ; - return (T) ; -} - diff --git a/CHOLMOD/Utility/t_cholmod_sparse_to_triplet_worker.c b/CHOLMOD/Utility/t_cholmod_sparse_to_triplet_worker.c deleted file mode 100644 index a68b1faa7e..0000000000 --- a/CHOLMOD/Utility/t_cholmod_sparse_to_triplet_worker.c +++ /dev/null @@ -1,122 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/t_cholmod_sparse_to_triplet_worker -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -#include "cholmod_template.h" - -static void TEMPLATE (cholmod_sparse_to_triplet_worker) -( - cholmod_triplet *T, - cholmod_sparse *A -) -{ - - //-------------------------------------------------------------------------- - // get inputs - //-------------------------------------------------------------------------- - - Int nrow = A->nrow ; - Int ncol = A->ncol ; - bool packed = (bool) A->packed ; - Int *Ap = (Int *) A->p ; - Int *Ai = (Int *) A->i ; - Real *Ax = (Real *) A->x ; - Real *Az = (Real *) A->z ; - Int *Anz = (Int *) A->nz ; - - Int *Ti = (Int *) T->i ; - Int *Tj = (Int *) T->j ; - Real *Tx = (Real *) T->x ; - Real *Tz = (Real *) T->z ; - - Int k = 0 ; - - //-------------------------------------------------------------------------- - // copy entries from A into T - //-------------------------------------------------------------------------- - - #define COPY_ENTRY(entry_test) \ - if (entry_test) \ - { \ - Ti [k] = i ; \ - Tj [k] = j ; \ - /* Tx (k) = Ax (p) */ \ - ASSIGN (Tx, Tz, k, Ax, Az, p) ; \ - k++ ; \ - } - - if (A->stype == 0) - { - - //---------------------------------------------------------------------- - // A is unsymmetric - //---------------------------------------------------------------------- - - for (Int j = 0 ; j < ncol ; j++) - { - Int p = Ap [j] ; - Int pend = (packed) ? (Ap [j+1]) : (p + Anz [j]) ; - for ( ; p < pend ; p++) - { - Int i = Ai [p] ; - COPY_ENTRY (true) ; - } - } - - } - else if (A->stype > 0) - { - - //---------------------------------------------------------------------- - // A is symmetric, with just upper triangular part stored - //---------------------------------------------------------------------- - - for (Int j = 0 ; j < ncol ; j++) - { - Int p = Ap [j] ; - Int pend = (packed) ? (Ap [j+1]) : (p + Anz [j]) ; - for ( ; p < pend ; p++) - { - Int i = Ai [p] ; - COPY_ENTRY (i <= j) ; - } - } - - } - else - { - - //---------------------------------------------------------------------- - // A is symmetric, with just lower triangular part stored - //---------------------------------------------------------------------- - - for (Int j = 0 ; j < ncol ; j++) - { - Int p = Ap [j] ; - Int pend = (packed) ? (Ap [j+1]) : (p + Anz [j]) ; - for ( ; p < pend ; p++) - { - Int i = Ai [p] ; - COPY_ENTRY (i >= j) ; - } - } - } - - //-------------------------------------------------------------------------- - // log the number of entries in T - //-------------------------------------------------------------------------- - - T->nnz = k ; -} - -#undef PATTERN -#undef REAL -#undef COMPLEX -#undef ZOMPLEX - diff --git a/CHOLMOD/Utility/t_cholmod_speye.c b/CHOLMOD/Utility/t_cholmod_speye.c deleted file mode 100644 index 0c08e9a23d..0000000000 --- a/CHOLMOD/Utility/t_cholmod_speye.c +++ /dev/null @@ -1,121 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/t_cholmod_speye: sparse identity matrix -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -// Create a sparse identity matrix, possibly rectangular, of any xtype or -// dtype. The A->stype is zero (unsymmetric) but this can be modified by the -// caller to either +1 or -1, and the matrix will still be valid. - -#include "cholmod_internal.h" - -#define RETURN_IF_ERROR \ - if (Common->status < CHOLMOD_OK) \ - { \ - CHOLMOD(free_sparse) (&A, Common) ; \ - return (NULL) ; \ - } - -//------------------------------------------------------------------------------ -// t_cholmod_speye_worker template -//------------------------------------------------------------------------------ - -#define PATTERN -#include "t_cholmod_speye_worker.c" - -#define DOUBLE -#define REAL -#include "t_cholmod_speye_worker.c" -#define COMPLEX -#include "t_cholmod_speye_worker.c" -#define ZOMPLEX -#include "t_cholmod_speye_worker.c" - -#undef DOUBLE -#define SINGLE -#define REAL -#include "t_cholmod_speye_worker.c" -#define COMPLEX -#include "t_cholmod_speye_worker.c" -#define ZOMPLEX -#include "t_cholmod_speye_worker.c" - -//------------------------------------------------------------------------------ -// cholmod_speye: create a sparse identity matrix -//------------------------------------------------------------------------------ - -cholmod_sparse *CHOLMOD(speye) -( - size_t nrow, // # of rows - size_t ncol, // # of columns - int xdtype, // xtype + dtype of the matrix: - // (CHOLMOD_DOUBLE, _SINGLE) + - // (CHOLMOD_PATTERN, _REAL, _COMPLEX, or _ZOMPLEX) - cholmod_common *Common -) -{ - - //-------------------------------------------------------------------------- - // check inputs - //-------------------------------------------------------------------------- - - RETURN_IF_NULL_COMMON (NULL) ; - Common->status = CHOLMOD_OK ; - - //-------------------------------------------------------------------------- - // allocate the matrix - //-------------------------------------------------------------------------- - - cholmod_sparse *A = CHOLMOD(allocate_sparse) (nrow, ncol, MIN (nrow, ncol), - /* A is sorted: */ TRUE, /* A is packed: */ TRUE, /* stype: */ 0, - xdtype, Common) ; - RETURN_IF_ERROR ; - - //-------------------------------------------------------------------------- - // fill the matrix with all 1's on the diagonal - //-------------------------------------------------------------------------- - - switch (xdtype % 8) - { - default: - p_cholmod_speye_worker (A) ; - break ; - - case CHOLMOD_SINGLE + CHOLMOD_REAL: - r_s_cholmod_speye_worker (A) ; - break ; - - case CHOLMOD_SINGLE + CHOLMOD_COMPLEX: - c_s_cholmod_speye_worker (A) ; - break ; - - case CHOLMOD_SINGLE + CHOLMOD_ZOMPLEX: - z_s_cholmod_speye_worker (A) ; - break ; - - case CHOLMOD_DOUBLE + CHOLMOD_REAL: - r_cholmod_speye_worker (A) ; - break ; - - case CHOLMOD_DOUBLE + CHOLMOD_COMPLEX: - c_cholmod_speye_worker (A) ; - break ; - - case CHOLMOD_DOUBLE + CHOLMOD_ZOMPLEX: - z_cholmod_speye_worker (A) ; - break ; - } - - //-------------------------------------------------------------------------- - // return result - //-------------------------------------------------------------------------- - - ASSERT (CHOLMOD(dump_sparse) (A, "speye:A", Common) >= 0) ; - return (A) ; -} - diff --git a/CHOLMOD/Utility/t_cholmod_speye_worker.c b/CHOLMOD/Utility/t_cholmod_speye_worker.c deleted file mode 100644 index 06a86ac77c..0000000000 --- a/CHOLMOD/Utility/t_cholmod_speye_worker.c +++ /dev/null @@ -1,57 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/t_cholmod_speye_worker: sparse identity matrix -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -#include "cholmod_template.h" - -static void TEMPLATE (cholmod_speye_worker) -( - cholmod_sparse *A -) -{ - - //-------------------------------------------------------------------------- - // fill the matrix with all 1's on the diagonal - //-------------------------------------------------------------------------- - - Int *Ap = (Int *) A->p ; - Int *Ai = (Int *) A->i ; - Real *Ax = (Real *) A->x ; - Real *Az = (Real *) A->z ; - - Int ncol = (Int) A->ncol ; - Int nrow = (Int) A->nrow ; - Int n = MIN (nrow, ncol) ; - - Real onex [2] = {1,0} ; - Real onez [1] = {0} ; - - for (Int k = 0 ; k < n ; k++) - { - // A(k,k) = 1 - Ap [k] = k ; - Ai [k] = k ; - ASSIGN (Ax, Az, k, onex, onez, 0) ; - } - - //-------------------------------------------------------------------------- - // finish the rest of A->p for any remaining empty columns - //-------------------------------------------------------------------------- - - for (Int k = n ; k <= ncol ; k++) - { - Ap [k] = n ; - } -} - -#undef PATTERN -#undef REAL -#undef COMPLEX -#undef ZOMPLEX - diff --git a/CHOLMOD/Utility/t_cholmod_spzeros.c b/CHOLMOD/Utility/t_cholmod_spzeros.c deleted file mode 100644 index 44353cb17d..0000000000 --- a/CHOLMOD/Utility/t_cholmod_spzeros.c +++ /dev/null @@ -1,34 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/t_cholmod_spzeros: all-zero sparse matrix -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -// Create a sparse matrix with no entries, of any xtype or dtype. The A->stype -// is zero (unsymmetric) but this can be modified by the caller to either +1 or -// -1, and the matrix will still be valid. - -#include "cholmod_internal.h" - -cholmod_sparse *CHOLMOD(spzeros) // return a sparse matrix with no entries -( - size_t nrow, // # of rows - size_t ncol, // # of columns - size_t nzmax, // max # of entries the matrix can hold - int xdtype, // xtype + dtype of the matrix: - // (CHOLMOD_DOUBLE, _SINGLE) + - // (CHOLMOD_PATTERN, _REAL, _COMPLEX, or _ZOMPLEX) - cholmod_common *Common -) -{ - return (CHOLMOD(allocate_sparse) (nrow, ncol, nzmax, - /* A is sorted: */ TRUE, - /* A is packed: */ TRUE, - /* A is unsymmetric: */ 0, - xdtype, Common)) ; -} - diff --git a/CHOLMOD/Utility/t_cholmod_start.c b/CHOLMOD/Utility/t_cholmod_start.c deleted file mode 100644 index 02478cc0b9..0000000000 --- a/CHOLMOD/Utility/t_cholmod_start.c +++ /dev/null @@ -1,61 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/t_cholmod_start: start CHOLMOD (int32/int64 version) -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -#include "cholmod_internal.h" - -// cholmod_start or cholmod_l_start must be called once prior to calling any -// other CHOLMOD method. It contains workspace that must be freed by -// cholmod_finish or cholmod_l_finish. - -int CHOLMOD(start) (cholmod_common *Common) -{ - - //-------------------------------------------------------------------------- - // check inputs - //-------------------------------------------------------------------------- - - if (Common == NULL) return (FALSE) ; - - //-------------------------------------------------------------------------- - // settings required before CHOLMOD(defaults) - //-------------------------------------------------------------------------- - - memset ((void *) Common, 0, sizeof (struct cholmod_common_struct)) ; - Common->itype = ITYPE ; // CHOLMOD_INT or CHOLMOD_LONG - - //-------------------------------------------------------------------------- - // set defaults - //-------------------------------------------------------------------------- - - CHOLMOD(defaults) (Common) ; - - //-------------------------------------------------------------------------- - // initialize the rest of Common to various nonzero values - //-------------------------------------------------------------------------- - - Common->gpuMemorySize = 1 ; - Common->chunk = 128000 ; - Common->nthreads_max = SUITESPARSE_OPENMP_MAX_THREADS ; - - Common->modfl = EMPTY ; - Common->aatfl = EMPTY ; - Common->blas_ok = TRUE ; - - Common->SPQR_grain = 1 ; - Common->SPQR_small = 1e6 ; - Common->SPQR_shrink = 1 ; - - Common->mark = EMPTY ; - Common->fl = EMPTY ; - Common->lnz = EMPTY ; - - return (TRUE) ; -} - diff --git a/CHOLMOD/Utility/t_cholmod_transpose.c b/CHOLMOD/Utility/t_cholmod_transpose.c deleted file mode 100644 index 3579c67dc5..0000000000 --- a/CHOLMOD/Utility/t_cholmod_transpose.c +++ /dev/null @@ -1,24 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/t_cholmod_transpose: transpose a sparse matrix -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -#include "cholmod_internal.h" - -cholmod_sparse *CHOLMOD(transpose) -( - cholmod_sparse *A, // input matrix - int mode, // 2: numerical (conj), 1: numerical (non-conj.), - // <= 0: pattern (with diag) - cholmod_common *Common -) -{ - return (CHOLMOD(ptranspose) (A, mode, /* Perm: */ NULL, - /* fset: */ NULL, /* fsize: */ 0, Common)) ; -} - diff --git a/CHOLMOD/Utility/t_cholmod_transpose_sym.c b/CHOLMOD/Utility/t_cholmod_transpose_sym.c deleted file mode 100644 index f2ca2ef5ec..0000000000 --- a/CHOLMOD/Utility/t_cholmod_transpose_sym.c +++ /dev/null @@ -1,241 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/t_cholmod_transpose_sym: symmetric permuted transpose -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -// C = A' or A(p,p)' if A is symmetric. The output matrix C must already be -// allocated, with enough space, and with the correct xtype (the same as A, -// or CHOLMOD_PATTERN if only the pattern of C is to be computed. The dtype -// of C and A must also match. A must be symmetric; and C is constructed as -// symmetric with the C->stype = -(A->stype). C->packed must be true. -// -// For a method that creates C itself, see cholmod_ptranspose instead. -// -// workspace: at most 2*nrow - -#include "cholmod_internal.h" - -#define RETURN_IF_ERROR \ - if (Common->status < CHOLMOD_OK) \ - { \ - return (FALSE) ; \ - } - -//------------------------------------------------------------------------------ -// t_cholmod_transpose_sym_worker template -//------------------------------------------------------------------------------ - -#define PATTERN -#include "t_cholmod_transpose_sym_worker.c" - -#define DOUBLE -#define REAL -#include "t_cholmod_transpose_sym_worker.c" - -#define COMPLEX -#include "t_cholmod_transpose_sym_worker.c" -#define COMPLEX -#define NCONJUGATE -#include "t_cholmod_transpose_sym_worker.c" - -#define ZOMPLEX -#include "t_cholmod_transpose_sym_worker.c" -#define ZOMPLEX -#define NCONJUGATE -#include "t_cholmod_transpose_sym_worker.c" - -#undef DOUBLE -#define SINGLE -#define REAL -#include "t_cholmod_transpose_sym_worker.c" - -#define COMPLEX -#include "t_cholmod_transpose_sym_worker.c" -#define COMPLEX -#define NCONJUGATE -#include "t_cholmod_transpose_sym_worker.c" - -#define ZOMPLEX -#include "t_cholmod_transpose_sym_worker.c" -#define ZOMPLEX -#define NCONJUGATE -#include "t_cholmod_transpose_sym_worker.c" - -//------------------------------------------------------------------------------ - -int CHOLMOD(transpose_sym) -( - cholmod_sparse *A, // input matrix - int mode, // 2: numerical (conj), 1: numerical (non-conj.), - // <= 0: pattern (with diag) - Int *Perm, // permutation for C=A(p,p)', or NULL - cholmod_sparse *C, // output matrix, must be allocated on input - cholmod_common *Common -) -{ - - //-------------------------------------------------------------------------- - // check inputs - //-------------------------------------------------------------------------- - - RETURN_IF_NULL_COMMON (FALSE) ; - RETURN_IF_SPARSE_MATRIX_INVALID (A, FALSE) ; - RETURN_IF_NULL (C, FALSE) ; - Common->status = CHOLMOD_OK ; - - if (A->xtype == CHOLMOD_PATTERN || C->xtype == CHOLMOD_PATTERN) - { - // A or C is pattern: C must be pattern, so mode can only be zero - mode = 0 ; - } - - Int n = A->ncol ; - if (A->stype == 0 || n != A->nrow) - { - ERROR (CHOLMOD_INVALID, "A must be symmetric") ; - return (FALSE) ; - } - - if ((C->xtype != ((mode == 0) ? CHOLMOD_PATTERN : A->xtype)) || - (C->dtype != A->dtype) || (n != C->ncol) || (n != C->nrow) || - (!C->packed)) - { - ERROR (CHOLMOD_INVALID, "C is invalid") ; - return (FALSE) ; - } - - ASSERT (CHOLMOD(dump_sparse) (A, "transpose_sym:A", Common) >= 0) ; - - //-------------------------------------------------------------------------- - // allocate workspace - //-------------------------------------------------------------------------- - - CHOLMOD(allocate_work) (0, ((Perm == NULL) ? 1: 2) * n, 0, Common) ; - RETURN_IF_ERROR ; - - Int *Wi = (Int *) Common->Iwork ; // size n integers - Int *Pinv = NULL ; - memset (Wi, 0, n * sizeof (Int)) ; - - //-------------------------------------------------------------------------- - // compute Pinv and make sure Perm is valid - //-------------------------------------------------------------------------- - - if (Perm != NULL) - { - Pinv = Wi + n ; // size n - CHOLMOD(set_empty) (Pinv, n) ; - for (Int k = 0 ; k < n ; k++) - { - Int i = Perm [k] ; - if ((i < 0 || i > n) || (Pinv [i] >= 0)) - { - ERROR (CHOLMOD_INVALID, "invalid permutation") ; - return (FALSE) ; - } - Pinv [i] = k ; - } - } - - //-------------------------------------------------------------------------- - // count the # of entries in each column of C - //-------------------------------------------------------------------------- - - Int *Ap = (Int *) A->p ; - Int *Ai = (Int *) A->i ; - Int *Anz = (Int *) A->nz ; - - #include "t_cholmod_transpose_sym_template.c" - - //-------------------------------------------------------------------------- - // compute the column pointers of C - //-------------------------------------------------------------------------- - - if (CHOLMOD(cumsum) (C->p, Wi, n) > C->nzmax) - { - ERROR (CHOLMOD_INVALID, "C->nzmax is too small") ; - return (FALSE) ; - } - memcpy (Wi, C->p, n * sizeof (Int)) ; - - //-------------------------------------------------------------------------- - // compute the pattern and values of C - //-------------------------------------------------------------------------- - - bool conj = (mode >= 2) ; - - switch ((C->xtype + C->dtype) % 8) - { - - default: - p_cholmod_transpose_sym_worker (C, A, Pinv, Wi) ; - break ; - - case CHOLMOD_SINGLE + CHOLMOD_REAL: - r_s_cholmod_transpose_sym_worker (C, A, Pinv, Wi) ; - break ; - - case CHOLMOD_SINGLE + CHOLMOD_COMPLEX: - if (conj) - { - c_s_cholmod_transpose_sym_worker (C, A, Pinv, Wi) ; - } - else - { - ct_s_cholmod_transpose_sym_worker (C, A, Pinv, Wi) ; - } - break ; - - case CHOLMOD_SINGLE + CHOLMOD_ZOMPLEX: - if (conj) - { - z_s_cholmod_transpose_sym_worker (C, A, Pinv, Wi) ; - } - else - { - zt_s_cholmod_transpose_sym_worker (C, A, Pinv, Wi) ; - } - break ; - - case CHOLMOD_DOUBLE + CHOLMOD_REAL: - r_cholmod_transpose_sym_worker (C, A, Pinv, Wi) ; - break ; - - case CHOLMOD_DOUBLE + CHOLMOD_COMPLEX: - if (conj) - { - c_cholmod_transpose_sym_worker (C, A, Pinv, Wi) ; - } - else - { - ct_cholmod_transpose_sym_worker (C, A, Pinv, Wi) ; - } - break ; - - case CHOLMOD_DOUBLE + CHOLMOD_ZOMPLEX: - if (conj) - { - z_cholmod_transpose_sym_worker (C, A, Pinv, Wi) ; - } - else - { - zt_cholmod_transpose_sym_worker (C, A, Pinv, Wi) ; - } - break ; - } - - //-------------------------------------------------------------------------- - // finalize C and return result - //-------------------------------------------------------------------------- - - C->sorted = (Perm == NULL) ; - C->stype = - SIGN (A->stype) ; - ASSERT (CHOLMOD(dump_sparse) (C, "transpose_sym:C", Common) >= 0) ; - return (TRUE) ; -} - diff --git a/CHOLMOD/Utility/t_cholmod_transpose_sym_permuted.c b/CHOLMOD/Utility/t_cholmod_transpose_sym_permuted.c deleted file mode 100644 index 26299b10c8..0000000000 --- a/CHOLMOD/Utility/t_cholmod_transpose_sym_permuted.c +++ /dev/null @@ -1,68 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/t_cholmod_transpose_sym_permuted -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ -// C = A(p,p)' where A and C are symmetric -//------------------------------------------------------------------------------ - -// The including file must define or undef PACKED, NUMERIC, and LO. -// define PACKED: if A->packed is true, undefine if A->packed is false -// define LO: if A is symmetric lower, undefine it if A is upper -// define NUMERIC: if computing values and pattern of C, undefine it if -// computing just the column counts of C. - -//------------------------------------------------------------------------------ - -{ - for (Int jold = 0 ; jold < n ; jold++) - { - Int jnew = Pinv [jold] ; - Int pa = Ap [jold] ; - #ifdef PACKED - Int paend = Ap [jold+1] ; - #else - Int paend = pa + Anz [jold] ; - #endif - for ( ; pa < paend ; pa++) - { - // get A(iold,jold) - Int iold = Ai [pa] ; - Int inew = Pinv [iold] ; - #ifdef LO - // A is symmetric lower, C is symmetric upper - if (iold < jold) continue ; - if (inew > jnew) - #else - // A is symmetric upper, C is symmetric lower - if (iold > jold) continue ; - if (inew < jnew) - #endif - { - // C(jnew,inew) = conj (A(iold,jold)) - Int pc = Wi [inew]++ ; - #ifdef NUMERIC - ASSIGN_CONJ_OR_NCONJ (Cx, Cz, pc, Ax, Az, pa) ; - Ci [pc] = jnew ; - #endif - } - else - { - // C(inew,jnew) = A(iold,jold) - Int pc = Wi [jnew]++ ; - #ifdef NUMERIC - ASSIGN (Cx, Cz, pc, Ax, Az, pa) ; - Ci [pc] = inew ; - #endif - } - } - } -} - -#undef PACKED -#undef LO - diff --git a/CHOLMOD/Utility/t_cholmod_transpose_sym_template.c b/CHOLMOD/Utility/t_cholmod_transpose_sym_template.c deleted file mode 100644 index 82f5cafa0d..0000000000 --- a/CHOLMOD/Utility/t_cholmod_transpose_sym_template.c +++ /dev/null @@ -1,122 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/t_cholmod_transpose_sym_template: -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ -// C = A' or A(p,p)', either symbolic or numeric phase -//------------------------------------------------------------------------------ - -// The including file must define or undef NUMERIC. -// define NUMERIC: if computing values and pattern of C, undefine it if -// computing just the column counts of C. - -//------------------------------------------------------------------------------ - -{ - if (Pinv == NULL) - { - - //---------------------------------------------------------------------- - // C = A', unpermuted transpose - //---------------------------------------------------------------------- - - if (A->stype < 0) - { - - //------------------------------------------------------------------ - // C = A', A is symmetric lower, C will be symmetric upper - //------------------------------------------------------------------ - - if (A->packed) - { - // A is packed - #define PACKED - #define LO - #include "t_cholmod_transpose_sym_unpermuted.c" - } - else - { - // A is unpacked - #define LO - #include "t_cholmod_transpose_sym_unpermuted.c" - } - - } - else - { - - //------------------------------------------------------------------ - // C = A', A is symmetric upper, C will be symmetric lower - //------------------------------------------------------------------ - - if (A->packed) - { - // A is packed - #define PACKED - #include "t_cholmod_transpose_sym_unpermuted.c" - } - else - { - // A is unpacked - #include "t_cholmod_transpose_sym_unpermuted.c" - } - } - - } - else - { - - //---------------------------------------------------------------------- - // C = A(p,p)', permuted transpose - //---------------------------------------------------------------------- - - if (A->stype < 0) - { - - //------------------------------------------------------------------ - // C = A(p,p)', A is symmetric lower, C will be symmetric upper - //------------------------------------------------------------------ - - if (A->packed) - { - // A is packed - #define PACKED - #define LO - #include "t_cholmod_transpose_sym_permuted.c" - } - else - { - // A is unpacked - #define LO - #include "t_cholmod_transpose_sym_permuted.c" - } - - } - else - { - - //------------------------------------------------------------------ - // C = A(p,p)', A is symmetric upper, C will be symmetric lower - //------------------------------------------------------------------ - - if (A->packed) - { - // A is packed - #define PACKED - #include "t_cholmod_transpose_sym_permuted.c" - } - else - { - // A is unpacked - #include "t_cholmod_transpose_sym_permuted.c" - } - } - } -} - -#undef NUMERIC - diff --git a/CHOLMOD/Utility/t_cholmod_transpose_sym_unpermuted.c b/CHOLMOD/Utility/t_cholmod_transpose_sym_unpermuted.c deleted file mode 100644 index 17811443e8..0000000000 --- a/CHOLMOD/Utility/t_cholmod_transpose_sym_unpermuted.c +++ /dev/null @@ -1,54 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/t_cholmod_transpose_sym_unpermuted -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ -// C = A' where A and C are symmetric -//------------------------------------------------------------------------------ - -// The including file must define or undef PACKED, NUMERIC, and LO. -// define PACKED: if A->packed is true, undefine if A->packed is false -// define LO: if A is symmetric lower, undefine it if A is upper -// define NUMERIC: if computing values and pattern of C, undefine it if -// computing just the column counts of C. - -//------------------------------------------------------------------------------ - -{ - - for (Int j = 0 ; j < n ; j++) - { - Int pa = Ap [j] ; - #ifdef PACKED - Int paend = Ap [j+1] ; - #else - Int paend = pa + Anz [j] ; - #endif - for ( ; pa < paend ; pa++) - { - // get A(i,j) - Int i = Ai [pa] ; - #ifdef LO - // A is symmetric lower, C is symmetric upper - if (i < j) continue ; - #else - // A is symmetric upper, C is symmetric lower - if (i > j) continue ; - #endif - // C(j,i) = conj (A(i,j)) - Int pc = Wi [i]++ ; - #ifdef NUMERIC - ASSIGN_CONJ_OR_NCONJ (Cx, Cz, pc, Ax, Az, pa) ; - Ci [pc] = j ; - #endif - } - } -} - -#undef PACKED -#undef LO - diff --git a/CHOLMOD/Utility/t_cholmod_transpose_sym_worker.c b/CHOLMOD/Utility/t_cholmod_transpose_sym_worker.c deleted file mode 100644 index e4377d7e76..0000000000 --- a/CHOLMOD/Utility/t_cholmod_transpose_sym_worker.c +++ /dev/null @@ -1,53 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/t_cholmod_transpose_sym_worker: C = A' or A(p,p)' -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -#include "cholmod_template.h" - -static void TEMPLATE (cholmod_transpose_sym_worker) -( - cholmod_sparse *C, // output matrix of size n-by-n - cholmod_sparse *A, // input matrix of size n-by-n - Int *Pinv, // size n, inverse permutation, or NULL if none - Int *Wi // size n workspace; column pointers of C on input -) -{ - - //-------------------------------------------------------------------------- - // get inputs - //-------------------------------------------------------------------------- - - Int n = A->ncol ; - - Int *Ap = (Int *) A->p ; - Int *Ai = (Int *) A->i ; - Int *Anz = (Int *) A->nz ; - Real *Ax = (Real *) A->x ; - Real *Az = (Real *) A->z ; - - Int *Cp = (Int *) C->p ; - Int *Ci = (Int *) C->i ; - Real *Cx = (Real *) C->x ; - Real *Cz = (Real *) C->z ; - - //-------------------------------------------------------------------------- - // compute pattern and values of C - //-------------------------------------------------------------------------- - - #define NUMERIC - #include "t_cholmod_transpose_sym_template.c" - -} - -#undef PATTERN -#undef REAL -#undef COMPLEX -#undef ZOMPLEX -#undef NCONJUGATE - diff --git a/CHOLMOD/Utility/t_cholmod_transpose_unsym.c b/CHOLMOD/Utility/t_cholmod_transpose_unsym.c deleted file mode 100644 index 8bc9967ef1..0000000000 --- a/CHOLMOD/Utility/t_cholmod_transpose_unsym.c +++ /dev/null @@ -1,398 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/t_cholmod_transpose_unsym: unsymmetric permuted transpose -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -#include "cholmod_internal.h" - -// Creates C = A', A(:,f)' or A(p,f)' C must be already allocated on input. -// The matrices A and C are unsymmetric (with stype of zero). See -// cholmod_transpose and cholmod_ptranspose for methods with a simpler -// interface. - -// The notation A(:,f) and A(p,f) refers to a matrix of the same size as A, -// where p is a permutation vector and f is a vector fset of size fsize. -// Any column j not in the fset list still appears in A(:,f), just empty. -// p must be a permutation of 0:A->nrow-1, and f must be a permutation of -// a subset of 0:A->ncol-1. - -#define RETURN_IF_ERROR \ - if (Common->status < CHOLMOD_OK) \ - { \ - return (FALSE) ; \ - } - -//------------------------------------------------------------------------------ -// t_cholmod_transpose_unsym_worker template -//------------------------------------------------------------------------------ - -#define NUMERIC - -#define PATTERN -#include "t_cholmod_transpose_unsym_worker.c" - -#define DOUBLE -#define REAL -#include "t_cholmod_transpose_unsym_worker.c" - -#define COMPLEX -#include "t_cholmod_transpose_unsym_worker.c" -#define COMPLEX -#define NCONJUGATE -#include "t_cholmod_transpose_unsym_worker.c" - -#define ZOMPLEX -#include "t_cholmod_transpose_unsym_worker.c" -#define ZOMPLEX -#define NCONJUGATE -#include "t_cholmod_transpose_unsym_worker.c" - -#undef DOUBLE -#define SINGLE -#define REAL -#include "t_cholmod_transpose_unsym_worker.c" - -#define COMPLEX -#include "t_cholmod_transpose_unsym_worker.c" -#define COMPLEX -#define NCONJUGATE -#include "t_cholmod_transpose_unsym_worker.c" - -#define ZOMPLEX -#include "t_cholmod_transpose_unsym_worker.c" -#define ZOMPLEX -#define NCONJUGATE -#include "t_cholmod_transpose_unsym_worker.c" - -#undef NUMERIC - -//------------------------------------------------------------------------------ -// cm_copy_Cnz: copy Wi into Cnz -//------------------------------------------------------------------------------ - -static void cm_copy_Cnz (Int *Cnz, Int *Wi, Int *Perm, Int nrow) -{ - if (Perm == NULL) - { - // Cnz [0..nrow-1] = Wi [0..nrow-1] - memcpy (Cnz, Wi, nrow * sizeof (Int)) ; - } - else - { - // Cnz [0..nrow-1] = Wi [Perm [0..nrow-1]] - for (Int i = 0 ; i < nrow ; i++) - { - Cnz [i] = Wi [Perm [i]] ; - } - } -} - -//------------------------------------------------------------------------------ -//------------------------------------------------------------------------------ - -int CHOLMOD(transpose_unsym) -( - cholmod_sparse *A, // input matrix - int mode, // 2: numerical (conj), 1: numerical (non-conj.), - // <= 0: pattern (with diag) - Int *Perm, // permutation for C=A(p,f)', or NULL - Int *fset, // a list of column indices in range 0:A->ncol-1 - size_t fsize, // # of entries in fset - cholmod_sparse *C, // output matrix, must be allocated on input - cholmod_common *Common -) -{ - - //-------------------------------------------------------------------------- - // check inputs - //-------------------------------------------------------------------------- - - RETURN_IF_NULL_COMMON (FALSE) ; - RETURN_IF_SPARSE_MATRIX_INVALID (A, FALSE) ; - RETURN_IF_NULL (C, FALSE) ; - Common->status = CHOLMOD_OK ; - - if (A->xtype == CHOLMOD_PATTERN || C->xtype == CHOLMOD_PATTERN) - { - // A or C is pattern: C must be pattern, so mode can only be zero - mode = 0 ; - } - - Int nrow = A->nrow ; - Int ncol = A->ncol ; - - if (A->stype != 0) - { - ERROR (CHOLMOD_INVALID, "A is invalid") ; - return (FALSE) ; - } - - if ((C->xtype != ((mode <= 0) ? CHOLMOD_PATTERN : A->xtype)) || - (C->dtype != A->dtype) || (nrow != C->ncol) || (ncol != C->nrow) || - (C->stype != 0)) - { - ERROR (CHOLMOD_INVALID, "C is invalid") ; - return (FALSE) ; - } - - ASSERT (CHOLMOD(dump_sparse) (A, "transpose_unsym:A", Common) >= 0) ; - - //-------------------------------------------------------------------------- - // allocate workspace - //-------------------------------------------------------------------------- - - size_t iworksize = (fset == NULL) ? nrow : MAX (nrow, ncol) ; - CHOLMOD(allocate_work) (0, iworksize, 0, Common) ; - RETURN_IF_ERROR ; - Int *Wi = (Int *) Common->Iwork ; // size n integers - - //-------------------------------------------------------------------------- - // get inputs - //-------------------------------------------------------------------------- - - Int *Ap = (Int *) A->p ; - Int *Ai = (Int *) A->i ; - Int *Anz = (Int *) A->nz ; - - Int *Cp = (Int *) C->p ; - Int *Cnz = (Int *) C->nz ; - - //-------------------------------------------------------------------------- - // check Perm if present - //-------------------------------------------------------------------------- - - if (Perm != NULL) - { - memset (Wi, 0, nrow * sizeof (Int)) ; - for (Int k = 0 ; k < nrow ; k++) - { - Int i = Perm [k] ; - if (i < 0 || i > nrow || Wi [i] == 1) - { - ERROR (CHOLMOD_INVALID, "invalid permutation") ; - return (FALSE) ; - } - Wi [i] = 1 ; - } - } - - ASSERT (CHOLMOD(dump_perm) (Perm, nrow, nrow, "Perm", Common)) ; - - //-------------------------------------------------------------------------- - // check fset if present, and also determine if it's sorted - //-------------------------------------------------------------------------- - - Int nf = (Int) fsize ; - bool fsorted = true ; - if (fset != NULL) - { - Int jlast = EMPTY ; - memset (Wi, 0, ncol * sizeof (Int)) ; - for (Int k = 0 ; k < nf ; k++) - { - Int j = fset [k] ; - if (j < 0 || j > ncol || Wi [j] == 1) - { - ERROR (CHOLMOD_INVALID, "invalid fset") ; - return (FALSE) ; - } - Wi [j] = 1 ; - fsorted = fsorted && (j > jlast) ; - jlast = j ; - } - } - - ASSERT (CHOLMOD(dump_perm) (fset, fsize, ncol, "fset", Common)) ; - - //-------------------------------------------------------------------------- - // count entries in each row of A or A(:,f) - //-------------------------------------------------------------------------- - - memset (Wi, 0, nrow * sizeof (Int)) ; - - if (fset != NULL) - { - - //---------------------------------------------------------------------- - // count entries in rows of (A:,f) - //---------------------------------------------------------------------- - - if (A->packed) - { - #define PACKED - #define FSET - #include "t_cholmod_transpose_unsym_template.c" - } - else - { - #define FSET - #include "t_cholmod_transpose_unsym_template.c" - } - - //---------------------------------------------------------------------- - // save the nz counts if C is unpacked, and recount all of A - //---------------------------------------------------------------------- - - if (!(C->packed)) - { - - cm_copy_Cnz (Cnz, Wi, Perm, nrow) ; - - //------------------------------------------------------------------ - // count entries in rows of A - //------------------------------------------------------------------ - - memset (Wi, 0, nrow * sizeof (Int)) ; - if (A->packed) - { - #define PACKED - #include "t_cholmod_transpose_unsym_template.c" - } - else - { - #include "t_cholmod_transpose_unsym_template.c" - } - } - - } - else - { - - //---------------------------------------------------------------------- - // count entries in rows of A - //---------------------------------------------------------------------- - - if (A->packed) - { - #define PACKED - #include "t_cholmod_transpose_unsym_template.c" - } - else - { - #include "t_cholmod_transpose_unsym_template.c" - } - - //---------------------------------------------------------------------- - // save the nz counts if C is unpacked, and recount all of A - //---------------------------------------------------------------------- - - if (!(C->packed)) - { - cm_copy_Cnz (Cnz, Wi, Perm, nrow) ; - } - } - - //-------------------------------------------------------------------------- - // Compute Cp - //-------------------------------------------------------------------------- - - Int p = 0 ; - if (Perm == NULL) - { - // Cp = cumsum (Wi) - p = CHOLMOD(cumsum) (Cp, Wi, nrow) ; - // Wi [0..nrow-1] = Cp [0..nrow-1] - memcpy (Wi, Cp, nrow * sizeof (Int)) ; - } - else - { - // Cp = cumsum (Wi [Perm]) - for (Int i = 0 ; i < nrow ; i++) - { - Cp [i] = p ; - p += Wi [Perm [i]] ; - } - Cp [nrow] = p ; - // Wi [Perm [0..nrow-1]] = Cp [0..nrow-1] - for (Int i = 0 ; i < nrow ; i++) - { - Wi [Perm [i]] = Cp [i] ; - } - } - - if (p > (Int) C->nzmax) - { - ERROR (CHOLMOD_INVALID, "C is too small") ; - return (FALSE) ; - } - - //-------------------------------------------------------------------------- - // compute the pattern and values of C - //-------------------------------------------------------------------------- - - bool conj = (mode >= 2) ; - - switch ((C->xtype + C->dtype) % 8) - { - - default: - p_cholmod_transpose_unsym_worker (A, fset, nf, C, Wi) ; - break ; - - case CHOLMOD_SINGLE + CHOLMOD_REAL: - r_s_cholmod_transpose_unsym_worker (A, fset, nf, C, Wi) ; - break ; - - case CHOLMOD_SINGLE + CHOLMOD_COMPLEX: - if (conj) - { - c_s_cholmod_transpose_unsym_worker (A, fset, nf, C, Wi) ; - } - else - { - ct_s_cholmod_transpose_unsym_worker (A, fset, nf, C, Wi) ; - } - break ; - - case CHOLMOD_SINGLE + CHOLMOD_ZOMPLEX: - if (conj) - { - z_s_cholmod_transpose_unsym_worker (A, fset, nf, C, Wi) ; - } - else - { - zt_s_cholmod_transpose_unsym_worker (A, fset, nf, C, Wi) ; - } - break ; - - case CHOLMOD_DOUBLE + CHOLMOD_REAL: - r_cholmod_transpose_unsym_worker (A, fset, nf, C, Wi) ; - break ; - - case CHOLMOD_DOUBLE + CHOLMOD_COMPLEX: - if (conj) - { - c_cholmod_transpose_unsym_worker (A, fset, nf, C, Wi) ; - } - else - { - ct_cholmod_transpose_unsym_worker (A, fset, nf, C, Wi) ; - } - break ; - - case CHOLMOD_DOUBLE + CHOLMOD_ZOMPLEX: - if (conj) - { - z_cholmod_transpose_unsym_worker (A, fset, nf, C, Wi) ; - } - else - { - zt_cholmod_transpose_unsym_worker (A, fset, nf, C, Wi) ; - } - break ; - } - - //-------------------------------------------------------------------------- - // finalize C and return result - //-------------------------------------------------------------------------- - - C->sorted = fsorted ; - ASSERT (CHOLMOD(dump_sparse) (C, "transpose_unsym:C", Common) >= 0) ; - return (TRUE) ; -} - diff --git a/CHOLMOD/Utility/t_cholmod_transpose_unsym_template.c b/CHOLMOD/Utility/t_cholmod_transpose_unsym_template.c deleted file mode 100644 index 3a78d0fd2c..0000000000 --- a/CHOLMOD/Utility/t_cholmod_transpose_unsym_template.c +++ /dev/null @@ -1,74 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/t_cholmod_transpose_unsym_template -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ -// C = A', C = A(:,f)', C = A(p,:)', or C = A(p,f)'; A and C are unsymmetric -//------------------------------------------------------------------------------ - -// The including file must define or undef PACKED, NUMERIC, and FSET - -// define PACKED: if A->packed is true, undefine if A->packed is false - -// define NUMERIC: if computing values and pattern of C, undefine it if -// computing just the column counts of C. - -//------------------------------------------------------------------------------ - -{ - - #undef N - #ifdef FSET - #define N nf - #else - #define N ncol - #endif - - for (Int k = 0 ; k < N ; k++) - { - - //---------------------------------------------------------------------- - // get the fset, if present - //---------------------------------------------------------------------- - - #ifdef FSET - Int j = fset [k] ; - #else - Int j = k ; - #endif - - //---------------------------------------------------------------------- - // get A(:,k) - //---------------------------------------------------------------------- - - Int p = Ap [j] ; - #ifdef PACKED - Int pend = Ap [j+1] ; - #else - Int pend = p + Anz [j] ; - #endif - - //---------------------------------------------------------------------- - // scan entries in A(:,k) - //---------------------------------------------------------------------- - - for ( ; p < pend ; p++) - { - // get A(i,j) and count it or get its place in C - Int pc = Wi [Ai [p]]++ ; - #ifdef NUMERIC - // C(j,i) = conj (A(i,j)) - ASSIGN_CONJ_OR_NCONJ (Cx, Cz, pc, Ax, Az, p) ; - Ci [pc] = j ; - #endif - } - } -} - -#undef FSET -#undef PACKED - diff --git a/CHOLMOD/Utility/t_cholmod_transpose_unsym_worker.c b/CHOLMOD/Utility/t_cholmod_transpose_unsym_worker.c deleted file mode 100644 index f87b9a94b4..0000000000 --- a/CHOLMOD/Utility/t_cholmod_transpose_unsym_worker.c +++ /dev/null @@ -1,80 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/t_cholmod_transpose_unsym_worker: C = A', A(:,f)', or A(p,f)' -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -#include "cholmod_template.h" - -static void TEMPLATE (cholmod_transpose_unsym_worker) -( - cholmod_sparse *A, // input matrix - Int *fset, // a list of column indices in range 0:A->ncol-1 - Int nf, // # of entries in fset - cholmod_sparse *C, // output matrix, must be allocated on input - Int *Wi // workspace of size nrow -) -{ - - //-------------------------------------------------------------------------- - // get inputs - //-------------------------------------------------------------------------- - - Int *Ap = (Int *) A->p ; - Int *Ai = (Int *) A->i ; - Int *Anz = (Int *) A->nz ; - Real *Ax = (Real *) A->x ; - Real *Az = (Real *) A->z ; - Int ncol = A->ncol ; - - Int *Cp = (Int *) C->p ; - Int *Ci = (Int *) C->i ; - Real *Cx = (Real *) C->x ; - Real *Cz = (Real *) C->z ; - - //-------------------------------------------------------------------------- - // compute the pattern and values of C - //-------------------------------------------------------------------------- - - if (fset != NULL) - { - if (A->packed) - { - // C = A (p,f)' or A(:,f)' where A is packed - #define PACKED - #define FSET - #include "t_cholmod_transpose_unsym_template.c" - } - else - { - // C = A (p,f)' or A(:,f)' where A is unpacked - #define FSET - #include "t_cholmod_transpose_unsym_template.c" - } - } - else - { - if (A->packed) - { - // C = A (p,:)' or A' where A is packed - #define PACKED - #include "t_cholmod_transpose_unsym_template.c" - } - else - { - // C = A (p,:)' or A' where A is unpacked - #include "t_cholmod_transpose_unsym_template.c" - } - } -} - -#undef PATTERN -#undef REAL -#undef COMPLEX -#undef ZOMPLEX -#undef NCONJUGATE - diff --git a/CHOLMOD/Utility/t_cholmod_triplet_to_sparse.c b/CHOLMOD/Utility/t_cholmod_triplet_to_sparse.c deleted file mode 100644 index 4b777a244c..0000000000 --- a/CHOLMOD/Utility/t_cholmod_triplet_to_sparse.c +++ /dev/null @@ -1,222 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/t_cholmod_triplet_to_sparse: convert triplet to sparse -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -#include "cholmod_internal.h" - -//------------------------------------------------------------------------------ -// t_cholmod_triplet_to_sparse_worker template -//------------------------------------------------------------------------------ - -#define PATTERN -#include "t_cholmod_triplet_to_sparse_worker.c" - -#define DOUBLE -#define REAL -#include "t_cholmod_triplet_to_sparse_worker.c" -#define COMPLEX -#include "t_cholmod_triplet_to_sparse_worker.c" -#define ZOMPLEX -#include "t_cholmod_triplet_to_sparse_worker.c" - -#undef DOUBLE -#define SINGLE -#define REAL -#include "t_cholmod_triplet_to_sparse_worker.c" -#define COMPLEX -#include "t_cholmod_triplet_to_sparse_worker.c" -#define ZOMPLEX -#include "t_cholmod_triplet_to_sparse_worker.c" - -//------------------------------------------------------------------------------ -// cholmod_triplet_to_sparse: convert triplet matrix to sparse matrix -//------------------------------------------------------------------------------ - -#define RETURN_IF_ERROR \ - if (Common->status < CHOLMOD_OK) \ - { \ - CHOLMOD(free_sparse) (&A, Common) ; \ - CHOLMOD(free_sparse) (&R, Common) ; \ - return (NULL) ; \ - } - -// Converts a triplet matrix T into a sparse matrix A. The nzmax parameter -// can be used to add additional space in A for future entries. The # of -// entries that can be held in A is max (nnz (A), nzmax), so pass in nzmax -// as zero if you do not need any additional space for future growth. - -// workspace: Iwork (max (nrow,ncol)) - -cholmod_sparse *CHOLMOD(triplet_to_sparse) // return sparse matrix A -( - cholmod_triplet *T, // input triplet matrix - size_t nzmax, // allocate space for max(nzmax,nnz(A)) entries - cholmod_common *Common -) -{ - - //-------------------------------------------------------------------------- - // check inputs - //-------------------------------------------------------------------------- - - RETURN_IF_NULL_COMMON (NULL) ; - RETURN_IF_TRIPLET_MATRIX_INVALID (T, NULL) ; - Common->status = CHOLMOD_OK ; - cholmod_sparse *A = NULL ; - - //-------------------------------------------------------------------------- - // get inputs - //-------------------------------------------------------------------------- - - size_t nrow = T->nrow ; - size_t ncol = T->ncol ; - size_t nz = T->nnz ; - Int *Ti = (Int *) T->i ; - Int *Tj = (Int *) T->j ; - int stype = T->stype ; - - //-------------------------------------------------------------------------- - // allocate temporary matrix R to hold the transpose of A - //-------------------------------------------------------------------------- - - // R is unpacked so that duplicates can be easily assembled in place. - // Note that the stype of R is negated, to hold the transpose of A. - cholmod_sparse *R = CHOLMOD(allocate_sparse) (ncol, nrow, nz, - /* R is unsorted: */ FALSE, /* R is unpacked: */ FALSE, - /* stype is flipped: */ -stype, T->xtype + T->dtype, Common) ; - RETURN_IF_ERROR ; - - Int *Rp = (Int *) R->p ; - Int *Rnz = (Int *) R->nz ; - - //-------------------------------------------------------------------------- - // count entries in each column of R, imcluding duplicates - //-------------------------------------------------------------------------- - - // Rnz [0..nrow-1] = 0 - memset (Rnz, 0, nrow * sizeof (Int)) ; - - for (Int k = 0 ; k < nz ; k++) - { - // get the entry T(i,j), which becomes R(j,i) - Int i = Ti [k] ; - Int j = Tj [k] ; - if (i < 0 || j < 0 || i >= nrow || j >= ncol) - { - ERROR (CHOLMOD_INVALID, "index out of range") ; - break ; - } - if (stype > 0) - { - // A will be symmetric, and only its upper triangular part is - // stored, so R must be lower triangular. Ensure that entries - // in the upper triangular part of R are transposed to the lower - // triangular part, by placing the entry T(i,j) in column - // MIN(i,j) of R. - Rnz [MIN (i,j)]++ ; - } - else if (stype < 0) - { - // See comment above; A is lower triangular so R must be upper. - Rnz [MAX (i,j)]++ ; - } - else - { - // T and A are unsymmetric - Rnz [i]++ ; - } - } - - RETURN_IF_ERROR ; // return if index out of range - - //-------------------------------------------------------------------------- - // Rp = cumulative sum of the row counts, Rnz - //-------------------------------------------------------------------------- - - CHOLMOD(cumsum) (Rp, Rnz, nrow) ; - - //-------------------------------------------------------------------------- - // allocate Iwork workspace for the template work, of size MAX (nrow,ncol) - //-------------------------------------------------------------------------- - - CHOLMOD(alloc_work) (0, MAX (nrow, ncol), 0, 0, Common) ; - RETURN_IF_ERROR ; - - //-------------------------------------------------------------------------- - // R = T' using template worker - //-------------------------------------------------------------------------- - - size_t anz = 0 ; - - switch ((T->xtype + T->dtype) % 8) - { - default: - anz = p_cholmod_triplet_to_sparse_worker (T, R, Common) ; - break ; - - case CHOLMOD_SINGLE + CHOLMOD_REAL: - anz = r_s_cholmod_triplet_to_sparse_worker (T, R, Common) ; - break ; - - case CHOLMOD_SINGLE + CHOLMOD_COMPLEX: - anz = c_s_cholmod_triplet_to_sparse_worker (T, R, Common) ; - break ; - - case CHOLMOD_SINGLE + CHOLMOD_ZOMPLEX: - anz = z_s_cholmod_triplet_to_sparse_worker (T, R, Common) ; - break ; - - case CHOLMOD_DOUBLE + CHOLMOD_REAL: - anz = r_cholmod_triplet_to_sparse_worker (T, R, Common) ; - break ; - - case CHOLMOD_DOUBLE + CHOLMOD_COMPLEX: - anz = c_cholmod_triplet_to_sparse_worker (T, R, Common) ; - break ; - - case CHOLMOD_DOUBLE + CHOLMOD_ZOMPLEX: - anz = z_cholmod_triplet_to_sparse_worker (T, R, Common) ; - break ; - } - - //-------------------------------------------------------------------------- - // allocate the final output matrix A - //-------------------------------------------------------------------------- - - anz = MAX (anz, nzmax) ; - A = CHOLMOD(allocate_sparse) (nrow, ncol, anz, TRUE, TRUE, stype, - T->xtype + T->dtype, Common) ; - RETURN_IF_ERROR ; - - //-------------------------------------------------------------------------- - // A = R' - //-------------------------------------------------------------------------- - - // uses Iwork [0..ncol-1] workspace - if (stype == 0) - { - // unsymmetric transpose - CHOLMOD(transpose_unsym) (R, 1, NULL, NULL, 0, A, Common) ; - } - else - { - // symmetric array transpose (not conjugate tranpose if complex) - CHOLMOD(transpose_sym) (R, 1, NULL, A, Common) ; - } - RETURN_IF_ERROR ; - - //-------------------------------------------------------------------------- - // free workspace and return result - //-------------------------------------------------------------------------- - - CHOLMOD(free_sparse) (&R, Common) ; - ASSERT (CHOLMOD(dump_sparse) (A, "triplet_to_sparse:A", Common) >= 0) ; - return (A) ; -} - diff --git a/CHOLMOD/Utility/t_cholmod_triplet_to_sparse_worker.c b/CHOLMOD/Utility/t_cholmod_triplet_to_sparse_worker.c deleted file mode 100644 index c385f07fab..0000000000 --- a/CHOLMOD/Utility/t_cholmod_triplet_to_sparse_worker.c +++ /dev/null @@ -1,189 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/t_cholmod_triplet_to_sparse_worker -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -#include "cholmod_template.h" - -static size_t TEMPLATE (cholmod_triplet_to_sparse_worker) // return nnz(R) -( - cholmod_triplet *T, // input matrix - cholmod_sparse *R, // output matrix - cholmod_common *Common -) -{ - - //-------------------------------------------------------------------------- - // get inputs - //-------------------------------------------------------------------------- - - Int *Rp = (Int *) R->p ; - Int *Ri = (Int *) R->i ; - Int *Rnz = (Int *) R->nz ; - Real *Rx = (Real *) R->x ; - Real *Rz = (Real *) R->z ; - - Int *Ti = (Int *) T->i ; - Int *Tj = (Int *) T->j ; - Real *Tx = (Real *) T->x ; - Real *Tz = (Real *) T->z ; - size_t nrow = T->nrow ; - size_t ncol = T->ncol ; - Int nz = T->nnz ; - - //-------------------------------------------------------------------------- - // W [0..nrow-1] = Rp [0..nrow-1] using Iwork workspace - //-------------------------------------------------------------------------- - - // using W [0..nrow-1] as workspace for row pointers [ - Int *W = (Int *) Common->Iwork ; - memcpy (W, Rp, nrow * sizeof (Int)) ; - - //-------------------------------------------------------------------------- - // construct the matrix R, keeping duplicates for now - //-------------------------------------------------------------------------- - - // R is treated as if it is stored by row, in the comments below - - int stype = T->stype ; - - for (Int k = 0 ; k < nz ; k++) - { - // get the T (i,j) entry - Int i = Ti [k] ; - Int j = Tj [k] ; - Int p ; - if (stype > 0) - { - // T represents a symmetric matrix with upper part stored - if (i < j) - { - // R (i,j) = T (i,j), placed in row R (i,:) - Ri [p = W [i]++] = j ; - } - else - { - // R (j,i) = T (i,j), placed in row R (j,:) - Ri [p = W [j]++] = i ; - } - } - else if (stype < 0) - { - // T represents a symmetric matrix with lower part stored - if (i > j) - { - // R (i,j) = T (i,j), placed in row R (i,:) - Ri [p = W [i]++] = j ; - } - else - { - // R (j,i) = T (i,j), placed in row R (j,:) - Ri [p = W [j]++] = i ; - } - } - else - { - // T represents an unsymmetric matrix - // R (i,j) = T (i,j), placed in row R (i,:) - Ri [p = W [i]++] = j ; - } - ASSIGN (Rx, Rz, p, Tx, Tz, k) ; // Rx [p] = Tx [k] - } - - // no longer using W as temporary workspace for row pointers ] - - //-------------------------------------------------------------------------- - // assemble any duplicate entries - //-------------------------------------------------------------------------- - - // use W [0..ncol-1] for pointers to duplicates in each row of R [ - CHOLMOD(set_empty) (W, ncol) ; - - size_t rnz = 0 ; // total # of entries in R after assembling duplicates - - for (Int i = 0 ; i < nrow ; i++) - { - - //---------------------------------------------------------------------- - // get the location of R (i,:) before assemblying duplicates - //---------------------------------------------------------------------- - - // row R (i,:) is in located in Ri [pstart..pend-1]. If duplicates are - // detected, the new row i will be located in Ri [pstart..pp-1]. - - Int pstart = Rp [i] ; - Int pend = Rp [i+1] ; - Int pp = pstart ; - - // W [j] is the position in Ri of the last time column j was seen. - // Here, W [0..ncol-1] < pstart is true because R is stored by row, - // and any column j already seen will have been seen in an earlier - // row. If column j has never been seen, W [j] is EMPTY (-1). - - //---------------------------------------------------------------------- - // assemble duplicates in R (i,:) - //---------------------------------------------------------------------- - - for (Int p = pstart ; p < pend ; p++) - { - - //------------------------------------------------------------------ - // get R(i,j) - //------------------------------------------------------------------ - - Int j = Ri [p] ; - Int plastj = W [j] ; // last seen position of column index j - - //------------------------------------------------------------------ - // assemble R(i,j) - //------------------------------------------------------------------ - - if (plastj < pstart) - { - // column j has been seen for the first time in row R (i,:), - // at position pp. Move the entry to position pp, and keep - // track of it in case column j appears again in row R (i,:). - // Rx [pp] = Rx [p] - ASSIGN (Rx, Rz, pp, Rx, Rz, p) ; - Ri [pp] = j ; - // one more unique entry has been seen in R (i,:) - W [j] = pp++ ; - } - else - { - // column j has already been seen in this row R (i,;), at - // position plastj, so assemble this duplicate entry into that - // position. - // Rx [plastj] += Rx [p] - ASSEMBLE (Rx, Rz, plastj, Rx, Rz, p) ; - } - } - - //---------------------------------------------------------------------- - // count the number of entries in R (i,:) - //---------------------------------------------------------------------- - - Int rnz_i = pp - pstart ; - Rnz [i] = rnz_i ; - rnz += rnz_i ; - } - - // done using W [0..ncol-1] workspace ] - - //-------------------------------------------------------------------------- - // return result: # of entries in R after assembling duplicates - //-------------------------------------------------------------------------- - - return (rnz) ; -} - -#undef PATTERN -#undef REAL -#undef COMPLEX -#undef ZOMPLEX - diff --git a/CHOLMOD/Utility/t_cholmod_version.c b/CHOLMOD/Utility/t_cholmod_version.c deleted file mode 100644 index 7ac1d4ca7a..0000000000 --- a/CHOLMOD/Utility/t_cholmod_version.c +++ /dev/null @@ -1,41 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/t_cholmod_version: CHOLMOD version -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -#include "cholmod_internal.h" - -int CHOLMOD(version) // returns CHOLMOD_VERSION -( - // if version is not NULL, then cholmod_version returns its contents as: - // version [0] = CHOLMOD_MAIN_VERSION - // version [1] = CHOLMOD_SUB_VERSION - // version [2] = CHOLMOD_SUBSUB_VERSION - int version [3] -) -{ - - //-------------------------------------------------------------------------- - // check inputs - //-------------------------------------------------------------------------- - - if (version == NULL) - { - return (CHOLMOD_VERSION) ; - } - - //-------------------------------------------------------------------------- - // return the full version of CHOLMOD - //-------------------------------------------------------------------------- - - version [0] = CHOLMOD_MAIN_VERSION ; - version [1] = CHOLMOD_SUB_VERSION ; - version [2] = CHOLMOD_SUBSUB_VERSION ; - return (CHOLMOD_VERSION) ; -} - diff --git a/CHOLMOD/Utility/t_cholmod_zeros.c b/CHOLMOD/Utility/t_cholmod_zeros.c deleted file mode 100644 index eff8dad7b8..0000000000 --- a/CHOLMOD/Utility/t_cholmod_zeros.c +++ /dev/null @@ -1,77 +0,0 @@ -//------------------------------------------------------------------------------ -// CHOLMOD/Utility/t_cholmod_zeros: allocate an all-zero dense matrix -//------------------------------------------------------------------------------ - -// CHOLMOD/Utility Module. Copyright (C) 2023, Timothy A. Davis, All Rights -// Reserved. -// SPDX-License-Identifier: LGPL-2.1+ - -//------------------------------------------------------------------------------ - -// Allocate a dense matrix. The space is set to zero. - -#include "cholmod_internal.h" - -#define RETURN_IF_ERROR \ - if (Common->status < CHOLMOD_OK) \ - { \ - CHOLMOD(free_dense) (&X, Common) ; \ - return (NULL) ; \ - } - -cholmod_dense *CHOLMOD(zeros) -( - size_t nrow, // # of rows - size_t ncol, // # of columns - int xdtype, // xtype + dtype of the matrix: - // (CHOLMOD_DOUBLE, _SINGLE) + - // (CHOLMOD_REAL, _COMPLEX, or _ZOMPLEX) - cholmod_common *Common -) -{ - - //-------------------------------------------------------------------------- - // check inputs - //-------------------------------------------------------------------------- - - RETURN_IF_NULL_COMMON (NULL) ; - Common->status = CHOLMOD_OK ; - - //-------------------------------------------------------------------------- - // allocate a dense matrix - //-------------------------------------------------------------------------- - - cholmod_dense *X = CHOLMOD(allocate_dense) (nrow, ncol, nrow, xdtype, - Common) ; - RETURN_IF_ERROR ; - - //-------------------------------------------------------------------------- - // get the xtype and dtype - //-------------------------------------------------------------------------- - - int xtype = xdtype & 3 ; // real, complex, or zomplex (not pattern) - int dtype = xdtype & 4 ; // double or single - - //-------------------------------------------------------------------------- - // get the sizes of the entries - //-------------------------------------------------------------------------- - - size_t e = (dtype == CHOLMOD_SINGLE) ? sizeof (float) : sizeof (double) ; - size_t ex = e * ((xtype == CHOLMOD_COMPLEX) ? 2 : 1) ; - size_t ez = e * ((xtype == CHOLMOD_ZOMPLEX) ? 1 : 0) ; - - //-------------------------------------------------------------------------- - // clear the contents - //-------------------------------------------------------------------------- - - if (X->x != NULL) memset (X->x, 0, X->nzmax * ex) ; - if (X->z != NULL) memset (X->z, 0, X->nzmax * ez) ; - - //-------------------------------------------------------------------------- - // return result - //-------------------------------------------------------------------------- - - ASSERT (CHOLMOD(dump_dense) (X, "zeros:X", Common) >= 0) ; - return (X) ; -} - diff --git a/CHOLMOD/Valgrind/Make.inc b/CHOLMOD/Valgrind/Make.inc new file mode 100644 index 0000000000..08bdba2ae2 --- /dev/null +++ b/CHOLMOD/Valgrind/Make.inc @@ -0,0 +1,18 @@ +# ------------------------------------------------------------------------------ +# CHOLMOD/Valgrind/Makefile +# ------------------------------------------------------------------------------ + +# ------------------------------------------------------------------------------ +# CHOLMOD/Valgrind Module. Copyright (C) 2005-2022, Timothy A. Davis. +# All Rights Reserved. +# SPDX-License-Identifier: GPL-2.0+ +# ------------------------------------------------------------------------------ + +# valgrind options +V = valgrind --suppressions=suppress --quiet + +# covall is not used +COVER = + +# no test coverage needed +CF = -O0 -g diff --git a/CHOLMOD/Valgrind/Makefile b/CHOLMOD/Valgrind/Makefile new file mode 100644 index 0000000000..8717d253bf --- /dev/null +++ b/CHOLMOD/Valgrind/Makefile @@ -0,0 +1,43 @@ +# ------------------------------------------------------------------------------ +# CHOLMOD/Valgrind/Makefile +# ------------------------------------------------------------------------------ + +# ------------------------------------------------------------------------------ +# CHOLMOD/Valgrind Module. Copyright (C) 2005-2022, Timothy A. Davis. +# All Rights Reserved. +# SPDX-License-Identifier: GPL-2.0+ +# ------------------------------------------------------------------------------ + +doall: links go + +links: + touch links + ln -s ../Tcov/amdtest.c + ln -s ../Tcov/aug.c + ln -s ../Tcov/camdtest.c + ln -s ../Tcov/cctest.c + ln -s ../Tcov/cm.c + ln -s ../Tcov/cm.h + ln -s ../Tcov/cmread.c + ln -s ../Tcov/ctest.c + ln -s ../Tcov/huge.c + ln -s ../Tcov/leak.c + ln -s ../Tcov/lpdemo.c + ln -s ../Tcov/memory.c + ln -s ../Tcov/null2.c + ln -s ../Tcov/null.c + ln -s ../Tcov/raw_factor.c + ln -s ../Tcov/solve.c + ln -s ../Tcov/test_ops.c + ln -s ../Tcov/unpack.c + ln -s ../Tcov/comments.txt + ln -s ../Tcov/Matrix + +include ../Tcov/Makefile + +dopurge: distclean + - $(RM) amdtest.c aug.c camdtest.c cctest.c cm.c cm.h cmread.c \ + ctest.c huge.c leak.c lpdemo.c memory.c null2.c null.c \ + raw_factor.c solve.c test_ops.c unpack.c comments.txt \ + links Matrix + diff --git a/CHOLMOD/Valgrind/README.txt b/CHOLMOD/Valgrind/README.txt new file mode 100644 index 0000000000..e4d5bca7d0 --- /dev/null +++ b/CHOLMOD/Valgrind/README.txt @@ -0,0 +1,19 @@ +Torture test for CHOLMOD, using valgrind. Requires Linux. +http://www.suitesparse.com + +Type "make" to compile and run CHOLMOMD with valgrind. +Every line of CHOLMOD will be exercised, and its results +checked. The line "All tests passed" should appear in each +output file (*.grind). Valgrind should report no errors, +and no malloc'd blocks should be in use at exit. + +Note that many, many error messages will appear in the +test output itself (tmp/*.out), because all of CHOLMOD's +error handling is checked as well. These errors are +expected. + +To remove all but the source files and output files from +this directory, type "make clean". To remove all but the +files in the original distribution and the symbolic links, +type "make distclean". To remove all but the files in +the original distribution, type "make dopurge". diff --git a/CHOLMOD/Valgrind/gpl.txt b/CHOLMOD/Valgrind/gpl.txt new file mode 100644 index 0000000000..3912109b5c --- /dev/null +++ b/CHOLMOD/Valgrind/gpl.txt @@ -0,0 +1,340 @@ + GNU GENERAL PUBLIC LICENSE + Version 2, June 1991 + + Copyright (C) 1989, 1991 Free Software Foundation, Inc. + 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + Everyone is permitted to copy and distribute verbatim copies + of this license document, but changing it is not allowed. + + Preamble + + The licenses for most software are designed to take away your +freedom to share and change it. By contrast, the GNU General Public +License is intended to guarantee your freedom to share and change free +software--to make sure the software is free for all its users. This +General Public License applies to most of the Free Software +Foundation's software and to any other program whose authors commit to +using it. (Some other Free Software Foundation software is covered by +the GNU Library General Public License instead.) You can apply it to +your programs, too. + + When we speak of free software, we are referring to freedom, not +price. Our General Public Licenses are designed to make sure that you +have the freedom to distribute copies of free software (and charge for +this service if you wish), that you receive source code or can get it +if you want it, that you can change the software or use pieces of it +in new free programs; and that you know you can do these things. + + To protect your rights, we need to make restrictions that forbid +anyone to deny you these rights or to ask you to surrender the rights. +These restrictions translate to certain responsibilities for you if you +distribute copies of the software, or if you modify it. + + For example, if you distribute copies of such a program, whether +gratis or for a fee, you must give the recipients all the rights that +you have. You must make sure that they, too, receive or can get the +source code. And you must show them these terms so they know their +rights. + + We protect your rights with two steps: (1) copyright the software, and +(2) offer you this license which gives you legal permission to copy, +distribute and/or modify the software. + + Also, for each author's protection and ours, we want to make certain +that everyone understands that there is no warranty for this free +software. If the software is modified by someone else and passed on, we +want its recipients to know that what they have is not the original, so +that any problems introduced by others will not reflect on the original +authors' reputations. + + Finally, any free program is threatened constantly by software +patents. We wish to avoid the danger that redistributors of a free +program will individually obtain patent licenses, in effect making the +program proprietary. To prevent this, we have made it clear that any +patent must be licensed for everyone's free use or not licensed at all. + + The precise terms and conditions for copying, distribution and +modification follow. + + GNU GENERAL PUBLIC LICENSE + TERMS AND CONDITIONS FOR COPYING, DISTRIBUTION AND MODIFICATION + + 0. This License applies to any program or other work which contains +a notice placed by the copyright holder saying it may be distributed +under the terms of this General Public License. The "Program", below, +refers to any such program or work, and a "work based on the Program" +means either the Program or any derivative work under copyright law: +that is to say, a work containing the Program or a portion of it, +either verbatim or with modifications and/or translated into another +language. (Hereinafter, translation is included without limitation in +the term "modification".) Each licensee is addressed as "you". + +Activities other than copying, distribution and modification are not +covered by this License; they are outside its scope. The act of +running the Program is not restricted, and the output from the Program +is covered only if its contents constitute a work based on the +Program (independent of having been made by running the Program). +Whether that is true depends on what the Program does. + + 1. You may copy and distribute verbatim copies of the Program's +source code as you receive it, in any medium, provided that you +conspicuously and appropriately publish on each copy an appropriate +copyright notice and disclaimer of warranty; keep intact all the +notices that refer to this License and to the absence of any warranty; +and give any other recipients of the Program a copy of this License +along with the Program. + +You may charge a fee for the physical act of transferring a copy, and +you may at your option offer warranty protection in exchange for a fee. + + 2. You may modify your copy or copies of the Program or any portion +of it, thus forming a work based on the Program, and copy and +distribute such modifications or work under the terms of Section 1 +above, provided that you also meet all of these conditions: + + a) You must cause the modified files to carry prominent notices + stating that you changed the files and the date of any change. + + b) You must cause any work that you distribute or publish, that in + whole or in part contains or is derived from the Program or any + part thereof, to be licensed as a whole at no charge to all third + parties under the terms of this License. + + c) If the modified program normally reads commands interactively + when run, you must cause it, when started running for such + interactive use in the most ordinary way, to print or display an + announcement including an appropriate copyright notice and a + notice that there is no warranty (or else, saying that you provide + a warranty) and that users may redistribute the program under + these conditions, and telling the user how to view a copy of this + License. (Exception: if the Program itself is interactive but + does not normally print such an announcement, your work based on + the Program is not required to print an announcement.) + +These requirements apply to the modified work as a whole. If +identifiable sections of that work are not derived from the Program, +and can be reasonably considered independent and separate works in +themselves, then this License, and its terms, do not apply to those +sections when you distribute them as separate works. But when you +distribute the same sections as part of a whole which is a work based +on the Program, the distribution of the whole must be on the terms of +this License, whose permissions for other licensees extend to the +entire whole, and thus to each and every part regardless of who wrote it. + +Thus, it is not the intent of this section to claim rights or contest +your rights to work written entirely by you; rather, the intent is to +exercise the right to control the distribution of derivative or +collective works based on the Program. + +In addition, mere aggregation of another work not based on the Program +with the Program (or with a work based on the Program) on a volume of +a storage or distribution medium does not bring the other work under +the scope of this License. + + 3. You may copy and distribute the Program (or a work based on it, +under Section 2) in object code or executable form under the terms of +Sections 1 and 2 above provided that you also do one of the following: + + a) Accompany it with the complete corresponding machine-readable + source code, which must be distributed under the terms of Sections + 1 and 2 above on a medium customarily used for software interchange; or, + + b) Accompany it with a written offer, valid for at least three + years, to give any third party, for a charge no more than your + cost of physically performing source distribution, a complete + machine-readable copy of the corresponding source code, to be + distributed under the terms of Sections 1 and 2 above on a medium + customarily used for software interchange; or, + + c) Accompany it with the information you received as to the offer + to distribute corresponding source code. (This alternative is + allowed only for noncommercial distribution and only if you + received the program in object code or executable form with such + an offer, in accord with Subsection b above.) + +The source code for a work means the preferred form of the work for +making modifications to it. For an executable work, complete source +code means all the source code for all modules it contains, plus any +associated interface definition files, plus the scripts used to +control compilation and installation of the executable. However, as a +special exception, the source code distributed need not include +anything that is normally distributed (in either source or binary +form) with the major components (compiler, kernel, and so on) of the +operating system on which the executable runs, unless that component +itself accompanies the executable. + +If distribution of executable or object code is made by offering +access to copy from a designated place, then offering equivalent +access to copy the source code from the same place counts as +distribution of the source code, even though third parties are not +compelled to copy the source along with the object code. + + 4. You may not copy, modify, sublicense, or distribute the Program +except as expressly provided under this License. Any attempt +otherwise to copy, modify, sublicense or distribute the Program is +void, and will automatically terminate your rights under this License. +However, parties who have received copies, or rights, from you under +this License will not have their licenses terminated so long as such +parties remain in full compliance. + + 5. You are not required to accept this License, since you have not +signed it. However, nothing else grants you permission to modify or +distribute the Program or its derivative works. These actions are +prohibited by law if you do not accept this License. Therefore, by +modifying or distributing the Program (or any work based on the +Program), you indicate your acceptance of this License to do so, and +all its terms and conditions for copying, distributing or modifying +the Program or works based on it. + + 6. Each time you redistribute the Program (or any work based on the +Program), the recipient automatically receives a license from the +original licensor to copy, distribute or modify the Program subject to +these terms and conditions. You may not impose any further +restrictions on the recipients' exercise of the rights granted herein. +You are not responsible for enforcing compliance by third parties to +this License. + + 7. If, as a consequence of a court judgment or allegation of patent +infringement or for any other reason (not limited to patent issues), +conditions are imposed on you (whether by court order, agreement or +otherwise) that contradict the conditions of this License, they do not +excuse you from the conditions of this License. If you cannot +distribute so as to satisfy simultaneously your obligations under this +License and any other pertinent obligations, then as a consequence you +may not distribute the Program at all. For example, if a patent +license would not permit royalty-free redistribution of the Program by +all those who receive copies directly or indirectly through you, then +the only way you could satisfy both it and this License would be to +refrain entirely from distribution of the Program. + +If any portion of this section is held invalid or unenforceable under +any particular circumstance, the balance of the section is intended to +apply and the section as a whole is intended to apply in other +circumstances. + +It is not the purpose of this section to induce you to infringe any +patents or other property right claims or to contest validity of any +such claims; this section has the sole purpose of protecting the +integrity of the free software distribution system, which is +implemented by public license practices. Many people have made +generous contributions to the wide range of software distributed +through that system in reliance on consistent application of that +system; it is up to the author/donor to decide if he or she is willing +to distribute software through any other system and a licensee cannot +impose that choice. + +This section is intended to make thoroughly clear what is believed to +be a consequence of the rest of this License. + + 8. If the distribution and/or use of the Program is restricted in +certain countries either by patents or by copyrighted interfaces, the +original copyright holder who places the Program under this License +may add an explicit geographical distribution limitation excluding +those countries, so that distribution is permitted only in or among +countries not thus excluded. In such case, this License incorporates +the limitation as if written in the body of this License. + + 9. The Free Software Foundation may publish revised and/or new versions +of the General Public License from time to time. Such new versions will +be similar in spirit to the present version, but may differ in detail to +address new problems or concerns. + +Each version is given a distinguishing version number. If the Program +specifies a version number of this License which applies to it and "any +later version", you have the option of following the terms and conditions +either of that version or of any later version published by the Free +Software Foundation. If the Program does not specify a version number of +this License, you may choose any version ever published by the Free Software +Foundation. + + 10. If you wish to incorporate parts of the Program into other free +programs whose distribution conditions are different, write to the author +to ask for permission. For software which is copyrighted by the Free +Software Foundation, write to the Free Software Foundation; we sometimes +make exceptions for this. Our decision will be guided by the two goals +of preserving the free status of all derivatives of our free software and +of promoting the sharing and reuse of software generally. + + NO WARRANTY + + 11. BECAUSE THE PROGRAM IS LICENSED FREE OF CHARGE, THERE IS NO WARRANTY +FOR THE PROGRAM, TO THE EXTENT PERMITTED BY APPLICABLE LAW. EXCEPT WHEN +OTHERWISE STATED IN WRITING THE COPYRIGHT HOLDERS AND/OR OTHER PARTIES +PROVIDE THE PROGRAM "AS IS" WITHOUT WARRANTY OF ANY KIND, EITHER EXPRESSED +OR IMPLIED, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF +MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE. THE ENTIRE RISK AS +TO THE QUALITY AND PERFORMANCE OF THE PROGRAM IS WITH YOU. SHOULD THE +PROGRAM PROVE DEFECTIVE, YOU ASSUME THE COST OF ALL NECESSARY SERVICING, +REPAIR OR CORRECTION. + + 12. IN NO EVENT UNLESS REQUIRED BY APPLICABLE LAW OR AGREED TO IN WRITING +WILL ANY COPYRIGHT HOLDER, OR ANY OTHER PARTY WHO MAY MODIFY AND/OR +REDISTRIBUTE THE PROGRAM AS PERMITTED ABOVE, BE LIABLE TO YOU FOR DAMAGES, +INCLUDING ANY GENERAL, SPECIAL, INCIDENTAL OR CONSEQUENTIAL DAMAGES ARISING +OUT OF THE USE OR INABILITY TO USE THE PROGRAM (INCLUDING BUT NOT LIMITED +TO LOSS OF DATA OR DATA BEING RENDERED INACCURATE OR LOSSES SUSTAINED BY +YOU OR THIRD PARTIES OR A FAILURE OF THE PROGRAM TO OPERATE WITH ANY OTHER +PROGRAMS), EVEN IF SUCH HOLDER OR OTHER PARTY HAS BEEN ADVISED OF THE +POSSIBILITY OF SUCH DAMAGES. + + END OF TERMS AND CONDITIONS + + How to Apply These Terms to Your New Programs + + If you develop a new program, and you want it to be of the greatest +possible use to the public, the best way to achieve this is to make it +free software which everyone can redistribute and change under these terms. + + To do so, attach the following notices to the program. It is safest +to attach them to the start of each source file to most effectively +convey the exclusion of warranty; and each file should have at least +the "copyright" line and a pointer to where the full notice is found. + + + Copyright (C) + + This program is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation; either version 2 of the License, or + (at your option) any later version. + + This program is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with this program; if not, write to the Free Software + Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + + +Also add information on how to contact you by electronic and paper mail. + +If the program is interactive, make it output a short notice like this +when it starts in an interactive mode: + + Gnomovision version 69, Copyright (C) year name of author + Gnomovision comes with ABSOLUTELY NO WARRANTY; for details type `show w'. + This is free software, and you are welcome to redistribute it + under certain conditions; type `show c' for details. + +The hypothetical commands `show w' and `show c' should show the appropriate +parts of the General Public License. Of course, the commands you use may +be called something other than `show w' and `show c'; they could even be +mouse-clicks or menu items--whatever suits your program. + +You should also get your employer (if you work as a programmer) or your +school, if any, to sign a "copyright disclaimer" for the program, if +necessary. Here is a sample; alter the names: + + Yoyodyne, Inc., hereby disclaims all copyright interest in the program + `Gnomovision' (which makes passes at compilers) written by James Hacker. + + , 1 April 1989 + Ty Coon, President of Vice + +This General Public License does not permit incorporating your program into +proprietary programs. If your program is a subroutine library, you may +consider it more useful to permit linking proprietary applications with the +library. If this is what you want to do, use the GNU Library General +Public License instead of this License. diff --git a/CHOLMOD/Tcov/suppress b/CHOLMOD/Valgrind/suppress similarity index 100% rename from CHOLMOD/Tcov/suppress rename to CHOLMOD/Valgrind/suppress diff --git a/CHOLMOD/Valgrind/tmp/.gitignore b/CHOLMOD/Valgrind/tmp/.gitignore new file mode 100644 index 0000000000..5e7d2734cf --- /dev/null +++ b/CHOLMOD/Valgrind/tmp/.gitignore @@ -0,0 +1,4 @@ +# Ignore everything in this directory +* +# Except this file +!.gitignore diff --git a/ChangeLog b/ChangeLog index fc3f2bdf53..f0733f5685 100644 --- a/ChangeLog +++ b/ChangeLog @@ -1,10 +1,3 @@ -Oct 23, 2023: version 7.3.0 - - * CHOLMOD 5.0.0: initial support for sparse single precision matries. - CHOLMOD:Core replaced with CHOLMOD:Utility - * updated to require CHOLMOD 5.0.0: - Example 1.4.3, GPUQREngine 3.3.3, KLU 2.2.2, SPQR 4.2.2, UMFPACK 6.2.2 - Oct 7, 2023: version 7.2.1 * GraphBLAS 8.2.1: bug fix to GrB_mxm; incorrect handling of typecasting diff --git a/Example/CMakeLists.txt b/Example/CMakeLists.txt index 60f61fab98..46f8af4efb 100644 --- a/Example/CMakeLists.txt +++ b/Example/CMakeLists.txt @@ -12,10 +12,10 @@ cmake_minimum_required ( VERSION 3.20 ) # cmake inserts the date and version number into Include/my.h: -set ( MY_DATE "Oct 23, 2023" ) +set ( MY_DATE "Oct 16, 2023" ) set ( MY_VERSION_MAJOR 1 ) set ( MY_VERSION_MINOR 4 ) -set ( MY_VERSION_PATCH 3 ) +set ( MY_VERSION_PATCH 2 ) message ( STATUS "Building MY library version: v" ${MY_VERSION_MAJOR}. @@ -61,28 +61,28 @@ project ( my #------------------------------------------------------------------------------- # look for all SuiteSparse packages: -find_package ( SuiteSparse_config 7.3.0 REQUIRED ) +find_package ( SuiteSparse_config 7.2.2 REQUIRED ) find_package ( AMD 3.2.1 REQUIRED ) find_package ( BTF 2.2.1 REQUIRED ) find_package ( CAMD 3.2.1 REQUIRED ) find_package ( CCOLAMD 3.2.1 REQUIRED ) find_package ( COLAMD 3.2.1 REQUIRED ) -find_package ( CHOLMOD 5.0.0 REQUIRED ) +find_package ( CHOLMOD 4.2.2 REQUIRED ) find_package ( CXSparse 4.2.1 REQUIRED ) find_package ( GraphBLAS 8.2.1 ) -find_package ( KLU 2.2.2 REQUIRED ) -find_package ( KLU_CHOLMOD 2.2.2 REQUIRED ) +find_package ( KLU 2.2.1 REQUIRED ) +find_package ( KLU_CHOLMOD 2.2.1 REQUIRED ) find_package ( LDL 3.2.1 REQUIRED ) find_package ( Mongoose 3.2.1 REQUIRED ) find_package ( RBio 4.2.1 REQUIRED ) find_package ( SPEX 2.2.1 REQUIRED ) -find_package ( SPQR 4.2.2 REQUIRED ) -find_package ( UMFPACK 6.2.2 REQUIRED ) +find_package ( SPQR 4.2.1 REQUIRED ) +find_package ( UMFPACK 6.2.1 REQUIRED ) if ( TARGET CUDA::nvrtc ) # CHOLMOD and SPQR have been compiled with CUDA enabled. find_package ( SuiteSparse_GPURuntime 3.2.1 REQUIRED ) - find_package ( GPUQREngine 3.2.2 REQUIRED ) + find_package ( GPUQREngine 3.2.1 REQUIRED ) endif ( ) # look for all external libaries: diff --git a/GPUQREngine/CMakeLists.txt b/GPUQREngine/CMakeLists.txt index bf56f2e3f1..1a592b016c 100644 --- a/GPUQREngine/CMakeLists.txt +++ b/GPUQREngine/CMakeLists.txt @@ -12,10 +12,10 @@ cmake_minimum_required ( VERSION 3.20 ) -set ( GPUQRENGINE_DATE "Oct 23, 2023" ) +set ( GPUQRENGINE_DATE "Sept 18, 2023" ) set ( GPUQRENGINE_VERSION_MAJOR 3 ) set ( GPUQRENGINE_VERSION_MINOR 2 ) -set ( GPUQRENGINE_VERSION_SUB 2 ) +set ( GPUQRENGINE_VERSION_SUB 1 ) message ( STATUS "Building GPUQRENGINE version: v" ${GPUQRENGINE_VERSION_MAJOR}. @@ -54,17 +54,17 @@ endif ( ) #------------------------------------------------------------------------------- # for the library itself -find_package ( SuiteSparse_config 7.3.0 +find_package ( SuiteSparse_config 7.2.0 PATHS ${CMAKE_SOURCE_DIR}/../SuiteSparse_config/build NO_DEFAULT_PATH ) if ( NOT TARGET SuiteSparse::SuiteSparseConfig ) - find_package ( SuiteSparse_config 7.3.0 REQUIRED ) + find_package ( SuiteSparse_config 7.2.0 REQUIRED ) endif ( ) if ( SUITESPARSE_CUDA ) - find_package ( SuiteSparse_GPURuntime 3.2.1 + find_package ( SuiteSparse_GPURuntime 3.2.0 PATHS ${CMAKE_SOURCE_DIR}/../SuiteSparse_GPURuntime/build NO_DEFAULT_PATH ) if ( NOT TARGET SuiteSparse::GPURuntime ) - find_package ( SuiteSparse_GPURuntime 3.2.1 REQUIRED ) + find_package ( SuiteSparse_GPURuntime 3.2.0 REQUIRED ) endif ( ) endif ( ) @@ -73,40 +73,40 @@ set ( DEMO_OK false ) if ( DEMO AND DEMO_OK ) # for the demo only: - find_package ( AMD 3.2.1 + find_package ( AMD 3.2.0 PATHS ${CMAKE_SOURCE_DIR}/../AMD/build NO_DEFAULT_PATH ) if ( NOT TARGET SuiteSparse::AMD ) - find_package ( AMD 3.2.1 ) + find_package ( AMD 3.2.0 ) endif ( ) - find_package ( COLAMD 3.2.1 + find_package ( COLAMD 3.2.0 PATHS ${CMAKE_SOURCE_DIR}/../COLAMD/build NO_DEFAULT_PATH ) if ( NOT TARGET SuiteSparse::COLAMD ) - find_package ( COLAMD 3.2.1 ) + find_package ( COLAMD 3.2.0 ) endif ( ) - find_package ( CAMD 3.2.1 + find_package ( CAMD 3.2.0 PATHS ${CMAKE_SOURCE_DIR}/../CAMD/build NO_DEFAULT_PATH ) if ( NOT TARGET SuiteSparse::CAMD ) - find_package ( CAMD 3.2.1 ) + find_package ( CAMD 3.2.0 ) endif ( ) - find_package ( CCOLAMD 3.2.1 + find_package ( CCOLAMD 3.2.0 PATHS ${CMAKE_SOURCE_DIR}/../CCOLAMD/build NO_DEFAULT_PATH ) if ( NOT TARGET SuiteSparse::CCOLAMD ) - find_package ( CCOLAMD 3.2.1 ) + find_package ( CCOLAMD 3.2.0 ) endif ( ) - find_package ( CHOLMOD 5.0.0 + find_package ( CHOLMOD 4.2.0 PATHS ${CMAKE_SOURCE_DIR}/../CHOLMOD/build NO_DEFAULT_PATH ) if ( NOT TARGET SuiteSparse::CHOLMOD ) - find_package ( CHOLMOD 5.0.0 ) + find_package ( CHOLMOD 4.2.0 ) endif ( ) - find_package ( CHOLMOD_CUDA 5.0.0 + find_package ( CHOLMOD_CUDA 4.2.0 PATHS ${CMAKE_SOURCE_DIR}/../CHOLMOD/build NO_DEFAULT_PATH ) if ( NOT TARGET SuiteSparse::CHOLMOD_CUDA ) - find_package ( CHOLMOD_CUDA 5.0.0 ) + find_package ( CHOLMOD_CUDA 4.2.0 ) endif ( ) endif ( ) diff --git a/GPUQREngine/Doc/ChangeLog b/GPUQREngine/Doc/ChangeLog index d6193cc516..ee328927e8 100644 --- a/GPUQREngine/Doc/ChangeLog +++ b/GPUQREngine/Doc/ChangeLog @@ -1,7 +1,3 @@ -Oct 23, 2023: version 3.2.2 - - * for SuiteSparse 7.3.0: update for CHOLMOD 5.0.0 - Sept 18, 2023: version 3.2.1 * cmake update: add "None" build type, from Antonio Rojas, for Arch Linux diff --git a/GPUQREngine/Include/GPUQREngine.hpp b/GPUQREngine/Include/GPUQREngine.hpp index f35aff022a..b262c93464 100644 --- a/GPUQREngine/Include/GPUQREngine.hpp +++ b/GPUQREngine/Include/GPUQREngine.hpp @@ -12,10 +12,10 @@ #define GPUQRENGINE_HPP // Version information: -#define GPUQRENGINE_DATE "Oct 23, 2023" +#define GPUQRENGINE_DATE "Sept 18, 2023" #define GPUQRENGINE_MAIN_VERSION 3 #define GPUQRENGINE_SUB_VERSION 2 -#define GPUQRENGINE_SUBSUB_VERSION 2 +#define GPUQRENGINE_SUBSUB_VERSION 1 #define GPUQRENGINE_VER_CODE(main,sub) ((main) * 1000 + (sub)) #define GPUQRENGINE_VERSION \ diff --git a/KLU/CMakeLists.txt b/KLU/CMakeLists.txt index 6b21b87081..345b29f9c7 100644 --- a/KLU/CMakeLists.txt +++ b/KLU/CMakeLists.txt @@ -12,10 +12,10 @@ cmake_minimum_required ( VERSION 3.20 ) -set ( KLU_DATE "Oct 23, 2023" ) +set ( KLU_DATE "Sept 18, 2023" ) set ( KLU_VERSION_MAJOR 2 ) set ( KLU_VERSION_MINOR 2 ) -set ( KLU_VERSION_SUB 2 ) +set ( KLU_VERSION_SUB 1 ) message ( STATUS "Building KLU version: v" ${KLU_VERSION_MAJOR}. @@ -53,51 +53,51 @@ endif ( ) # find library dependencies #------------------------------------------------------------------------------- -find_package ( SuiteSparse_config 7.3.0 +find_package ( SuiteSparse_config 7.2.0 PATHS ${CMAKE_SOURCE_DIR}/../SuiteSparse_config/build NO_DEFAULT_PATH ) if ( NOT TARGET SuiteSparse::SuiteSparseConfig ) - find_package ( SuiteSparse_config 7.3.0 REQUIRED ) + find_package ( SuiteSparse_config 7.2.0 REQUIRED ) endif ( ) -find_package ( BTF 2.2.1 +find_package ( BTF 2.2.0 PATHS ${CMAKE_SOURCE_DIR}/../BTF/build NO_DEFAULT_PATH ) if ( NOT TARGET SuiteSparse::BTF ) - find_package ( BTF 2.2.1 REQUIRED ) + find_package ( BTF 2.2.0 REQUIRED ) endif ( ) -find_package ( COLAMD 3.2.1 +find_package ( COLAMD 3.2.0 PATHS ${CMAKE_SOURCE_DIR}/../COLAMD/build NO_DEFAULT_PATH ) if ( NOT TARGET SuiteSparse::COLAMD ) - find_package ( COLAMD 3.2.1 REQUIRED ) + find_package ( COLAMD 3.2.0 REQUIRED ) endif ( ) -find_package ( AMD 3.2.1 +find_package ( AMD 3.2.0 PATHS ${CMAKE_SOURCE_DIR}/../AMD/build NO_DEFAULT_PATH ) if ( NOT TARGET SuiteSparse::AMD ) - find_package ( AMD 3.2.1 REQUIRED ) + find_package ( AMD 3.2.0 REQUIRED ) endif ( ) option ( NCHOLMOD "ON: do not use CHOLMOD. OFF (default): use CHOLMOD" off ) if ( NOT NCHOLMOD ) # look for CHOLMOD (optional fill-reducing orderings) - find_package ( CHOLMOD 5.0.0 + find_package ( CHOLMOD 4.2.0 PATHS ${CMAKE_SOURCE_DIR}/../CHOLMOD/build NO_DEFAULT_PATH ) if ( NOT TARGET SuiteSparse::CHOLMOD ) - find_package ( CHOLMOD 5.0.0 ) + find_package ( CHOLMOD 4.2.0 ) endif ( ) # look for CHOLMOD's dependencies: AMD and COLAMD are required. CAMD and # CCOLAMD are optional, but must be found if CHOLMOD was built with them. - find_package ( CAMD 3.2.1 + find_package ( CAMD 3.2.0 PATHS ${CMAKE_SOURCE_DIR}/../CAMD/build NO_DEFAULT_PATH ) if ( NOT TARGET SuiteSparse::CAMD ) - find_package ( CAMD 3.2.1 ) + find_package ( CAMD 3.2.0 ) endif ( ) - find_package ( CCOLAMD 3.2.1 + find_package ( CCOLAMD 3.2.0 PATHS ${CMAKE_SOURCE_DIR}/../CCOLAMD/build NO_DEFAULT_PATH ) if ( NOT TARGET SuiteSparse::CCOLAMD ) - find_package ( CCOLAMD 3.2.1 ) + find_package ( CCOLAMD 3.2.0 ) endif ( ) if ( NOT CHOLMOD_FOUND OR NOT AMD_FOUND OR NOT COLAMD_FOUND ) diff --git a/KLU/Doc/ChangeLog b/KLU/Doc/ChangeLog index 2fabbdec20..f7c7aedee6 100644 --- a/KLU/Doc/ChangeLog +++ b/KLU/Doc/ChangeLog @@ -1,7 +1,3 @@ -Oct 23, 2023: version 2.2.2 - - * for SuiteSparse 7.3.0: update for CHOLMOD 5.0.0 - Sept 18, 2023: version 2.2.1 * cmake update: add "None" build type, from Antonio Rojas, for Arch Linux diff --git a/KLU/Doc/KLU_UserGuide.pdf b/KLU/Doc/KLU_UserGuide.pdf index 15384afc15..1d4c9f9256 100644 Binary files a/KLU/Doc/KLU_UserGuide.pdf and b/KLU/Doc/KLU_UserGuide.pdf differ diff --git a/KLU/Doc/klu_version.tex b/KLU/Doc/klu_version.tex index 6263661a97..7501802671 100644 --- a/KLU/Doc/klu_version.tex +++ b/KLU/Doc/klu_version.tex @@ -1,2 +1,2 @@ % version of SuiteSparse/KLU -\date{VERSION 2.2.2, Oct 23, 2023} +\date{VERSION 2.2.1, Sept 18, 2023} diff --git a/KLU/Include/klu.h b/KLU/Include/klu.h index 41c0d1f3e7..d855727f01 100644 --- a/KLU/Include/klu.h +++ b/KLU/Include/klu.h @@ -814,10 +814,10 @@ void *klu_l_realloc (size_t, size_t, size_t, void *, klu_l_common *) ; * #endif */ -#define KLU_DATE "Oct 23, 2023" +#define KLU_DATE "Sept 18, 2023" #define KLU_MAIN_VERSION 2 #define KLU_SUB_VERSION 2 -#define KLU_SUBSUB_VERSION 2 +#define KLU_SUBSUB_VERSION 1 #define KLU_VERSION_CODE(main,sub) ((main) * 1000 + (sub)) #define KLU_VERSION KLU_VERSION_CODE(KLU_MAIN_VERSION,KLU_SUB_VERSION) diff --git a/KLU/User/klu_l_cholmod.c b/KLU/User/klu_l_cholmod.c index 2ab55e3783..8dd765b23c 100644 --- a/KLU/User/klu_l_cholmod.c +++ b/KLU/User/klu_l_cholmod.c @@ -43,6 +43,7 @@ int64_t klu_l_cholmod int64_t *P ; int64_t k ; int symmetric ; + printf ("------------------- KLU User\n") ; klu_l_common km ; klu_l_defaults (&km) ; @@ -64,7 +65,7 @@ int64_t klu_l_cholmod A->nzmax = Ap [n] ; /* with nzmax entries */ A->packed = TRUE ; /* there is no A->nz array */ A->stype = 0 ; /* A is unsymmetric */ - A->itype = CHOLMOD_LONG ; + A->itype = CHOLMOD_INT ; A->xtype = CHOLMOD_PATTERN ; A->dtype = CHOLMOD_DOUBLE ; A->nz = NULL ; diff --git a/LICENSE.txt b/LICENSE.txt index 71525a6806..0e51e9e0c8 100644 --- a/LICENSE.txt +++ b/LICENSE.txt @@ -235,14 +235,14 @@ found in the lists below. Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA -------------------------------------------------------------------------------- - ==> Utility/License.txt <== + ==> Core/License.txt <== -------------------------------------------------------------------------------- - CHOLMOD/Utility Module, Copyright (C) 2023, Timothy A. Davis. - CHOLMOD is also available under other licenses; contact authors for - details. http://suitesparse.com + CHOLMOD/Core Module. Copyright (C) 2005-2022, Univ. of Florida. Author: + Timothy A. Davis. CHOLMOD is also available under other licenses; contact + authors for details. http://suitesparse.com - Note that this license is for the CHOLMOD/Utility module only. + Note that this license is for the CHOLMOD/Core module only. All CHOLMOD modules are licensed separately. @@ -303,9 +303,22 @@ found in the lists below. contains definitions and prototypes: Include/cholmod.h LGPL + Include/cholmod_camd.h part of Partition module + Include/cholmod_check.h part of Check module + Include/cholmod_cholesky.h part of Cholesky module + Include/cholmod_complexity.h LGPL + Include/cholmod_config.h LGPL + Include/cholmod_core.h part of Core module + Include/cholmod_function.h no license; freely usable, no restrictions + Include/cholmod_gpu.h part of GPU module + Include/cholmod_gpu_kernels.h part of GPU module Include/cholmod_internal.h LGPL + Include/cholmod_io64.h LGPL + Include/cholmod_matrixops.h part of MatrixOps module + Include/cholmod_modify.h part of Modify module + Include/cholmod_partition.h part of Partition module + Include/cholmod_supernodal.h part of Supernodal module Include/cholmod_template.h LGPL - Include/cholmod_types.h -------------------------------------------------------------------------------- ==> MATLAB/License.txt <== diff --git a/README.md b/README.md index 65fac5cdd3..1f09b5deea 100644 --- a/README.md +++ b/README.md @@ -2,7 +2,7 @@ SuiteSparse: A Suite of Sparse matrix packages at http://suitesparse.com ----------------------------------------------------------------------------- -Oct 23, 2023, SuiteSparse VERSION 7.3.0 +Oct 15, 2023, SuiteSparse VERSION 7.2.2 SuiteSparse is a set of sparse-matrix-related packages written or co-authored by Tim Davis, available at https://github.com/DrTimothyAldenDavis/SuiteSparse . diff --git a/SPQR/CMakeLists.txt b/SPQR/CMakeLists.txt index abb0fb1ef8..cb88165ba0 100644 --- a/SPQR/CMakeLists.txt +++ b/SPQR/CMakeLists.txt @@ -13,10 +13,10 @@ # cmake 3.22 is required to find the BLAS in SuiteSparsePolicy.cmake cmake_minimum_required ( VERSION 3.22 ) -set ( SPQR_DATE "Oct 23, 2023" ) +set ( SPQR_DATE "Sept 18, 2023" ) set ( SPQR_VERSION_MAJOR 4 ) set ( SPQR_VERSION_MINOR 2 ) -set ( SPQR_VERSION_SUB 2 ) +set ( SPQR_VERSION_SUB 1 ) message ( STATUS "Building SPQR version: v" ${SPQR_VERSION_MAJOR}. @@ -54,63 +54,63 @@ else ( ) find_package ( OpenMP ) endif ( ) -find_package ( SuiteSparse_config 7.3.0 +find_package ( SuiteSparse_config 7.2.0 PATHS ${CMAKE_SOURCE_DIR}/../SuiteSparse_config/build NO_DEFAULT_PATH ) if ( NOT TARGET SuiteSparse::SuiteSparseConfig ) - find_package ( SuiteSparse_config 7.3.0 REQUIRED ) + find_package ( SuiteSparse_config 7.2.0 REQUIRED ) endif ( ) -find_package ( AMD 3.2.1 +find_package ( AMD 3.2.0 PATHS ${CMAKE_SOURCE_DIR}/../AMD/build NO_DEFAULT_PATH ) if ( NOT TARGET SuiteSparse::AMD ) - find_package ( AMD 3.2.1 REQUIRED ) + find_package ( AMD 3.2.0 REQUIRED ) endif ( ) -find_package ( COLAMD 3.2.1 +find_package ( COLAMD 3.2.0 PATHS ${CMAKE_SOURCE_DIR}/../COLAMD/build NO_DEFAULT_PATH ) if ( NOT TARGET SuiteSparse::COLAMD ) - find_package ( COLAMD 3.2.1 REQUIRED ) + find_package ( COLAMD 3.2.0 REQUIRED ) endif ( ) # It would be nice if just checking for CHOLMOD would automatically pull in # the targets for its dependencies. -find_package ( CHOLMOD 5.0.0 +find_package ( CHOLMOD 4.2.0 PATHS ${CMAKE_SOURCE_DIR}/../CHOLMOD/build NO_DEFAULT_PATH ) if ( NOT TARGET SuiteSparse::CHOLMOD ) - find_package ( CHOLMOD 5.0.0 REQUIRED ) + find_package ( CHOLMOD 4.2.0 REQUIRED ) endif ( ) # look for CHOLMOD's dependencies: AMD and COLAMD are required. CAMD and # CCOLAMD are optional, but must be found if CHOLMOD was built with them. -find_package ( CAMD 3.2.1 +find_package ( CAMD 3.2.0 PATHS ${CMAKE_SOURCE_DIR}/../CAMD/build NO_DEFAULT_PATH ) if ( NOT TARGET SuiteSparse::CAMD ) - find_package ( CAMD 3.2.1 ) + find_package ( CAMD 3.2.0 ) endif ( ) -find_package ( CCOLAMD 3.2.1 +find_package ( CCOLAMD 3.2.0 PATHS ${CMAKE_SOURCE_DIR}/../CCOLAMD/build NO_DEFAULT_PATH ) if ( NOT TARGET SuiteSparse::CCOLAMD ) - find_package ( CCOLAMD 3.2.1 ) + find_package ( CCOLAMD 3.2.0 ) endif ( ) if ( SUITESPARSE_CUDA ) - find_package ( SuiteSparse_GPURuntime 3.2.1 + find_package ( SuiteSparse_GPURuntime 3.2.0 PATHS ${CMAKE_SOURCE_DIR}/../SuiteSparse_GPURuntime/build NO_DEFAULT_PATH ) if ( NOT TARGET SuiteSparse::GPURuntime ) - find_package ( SuiteSparse_GPURuntime 3.2.1 REQUIRED ) + find_package ( SuiteSparse_GPURuntime 3.2.0 REQUIRED ) endif ( ) - find_package ( GPUQREngine 3.2.2 + find_package ( GPUQREngine 3.2.0 PATHS ${CMAKE_SOURCE_DIR}/../GPUQREngine/build NO_DEFAULT_PATH ) if ( NOT TARGET SuiteSparse::GPUQREngine ) - find_package ( GPUQREngine 3.2.2 REQUIRED ) + find_package ( GPUQREngine 3.2.0 REQUIRED ) endif ( ) - find_package ( CHOLMOD_CUDA 5.0.0 + find_package ( CHOLMOD_CUDA 4.2.0 PATHS ${CMAKE_SOURCE_DIR}/../CHOLMOD/build NO_DEFAULT_PATH ) if ( NOT TARGET SuiteSparse::CHOLMOD_CUDA ) - find_package ( CHOLMOD_CUDA 5.0.0 REQUIRED ) + find_package ( CHOLMOD_CUDA 4.2.0 REQUIRED ) endif ( ) endif ( ) diff --git a/SPQR/Doc/ChangeLog b/SPQR/Doc/ChangeLog index ae16defb9d..fe55a9fb51 100644 --- a/SPQR/Doc/ChangeLog +++ b/SPQR/Doc/ChangeLog @@ -1,7 +1,3 @@ -Oct 23, 2023: version 4.2.2 - - * for SuiteSparse 7.3.0: update for CHOLMOD 5.0.0 - Sept 18, 2023: version 4.2.1 * cmake update: add "None" build type, from Antonio Rojas, for Arch Linux diff --git a/SPQR/Doc/spqr_user_guide.pdf b/SPQR/Doc/spqr_user_guide.pdf index 7993671475..77727f5ecd 100644 Binary files a/SPQR/Doc/spqr_user_guide.pdf and b/SPQR/Doc/spqr_user_guide.pdf differ diff --git a/SPQR/Doc/spqr_version.tex b/SPQR/Doc/spqr_version.tex index 56b54f9031..63a04a715a 100644 --- a/SPQR/Doc/spqr_version.tex +++ b/SPQR/Doc/spqr_version.tex @@ -1,2 +1,2 @@ % version of SuiteSparse/SPQR -\date{VERSION 4.2.2, Oct 23, 2023} +\date{VERSION 4.2.1, Sept 18, 2023} diff --git a/SPQR/Include/SuiteSparseQR_definitions.h b/SPQR/Include/SuiteSparseQR_definitions.h index 5793d7976b..0dce203a9a 100644 --- a/SPQR/Include/SuiteSparseQR_definitions.h +++ b/SPQR/Include/SuiteSparseQR_definitions.h @@ -62,10 +62,10 @@ #endif */ -#define SPQR_DATE "Oct 23, 2023" +#define SPQR_DATE "Sept 18, 2023" #define SPQR_MAIN_VERSION 4 #define SPQR_SUB_VERSION 2 -#define SPQR_SUBSUB_VERSION 2 +#define SPQR_SUBSUB_VERSION 1 #define SPQR_VER_CODE(main,sub) ((main) * 1000 + (sub)) #define SPQR_VERSION SPQR_VER_CODE(SPQR_MAIN_VERSION,SPQR_SUB_VERSION) diff --git a/SPQR/Include/spqr.hpp b/SPQR/Include/spqr.hpp index e7c454c16a..5b62502d98 100644 --- a/SPQR/Include/spqr.hpp +++ b/SPQR/Include/spqr.hpp @@ -118,6 +118,11 @@ { \ return (result) ; \ } \ + if (cc->dtype != DTYPE) \ + { \ + cc->status = CHOLMOD_INVALID ; \ + return (result) ; \ + } \ } #define RETURN_IF_XTYPE_INVALID(A,result) \ diff --git a/SuiteSparse_config/CMakeLists.txt b/SuiteSparse_config/CMakeLists.txt index 752a7297f9..b7d06a1401 100644 --- a/SuiteSparse_config/CMakeLists.txt +++ b/SuiteSparse_config/CMakeLists.txt @@ -14,10 +14,10 @@ cmake_minimum_required ( VERSION 3.22 ) # version of both SuiteSparse and SuiteSparse_config -set ( SUITESPARSE_DATE "Oct 23, 2023" ) +set ( SUITESPARSE_DATE "Oct 15, 2023" ) set ( SUITESPARSE_VERSION_MAJOR 7 ) -set ( SUITESPARSE_VERSION_MINOR 3 ) -set ( SUITESPARSE_VERSION_SUB 0 ) +set ( SUITESPARSE_VERSION_MINOR 2 ) +set ( SUITESPARSE_VERSION_SUB 2 ) message ( STATUS "Building SuiteSparse_config version: v" ${SUITESPARSE_VERSION_MAJOR}. diff --git a/SuiteSparse_config/SuiteSparse_config.h b/SuiteSparse_config/SuiteSparse_config.h index 780f2bfecb..d255a695ac 100644 --- a/SuiteSparse_config/SuiteSparse_config.h +++ b/SuiteSparse_config/SuiteSparse_config.h @@ -409,10 +409,10 @@ int SuiteSparse_version // returns SUITESPARSE_VERSION #define SUITESPARSE_HAS_VERSION_FUNCTION -#define SUITESPARSE_DATE "Oct 23, 2023" +#define SUITESPARSE_DATE "Oct 15, 2023" #define SUITESPARSE_MAIN_VERSION 7 -#define SUITESPARSE_SUB_VERSION 3 -#define SUITESPARSE_SUBSUB_VERSION 0 +#define SUITESPARSE_SUB_VERSION 2 +#define SUITESPARSE_SUBSUB_VERSION 2 #define SUITESPARSE_VER_CODE(main,sub) ((main) * 1000 + (sub)) #define SUITESPARSE_VERSION \ diff --git a/UMFPACK/CMakeLists.txt b/UMFPACK/CMakeLists.txt index 135d3d04da..56b4432b7b 100644 --- a/UMFPACK/CMakeLists.txt +++ b/UMFPACK/CMakeLists.txt @@ -12,10 +12,10 @@ # cmake 3.22 is required to find the BLAS in SuiteSparse_config cmake_minimum_required ( VERSION 3.22 ) -set ( UMFPACK_DATE "Oct 23, 2023" ) +set ( UMFPACK_DATE "Sept 18, 2023" ) set ( UMFPACK_VERSION_MAJOR 6 ) set ( UMFPACK_VERSION_MINOR 2 ) -set ( UMFPACK_VERSION_SUB 2 ) +set ( UMFPACK_VERSION_SUB 1 ) message ( STATUS "Building UMFPACK version: v" ${UMFPACK_VERSION_MAJOR}. @@ -61,15 +61,15 @@ else ( ) find_package ( OpenMP ) endif ( ) -find_package ( SuiteSparse_config 7.3.0 +find_package ( SuiteSparse_config 7.2.0 PATHS ${CMAKE_SOURCE_DIR}/../SuiteSparse_config/build NO_DEFAULT_PATH ) if ( NOT TARGET SuiteSparse::SuiteSparseConfig ) - find_package ( SuiteSparse_config 7.3.0 REQUIRED ) + find_package ( SuiteSparse_config 7.2.0 REQUIRED ) endif ( ) -find_package ( AMD 3.2.1 +find_package ( AMD 3.2.0 PATHS ${CMAKE_SOURCE_DIR}/../AMD/build NO_DEFAULT_PATH ) if ( NOT TARGET SuiteSparse::AMD ) - find_package ( AMD 3.2.1 REQUIRED ) + find_package ( AMD 3.2.0 REQUIRED ) endif ( ) include ( SuiteSparseBLAS ) # requires cmake 3.22 @@ -77,30 +77,30 @@ option ( NCHOLMOD "ON: do not use CHOLMOD. OFF (default): use CHOLMOD" off ) if ( NOT NCHOLMOD ) # look for CHOLMOD (optional fill-reducing orderings) - find_package ( CHOLMOD 5.0.0 + find_package ( CHOLMOD 4.2.0 PATHS ${CMAKE_SOURCE_DIR}/../CHOLMOD/build NO_DEFAULT_PATH ) if ( NOT TARGET SuiteSparse::CHOLMOD ) - find_package ( CHOLMOD 5.0.0 ) + find_package ( CHOLMOD 4.2.0 ) endif ( ) # look for CHOLMOD's dependencies: AMD and COLAMD are required. CAMD and # CCOLAMD are optional, but must be found if CHOLMOD was built with them. - find_package ( COLAMD 3.2.1 + find_package ( COLAMD 3.2.0 PATHS ${CMAKE_SOURCE_DIR}/../COLAMD/build NO_DEFAULT_PATH ) if ( NOT TARGET SuiteSparse::COLAMD ) - find_package ( COLAMD 3.2.1 ) + find_package ( COLAMD 3.2.0 ) endif ( ) - find_package ( CAMD 3.2.1 + find_package ( CAMD 3.2.0 PATHS ${CMAKE_SOURCE_DIR}/../CAMD/build NO_DEFAULT_PATH ) if ( NOT TARGET SuiteSparse::CAMD ) - find_package ( CAMD 3.2.1 ) + find_package ( CAMD 3.2.0 ) endif ( ) - find_package ( CCOLAMD 3.2.1 + find_package ( CCOLAMD 3.2.0 PATHS ${CMAKE_SOURCE_DIR}/../CCOLAMD/build NO_DEFAULT_PATH ) if ( NOT TARGET SuiteSparse::CCOLAMD ) - find_package ( CCOLAMD 3.2.1 ) + find_package ( CCOLAMD 3.2.0 ) endif ( ) if ( NOT CHOLMOD_FOUND OR NOT AMD_FOUND OR NOT COLAMD_FOUND ) diff --git a/UMFPACK/Doc/ChangeLog b/UMFPACK/Doc/ChangeLog index 6a027a4227..564ddaa09e 100644 --- a/UMFPACK/Doc/ChangeLog +++ b/UMFPACK/Doc/ChangeLog @@ -1,7 +1,3 @@ -Oct 23, 2023: version 6.2.2 - - * for SuiteSparse 7.3.0: update for CHOLMOD 5.0.0 - Sept 18, 2023: version 6.2.1 * cmake update: add "None" build type, from Antonio Rojas, for Arch Linux diff --git a/UMFPACK/Doc/UMFPACK_QuickStart.pdf b/UMFPACK/Doc/UMFPACK_QuickStart.pdf index cf954032f0..0521a0ec04 100644 Binary files a/UMFPACK/Doc/UMFPACK_QuickStart.pdf and b/UMFPACK/Doc/UMFPACK_QuickStart.pdf differ diff --git a/UMFPACK/Doc/UMFPACK_UserGuide.pdf b/UMFPACK/Doc/UMFPACK_UserGuide.pdf index 6d20968f5e..102284ccea 100644 Binary files a/UMFPACK/Doc/UMFPACK_UserGuide.pdf and b/UMFPACK/Doc/UMFPACK_UserGuide.pdf differ diff --git a/UMFPACK/Doc/umfpack_version.tex b/UMFPACK/Doc/umfpack_version.tex index e33c0327a0..14737caa64 100644 --- a/UMFPACK/Doc/umfpack_version.tex +++ b/UMFPACK/Doc/umfpack_version.tex @@ -1,2 +1,2 @@ % version of SuiteSparse/UMFPACK -\date{VERSION 6.2.2, Oct 23, 2023} +\date{VERSION 6.2.1, Sept 18, 2023} diff --git a/UMFPACK/Include/umfpack.h b/UMFPACK/Include/umfpack.h index e8c1c80462..32b784404b 100644 --- a/UMFPACK/Include/umfpack.h +++ b/UMFPACK/Include/umfpack.h @@ -82,10 +82,10 @@ extern "C" { * below. */ -#define UMFPACK_DATE "Oct 23, 2023" +#define UMFPACK_DATE "Sept 18, 2023" #define UMFPACK_MAIN_VERSION 6 #define UMFPACK_SUB_VERSION 2 -#define UMFPACK_SUBSUB_VERSION 2 +#define UMFPACK_SUBSUB_VERSION 1 #define UMFPACK_VER_CODE(main,sub) ((main) * 1000 + (sub)) #define UMFPACK_VER UMFPACK_VER_CODE(UMFPACK_MAIN_VERSION,UMFPACK_SUB_VERSION)