1 
2 /* ----------------------------------------------  */
3 /* Modified file for use with Elmer.               */
4 /* Original copyright and usage information below: */
5 
6 
7 /* ========================================================================== */
8 /* === umf4_f77wrapper ====================================================== */
9 /* ========================================================================== */
10 
11 /* -------------------------------------------------------------------------- */
12 /* UMFPACK Version 4.4, Copyright (c) 2005 by Timothy A. Davis.  CISE Dept,   */
13 /* Univ. of Florida.  All Rights Reserved.  See ../Doc/License for License.   */
14 /* web: http://www.cise.ufl.edu/research/sparse/umfpack                       */
15 /* -------------------------------------------------------------------------- */
16 
17 /* FORTRAN interface for the C-callable UMFPACK library (double / int version
18  * only and double / long versions only).  This is HIGHLY non-portable.  You
19  * will need to modify this depending on how your FORTRAN and C compilers
20  * behave.  This has been tested in Linux, Sun Solaris, SGI IRIX, and IBM AIX,
21  * with various compilers.  It has not been exhaustively tested on all possible
22  * combinations of C and FORTRAN compilers.  The long version works on
23  * Solaris, SGI IRIX, and IBM AIX when the UMFPACK library is compiled in
24  * 64-bit mode.
25  *
26  * Only a subset of UMFPACK's capabilities are provided.  Refer to the UMFPACK
27  * User Guide for details.
28  *
29  * For some C and FORTRAN compilers, the FORTRAN compiler appends a single
30  * underscore ("_") after each routine name.  C doesn't do this, so the
31  * translation is made here.  Other FORTRAN compilers treat underscores
32  * differently.  For example, a FORTRAN call to a_b gets translated to a call
33  * to a_b__ by g77, and to a_b_ by most other FORTRAN compilers.  Thus, the
34  * FORTRAN names here do not use underscores.  The xlf compiler in IBM AIX
35  * doesn't add an underscore.
36  *
37  * The matrix A is passed to UMFPACK in compressed column form, with 0-based
38  * indices.  In FORTRAN, for an m-by-n matrix A with nz entries, the row
39  * indices of the first column (column 1) are in Ai (Ap (1) + 1 ... Ap (2)),
40  * with values in Ax (Ap (1) + 1 ... Ap (2)).  The last column (column n) is
41  * in Ai (Ap (n) + 1 ... Ap (n+1)) and Ax (Ap (n) + 1 ... Ap (n+1)).  The row
42  * indices in Ai are in the range 0 to m-1.  They must be sorted, with no
43  * duplicate entries allowed.  Refer to umfpack_di_triplet_to_col for a more
44  * flexible format for the input matrix.  The following definitions apply
45  * for each of the routines in this file:
46  *
47  *	integer m, n, Ap (n+1), Ai (nz), symbolic, numeric, filenum, status
48  *	double precision Ax (nz), control (20), info (90), x (n), b (n)
49  *
50  * UMFPACK's status is returned in either a status argument, or in info (1).
51  * It is zero if everything is OK, 1 if the matrix is singular (this is a
52  * warning, not an error), and negative if an error occurred.  See umfpack.h
53  * for more details on the contents of the control and info arrays, and the
54  * value of the sys argument.
55  *
56  * For the Numeric and Symbolic handles, it's probably safe to assume that a
57  * FORTRAN integer is sufficient to store a C pointer.  If that doesn't work,
58  * try defining numeric and symbolic as integer arrays of size 2, or as
59  * integer*8, in the FORTRAN routine that calls these wrapper routines.
60  * The latter is required on Solaris, SGI IRIX, and IBM AIX when UMFPACK is
61  * compiled in 64-bit mode.
62  *
63  * If you want to use 64-bit integers, try compiling this file with the -DDLONG
64  * compiler option (via "make fortran64").  First modify your Make/Make.include
65  * and Make/Make.<arch> files to compile UMFPACK in LP64 mode (see the User
66  * Guide for details).  Your FORTRAN code should use integer*8.  See umf4hb64.f
67  * for an example.
68  *
69  * Tested with the following compilers:
70  *	* Solaris with cc and f77 from Sun WorkShop 6 update 1
71  *	    (32-bit and 64-bit modes)
72  *	* SGI Irix with MIPSpro cc and f77 compilers version 7.4
73  *	    (32-bit and 64-bit modes)
74  *	* Linux with GNU gcc and Intel's icc, and GNU g77 and Intel's
75  *	    ifc FORTRAN compiler.  See the comments above about g77 and
76  *	    underscores.  Only supports 32-bit mode.
77  *	* IBM AIX xlc and xlf compilers.
78  *	    (32-bit and 64-bit modes)
79  */
80 
81 #include "../config.h"
82 
83 #ifdef NULL
84 #undef NULL
85 #endif
86 #define NULL 0
87 
88 /* Use no name mangling when ISO_C_BINDING is being used */
89 #ifdef USE_ISO_C_BINDINGS
90 #undef FC_FUNC
91 #define FC_FUNC(ARG1,ARG2) ARG1
92 #undef FC_FUNC_
93 #define FC_FUNC_(ARG1,ARG2) ARG1
94 #endif
95 
96 /* -------------------------------------------------------------------------- */
97 /* integer type: int or long */
98 /* -------------------------------------------------------------------------- */
99 
100 #define Int int
101 #define UMFPACK_defaults	 umfpack_di_defaults
102 #define UMFPACK_free_numeric	 umfpack_di_free_numeric
103 #define UMFPACK_free_symbolic	 umfpack_di_free_symbolic
104 #define UMFPACK_numeric		 umfpack_di_numeric
105 #define UMFPACK_report_control	 umfpack_di_report_control
106 #define UMFPACK_report_info	 umfpack_di_report_info
107 #define UMFPACK_save_numeric	 umfpack_di_save_numeric
108 #define UMFPACK_save_symbolic	 umfpack_di_save_symbolic
109 #define UMFPACK_load_numeric	 umfpack_di_load_numeric
110 #define UMFPACK_load_symbolic	 umfpack_di_load_symbolic
111 #define UMFPACK_scale		 umfpack_di_scale
112 #define UMFPACK_solve		 umfpack_di_solve
113 #define UMFPACK_symbolic	 umfpack_di_symbolic
114 
115 #define UMFPACK_IRSTEP 7
116 
117 
118 /* -------------------------------------------------------------------------- */
119 /* umf4def: set default control parameters */
120 /* -------------------------------------------------------------------------- */
121 
122 /* call umf4def (control) */
123 
FC_FUNC(umf4def,UMF4DEF)124 void STDCALLBULL FC_FUNC(umf4def,UMF4DEF) (double Control[])
125 {
126 #ifdef HAVE_UMFPACK
127     UMFPACK_defaults (Control) ;
128 #endif
129 }
130 
131 
132 /* -------------------------------------------------------------------------- */
133 /* umf4sym: pre-ordering and symbolic factorization */
134 /* -------------------------------------------------------------------------- */
135 
136 /* call umf4sym (m, n, Ap, Ai, Ax, symbolic, control, info) */
137 
FC_FUNC(umf4sym,UMF4SYM)138 void STDCALLBULL FC_FUNC(umf4sym,UMF4SYM) (Int *m, Int *n, Int Ap [ ], Int Ai [ ],
139     double Ax [ ], void **Symbolic,
140     double Control[], double Info[])
141 {
142 #ifdef HAVE_UMFPACK
143     (void) UMFPACK_symbolic (*m, *n, Ap, Ai, Ax, Symbolic, Control, Info) ;
144 #endif
145 }
146 
147 /* -------------------------------------------------------------------------- */
148 /* umf4num: numeric factorization */
149 /* -------------------------------------------------------------------------- */
150 
151 /* call umf4num (Ap, Ai, Ax, symbolic, numeric, control, info) */
152 
FC_FUNC(umf4num,UMF4NUM)153 void STDCALLBULL FC_FUNC(umf4num,UMF4NUM) (Int Ap [ ], Int Ai [ ], double Ax [ ],
154     void **Symbolic, void **Numeric,
155     double Control[], double Info[])
156 {
157 #ifdef HAVE_UMFPACK
158     (void) UMFPACK_numeric (Ap, Ai, Ax, *Symbolic, Numeric, Control, Info);
159 #endif
160 }
161 
162 /* -------------------------------------------------------------------------- */
163 /* umf4solr: solve a linear system with iterative refinement */
164 /* -------------------------------------------------------------------------- */
165 
166 /* call umf4solr (sys, Ap, Ai, Ax, x, b, numeric, control, info) */
167 
FC_FUNC(umf4solr,UMF4SOLR)168 void STDCALLBULL FC_FUNC(umf4solr,UMF4SOLR) (Int *sys, Int Ap [ ], Int Ai [ ], double Ax [ ],
169     double x [ ], double b [ ], void **Numeric,
170     double Control[], double Info[])
171 {
172 #ifdef HAVE_UMFPACK
173     (void) UMFPACK_solve (*sys, Ap, Ai, Ax, x, b, *Numeric, Control, Info) ;
174 #endif
175 }
176 
177 /* -------------------------------------------------------------------------- */
178 /* umf4sol: solve a linear system without iterative refinement */
179 /* -------------------------------------------------------------------------- */
180 
181 /* call umf4sol (sys, x, b, numeric, control, info) */
182 
FC_FUNC(umf4sol,UMF4SOL)183 void STDCALLBULL FC_FUNC(umf4sol,UMF4SOL) (Int *sys, double x [ ], double b [ ], void **Numeric,
184     double Control[], double Info[])
185 {
186 #ifdef HAVE_UMFPACK
187     Control [UMFPACK_IRSTEP] = 0 ;
188     (void) UMFPACK_solve (*sys, (Int *) NULL, (Int *) NULL, (double *) NULL,
189 	x, b, *Numeric, Control, Info) ;
190 #endif
191 }
192 
193 /* -------------------------------------------------------------------------- */
194 /* umf4fnum: free the Numeric object */
195 /* -------------------------------------------------------------------------- */
196 
197 /* call umf4fnum (numeric) */
198 
FC_FUNC(umf4fnum,UMF4FNUM)199 void STDCALLBULL FC_FUNC(umf4fnum,UMF4FNUM) (void **Numeric)
200 {
201 #ifdef HAVE_UMFPACK
202     UMFPACK_free_numeric (Numeric) ;
203 #endif
204 }
205 
206 /* -------------------------------------------------------------------------- */
207 /* umf4fsym: free the Symbolic object */
208 /* -------------------------------------------------------------------------- */
209 
210 /* call umf4fsym (symbolic) */
211 
FC_FUNC(umf4fsym,UMF4FSYM)212 void STDCALLBULL FC_FUNC(umf4fsym,UMF4FSYM) (void **Symbolic)
213 {
214 #ifdef HAVE_UMFPACK
215     UMFPACK_free_symbolic (Symbolic) ;
216 #endif
217 }
218 
219 
220 #undef Int
221 #undef UMFPACK_defaults
222 #undef UMFPACK_free_numeric
223 #undef UMFPACK_free_symbolic
224 #undef UMFPACK_numeric
225 #undef UMFPACK_report_control
226 #undef UMFPACK_report_info
227 #undef UMFPACK_save_numeric
228 #undef UMFPACK_save_symbolic
229 #undef UMFPACK_load_numeric
230 #undef UMFPACK_load_symbolic
231 #undef UMFPACK_scale
232 #undef UMFPACK_solve
233 #undef UMFPACK_symbolic
234 
235 #define Int long
236 #define UMFPACK_defaults	 umfpack_dl_defaults
237 #define UMFPACK_free_numeric	 umfpack_dl_free_numeric
238 #define UMFPACK_free_symbolic	 umfpack_dl_free_symbolic
239 #define UMFPACK_numeric		 umfpack_dl_numeric
240 #define UMFPACK_report_control	 umfpack_dl_report_control
241 #define UMFPACK_report_info	 umfpack_dl_report_info
242 #define UMFPACK_save_numeric	 umfpack_dl_save_numeric
243 #define UMFPACK_save_symbolic	 umfpack_dl_save_symbolic
244 #define UMFPACK_load_numeric	 umfpack_dl_load_numeric
245 #define UMFPACK_load_symbolic	 umfpack_dl_load_symbolic
246 #define UMFPACK_scale		 umfpack_dl_scale
247 #define UMFPACK_solve		 umfpack_dl_solve
248 #define UMFPACK_symbolic	 umfpack_dl_symbolic
249 
250 
251 /* -------------------------------------------------------------------------- */
252 /* umf4def: set default control parameters */
253 /* -------------------------------------------------------------------------- */
254 
255 /* call umf4def (control) */
FC_FUNC_(umf4_l_def,UMF4_L_DEF)256 void STDCALLBULL FC_FUNC_(umf4_l_def,UMF4_L_DEF) (double Control[])
257 {
258 #ifdef HAVE_UMFPACK
259     UMFPACK_defaults (Control) ;
260 #endif
261 }
262 
263 /* -------------------------------------------------------------------------- */
264 /* umf4sym: pre-ordering and symbolic factorization */
265 /* -------------------------------------------------------------------------- */
266 
267 /* call umf4sym (m, n, Ap, Ai, Ax, symbolic, control, info) */
268 
FC_FUNC_(umf4_l_sym,UMF4_L_SYM)269 void STDCALLBULL FC_FUNC_(umf4_l_sym,UMF4_L_SYM) (Int *m, Int *n, Int Ap [ ], Int Ai [ ],
270     double Ax [ ], void **Symbolic,
271     double Control[], double Info[])
272 {
273 #ifdef HAVE_UMFPACK
274     (void) UMFPACK_symbolic (*m, *n, Ap, Ai, Ax, Symbolic, Control, Info) ;
275 #endif
276 }
277 
278 /* -------------------------------------------------------------------------- */
279 /* umf4num: numeric factorization */
280 /* -------------------------------------------------------------------------- */
281 
282 /* call umf4num (Ap, Ai, Ax, symbolic, numeric, control, info) */
283 
FC_FUNC_(umf4_l_num,UMF4_L_NUM)284 void STDCALLBULL FC_FUNC_(umf4_l_num,UMF4_L_NUM) (Int Ap [ ], Int Ai [ ], double Ax [ ],
285     void **Symbolic, void **Numeric,
286     double Control[], double Info[])
287 {
288 #ifdef HAVE_UMFPACK
289     (void) UMFPACK_numeric (Ap, Ai, Ax, *Symbolic, Numeric, Control, Info);
290 #endif
291 }
292 
293 /* -------------------------------------------------------------------------- */
294 /* umf4solr: solve a linear system with iterative refinement */
295 /* -------------------------------------------------------------------------- */
296 
297 /* call umf4solr (sys, Ap, Ai, Ax, x, b, numeric, control, info) */
298 
FC_FUNC_(umf4_l_solr,UMF4_L_SOLR)299 void STDCALLBULL FC_FUNC_(umf4_l_solr,UMF4_L_SOLR) (Int *sys, Int Ap [ ], Int Ai [ ], double Ax [ ],
300     double x [ ], double b [ ], void **Numeric,
301     double Control[], double Info[])
302 {
303 #ifdef HAVE_UMFPACK
304     (void) UMFPACK_solve (*sys, Ap, Ai, Ax, x, b, *Numeric, Control, Info) ;
305 #endif
306 }
307 
308 /* -------------------------------------------------------------------------- */
309 /* umf4sol: solve a linear system without iterative refinement */
310 /* -------------------------------------------------------------------------- */
311 
312 /* call umf4sol (sys, x, b, numeric, control, info) */
FC_FUNC_(umf4_l_sol,UMF4_L_SOL)313 void STDCALLBULL FC_FUNC_(umf4_l_sol,UMF4_L_SOL) (Int *sys, double x [ ], double b [ ], void **Numeric,
314     double Control[], double Info[])
315 {
316 #ifdef HAVE_UMFPACK
317     Control [UMFPACK_IRSTEP] = 0 ;
318     (void) UMFPACK_solve (*sys, (Int *) NULL, (Int *) NULL, (double *) NULL,
319 	x, b, *Numeric, Control, Info) ;
320 #endif
321 }
322 
323 /* -------------------------------------------------------------------------- */
324 /* umf4fnum: free the Numeric object */
325 /* -------------------------------------------------------------------------- */
326 
327 /* call umf4fnum (numeric) */
328 
FC_FUNC_(umf4_l_fnum,UMF4FNUM)329 void STDCALLBULL FC_FUNC_(umf4_l_fnum,UMF4FNUM) (void **Numeric)
330 {
331 #ifdef HAVE_UMFPACK
332     UMFPACK_free_numeric (Numeric) ;
333 #endif
334 }
335 
336 /* -------------------------------------------------------------------------- */
337 /* umf4fsym: free the Symbolic object */
338 /* -------------------------------------------------------------------------- */
339 
340 /* call umf4fsym (symbolic) */
341 
FC_FUNC_(umf4_l_fsym,UMF4FSYM)342 void STDCALLBULL FC_FUNC_(umf4_l_fsym,UMF4FSYM) (void **Symbolic)
343 {
344 #ifdef HAVE_UMFPACK
345     UMFPACK_free_symbolic (Symbolic) ;
346 #endif
347 }
348