solparser_atmosphere.c (4273B)
1 /* Copyright (C) 2018-2026 |Meso|Star> (contact@meso-star.com) 2 * Copyright (C) 2016-2018 CNRS 3 * 4 * This program is free software: you can redistribute it and/or modify 5 * it under the terms of the GNU General Public License as published by 6 * the Free Software Foundation, either version 3 of the License, or 7 * (at your option) any later version. 8 * 9 * This program is distributed in the hope that it will be useful, 10 * but WITHOUT ANY WARRANTY; without even the implied warranty of 11 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 12 * GNU General Public License for more details. 13 * 14 * You should have received a copy of the GNU General Public License 15 * along with this program. If not, see <http://www.gnu.org/licenses/>. */ 16 17 #define _POSIX_C_SOURCE 200112L /* nextafter support */ 18 19 #include "solparser_c.h" 20 #include <math.h> /* nextafter */ 21 22 /******************************************************************************* 23 * Local function 24 ******************************************************************************/ 25 res_T 26 parse_atmosphere 27 (struct solparser* parser, 28 yaml_document_t* doc, 29 yaml_node_t* atm, 30 struct solparser_atmosphere** out_solatm) 31 { 32 enum { EXTINCTION }; 33 struct solparser_atmosphere* solatm = NULL; 34 int mask = 0; /* Register the parsed attributes */ 35 intptr_t i, n; 36 res_T res = RES_OK; 37 ASSERT(doc && atm && out_solatm); 38 39 if(atm == parser->atmosphere_key) { 40 solatm = &parser->atmosphere; 41 goto exit; 42 } else if(parser->atmosphere_key != 0) { 43 log_err(parser, atm, 44 "an atmosphere is already defined. Previous definition is here %lu:%lu.\n", 45 (unsigned long)parser->atmosphere_key->start_mark.line + 1, 46 (unsigned long)parser->atmosphere_key->start_mark.column + 1); 47 res = RES_BAD_ARG; 48 goto error; 49 } else { 50 solatm = &parser->atmosphere; 51 parser->atmosphere_key = atm; 52 } 53 54 if(atm->type != YAML_MAPPING_NODE) { 55 log_err(parser, atm, "expect a mapping of atmosphere attributes.\n"); 56 res = RES_BAD_ARG; 57 goto error; 58 } 59 60 n = atm->data.mapping.pairs.top - atm->data.mapping.pairs.start; 61 FOR_EACH(i, 0, n) { 62 yaml_node_t* key; 63 yaml_node_t* val; 64 65 key = yaml_document_get_node(doc, atm->data.mapping.pairs.start[i].key); 66 val = yaml_document_get_node(doc, atm->data.mapping.pairs.start[i].value); 67 if(key->type != YAML_SCALAR_NODE) { 68 log_err(parser, key, "expect an atmosphere parameter.\n"); 69 res = RES_BAD_ARG; 70 goto error; 71 } 72 #define SETUP_MASK(Flag, Name) { \ 73 if(mask & BIT(Flag)) { \ 74 log_err(parser, key, \ 75 "the "Name" of the atmosphere is already defined.\n"); \ 76 res = RES_BAD_ARG; \ 77 goto error; \ 78 } \ 79 mask |= BIT(Flag); \ 80 } (void)0 81 if(!strcmp((char*)key->data.scalar.value, "extinction")) { 82 SETUP_MASK(EXTINCTION, "extinction"); 83 res = parse_mtl_data 84 (parser, doc, val, 0, 1, &solatm->extinction); 85 } else { 86 log_err(parser, key, "unknown atmosphere parameter `%s'.\n", 87 key->data.scalar.value); 88 res = RES_BAD_ARG; 89 goto error; 90 } 91 if(res != RES_OK) { 92 log_node(parser, key); 93 goto error; 94 } 95 #undef SETUP_MASK 96 } 97 98 #define CHECK_PARAM(Flag, Name) \ 99 if(!(mask & BIT(Flag))) { \ 100 log_err(parser, atm, "the "Name" of the atmosphere is missing.\n"); \ 101 res = RES_BAD_ARG; \ 102 goto error; \ 103 } (void)0 104 CHECK_PARAM(EXTINCTION, "extinction"); 105 #undef CHECK_PARAM 106 107 exit: 108 *out_solatm = solatm; 109 return res; 110 error: 111 if(solatm) { 112 solparser_atmosphere_clear(solatm); 113 solatm = NULL; 114 parser->atmosphere_key = 0; 115 } 116 solatm = NULL; 117 goto exit; 118 } 119