34#include <mf_wrap_config.h>
35#include <telluriccorr.h>
48#define RECIPE_ID "xsh_molecfit_telluric"
49#define RECIPE_AUTHOR "N. Fernando, B. Miszalski"
50#define RECIPE_CONTACT "nuwanthika.fernando@partner.eso.org"
74"Normalize the reduced telluric spectrum by its continuum.";
77"Normalize the reduced telluric 1D spectrum by its continuum to compute the atmosperic telluric correction to feed to xshooter_molecfit_correct.";
124 cpl_recipe *recipe = NULL;
125 cpl_plugin *plugin = NULL;
127 recipe = cpl_calloc(1,
sizeof(*recipe));
128 if ( recipe == NULL ){
132 plugin = &recipe->interface ;
134 cpl_plugin_init(plugin,
137 CPL_PLUGIN_TYPE_RECIPE,
148 cpl_pluginlist_append(list, plugin);
150 return (cpl_error_get_code() != CPL_ERROR_NONE);
166 cpl_recipe *recipe = NULL;
181 assure( plugin != NULL, CPL_ERROR_NULL_INPUT,
"Null plugin");
184 assure( cpl_plugin_get_type(plugin) == CPL_PLUGIN_TYPE_RECIPE,
185 CPL_ERROR_TYPE_MISMATCH,
186 "Plugin is not a recipe");
188 recipe = (cpl_recipe *)plugin;
191 recipe->parameters = cpl_parameterlist_new();
192 assure( recipe->parameters != NULL,
193 CPL_ERROR_ILLEGAL_OUTPUT,
194 "Memory allocation failed!");
200 "COLUMN_WAVE",
"WAVE",
201 "Name of the column in the input that identifies the wavelength. This parameter has effect only for inputs in binary table format."));
205 "COLUMN_FLUX",
"FLUX",
206 "Name of the column in the input that identifies the flux. This parameter has effect only for inputs in binary table format."));
210 "COLUMN_DFLUX",
"ERR",
211 "Name of the column in the input that identifies the flux errors. This parameter has effect only for inputs in binary table format."));
216 "If a list of entries, it specifies the position (in microns) of the nodes to be used to compute the continuum. If a single entry, it specifies the number of equispaced nodes to be calculated."));
221 "Specifies the method to determine the continuum. Valid entries are `spline' (cubic spline), or `poly' (polynomial fit)."));
226 "Degree of polynomium to fit the continuum in the case --method=poly"));
231 "Semi-width of the nodes in pixels."));
234 if ( cpl_error_get_code() != CPL_ERROR_NONE ){
253 cpl_recipe *recipe = NULL;
256 assure( plugin != NULL, CPL_ERROR_NULL_INPUT,
"Null plugin" );
259 assure( cpl_plugin_get_type(plugin) == CPL_PLUGIN_TYPE_RECIPE,
260 CPL_ERROR_TYPE_MISMATCH,
"Plugin is not a recipe");
262 recipe = (cpl_recipe *)plugin;
267 if ( cpl_error_get_code() != CPL_ERROR_NONE ) {
286 cpl_recipe *recipe = NULL;
289 assure( plugin != NULL, CPL_ERROR_NULL_INPUT,
"Null plugin" );
292 assure( cpl_plugin_get_type(plugin) == CPL_PLUGIN_TYPE_RECIPE,
293 CPL_ERROR_TYPE_MISMATCH,
"Plugin is not a recipe");
295 recipe = (cpl_recipe *)plugin;
300 if (cpl_error_get_code() != CPL_ERROR_NONE)
400 cpl_msg_info(cpl_func,
"xsh_molecfit_telluric");
404 cpl_error_code err= CPL_ERROR_NONE;
405 cpl_errorstate initial_errorstate = cpl_errorstate_get();
418 const char* col_wave = cpl_parameter_get_string(cpl_parameterlist_find(parlist,
"COLUMN_WAVE"));
419 const char* col_flux = cpl_parameter_get_string(cpl_parameterlist_find(parlist,
"COLUMN_FLUX"));
420 const char* col_dflux = cpl_parameter_get_string(cpl_parameterlist_find(parlist,
"COLUMN_DFLUX"));
421 const char* nodes = cpl_parameter_get_string(cpl_parameterlist_find(parlist,
"NODES"));
422 const char*
method= cpl_parameter_get_string(cpl_parameterlist_find(parlist,
"METHOD"));
423 int degree_poly = cpl_parameter_get_int(cpl_parameterlist_find(parlist,
"DEGREE"));
424 double half_width = cpl_parameter_get_double(cpl_parameterlist_find(parlist,
"HALF_WIDTH"));
426 cpl_msg_info(cpl_func,
"loaded params");
431 cpl_parameterlist* iframe = cpl_parameterlist_new();
433 cpl_msg_info(cpl_func,
"finished xsh_molecfit_utils_find_input_frame");
435 const char* input_name = cpl_parameter_get_string(cpl_parameterlist_find(iframe,
"INPUTNAME"));
436 const char* arm = cpl_parameter_get_string(cpl_parameterlist_find(iframe,
"ARM"));
438 const char* is_idp = cpl_parameter_get_string(cpl_parameterlist_find(iframe,
"IDP"));
439 const char* fname = cpl_parameter_get_string(cpl_parameterlist_find(iframe,
"INPUTFILENAME"));
442 cpl_boolean USE_ONLY_INPUT_PRIMARY_DATA = CPL_TRUE;
444 if(!strcmp(is_idp,
"TRUE")){
445 USE_ONLY_INPUT_PRIMARY_DATA = CPL_FALSE;
448 cpl_table* table = NULL;
449 cpl_msg_info(cpl_func,
"loading input table %s",fname);
450 table = cpl_table_load(fname,1,0);
451 cpl_msg_info(cpl_func,
"loaded input table");
453 cpl_msg_info(cpl_func,
"loading columns");
457 cpl_array* wave = cpl_table_get_array(table,col_wave,0);
458 cpl_array* flux = cpl_table_get_array(table,col_flux,0);
459 cpl_array* dflux = cpl_table_get_array(table,col_dflux,0);
461 cpl_msg_info(cpl_func,
"loading data");
465 int wn = cpl_array_get_size(wave);
466 double* wave_data = cpl_array_get_data_double(wave);
468 wmax = wave_data[wn-1];
469 cpl_msg_info(cpl_func,
"wmin %.2f wmax %.2f",wmin,wmax);
488 cpl_error_code err = CPL_ERROR_NONE;
489 cpl_boolean USE_ONLY_INPUT_PRIMARY_DATA = CPL_TRUE;
490 if(!strcmp(is_idp,
"TRUE")){
491 USE_ONLY_INPUT_PRIMARY_DATA = CPL_FALSE;
499 if(USE_ONLY_INPUT_PRIMARY_DATA){
504 cpl_msg_info(cpl_func,
"spec_ext: %d",spec_ext);
514 cpl_size nrows = cpl_table_get_nrow(
data->v_ext[spec_ext].spectrum_data);
515 cpl_msg_info(cpl_func,
"nrows: %lld",nrows);
518 const char* FLUX_COLUMN = cpl_parameter_get_string(cpl_parameterlist_find(ilist,MF_PARAMETERS_COLUMN_FLUX));
519 cpl_msg_info(cpl_func,
"flux column: %s",FLUX_COLUMN);
523 double median = cpl_table_get_column_median(
data->v_ext[spec_ext].spectrum_data,FLUX_COLUMN);
524 cpl_msg_info(cpl_func,
"spectrum median: %.4e",median);
527 cpl_parameterlist_append(ilist,cpl_parameter_new_value(MF_PARAMETERS_CONTINUUM_CONST,CPL_TYPE_DOUBLE,NULL,NULL,median));
530 mf_parameters_fitting *fitting = &(parameters->mf_config->parameters->fitting);
531 fitting->fit_continuum.const_val = median;
532 cpl_propertylist_update_double(parameters->pl, MF_PARAMETERS_CONTEX_DEFAULT
" "MF_PARAMETERS_CONTINUUM_CONST, fitting->fit_continuum.const_val);
533 parameters->mf_config->parameters->fitting = *fitting;
541 cpl_msg_info(cpl_func,
"xsh_molecfit_telluric_spec_header_calcs");
543 cpl_msg_info(cpl_func,
"reading in %s",fname);
549 cpl_propertylist* hdr= cpl_propertylist_load(fname, ext);
552 const char* slit_width_kw;
553 if(!strcmp(arm,
"UVB")){
554 slit_width_kw =
"ESO INS OPTI3 NAME";
555 }
else if(!strcmp(arm,
"VIS")){
556 slit_width_kw =
"ESO INS OPTI4 NAME";
557 }
else if(!strcmp(arm,
"NIR")){
558 slit_width_kw =
"ESO INS OPTI5 NAME";
560 cpl_msg_info(cpl_func,
"to read in %s value",slit_width_kw);
561 cpl_property *prop_hval = cpl_propertylist_get_property(hdr, slit_width_kw);
563 const char* hval = cpl_property_get_string(prop_hval);
565 cpl_msg_info(cpl_func,
"SLIT_WIDTH_VALUE: %s (read from %s)",strtok(hval,
"x"),slit_width_kw);
571 cpl_parameterlist_append(ilist,cpl_parameter_new_value(
"SLIT_WIDTH_KEYWORD",CPL_TYPE_STRING,NULL,NULL,
"NONE"));
572 cpl_parameterlist_append(ilist,cpl_parameter_new_value(
"SLIT_WIDTH_VALUE",CPL_TYPE_DOUBLE,NULL,NULL,atof(strtok(hval,
"x"))));
576 const char* WAVELENGTH_FRAME;
577 const char* OBS_ERF_RV_KEY;
579 cpl_property *prop_tu = cpl_propertylist_get_property(hdr,
"TUCD1");
580 cpl_property *prop_ss = cpl_propertylist_get_property(hdr,
"SPECSYS");
581 cpl_property *prop_hb = cpl_propertylist_get_property(hdr,
"ESO QC VRAD BARYCOR");
582 cpl_property *prop_hh = cpl_propertylist_get_property(hdr,
"ESO QC VRAD HELICOR");
588 const char* val = cpl_property_get_string(prop_tu);
589 cpl_msg_info(cpl_func,
"TUCD1 found: %s",val);
590 if(!strcmp(val,
"em.wl;obs.atmos")){
591 WAVELENGTH_FRAME=
"AIR";
592 }
else if(!strcmp(val,
"em.wl")){
593 WAVELENGTH_FRAME=
"VAC";
597 WAVELENGTH_FRAME=
"AIR";
601 const char* val = cpl_property_get_string(prop_ss);
602 cpl_msg_info(cpl_func,
"SPECSYS found: %s",val);
603 if(!strcmp(val,
"TOPOCENT")){
604 OBS_ERF_RV_KEY =
"NONE";
605 }
else if(!strcmp(val,
"BARYCENT")){
606 OBS_ERF_RV_KEY =
"ESO QC VRAD BARYCOR";
607 sprintf(WAVELENGTH_FRAME,
"%s_RV",WAVELENGTH_FRAME);
608 }
else if(!strcmp(val,
"HELIOCENT")){
609 OBS_ERF_RV_KEY =
"ESO QC VRAD HELICOR";
610 sprintf(WAVELENGTH_FRAME,
"%s_RV",WAVELENGTH_FRAME);
614 OBS_ERF_RV_KEY =
"NONE";
625 if(!prop_hb || !prop_hh){
626 OBS_ERF_RV_KEY =
"NONE";
629 if(WAVELENGTH_FRAME){
631 cpl_msg_info(cpl_func,
"WAVELENGTH_FRAME: %s",WAVELENGTH_FRAME);
632 cpl_parameterlist_append(ilist,cpl_parameter_new_value(
"WAVELENGTH_FRAME",CPL_TYPE_STRING,NULL,NULL,WAVELENGTH_FRAME));
636 cpl_msg_info(cpl_func,
"OBS_ERF_RV_KEY: %s",OBS_ERF_RV_KEY);
638 cpl_parameterlist_append(ilist,cpl_parameter_new_value(
"OBS_ERF_RV_KEY",CPL_TYPE_STRING,NULL,NULL,OBS_ERF_RV_KEY));
648 cpl_propertylist_delete(hdr);
652 return CPL_ERROR_NONE;
cpl_error_code xsh_molecfit_telluric_spec_header_calcs(const char *fname, const char *arm, cpl_parameterlist *ilist)
int xsh_molecfit_telluric_create(cpl_plugin *)
Setup the recipe options.
int xsh_molecfit_telluric(cpl_frameset *frameset, const cpl_parameterlist *parlist)
Interpret the command line options and execute the data processing.
int xsh_molecfit_telluric_exec(cpl_plugin *)
Execute the plugin instance given by the interface.
int xsh_molecfit_telluric_destroy(cpl_plugin *)
Destroy what has been created by the 'create' function.
cpl_error_code xsh_molecfit_telluric_spec_data_calcs(mf_wrap_fits *data, const char *is_idp, cpl_parameterlist *ilist, mf_wrap_model_parameter *parameters)
int cpl_plugin_get_info(cpl_pluginlist *list)
Build the list of available plugins, for this module.
#define assure(CONDITION, ERROR_CODE,...)
#define xsh_error_dump(level)
void xsh_free_parameterlist(cpl_parameterlist **p)
Deallocate a parameter list and set the pointer to NULL.
const char * xsh_get_license(void)
Get the pipeline copyright and license.
void xsh_init(void)
Reset library state.
char xsh_molecfit_telluric_description[]
char xsh_molecfit_telluric_description_short[]
cpl_error_code xsh_molecfit_utils_find_input_frame(cpl_frameset *frameset, cpl_parameterlist *iframe)
void xsh_parameters_new_double(cpl_parameterlist *list, const char *recipe_id, const char *name, double value, const char *comment)
void xsh_parameters_new_string(cpl_parameterlist *list, const char *recipe_id, const char *name, const char *value, const char *comment)
void xsh_parameters_new_int(cpl_parameterlist *list, const char *recipe_id, const char *name, int value, const char *comment)