star-hitran

Load line-by-line data from the HITRAN database
git clone git://git.meso-star.fr/star-hitran.git
Log | Files | Refs | README | LICENSE

shtr.h (9660B)


      1 /* Copyright (C) 2022, 2025, 2026 |Méso|Star> (contact@meso-star.com)
      2  * Copyright (C) 2025, 2026 Université de Lorraine
      3  * Copyright (C) 2022 Centre National de la Recherche Scientifique
      4  * Copyright (C) 2022 Université Paul Sabatier
      5  *
      6  * This program is free software: you can redistribute it and/or modify
      7  * it under the terms of the GNU General Public License as published by
      8  * the Free Software Foundation, either version 3 of the License, or
      9  * (at your option) any later version.
     10  *
     11  * This program is distributed in the hope that it will be useful,
     12  * but WITHOUT ANY WARRANTY; without even the implied warranty of
     13  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
     14  * GNU General Public License for more details.
     15  *
     16  * You should have received a copy of the GNU General Public License
     17  * along with this program. If not, see <http://www.gnu.org/licenses/>. */
     18 
     19 #ifndef SHTR_H
     20 #define SHTR_H
     21 
     22 #include <rsys/rsys.h>
     23 
     24 #include <float.h>
     25 #include <limits.h>
     26 
     27 /* Library symbol management */
     28 #if defined(SHTR_SHARED_BUILD)  /* Build shared library */
     29   #define SHTR_API extern EXPORT_SYM
     30 #elif defined(SHTR_STATIC)  /* Use/build static library */
     31   #define SHTR_API extern LOCAL_SYM
     32 #else
     33   #define SHTR_API extern IMPORT_SYM
     34 #endif
     35 
     36 /* Helper macro that asserts if the invocation of the shtr function `Func'
     37  * returns an error. One should use this macro on shtr function calls for which
     38  * no explicit error checking is performed */
     39 #ifndef NDEBUG
     40   #define SHTR(Func) ASSERT(shtr_ ## Func == RES_OK)
     41 #else
     42   #define SHTR(Func) shtr_ ## Func
     43 #endif
     44 
     45 #define SHTR_MAX_MOLECULES_COUNT 100
     46 #define SHTR_MAX_ISOTOPES_COUNT 10
     47 #define SHTR_DEFAULT_COMPRESSION INT_MAX
     48 
     49 struct shtr_isotope {
     50   double abundance; /* in ]0, 1] */
     51   double Q296K; /* Partition function at Tref = 296K */
     52   double molar_mass; /* In g.mol^-1 */
     53 
     54   /* Local idx of the molecule to which the isotope belongs */
     55   size_t molecule_id_local;
     56 
     57   int gj; /* State independent degeneracy factor */
     58   int id; /* Identifier of the isotope <=> Global index */
     59 };
     60 #define SHTR_ISOTOPE_NULL__ {0,0,0,0,0,-1}
     61 static const struct shtr_isotope SHTR_ISOTOPE_NULL =
     62   SHTR_ISOTOPE_NULL__;
     63 
     64 struct shtr_molecule {
     65   const char* name;
     66   size_t nisotopes; /* Number of isotopes */
     67   const struct shtr_isotope* isotopes;
     68   int id; /* Unique identifier */
     69 };
     70 #define SHTR_MOLECULE_NULL__ {NULL, 0, NULL, -1}
     71 static const struct shtr_molecule SHTR_MOLECULE_NULL =
     72   SHTR_MOLECULE_NULL__;
     73 
     74 #define SHTR_MOLECULE_IS_NULL(Molecule) \
     75   ((Molecule)->id == SHTR_MOLECULE_NULL.id)
     76 
     77 struct shtr_line {
     78   double wavenumber; /* Central wavenumber in vacuum [cm^-1] */
     79   double intensity; /* Reference intensity [cm^-1/(molec.cm^2)] */
     80   double gamma_air; /* Air broadening half-width [cm^-1.atm^-1] */
     81   double gamma_self; /* Self broadening half-width [cm^-1.atm^-1] */
     82   double lower_state_energy; /* [cm^-1] */
     83   double n_air; /* Temperature-dependant exponent */
     84   double delta_air; /* Air-pressure wavenumber shift [cm^-1.atm^-1] */
     85 
     86   int32_t molecule_id;
     87 
     88   /* The value of the following isotopic index is _not_ the value of the
     89    * isotopic index read from the HITRAN file. The original value is in [0, 9]
     90    * with 0 actually meaning 10. Thus, once decoded, the index is located in
     91    * [1, 10]. The next member variable simply stores this index but decremented
     92    * by one in order to make it compatible with C indexing. As a result, it
     93    * can be used directly to index the 'isotopes' array of a 'shtr_molecule'
     94    * data structure loaded from an isotope metadata file */
     95   int32_t isotope_id_local;
     96 };
     97 #define SHTR_LINE_NULL__ {0,0,0,0,0,0,0,-1,-1}
     98 static const struct shtr_line SHTR_LINE_NULL = SHTR_LINE_NULL__;
     99 
    100 static INLINE int
    101 shtr_line_eq(const struct shtr_line* line0, const struct shtr_line* line1)
    102 {
    103   ASSERT(line0 && line1);
    104   return line0->wavenumber == line1->wavenumber
    105       && line0->intensity == line1->intensity
    106       && line0->gamma_air == line1->gamma_air
    107       && line0->gamma_self == line1->gamma_self
    108       && line0->lower_state_energy == line1->lower_state_energy
    109       && line0->n_air == line1->n_air
    110       && line0->delta_air == line1->delta_air
    111       && line0->molecule_id == line1->molecule_id
    112       && line0->isotope_id_local == line1->isotope_id_local;
    113 }
    114 
    115 struct shtr_line_param_info {
    116   double range[2];
    117   double err; /* Encoding error */
    118 };
    119 #define SHTR_LINE_PARAM_INFO_NULL__ {{DBL_MAX,-DBL_MAX}, 0}
    120 static const struct shtr_line_param_info SHTR_LINE_PARAM_INFO_NULL =
    121   SHTR_LINE_PARAM_INFO_NULL__;
    122 
    123 /* Information on a list of lines */
    124 struct shtr_line_list_info {
    125   struct shtr_line_param_info wavenumber;
    126   struct shtr_line_param_info intensity;
    127   struct shtr_line_param_info gamma_air;
    128   struct shtr_line_param_info gamma_self;
    129   struct shtr_line_param_info lower_state_energy;
    130   struct shtr_line_param_info n_air;
    131   struct shtr_line_param_info delta_air;
    132 };
    133 #define SHTR_LINE_LIST_INFO_NULL__ { \
    134   SHTR_LINE_PARAM_INFO_NULL__, \
    135   SHTR_LINE_PARAM_INFO_NULL__, \
    136   SHTR_LINE_PARAM_INFO_NULL__, \
    137   SHTR_LINE_PARAM_INFO_NULL__, \
    138   SHTR_LINE_PARAM_INFO_NULL__, \
    139   SHTR_LINE_PARAM_INFO_NULL__, \
    140   SHTR_LINE_PARAM_INFO_NULL__, \
    141 }
    142 static const struct shtr_line_list_info SHTR_LINE_LIST_INFO_NULL =
    143   SHTR_LINE_LIST_INFO_NULL__;
    144 
    145 /* Forward declarations of opaque data structures */
    146 struct shtr;
    147 struct shtr_isotope_metadata;
    148 struct shtr_line_list;
    149 struct shtr_line_view;
    150 
    151 /*******************************************************************************
    152  * Input arguments for API functions
    153  ******************************************************************************/
    154 struct shtr_create_args {
    155   struct logger* logger; /* May be NULL <=> default logger */
    156   struct mem_allocator* allocator; /* NULL <=> use default allocator */
    157   int verbose; /* Verbosity level */
    158 };
    159 #define SHTR_CREATE_ARGS_DEFAULT__ {NULL, NULL, 0}
    160 static const struct shtr_create_args SHTR_CREATE_ARGS_DEFAULT =
    161   SHTR_CREATE_ARGS_DEFAULT__;
    162 
    163 struct shtr_line_list_load_args {
    164   const char* filename; /* Name of the file to load or of the provided stream */
    165   FILE* file; /* Stream from where data are loaded. NULL <=> load from file */
    166   int compression_level;
    167 };
    168 #define SHTR_LINE_LIST_LOAD_ARGS_NULL__ {NULL, NULL, SHTR_DEFAULT_COMPRESSION}
    169 static const struct shtr_line_list_load_args SHTR_LINE_LIST_LOAD_ARGS_NULL =
    170   SHTR_LINE_LIST_LOAD_ARGS_NULL__;
    171 
    172 BEGIN_DECLS
    173 
    174 /*******************************************************************************
    175  * Device API
    176  ******************************************************************************/
    177 SHTR_API res_T
    178 shtr_create
    179   (const struct shtr_create_args* args,
    180    struct shtr** shtr);
    181 
    182 SHTR_API res_T
    183 shtr_ref_get
    184   (struct shtr* shtr);
    185 
    186 SHTR_API res_T
    187 shtr_ref_put
    188   (struct shtr* shtr);
    189 
    190 /*******************************************************************************
    191  * Isotope metadata API
    192  ******************************************************************************/
    193 SHTR_API res_T
    194 shtr_isotope_metadata_load
    195   (struct shtr* shtr,
    196    const char* path,
    197    struct shtr_isotope_metadata** metadata);
    198 
    199 SHTR_API res_T
    200 shtr_isotope_metadata_load_stream
    201   (struct shtr* shtr,
    202    FILE* stream,
    203    const char* stream_name, /* NULL <=> use default stream name */
    204    struct shtr_isotope_metadata** metadata);
    205 
    206 /* Load the isotope metadata serialized with the "shtr_isotope_metadata_write"
    207  * function */
    208 SHTR_API res_T
    209 shtr_isotope_metadata_create_from_stream
    210   (struct shtr* shtr,
    211    FILE* stream,
    212    struct shtr_isotope_metadata** metadata);
    213 
    214 SHTR_API res_T
    215 shtr_isotope_metadata_ref_get
    216   (struct shtr_isotope_metadata* metadata);
    217 
    218 SHTR_API res_T
    219 shtr_isotope_metadata_ref_put
    220   (struct shtr_isotope_metadata* metadata);
    221 
    222 SHTR_API res_T
    223 shtr_isotope_metadata_get_molecules_count
    224   (const struct shtr_isotope_metadata* metadata,
    225    size_t* nmolecules);
    226 
    227 SHTR_API res_T
    228 shtr_isotope_metadata_get_isotopes_count
    229   (const struct shtr_isotope_metadata* metadata,
    230    size_t* nisotopes);
    231 
    232 SHTR_API res_T
    233 shtr_isotope_metadata_get_molecule
    234   (const struct shtr_isotope_metadata* metadata,
    235    const size_t imolecule, /* Local index of the molecule in [0, molecules_count[ */
    236    struct shtr_molecule* molecule);
    237 
    238 /* `molecule' is set to SHTR_MOLECULE_NULL if `molecule_id' is not found */
    239 SHTR_API res_T
    240 shtr_isotope_metadata_find_molecule
    241   (struct shtr_isotope_metadata* metadata,
    242    const int molecule_id, /* Unique identifier of the molecule <=> Global index */
    243    struct shtr_molecule* molecule);
    244 
    245 SHTR_API res_T
    246 shtr_isotope_metadata_write
    247   (const struct shtr_isotope_metadata* metadata,
    248    FILE* stream);
    249 
    250 /*******************************************************************************
    251  * Lines API
    252  ******************************************************************************/
    253 SHTR_API res_T
    254 shtr_line_list_load
    255   (struct shtr* shtr,
    256    const struct shtr_line_list_load_args* args,
    257    struct shtr_line_list** list);
    258 
    259 /* Load the line list serialized with the "shtr_line_list_write" function */
    260 SHTR_API res_T
    261 shtr_line_list_create_from_stream
    262   (struct shtr* shtr,
    263    FILE* stream,
    264    struct shtr_line_list** list);
    265 
    266 SHTR_API res_T
    267 shtr_line_list_ref_get
    268    (struct shtr_line_list* list);
    269 
    270 SHTR_API res_T
    271 shtr_line_list_ref_put
    272    (struct shtr_line_list* list);
    273 
    274 SHTR_API res_T
    275 shtr_line_list_get_size
    276   (const struct shtr_line_list* list,
    277    size_t* nlines);
    278 
    279 SHTR_API res_T
    280 shtr_line_list_at
    281   (struct shtr_line_list* list,
    282    const size_t i,
    283    struct shtr_line* line);
    284 
    285 SHTR_API res_T
    286 shtr_line_list_write
    287   (const struct shtr_line_list* list,
    288    FILE* stream);
    289 
    290 SHTR_API res_T
    291 shtr_line_list_get_info
    292   (const struct shtr_line_list* list,
    293    struct shtr_line_list_info* info);
    294 
    295 END_DECLS
    296 
    297 #endif /* SHTR_H */