green-output.c (18337B)
1 /* Copyright (C) 2020-2022, 2024 |Méso|Star> (contact@meso-star.com) 2 * 3 * This program is free software: you can redistribute it and/or modify 4 * it under the terms of the GNU General Public License as published by 5 * the Free Software Foundation, either version 3 of the License, or 6 * (at your option) any later version. 7 * 8 * This program is distributed in the hope that it will be useful, 9 * but WITHOUT ANY WARRANTY; without even the implied warranty of 10 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 11 * GNU General Public License for more details. 12 * 13 * You should have received a copy of the GNU General Public License 14 * along with this program. If not, see <http://www.gnu.org/licenses/>. */ 15 16 #include <rsys/rsys.h> 17 #include <rsys/str.h> 18 #include <rsys/mem_allocator.h> 19 20 #include "green-output.h" 21 #include "green-types.h" 22 #include "green-version.h" 23 24 #include <stdio.h> 25 26 #define CELL(T,Val) \ 27 fprintf(stream, " <td>%" #T "</td>\n", (Val)) 28 29 #define VAR_CELL(Elt, Field) { \ 30 const char* name___ = str_cget(&(green->table[Elt].Field ## _name)); \ 31 if((green->table[Elt]). Field ## _unknown) { \ 32 fprintf(stream, " <td>%s = Unknown</td>\n", name___); \ 33 } else if(green->table[Elt].Field ## _defined \ 34 && green->table[Elt].Field ## _weight > 0) \ 35 { \ 36 fprintf(stream, " <td><u><b>%s = %g</b></u></td>\n", \ 37 name___, green->table[Elt].Field ## _value); \ 38 } else { \ 39 fprintf(stream, " <td>%s = %g</td>\n", \ 40 name___, green->table[Elt].Field ## _value); \ 41 } \ 42 } (void)0 43 44 void 45 print_version 46 (FILE* stream) 47 { 48 ASSERT(stream); 49 fprintf(stream, 50 "Green version %i.%i.%i\n", 51 GREEN_VERSION_MAJOR, GREEN_VERSION_MINOR, GREEN_VERSION_PATCH); 52 } 53 54 void 55 usage(FILE * stream) 56 { 57 58 fprintf(stream, 59 "sgreen [-ehv] [-a arguments] [-g green] [-s summary] [-t threads_count]\n" 60 " [-V verbosity_level]\n"); 61 } 62 63 void 64 green_print_result 65 (struct green* green, 66 const int mode, 67 FILE* out_stream) 68 { 69 size_t i, sz; 70 71 ASSERT(green && out_stream); 72 sz = darray_str_size_get(&green->settings); 73 74 for(i = 0; i < sz; i++) { 75 struct result* result = darray_result_data_get(&green->results) + i; 76 const char* line = str_cget(darray_str_data_get(&green->settings) + i); 77 if(mode & MODE_EXTENTED_RESULTS) 78 fprintf(out_stream, "%g K +/- %g ; %s\n", result->E, result->STD, line); 79 else fprintf(out_stream, "%g %g\n", result->E, result->STD); 80 } 81 } 82 83 void 84 dump_green_info 85 (struct green* green, 86 FILE* stream) 87 { 88 size_t i, local_count; 89 double t = 0; 90 int fst = 1; 91 92 ASSERT(green && stream); 93 ASSERT(green->references_checked); 94 95 /* Output html headers */ 96 fprintf(stream, "<!DOCTYPE html>\n"); 97 fprintf(stream, "<html>\n"); 98 fprintf(stream, "<head>\n"); 99 fprintf(stream, "<title>Green function description</title>\n"); 100 101 fprintf(stream, "<style>\n"); 102 fprintf(stream, " table, th, td{\n"); 103 fprintf(stream, " border: 1px solid black;\n"); 104 fprintf(stream, " border-collapse: collapse;\n"); 105 fprintf(stream, " }\n"); 106 fprintf(stream, " th, td{\n"); 107 fprintf(stream, " padding: 5px \n"); 108 fprintf(stream, " }\n"); 109 fprintf(stream, " td{\n"); 110 fprintf(stream, " text-align: right;\n"); 111 fprintf(stream, " }\n"); 112 fprintf(stream, "</style>\n"); 113 114 fprintf(stream, "</head>\n"); 115 fprintf(stream, "<body>\n"); 116 117 fprintf(stream, "<h1>Green function description</h1>\n"); 118 119 fprintf(stream, "<h2>List of variables</h2>\n"); 120 121 fprintf(stream, "<h3>Variables used in the Green function</h3>\n"); 122 123 fprintf(stream, "<p>These variable names are used in the following formula. " 124 "Using the syntax NAME=value in a settings file, their values are " 125 "modifiable when applying the Green Function. They are listed <u><b>NAME " 126 "= value</b></u> in the tables below.</p>"); 127 128 fst = 1; 129 FOR_EACH(i, 0, green->header.description_count + 1) { 130 struct table_elt* elt = green->table + i; 131 if(elt->imposed_T_defined && elt->imposed_T_weight > 0) { 132 if(!fst) fprintf(stream, ", "); 133 fst = 0; 134 fprintf(stream, "%s", str_cget(&elt->imposed_T_name)); 135 } 136 if(elt->initial_T_defined && elt->initial_T_weight > 0) { 137 if(!fst) fprintf(stream, ", "); 138 fst = 0; 139 fprintf(stream, "%s", str_cget(&elt->initial_T_name)); 140 } 141 if(elt->other_defined && elt->other_weight) { 142 if(!fst) fprintf(stream, ", "); 143 fst = 0; 144 fprintf(stream, "%s", str_cget(&elt->other_name)); 145 } 146 } 147 148 if(green->unused_variables) { 149 fprintf(stream, 150 "<h3>Unused variables in the Green function</h3>\n"); 151 152 fprintf(stream, "<p>These variable names are not used in the following " 153 "formula, just because they where not sampled. As a consequence, " 154 "changing their values in a settings file has no effect on the applied " 155 "Green function results. They are listed NAME = value in the tables " 156 "below.</p>\n"); 157 158 fst = 1; 159 FOR_EACH(i, 0, green->header.description_count + 1) { 160 struct table_elt* elt = green->table + i; 161 if(elt->imposed_T_defined 162 && !elt->imposed_T_unknown && elt->imposed_T_weight == 0) { 163 if(!fst) fprintf(stream, ", "); 164 fst = 0; 165 fprintf(stream, "%s", str_cget(&elt->imposed_T_name)); 166 } 167 if(elt->initial_T_defined 168 && !elt->initial_T_unknown && elt->initial_T_weight == 0) { 169 if(!fst) fprintf(stream, ", "); 170 fst = 0; 171 fprintf(stream, "%s", str_cget(&elt->initial_T_name)); 172 } 173 if(elt->other_defined 174 && !elt->other_unknown && !elt->other_weight) { 175 if(!fst) fprintf(stream, ", "); 176 fst = 0; 177 fprintf(stream, "%s", str_cget(&elt->other_name)); 178 } 179 } 180 } 181 182 if(green->unknown_variables) { 183 fprintf(stream, 184 "<h3>Unknown variables in the Green function</h3>\n"); 185 186 fprintf(stream, "<p>These names are not true variable names because their " 187 "values where defined as <i>unknown</i> in the system, meaning they " 188 "required to be solved. Attempting to change their values in a settings " 189 "file is an error. They are listed NAME = Unknown in the tables below." 190 "</p>\n"); 191 192 fst = 1; 193 FOR_EACH(i, 0, green->header.description_count + 1) { 194 struct table_elt* elt = green->table + i; 195 if(elt->imposed_T_unknown) { 196 if(!fst) fprintf(stream, ", "); 197 fst = 0; 198 fprintf(stream, "%s", str_cget(&elt->imposed_T_name)); 199 } 200 if(elt->initial_T_unknown) { 201 if(!fst) fprintf(stream, ", "); 202 fst = 0; 203 fprintf(stream, "%s", str_cget(&elt->initial_T_name)); 204 } 205 if(elt->other_defined && !elt->other_weight) { 206 if(!fst) fprintf(stream, ", "); 207 fst = 0; 208 fprintf(stream, "%s", str_cget(&elt->other_name)); 209 } 210 } 211 } 212 213 fprintf(stream, "<h2>Formula of the Monte-Carlo estimate</h2>\n"); 214 215 if(green->header.time_range[0] == green->header.time_range[1]) 216 fprintf(stream, "<p>The Monte-Carlo estimate of the Green function of the " 217 "system at t=%g is as follows:</p>\n", 218 green->header.time_range[0]); 219 else 220 fprintf(stream, "<p>The Monte-Carlo estimate of the Green function of the " 221 "system with t in [%g %g] is as follows:</p>\n", 222 SPLIT2(green->header.time_range)); 223 224 /* Print result */ 225 fst = 1; 226 FOR_EACH(i, 0, 1 + green->header.description_count) { 227 if(green->table[i].imposed_T_weight > 0) { 228 double k; 229 CHK(green->table[i].imposed_T_defined 230 && green->table[i].imposed_T_value >= 0); 231 if(fst) fprintf(stream, "<p>E[T] = "); 232 else fprintf(stream, " + "); 233 fst = 0; 234 k = (double)green->table[i].imposed_T_weight 235 / (double)green->header.ok_count; 236 t += k * green->table[i].imposed_T_value; 237 fprintf(stream, "%g * <b>%s</b>", 238 k, str_cget(&green->table[i].imposed_T_name)); 239 } 240 if(green->table[i].initial_T_weight > 0) { 241 double k; 242 CHK(green->table[i].initial_T_defined 243 && green->table[i].initial_T_value >= 0); 244 if(fst) fprintf(stream, "<p>E[T] = "); 245 else fprintf(stream, " + "); 246 fst = 0; 247 k = (double)green->table[i].initial_T_weight 248 / (double)green->header.ok_count; 249 t += k * green->table[i].initial_T_value; 250 fprintf(stream, "%g * <b>%s</b>", 251 k, str_cget(&green->table[i].initial_T_name)); 252 } 253 } 254 ASSERT(!fst); 255 FOR_EACH(i, 0, green->header.description_count) { 256 if(green->table[i].other_weight) { 257 double k; 258 CHK(green->table[i].other_defined); 259 k = (double)green->table[i].other_weight 260 / (double)green->header.ok_count; 261 t += k * green->table[i].other_value; 262 fprintf(stream, " + %g * <b>%s</b>", 263 k, str_cget(&green->table[i].other_name)); 264 } 265 } 266 fprintf(stream, " = %g</p>", t); 267 268 /* Counts table */ 269 fprintf(stream, "<h2>Counts</h2>\n"); 270 fprintf(stream, "<table>\n"); 271 /* fprintf(stream, "<table style=\"width:100%%\">\n"); */ 272 fprintf(stream, "<tr>\n"); 273 fprintf(stream, " <th>Solids</th>\n"); 274 fprintf(stream, " <th>Fluids</th>\n"); 275 fprintf(stream, " <th>T Boundaries</th>\n"); 276 fprintf(stream, " <th>H Boundaries</th>\n"); 277 fprintf(stream, " <th>F Boundaries</th>\n"); 278 fprintf(stream, " <th>Solid-Fluid Connections</th>\n"); 279 fprintf(stream, " <th>Solid-Solid Connections</th>\n"); 280 fprintf(stream, " <th>OK Samples</th>\n"); 281 fprintf(stream, " <th>Failures</th>\n"); 282 fprintf(stream, "</tr>\n"); 283 fprintf(stream, "<tr>\n"); 284 CELL(u, green->header.solid_count); 285 CELL(u, green->header.fluid_count); 286 CELL(u, green->header.tbound_count); 287 CELL(u, green->header.hbound_count); 288 CELL(u, green->header.fbound_count); 289 CELL(u, green->header.sfconnect_count); 290 CELL(u, green->header.ssconnect_count); 291 CELL(lu, (long unsigned)green->header.ok_count); 292 CELL(lu, (long unsigned)green->header.failed_count); 293 fprintf(stream, "</tr>\n"); 294 fprintf(stream, "</table>\n"); 295 296 /* Solids table */ 297 local_count = 0; 298 FOR_EACH(i, 0, green->header.description_count) { 299 const struct green_description* desc = green->descriptions + i; 300 const struct green_solid* sl; 301 if(desc->type != GREEN_MAT_SOLID) continue; 302 if(!local_count) { 303 fprintf(stream, "<h2>Solids</h2>\n"); 304 fprintf(stream, "<table>\n"); 305 fprintf(stream, "<tr>\n"); 306 fprintf(stream, " <th>Name</th>\n"); 307 fprintf(stream, " <th>Conductivity</th>\n"); 308 fprintf(stream, " <th>Volumic mass</th>\n"); 309 fprintf(stream, " <th>Calorific capacity</th>\n"); 310 fprintf(stream, " <th>Volumic Power</th>\n"); 311 fprintf(stream, " <th>Imposed temperature</th>\n"); 312 fprintf(stream, " <th>Initial temperature</th>\n"); 313 fprintf(stream, "</tr>\n"); 314 } 315 sl = &desc->d.solid; 316 fprintf(stream, "<tr>\n"); 317 CELL(s, sl->name); 318 CELL(g, sl->conductivity); 319 CELL(g, sl->volumic_mass); 320 CELL(g, sl->calorific_capacity); 321 VAR_CELL(i, other); 322 VAR_CELL(i, imposed_T); 323 VAR_CELL(i, initial_T); 324 fprintf(stream, "</tr>\n"); 325 local_count++; 326 } 327 if(local_count) fprintf(stream, "</table>\n"); 328 329 /* Fluids table */ 330 local_count = 0; 331 FOR_EACH(i, 0, green->header.description_count) { 332 const struct green_description* desc = green->descriptions + i; 333 const struct green_fluid* fl; 334 if(desc->type != GREEN_MAT_FLUID) continue; 335 if(!local_count) { 336 fprintf(stream, "<h2>Fluids</h2>\n"); 337 fprintf(stream, "<table>\n"); 338 fprintf(stream, "<tr>\n"); 339 fprintf(stream, " <th>Name</th>\n"); 340 fprintf(stream, " <th>Volumic mass</th>\n"); 341 fprintf(stream, " <th>Calorific capacity</th>\n"); 342 fprintf(stream, " <th>Imposed temperature</th>\n"); 343 fprintf(stream, " <th>Initial temperature</th>\n"); 344 fprintf(stream, "</tr>\n"); 345 } 346 fl = &desc->d.fluid; 347 fprintf(stream, "<tr>\n"); 348 CELL(s, fl->name); 349 CELL(g, fl->volumic_mass); 350 CELL(g, fl->calorific_capacity); 351 VAR_CELL(i, imposed_T); 352 VAR_CELL(i, initial_T); 353 fprintf(stream, "</tr>\n"); 354 local_count++; 355 } 356 if(local_count) fprintf(stream, "</table>\n"); 357 358 /* T boundaries tables */ 359 local_count = 0; 360 FOR_EACH(i, 0, green->header.description_count) { 361 const struct green_description* desc = green->descriptions + i; 362 const struct green_t_boundary* bd; 363 if(desc->type != GREEN_BOUND_T) continue; 364 if(!local_count) { 365 fprintf(stream, "<h2>T boundaries for solids</h2>\n"); 366 fprintf(stream, "<table>\n"); 367 fprintf(stream, "<tr>\n"); 368 fprintf(stream, " <th>Name</th>\n"); 369 fprintf(stream, " <th>Temperature</th>\n"); 370 fprintf(stream, "</tr>\n"); 371 } 372 bd = &desc->d.t_boundary; 373 fprintf(stream, "<tr>\n"); 374 CELL(s, bd->name); 375 ASSERT(green->table[i].imposed_T_defined); 376 VAR_CELL(i, imposed_T); 377 fprintf(stream, "</tr>\n"); 378 local_count++; 379 } 380 if(local_count) fprintf(stream, "</table>\n"); 381 382 /* H boundaries tables */ 383 local_count = 0; 384 FOR_EACH(i, 0, green->header.description_count) { 385 const struct green_description* desc = green->descriptions + i; 386 const struct green_h_boundary* bd; 387 if(desc->type != GREEN_BOUND_H) continue; 388 if(!local_count) { 389 fprintf(stream, "<h2>H boundaries for solids</h2>\n"); 390 fprintf(stream, "<table>\n"); 391 fprintf(stream, "<tr>\n"); 392 fprintf(stream, " <th>Name</th>\n"); 393 fprintf(stream, " <th>Emissivity</th>\n"); 394 fprintf(stream, " <th>Specular Fraction</th>\n"); 395 fprintf(stream, " <th>Convection coefficient</th>\n"); 396 fprintf(stream, " <th>Temperature</th>\n"); 397 fprintf(stream, "</tr>\n"); 398 } 399 bd = &desc->d.h_boundary; 400 fprintf(stream, "<tr>\n"); 401 CELL(s, bd->name); 402 CELL(g, bd->emissivity); 403 CELL(g, bd->specular_fraction); 404 CELL(g, bd->convection_coefficient); 405 ASSERT(green->table[i].imposed_T_defined); 406 VAR_CELL(i, imposed_T); 407 fprintf(stream, "</tr>\n"); 408 local_count++; 409 } 410 if(local_count) fprintf(stream, "</table>\n"); 411 412 local_count = 0; 413 FOR_EACH(i, 0, green->header.description_count) { 414 const struct green_description* desc = green->descriptions + i; 415 const struct green_h_boundary* bd; 416 if(desc->type != GREEN_BOUND_H) continue; 417 if(!local_count) { 418 fprintf(stream, "<h2>H boundaries for fluids</h2>\n"); 419 fprintf(stream, "<table>\n"); 420 fprintf(stream, "<tr>\n"); 421 fprintf(stream, " <th>Name</th>\n"); 422 fprintf(stream, " <th>Emissivity</th>\n"); 423 fprintf(stream, " <th>Specular Fraction</th>\n"); 424 fprintf(stream, " <th>Convection coefficient</th>\n"); 425 fprintf(stream, " <th>Temperature</th>\n"); 426 fprintf(stream, "</tr>\n"); 427 } 428 bd = &desc->d.h_boundary; 429 fprintf(stream, "<tr>\n"); 430 CELL(s, bd->name); 431 CELL(g, bd->emissivity); 432 CELL(g, bd->specular_fraction); 433 CELL(g, bd->convection_coefficient); 434 ASSERT(green->table[i].imposed_T_defined); 435 VAR_CELL(i, imposed_T); 436 fprintf(stream, "</tr>\n"); 437 local_count++; 438 } 439 if(local_count) fprintf(stream, "</table>\n"); 440 441 /* F boundaries table */ 442 local_count = 0; 443 FOR_EACH(i, 0, green->header.description_count) { 444 const struct green_description* desc = green->descriptions + i; 445 const struct green_f_boundary* bd; 446 if(desc->type != GREEN_BOUND_F) continue; 447 if(!local_count) { 448 fprintf(stream, "<h2>F boundaries for solids</h2>\n"); 449 fprintf(stream, "<table>\n"); 450 fprintf(stream, "<tr>\n"); 451 fprintf(stream, " <th>Name</th>\n"); 452 fprintf(stream, " <th>Flux</th>\n"); 453 fprintf(stream, "</tr>\n"); 454 } 455 bd = &desc->d.f_boundary; 456 fprintf(stream, "<tr>\n"); 457 CELL(s, bd->name); 458 ASSERT(green->table[i].other_defined); 459 VAR_CELL(i, other); 460 fprintf(stream, "</tr>\n"); 461 local_count++; 462 } 463 if(local_count) fprintf(stream, "</table>\n"); 464 465 /* S-F connection table */ 466 local_count = 0; 467 FOR_EACH(i, 0, green->header.description_count) { 468 const struct green_description* desc = green->descriptions + i; 469 const struct green_solid_fluid_connect* sf; 470 if(desc->type != GREEN_SOLID_FLUID_CONNECT) continue; 471 if(!local_count) { 472 fprintf(stream, "<h2>Solid-Fluid connections</h2>\n"); 473 fprintf(stream, "<table>\n"); 474 fprintf(stream, "<tr>\n"); 475 fprintf(stream, " <th>Name</th>\n"); 476 fprintf(stream, " <th>Emissivity</th>\n"); 477 fprintf(stream, " <th>Specular Fraction</th>\n"); 478 fprintf(stream, " <th>Convection coefficient</th>\n"); 479 fprintf(stream, "</tr>\n"); 480 } 481 sf = &desc->d.sf_connect; 482 fprintf(stream, "<tr>\n"); 483 CELL(s, sf->name); 484 CELL(g, sf->emissivity); 485 CELL(g, sf->specular_fraction); 486 CELL(g, sf->convection_coefficient); 487 fprintf(stream, "</tr>\n"); 488 local_count++; 489 } 490 if(local_count) fprintf(stream, "</table>\n"); 491 492 /* S-S connection table */ 493 local_count = 0; 494 FOR_EACH(i, 0, green->header.description_count) { 495 const struct green_description* desc = green->descriptions + i; 496 const struct green_solid_solid_connect* ss; 497 if(desc->type != GREEN_SOLID_SOLID_CONNECT) continue; 498 if(!local_count) { 499 fprintf(stream, "<h2>Solid-Solid connections</h2>\n"); 500 fprintf(stream, "<table>\n"); 501 fprintf(stream, "<tr>\n"); 502 fprintf(stream, " <th>Name</th>\n"); 503 fprintf(stream, " <th>Thermal Contact Resistance</th>\n"); 504 fprintf(stream, "</tr>\n"); 505 } 506 ss = &desc->d.ss_connect; 507 fprintf(stream, "<tr>\n"); 508 CELL(s, ss->name); 509 CELL(g, ss->thermal_contact_resistance); 510 fprintf(stream, "</tr>\n"); 511 local_count++; 512 } 513 if(local_count) fprintf(stream, "</table>\n"); 514 515 /* Radiative temperatures table */ 516 fprintf(stream, "<h2>Radiative temperatures</h2>\n"); 517 fprintf(stream, "<table>\n"); 518 fprintf(stream, "<tr>\n"); 519 fprintf(stream, " <th>Name</th>\n"); 520 fprintf(stream, " <th>Temperature</th>\n"); 521 fprintf(stream, "</tr>\n"); 522 fprintf(stream, "<tr>\n"); 523 CELL(s, "Ambient"); 524 ASSERT(green->table[green->header.description_count].imposed_T_defined); 525 VAR_CELL(green->header.description_count, imposed_T); 526 fprintf(stream, "</tr>\n"); 527 fprintf(stream, "<tr>\n"); 528 CELL(s, "Linearization"); 529 CELL(g, green->header.ambient_radiative_temperature_reference); 530 fprintf(stream, "</tr>\n"); 531 fprintf(stream, "</table>\n"); 532 533 /* Output html footers */ 534 fprintf(stream, "</body>\n"); 535 fprintf(stream, "</html>\n"); 536 } 537 538 #undef CELL 539 #undef VAR_CELL