1 //------------------------------------------------------------------------------
2 // GB_code_check: print an entry using a type code
3 //------------------------------------------------------------------------------
4 
5 // SuiteSparse:GraphBLAS, Timothy A. Davis, (c) 2017-2021, All Rights Reserved.
6 // SPDX-License-Identifier: Apache-2.0
7 
8 //------------------------------------------------------------------------------
9 
10 // Only prints entries of built-in types; user-defined types can't be printed.
11 
12 // for code development only:
13 // #define GB_DEVELOPER 1
14 
15 #include "GB.h"
16 
17 #define GB_PRINT_INF(x) GBPR ((x < 0) ? "-Inf" : "Inf")
18 
19 #define GB_PRINT_FLOAT(s)                                           \
20 {                                                                   \
21     switch (fpclassify (s))                                         \
22     {                                                               \
23         case FP_NAN:      GBPR ("NaN") ; break ;                    \
24         case FP_INFINITE: GB_PRINT_INF (s) ; break ;                \
25         case FP_ZERO:     GBPR ("0") ; break ;                      \
26         default:          GBPR ("%.6g", (double) s) ;               \
27     }                                                               \
28 }
29 
30 #define GB_PRINT_DOUBLE(d,pr_verbose)                               \
31 {                                                                   \
32     switch (fpclassify (d))                                         \
33     {                                                               \
34         case FP_NAN:      GBPR ("NaN") ; break ;                    \
35         case FP_INFINITE: GB_PRINT_INF (d) ; break ;                \
36         case FP_ZERO:     GBPR ("0") ; break ;                      \
37         default:                                                    \
38             if (pr_verbose)                                         \
39             {                                                       \
40                 /* long format */                                   \
41                 GBPR ("%.15g", d) ;                                 \
42             }                                                       \
43             else                                                    \
44             {                                                       \
45                 /* short format */                                  \
46                 GBPR ("%.6g", d) ;                                  \
47             }                                                       \
48             break ;                                                 \
49     }                                                               \
50 }
51 
52 GB_PUBLIC   // accessed by the MATLAB tests in GraphBLAS/Test only
GB_code_check(const GB_Type_code code,const void * x,int pr,FILE * f)53 GrB_Info GB_code_check          // print an entry using a type code
54 (
55     const GB_Type_code code,    // type code of value to print
56     const void *x,              // entry to print
57     int pr,                     // print level
58     FILE *f                     // file to print to
59 )
60 {
61 
62     ASSERT (code <= GB_UDT_code) ;
63     int64_t i ;
64     uint64_t u ;
65     double d ;
66     float s ;
67     GxB_FC32_t c ;
68     GxB_FC64_t z ;
69     bool pr_verbose = (pr == GxB_SHORT_VERBOSE || pr == GxB_COMPLETE_VERBOSE) ;
70 
71     switch (code)
72     {
73         #if GB_DEVELOPER
74 
75         case GB_BOOL_code:   i = *((bool     *) x) ; GBPR ("bool "    GBd, i) ;
76             break ;
77         case GB_INT8_code:   i = *((int8_t   *) x) ; GBPR ("int8 "    GBd, i) ;
78             break ;
79         case GB_UINT8_code:  u = *((uint8_t  *) x) ; GBPR ("uint8 "   GBu, u) ;
80             break ;
81         case GB_INT16_code:  i = *((int16_t  *) x) ; GBPR ("int16 "   GBd, i) ;
82             break ;
83         case GB_UINT16_code: u = *((uint16_t *) x) ; GBPR ("uint16 "  GBu, u) ;
84             break ;
85         case GB_INT32_code:  i = *((int32_t  *) x) ; GBPR ("int32 "   GBd, i) ;
86             break ;
87         case GB_UINT32_code: u = *((uint32_t *) x) ; GBPR ("uint32 "  GBu, u) ;
88             break ;
89         case GB_INT64_code:  i = *((int64_t  *) x) ; GBPR ("int64 "   GBd, i) ;
90             break ;
91         case GB_UINT64_code: u = *((uint64_t *) x) ; GBPR ("uint64 "  GBu, u) ;
92             break ;
93 
94         case GB_FP32_code:
95             s = *((float *) x) ;
96             GBPR ("float %.6g", (double) s) ;
97             break ;
98 
99         case GB_FP64_code:
100             d = *((double *) x) ;
101             GBPR ("double %.15g", d) ;
102             break ;
103 
104         case GB_FC32_code:
105             c = *((GxB_FC32_t *) x) ;
106             GBPR ("float complex (%.6g, %6.g)",
107                 (double) crealf (c), (double) cimagf (c)) ;
108             break ;
109 
110         case GB_FC64_code:
111             z = *((GxB_FC64_t *) x) ;
112             GBPR ("double complex (%.15g, %.15g)", creal (z), cimag (z)) ;
113             break ;
114 
115         #else
116 
117         case GB_BOOL_code   : i = *((bool     *) x) ; GBPR ("  " GBd, i) ;
118             break ;
119         case GB_INT8_code   : i = *((int8_t   *) x) ; GBPR ("  " GBd, i) ;
120             break ;
121         case GB_UINT8_code  : u = *((uint8_t  *) x) ; GBPR ("  " GBu, u) ;
122             break ;
123         case GB_INT16_code  : i = *((int16_t  *) x) ; GBPR ("  " GBd, i) ;
124             break ;
125         case GB_UINT16_code : u = *((uint16_t *) x) ; GBPR ("  " GBu, u) ;
126             break ;
127         case GB_INT32_code  : i = *((int32_t  *) x) ; GBPR ("  " GBd, i) ;
128             break ;
129         case GB_UINT32_code : u = *((uint32_t *) x) ; GBPR ("  " GBu, u) ;
130             break ;
131         case GB_INT64_code  : i = *((int64_t  *) x) ; GBPR ("  " GBd, i) ;
132             break ;
133         case GB_UINT64_code : u = *((uint64_t *) x) ; GBPR ("  " GBu, u) ;
134             break ;
135 
136         case GB_FP32_code   :
137             s = *((float *) x) ;
138             GBPR ("   ") ;
139             GB_PRINT_FLOAT (s) ;
140             break ;
141 
142         case GB_FP64_code   :
143             d = *((double *) x) ;
144             GBPR ("   ") ;
145             GB_PRINT_DOUBLE (d, pr_verbose) ;
146             break ;
147 
148         case GB_FC32_code   :
149             c = *((GxB_FC32_t *) x) ;
150             GBPR ("   ") ;
151             GB_PRINT_FLOAT (crealf (c)) ;
152             s = cimagf (c) ;
153             if (s < 0)
154             {
155                 GBPR (" - ") ;
156                 GB_PRINT_FLOAT (-s) ;
157             }
158             else
159             {
160                 GBPR (" + ") ;
161                 GB_PRINT_FLOAT (s) ;
162             }
163             GBPR ("i") ;
164             break ;
165 
166         case GB_FC64_code   :
167             z = *((GxB_FC64_t *) x) ;
168             GBPR ("   ") ;
169             GB_PRINT_DOUBLE (creal (z), pr_verbose) ;
170             d = cimag (z) ;
171             if (d < 0)
172             {
173                 GBPR (" - ") ;
174                 GB_PRINT_DOUBLE (-d, pr_verbose) ;
175             }
176             else
177             {
178                 GBPR (" + ") ;
179                 GB_PRINT_DOUBLE (d, pr_verbose) ;
180             }
181             GBPR ("i") ;
182             break ;
183 
184         #endif
185 
186         case GB_UDT_code    :
187             {
188                 GBPR ("[user-defined value]") ;
189                 // FUTURE: GraphBLAS does not have a method for the user to
190                 // register a print function for a user-defined type.
191             }
192             break ;
193         default: ;
194     }
195 
196     return (GrB_SUCCESS) ;
197 }
198 
199