1 #ifndef __CS_DEFS_H__
2 #define __CS_DEFS_H__
3 
4 /*============================================================================
5  * Base macro and typedef definitions for system portability
6  *============================================================================*/
7 
8 /*
9   This file is part of Code_Saturne, a general-purpose CFD tool.
10 
11   Copyright (C) 1998-2021 EDF S.A.
12 
13   This program is free software; you can redistribute it and/or modify it under
14   the terms of the GNU General Public License as published by the Free Software
15   Foundation; either version 2 of the License, or (at your option) any later
16   version.
17 
18   This program is distributed in the hope that it will be useful, but WITHOUT
19   ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS
20   FOR A PARTICULAR PURPOSE.  See the GNU General Public License for more
21   details.
22 
23   You should have received a copy of the GNU General Public License along with
24   this program; if not, write to the Free Software Foundation, Inc., 51 Franklin
25   Street, Fifth Floor, Boston, MA 02110-1301, USA.
26 */
27 
28 /*----------------------------------------------------------------------------*/
29 
30 /*============================================================================
31  * Autoconf-defined macros
32  *============================================================================*/
33 
34 #if defined(HAVE_CONFIG_H)
35 #  include "cs_config.h"
36 #endif
37 
38 /*============================================================================
39  * Internationalization
40  *============================================================================*/
41 
42 #ifdef __cplusplus
43 extern "C" {
44 #if 0
45 } /* Fake brace to force Emacs auto-indentation back to column 0 */
46 #endif
47 #endif /* __cplusplus */
48 
49 #if defined(ENABLE_NLS) && defined(HAVE_GETTEXT)
50 
51 #  include <libintl.h>
52 #  define _(String) dgettext(PACKAGE, String)
53 #  ifdef gettext_noop
54 #    define N_(String) gettext_noop(String)
55 #  else
56 #    define N_(String) String
57 #  endif /* gettext_noop */
58 
59 #else
60 
61 #  define _LIBINTL_H /* Prevent inclusion of <libintl.h> by other files
62                         with incorrect or missing checks;
63                         TODO locate files causing issues to avoid
64                         requiring this workaround */
65 
66 #  define _(String) (String)
67 #  define N_(String) String
68 #  define textdomain(String) (String)
69 #  define gettext(String) (String)
70 #  define dgettext(Domain,String) (String)
71 #  define dcgettext(Domain,String,Type) (String)
72 #  define bindtextdomain(Domain, Directory) (Domain)
73 
74 #endif /* ENABLE_NLS && HAVE_GETTEXT */
75 
76 #ifdef __cplusplus
77 }
78 #endif /* __cplusplus */
79 
80 /*============================================================================
81  * Parallelism
82  *============================================================================*/
83 
84 #if defined(HAVE_MPI) && !defined(CS_IGNORE_MPI)
85 
86 #  include <mpi.h>
87 
88 #  if !defined(MPI_VERSION) /* Defined in up-to-date MPI versions */
89 #    define MPI_VERSION 1
90 #  endif
91 
92 #  if MPI_VERSION == 1
93 #    define MPI_Info       int
94 #    define MPI_INFO_NULL  0
95 #  endif
96 
97 #endif
98 
99 #if defined(HAVE_OPENMP)
100 
101 #  include <omp.h>
102 
103 #if _OPENMP >= 201307     /* simd construct available from OpenMP 4.0 */
104 #undef HAVE_OPENMP_SIMD
105 #define HAVE_OPENMP_SIMD 1
106 #endif
107 
108 #endif
109 
110 /* Do we have accelerator support ? */
111 
112 #if defined(HAVE_CUDA)
113 #define HAVE_ACCEL 1
114 #elif defined(HAVE_OPENMP_TARGET)
115 #define HAVE_ACCEL 1
116 #endif
117 
118 /*============================================================================
119  * C99 Qualifiers
120  *============================================================================*/
121 
122 #ifndef __cplusplus /* C */
123 
124 /* inline provided by cs_config.h if necessary */
125 
126 #if !defined(__STDC_VERSION__)
127 #  define __STDC_VERSION__ 1989
128 #endif
129 
130 /*
131  * Redefinition of "inline" et "restrict" qualifiers incompatible with
132  * some C89 compilers (standard in C99)
133  */
134 
135 #if (__STDC_VERSION__ < 199901L)
136 
137 #  if defined(__GNUC__)
138 #    define inline __inline__
139 #    define restrict __restrict__
140 #  else
141 #    define inline
142 #    define restrict
143 #  endif
144 
145 #endif
146 
147 #else /* C++ */
148 
149 #  ifndef HAVE_RESTRICT /* Must be provided by caller */
150 #    define restrict
151 #  endif
152 
153 #endif /* __cplusplus */
154 
155 /*============================================================================
156  * Definitions that may not always be provided directly by the system
157  *============================================================================*/
158 
159 /*
160  * Obtain definitions such as that of size_t through stddef.h (C99 standard)
161  * if available (preferred method), or through stdlib.h (which defines
162  * malloc() and family and so must define size_t some way) otherwise.
163  */
164 
165 #if HAVE_STDDEF_H
166 #  include <stddef.h>
167 #else
168 #  include <stdlib.h>
169 #endif
170 
171 /*
172  * Usually stdint.h is included by inttypes.h, but only inttypes.h exists
173  * on certain systems, such as Tru64Unix.
174  */
175 
176 #if HAVE_STDINT_H
177 #  include <stdint.h>
178 #elif HAVE_INTTYPES_H
179 #  include <inttypes.h>
180 #endif
181 
182 /*
183  * Obtain the definition of off_t.
184  */
185 
186 #if defined(HAVE_SYS_TYPES_H)
187 #include <sys/types.h>
188 #endif
189 
190 /* C99 _Bool type */
191 
192 #if HAVE_STDBOOL_H
193 #  include <stdbool.h>
194 #else
195 #  ifndef __cplusplus
196 #    ifndef HAVE__BOOL
197 #      define _Bool signed char;
198 #    endif
199 #    define bool _Bool
200 #    define false 0
201 #    define true 1
202 #  else
203 #    define _Bool bool;
204 #  endif
205 #  define __bool_true_false_are_defined 1
206 #endif
207 
208 /* int32_t type */
209 
210 #if !defined(HAVE_INT32_T)
211 #  if (SIZEOF_INT == 4)
212 typedef int int32_t;
213 #  elif (SIZEOF_SHORT == 4)
214 typedef short int32_t;
215 #  else
216 #    error
217 #  endif
218 #endif
219 
220 /* int64_t type */
221 
222 #if !defined(HAVE_INT64_T)
223 #  if (SIZEOF_INT == 8)
224 typedef int int64_t;
225 #  elif (SIZEOF_LONG == 8)
226 typedef long int64_t;
227 #  elif (HAVE_LONG_LONG == 8)  /* SIZEOF_LONG_LONG not generally available */
228 typedef long long int64_t;
229 #  else
230 #    error
231 #  endif
232 #endif
233 
234 /* uint32_t type */
235 
236 #if !defined(HAVE_UINT32_T)
237 #  if (SIZEOF_INT == 4)
238 typedef unsigned uint32_t;
239 #  elif (SIZEOF_SHORT == 4)
240 typedef unsigned short uint32_t;
241 #  else
242 #    error
243 #  endif
244 #endif
245 
246 /* uint64_t type */
247 
248 #if !defined(HAVE_UINT64_T)
249 #  if (SIZEOF_INT == 8)
250 typedef unsigned uint64_t;
251 #  elif (SIZEOF_LONG == 8)
252 typedef unsigned long uint64_t;
253 #  elif (HAVE_LONG_LONG) /* SIZEOF_LONG_LONG not generally available */
254 typedef unsigned long long uint64_t;
255 #  else
256 #    error
257 #  endif
258 #endif
259 
260 /*============================================================================
261  * General types and macros used throughout Code_Saturne
262  *============================================================================*/
263 
264 #ifdef __cplusplus
265 extern "C" {
266 #if 0
267 } /* Fake brace to force Emacs auto-indentation back to column 0 */
268 #endif
269 #endif /* __cplusplus */
270 
271 /*----------------------------------------------------------------------------
272  * Variable value type.
273  *----------------------------------------------------------------------------*/
274 
275 typedef enum {
276 
277   CS_DATATYPE_NULL,      /* empty datatype */
278   CS_CHAR,               /* character values */
279   CS_FLOAT,              /* 4-byte floating point values */
280   CS_DOUBLE,             /* 8-byte floating point values */
281   CS_UINT16,             /* 2-byte unsigned integer values */
282   CS_INT32,              /* 4-byte signed integer values */
283   CS_INT64,              /* 8-byte signed integer values */
284   CS_UINT32,             /* 4-byte unsigned integer values */
285   CS_UINT64              /* 8-byte unsigned integer values */
286 
287 } cs_datatype_t;
288 
289 /*----------------------------------------------------------------------------
290  * Basic types used by Code_Saturne
291  * They may be modified here to better map to a given library, with the
292  * following constraints:
293  *  - cs_lnum_t must be signed
294  *  - cs_gnum_t may be signed or unsigned
295  *----------------------------------------------------------------------------*/
296 
297 /* Global integer index or number */
298 
299 #if defined(HAVE_LONG_GNUM)
300   #if (SIZEOF_LONG == 8)
301     typedef unsigned long       cs_gnum_t;
302   #elif (SIZEOF_LONG_LONG == 8)
303     typedef unsigned long long  cs_gnum_t;
304   #else
305     #error
306   #endif
307 #else
308   typedef unsigned  cs_gnum_t;
309 #endif
310 
311 /* Local integer index or number */
312 
313 #if defined(HAVE_LONG_LNUM)
314   typedef long  cs_lnum_t;
315 #else
316   typedef int   cs_lnum_t;
317 #endif
318 
319 /* Other types */
320 typedef double            cs_coord_t;  /* Real number (coordinate value) */
321 
322 typedef double              cs_real_t;   /* Fortran double precision */
323 typedef char                cs_byte_t;   /* Byte (untyped memory unit) */
324 typedef unsigned short int  cs_flag_t;   /* Flag storing metadata */
325 
326 /* Vector or array block types */
327 
328 typedef cs_lnum_t  cs_lnum_2_t[2];      /* Vector of 2 local numbers */
329 typedef cs_lnum_t  cs_lnum_3_t[3];      /* Vector of 3 local numbers */
330 
331 typedef cs_coord_t cs_coord_3_t[3];         /* Vector of 3 real (coordinate)
332                                                values */
333 
334 typedef cs_real_t  cs_real_2_t[2];          /* Vector of 2 real values */
335 typedef cs_real_t  cs_real_3_t[3];          /* Vector of 3 real values */
336 typedef cs_real_t  cs_real_4_t[4];          /* Vector of 4 real values */
337 typedef cs_real_t  cs_real_6_t[6];          /* Vector of 6 real values
338                                                (for symmetric tensor) */
339 typedef cs_real_t  cs_real_9_t[9];          /* Vector of 9 real values */
340 typedef cs_real_t  cs_real_10_t[10];        /* Vector of 10 real values */
341 
342 typedef cs_real_t  cs_real_33_t[3][3];      /* Matrix of 3x3 real values */
343 typedef cs_real_t  cs_real_66_t[6][6];      /* Matrix of 6x6 real values */
344 typedef cs_real_t  cs_real_99_t[9][9];      /* Matrix of 9x9 real values */
345 
346 typedef cs_real_t  cs_real_333_t[3][3][3];  /* tensor of 3x3x3 real values */
347 
348 typedef cs_real_t  cs_real_34_t[3][4];      /* Matrix of 3x4 real values */
349 
350 typedef cs_real_t  cs_real_63_t[6][3];      /* Matrix of 6x3 real values */
351 
352 typedef cs_real_t  cs_real_69_t[6][9];      /* Matrix of 6x9 real values */
353 
354 typedef cs_real_33_t  cs_real_332_t[2];     /* vector of 2 3x3 matrices
355                                                of real values */
356 typedef cs_real_66_t  cs_real_662_t[2];     /* vector of 2 6x6 matrices
357                                                of real values */
358 
359 typedef struct {
360 
361   double   val;  /* Value */
362   int      id;   /* Id related to value */
363 
364 } cs_double_int_t;
365 
366 /* Vector-valued quantity stored using its measure (i.e. length) and
367    its direction given by a unitary vector */
368 typedef struct {
369 
370   double  meas;
371   double  unitv[3];
372 
373 } cs_nvec3_t;
374 
375 /* Mappings to MPI datatypes */
376 /*---------------------------*/
377 
378 #if defined(HAVE_MPI) && !defined(CS_IGNORE_MPI)
379 
380 #  define CS_MPI_REAL      MPI_DOUBLE      /* If cs_real_t is a double */
381 
382 /* MPI type for cs_gnum_t integer type (depends on configuration) */
383 
384 #  if defined(HAVE_LONG_GNUM)
385 #    if (SIZEOF_LONG == 8)
386 #      define CS_MPI_GNUM     MPI_UNSIGNED_LONG
387 #    elif (SIZEOF_LONG_LONG == 8)
388 #      if defined(MPI_UNSIGNED_LONG_LONG)
389 #        define CS_MPI_GNUM     MPI_UNSIGNED_LONG_LONG
390 #      elif defined(MPI_LONG_LONG)
391 #        define CS_MPI_GNUM     MPI_LONG_LONG
392 #      endif
393 #    endif
394 #    if !defined(CS_MPI_GNUM)
395 #      error
396 #    endif
397 #  else
398 #    define CS_MPI_GNUM       MPI_UNSIGNED
399 #  endif
400 
401 /* MPI type for cs_lnum_t type */
402 
403 #  if defined(HAVE_LONG_LNUM)
404 #    define CS_MPI_LNUM     MPI_LONG
405 #  else
406 #    define CS_MPI_LNUM     MPI_INT
407 #  endif
408 
409 #  define CS_MPI_EFLAG    MPI_UNSIGNED       /* MPI type for cs_mflag_t type */
410 #  define CS_MPI_FLAG     MPI_UNSIGNED_SHORT /* MPI type for cs_flag_t type */
411 #  define CS_MPI_COORD    MPI_DOUBLE         /* MPI type for cs_coord_t type */
412 
413 #endif /* defined(HAVE_MPI) && !defined(CS_IGNORE_MPI) */
414 
415 /* Mappings to Code_Saturne datatypes */
416 /*------------------------------------*/
417 
418 #if defined(HAVE_LONG_GNUM)
419 # define CS_GNUM_TYPE     CS_UINT64
420 #elif (SIZEOF_INT == 8)
421 # define CS_GNUM_TYPE     CS_UINT64
422 #else
423 # define CS_GNUM_TYPE     CS_UINT32
424 #endif
425 
426 #if defined(HAVE_LONG_LNUM)
427 # if (SIZEOF_LONG == 8)
428 #  define CS_LNUM_TYPE     CS_INT64
429 # else
430 #  define CS_LNUM_TYPE     CS_INT32
431 # endif
432 #else
433 # if (SIZEOF_INT == 8)
434 #  define CS_LNUM_TYPE     CS_INT64
435 # else
436 #  define CS_LNUM_TYPE     CS_INT32
437 # endif
438 #endif
439 
440 #if (SIZEOF_INT == 8)
441 # define CS_INT_TYPE      CS_INT64
442 #else
443 # define CS_INT_TYPE      CS_INT32
444 #endif
445 
446 #if (SIZEOF_INT == 8)
447 # define CS_UINT_TYPE     CS_UINT64
448 #else
449 # define CS_UINT_TYPE     CS_UINT32
450 #endif
451 
452 #define CS_FLAG_TYPE      CS_UINT16
453 #define CS_EFLAG_TYPE     CS_UINT_TYPE
454 #define CS_REAL_TYPE      CS_DOUBLE
455 #define CS_COORD_TYPE     CS_DOUBLE
456 
457 /* Minimum size for OpenMP loops
458  *  (will need benchmarking and tuning for various systems)
459  *---------------------------------------------------------*/
460 
461 #define CS_THR_MIN 128
462 
463 /* Cache line size, or multiple thereof */
464 /*--------------------------------------*/
465 
466 #define CS_CL_SIZE 64
467 
468 /*----------------------------------------------------------------------------
469  * Type independent min an max (caution: the argument is evaluated)
470  *----------------------------------------------------------------------------*/
471 
472 #define CS_ABS(a)     ((a) <  0  ? -(a) : (a))  /*!< Absolute value of a */
473 #define CS_MIN(a,b)   ((a) < (b) ?  (a) : (b))  /*!< Minimum of a et b */
474 #define CS_MAX(a,b)   ((a) > (b) ?  (a) : (b))  /*!< Maximum of a et b */
475 
476 /*----------------------------------------------------------------------------
477  * Variable interlace type:
478  * {x1, y1, z1, x2, y2, z2, ...,xn, yn, zn} if interlaced
479  * {x1, x2, ..., xn, y1, y2, ..., yn, z1, z2, ..., zn} if non interlaced
480  *----------------------------------------------------------------------------*/
481 
482 typedef enum {
483 
484   CS_INTERLACE,          /* Variable is interlaced */
485   CS_NO_INTERLACE        /* Variable is not interlaced */
486 
487 } cs_interlace_t;
488 
489 /*----------------------------------------------------------------------------
490  * Macro used to silence "unused argument" warnings.
491  *
492  * This is useful when a function must match a given function pointer
493  * type, but does not use all possible arguments.
494  *----------------------------------------------------------------------------*/
495 
496 #define CS_UNUSED(x) (void)(x)
497 #define CS_NO_WARN_IF_UNUSED(x) (void)(x)
498 
499 /*----------------------------------------------------------------------------
500  * Macros for compilation with a C++ compiler
501  *----------------------------------------------------------------------------*/
502 
503 #undef BEGIN_C_DECLS
504 #undef   END_C_DECLS
505 
506 #if defined(__cplusplus)
507 #  define BEGIN_C_DECLS  extern "C" {
508 #  define   END_C_DECLS  }
509 #else
510 #  define BEGIN_C_DECLS
511 #  define   END_C_DECLS
512 #endif
513 
514 /*----------------------------------------------------------------------------
515  * Macros for Fortran interoperability
516  *----------------------------------------------------------------------------*/
517 
518 /*
519  * Macro for handling of different symbol names (underscored or not,
520  * lowercase or uppercase) between C and Fortran, for link resolution.
521  */
522 
523 #if !defined (__hpux)
524 #define CS_PROCF(x, y) x##_
525 #else
526 #define CS_PROCF(x, y) x
527 #endif
528 
529 /*
530  * Macro used to handle automatic "Fortran string length" arguments
531  * (not used by code_saturne calls, but set by many compilers).
532  * Some compilers may not
533  * support the variable length lists in mixed C/Fortran calls.
534  */
535 
536 #define CS_ARGF_SUPP_CHAINE , ...
537 
538 /*=============================================================================
539  * Global variables
540  *============================================================================*/
541 
542 /* Empty but non-NULL string */
543 
544 extern const char     cs_empty_string[];
545 
546 /* Sizes and names associated with datatypes */
547 
548 extern const size_t   cs_datatype_size[];
549 extern const char    *cs_datatype_name[];
550 
551 /* MPI Datatypes associated with Code_Saturne datatypes */
552 
553 #if defined(HAVE_MPI) && !defined(CS_IGNORE_MPI)
554 
555 extern MPI_Datatype   cs_datatype_to_mpi[];
556 
557 #endif
558 
559 /* Global variables indicating task state */
560 
561 extern int  cs_glob_n_threads;     /* Number of threads */
562 
563 extern int  cs_glob_rank_id;       /* Rank in main MPI communicator */
564 extern int  cs_glob_n_ranks;       /* Size of main MPI communicator */
565 
566 extern int  cs_glob_node_rank_id;  /* Rank on node in main MPI communicator */
567 extern int  cs_glob_node_n_ranks;  /* Number of ranks on node of main
568                                       MPI communicator */
569 
570 #if defined(HAVE_MPI) && !defined(CS_IGNORE_MPI)
571 
572 extern MPI_Comm       cs_glob_mpi_comm;      /* Main MPI intra-communicator */
573 
574 #endif
575 
576 /*=============================================================================
577  * Public functions
578  *============================================================================*/
579 
580 /*----------------------------------------------------------------------------*/
581 /*!
582  * \brief  Given a base index i, return the next index aligned with a size m.
583  *
584  * \param[in]  i   base index
585  * \param[in]  m   block size to align with
586  *
587  * \return aligned index
588  */
589 /*----------------------------------------------------------------------------*/
590 
591 inline static cs_lnum_t
cs_align(cs_lnum_t i,cs_lnum_t m)592 cs_align(cs_lnum_t  i,
593          cs_lnum_t  m)
594 {
595   return ((i > 0) ? ((i-1)/m+1)*m : 0);
596 }
597 
598 /*----------------------------------------------------------------------------*/
599 
600 #ifdef __cplusplus
601 }
602 #endif /* __cplusplus */
603 
604 #endif /* __CS_DEFS_H__ */
605