UVES Pipeline Reference Manual  5.4.0
uves_utl_rcosmic.c
1 /* $Id: uves_utl_rcosmic.c,v 1.3 2012-05-01 06:26:02 amodigli Exp $
2  *
3  * This file is part of the UVES Pipeline
4  * Copyright (C) 2002,2003 European Southern Observatory
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 2 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, write to the Free Software
18  * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
19  */
20 
21 /*
22  * $Author: amodigli $
23  * $Date: 2012-05-01 06:26:02 $
24  * $Revision: 1.3 $
25  * $Name: not supported by cvs2svn $
26  */
27 
28 #ifdef HAVE_CONFIG_H
29 #include <config.h>
30 #endif
31 
32 /*-----------------------------------------------------------------------------
33  Includes
34  ----------------------------------------------------------------------------*/
35 #include <string.h>
36 
37 /* cpl */
38 #include <cpl.h>
39 
40 /* irplib */
41 #include <irplib_utils.h>
42 
43 /*
44 #include <uves_tpl_utils.h>
45 #include <uves_pfits.h>
46 #include <uves_key_names.h>
47 #include <uves_raw_types.h>
48 #include <uves_pro_types.h>
49 #include <uves_functions.h>
50 */
51 
52 #include <uves_dfs.h>
53 #include <uves_msg.h>
54 #include <uves_error.h>
55 #include <uves_utils_wrappers.h>
56 #include <uves_utils.h>
57 
58 /*-----------------------------------------------------------------------------
59  Functions prototypes
60  ----------------------------------------------------------------------------*/
61 
62 static int uves_utl_rcosmic_create(cpl_plugin *) ;
63 static int uves_utl_rcosmic_exec(cpl_plugin *) ;
64 static int uves_utl_rcosmic_destroy(cpl_plugin *) ;
65 static int uves_utl_rcosmic(cpl_parameterlist *, cpl_frameset *) ;
66 
67 /*-----------------------------------------------------------------------------
68  Static variables
69  ----------------------------------------------------------------------------*/
70 
71 static char uves_utl_rcosmic_description[] =
72 "This recipe performs image computation.\n"
73 "The input files are two images\n"
74 "one (containing cosmic ray hits) with associated tag RAW_IMA.\n"
75 "[optional] a bias frame with tag BIAS_BLUE or BIAS_RED.\n"
76 "The output is the image cleaned from CRHs\n"
77 "Information on relevant parameters can be found with\n"
78 "esorex --params uves_utl_rcosmic\n"
79 "esorex --help uves_utl_rcosmic\n"
80 "\n";
81 
82 /*-----------------------------------------------------------------------------
83  Functions code
84  ----------------------------------------------------------------------------*/
85 /*---------------------------------------------------------------------------*/
89 /*---------------------------------------------------------------------------*/
90 
92 /*---------------------------------------------------------------------------*/
100 /*---------------------------------------------------------------------------*/
101 int cpl_plugin_get_info(cpl_pluginlist * list)
102 {
103  cpl_recipe * recipe = cpl_calloc(1, sizeof *recipe ) ;
104  cpl_plugin * plugin = &recipe->interface ;
105 
106  cpl_plugin_init(plugin,
107  CPL_PLUGIN_API,
108  UVES_BINARY_VERSION,
109  CPL_PLUGIN_TYPE_RECIPE,
110  "uves_utl_rcosmic",
111  "Remove CRHs from an image",
112  uves_utl_rcosmic_description,
113  "Andrea Modigliani",
114  "Andrea.Modigliani@eso.org",
119 
120  cpl_pluginlist_append(list, plugin) ;
121 
122  return 0;
123 }
124 
125 /*---------------------------------------------------------------------------*/
134 /*---------------------------------------------------------------------------*/
135 static int uves_utl_rcosmic_create(cpl_plugin * plugin)
136 {
137  cpl_recipe * recipe ;
138  cpl_parameter * p ;
139 
140  /* Get the recipe out of the plugin */
141  if (cpl_plugin_get_type(plugin) == CPL_PLUGIN_TYPE_RECIPE)
142  recipe = (cpl_recipe *)plugin ;
143  else return -1 ;
144  cpl_error_reset();
145  irplib_reset();
146 
147  /* Create the parameters list in the cpl_recipe object */
148  recipe->parameters = cpl_parameterlist_new() ;
149 
150  /* Fill the parameters list */
151  /* --stropt */
152  p = cpl_parameter_new_value("uves.uves_utl_rcosmic.sky_mean",
153  CPL_TYPE_DOUBLE,
154  "Mean sky value [ADUs]",
155  "uves.uves_utl_rcosmic",10.);
156  cpl_parameter_set_alias(p, CPL_PARAMETER_MODE_CLI, "sky_mean") ;
157  cpl_parameterlist_append(recipe->parameters, p) ;
158 
159  /* --doubleopt */
160  p = cpl_parameter_new_value("uves.uves_utl_rcosmic.ron",
161  CPL_TYPE_DOUBLE,
162  "RON [ADU]",
163  "uves.uves_utl_rcosmic", 3.) ;
164  cpl_parameter_set_alias(p, CPL_PARAMETER_MODE_CLI, "ron") ;
165  cpl_parameterlist_append(recipe->parameters, p) ;
166 
167 
168 
169  p = cpl_parameter_new_value("uves.uves_utl_rcosmic.gain",
170  CPL_TYPE_DOUBLE,
171  "Detector gain",
172  "uves.uves_utl_rcosmic", 0.7) ;
173  cpl_parameter_set_alias(p, CPL_PARAMETER_MODE_CLI, "gain") ;
174  cpl_parameterlist_append(recipe->parameters, p) ;
175 
176 
177  p = cpl_parameter_new_value("uves.uves_utl_rcosmic.kappa",
178  CPL_TYPE_INT,
179  "Kappa value in kappa-sigma CRH clip",
180  "uves.uves_utl_rcosmic",5) ;
181  cpl_parameter_set_alias(p, CPL_PARAMETER_MODE_CLI, "kappa") ;
182  cpl_parameterlist_append(recipe->parameters, p) ;
183 
184 
185  p = cpl_parameter_new_value("uves.uves_utl_rcosmic.nc",
186  CPL_TYPE_INT,
187  " critical ratio for discrimination of objects and cosmic rays",
188  "uves.uves_utl_rcosmic",5) ;
189  cpl_parameter_set_alias(p, CPL_PARAMETER_MODE_CLI, "nc") ;
190  cpl_parameterlist_append(recipe->parameters, p) ;
191 
192 
193  /* Return */
194  return 0;
195 }
196 
197 /*---------------------------------------------------------------------------*/
203 /*---------------------------------------------------------------------------*/
204 static int uves_utl_rcosmic_exec(cpl_plugin * plugin)
205 {
206  cpl_recipe * recipe ;
207  int code=0;
208  cpl_errorstate initial_errorstate = cpl_errorstate_get();
209 
210  /* Get the recipe out of the plugin */
211  if (cpl_plugin_get_type(plugin) == CPL_PLUGIN_TYPE_RECIPE)
212  recipe = (cpl_recipe *)plugin ;
213  else return -1 ;
214  cpl_error_reset();
215  irplib_reset();
216  code = uves_utl_rcosmic(recipe->parameters, recipe->frames) ;
217 
218 
219  if (!cpl_errorstate_is_equal(initial_errorstate)) {
220  /* Dump the error history since recipe execution start.
221  At this point the recipe cannot recover from the error */
222  cpl_errorstate_dump(initial_errorstate, CPL_FALSE, NULL);
223  }
224 
225  return code ;
226 }
227 
228 /*---------------------------------------------------------------------------*/
234 /*---------------------------------------------------------------------------*/
235 static int uves_utl_rcosmic_destroy(cpl_plugin * plugin)
236 {
237  cpl_recipe * recipe ;
238 
239  /* Get the recipe out of the plugin */
240  if (cpl_plugin_get_type(plugin) == CPL_PLUGIN_TYPE_RECIPE)
241  recipe = (cpl_recipe *)plugin ;
242  else return -1 ;
243 
244  cpl_parameterlist_delete(recipe->parameters) ;
245  return 0 ;
246 }
247 
248 /*---------------------------------------------------------------------------*/
255 /*---------------------------------------------------------------------------*/
256 static int
257 uves_utl_rcosmic( cpl_parameterlist * parlist,
258  cpl_frameset * framelist)
259 {
260  cpl_parameter * param= NULL ;
261  cpl_frameset * raw_on=NULL;
262  cpl_frameset * raw_off=NULL;
263 
264  double sky_mean=0;
265  double ron=0;
266  double gain=0;
267  int kappa=0;
268  int nc=0;
269 
270  int nraw=0;
271  cpl_image* ima_res=NULL;
272  cpl_image* ima_on=NULL;
273  cpl_image* ima_off=NULL;
274 
275 
276  cpl_image* ima_flt=NULL;
277  cpl_image* ima_msk=NULL;
278 
279  cpl_size next1=0;
280  const char* name1=NULL;
281 
282  cpl_size next2=0;
283  const char* name2=NULL;
284 
285  int noff=0;
286 
287  cpl_propertylist* plist1=NULL;
288  cpl_propertylist* plist2=NULL;
289  cpl_propertylist* pliste=NULL;
290  const char* name_r="ima_res.fits";
291  cpl_frame* product_frame=NULL;
292  cpl_frame* frame_on=NULL;
293  cpl_frame* frame_off=NULL;
294  int chips=0;
295  int nfrm=0;
296  int i=0;
297 
298  uves_msg("Welcome to UVES Pipeline release %d.%d.%d",
299  UVES_MAJOR_VERSION,UVES_MINOR_VERSION,UVES_MICRO_VERSION);
300 
301  /* HOW TO RETRIEVE INPUT PARAMETERS */
302  check_nomsg(param=cpl_parameterlist_find(parlist,
303  "uves.uves_utl_rcosmic.sky_mean"));
304  check_nomsg(sky_mean=cpl_parameter_get_double(param));
305 
306  check_nomsg(param=cpl_parameterlist_find(parlist,
307  "uves.uves_utl_rcosmic.ron"));
308  check_nomsg(ron = cpl_parameter_get_double(param)) ;
309 
310  check_nomsg(param=cpl_parameterlist_find(parlist,
311  "uves.uves_utl_rcosmic.gain"));
312  check_nomsg(gain = cpl_parameter_get_double(param)) ;
313 
314  check_nomsg(param=cpl_parameterlist_find(parlist,
315  "uves.uves_utl_rcosmic.kappa"));
316  check_nomsg(kappa = cpl_parameter_get_int(param)) ;
317 
318  check_nomsg(param=cpl_parameterlist_find(parlist,
319  "uves.uves_utl_rcosmic.nc"));
320  check_nomsg(nc = cpl_parameter_get_int(param)) ;
321 
322 
323  /* Identify the RAW and CALIB frames in the input frameset */
324  check(uves_dfs_set_groups(framelist),
325  "Cannot identify RAW and CALIB frames") ;
326  //cpl_frameset_dump(framelist,stdout);
327 
328  /* HOW TO ACCESS INPUT DATA */
329  nfrm=cpl_frameset_get_size(framelist);
330  if(nfrm<1) {
331  uves_msg_error("Empty input frame list!");
332  goto cleanup ;
333  }
334 
335  /* HOW TO ACCESS INPUT DATA */
336  check_nomsg(raw_on=cpl_frameset_new());
337 
338  check(uves_contains_frames_kind(framelist,raw_on,"RAW_IMA"),
339  "Found no input frames with tag %s","RAW_IMA");
340  check_nomsg(nraw=cpl_frameset_get_size(raw_on));
341  if (nraw<1) {
342  uves_msg_error("Found no input frames with tag %s","RAW_IMA");
343  goto cleanup;
344  }
345 
346  uves_msg("nraw=%d",nraw);
347 
348  check_nomsg(frame_on=cpl_frameset_get_first(raw_on));
349  check_nomsg(next1=cpl_frame_get_nextensions(frame_on));
350  check_nomsg(name1=cpl_frame_get_filename(frame_on));
351  check_nomsg(plist1=cpl_propertylist_load(name1,0));
352  uves_msg("CRH affected file name =%s",name1);
353 
354 
355 
356  if (nfrm>1) {
357  /* if input has more than a frame, search for bias */
358  check_nomsg(raw_off=cpl_frameset_new());
359 
360  chips=cpl_propertylist_get_int(plist1,"ESO DET CHIPS");
361 
362  /* deal with BLUE/RED arms and search for proper bias*/
363  if(chips==2) {
364  check(uves_contains_frames_kind(framelist,raw_off,"BIAS_RED"),
365  "Found no input frames with tag %s","BIAS_RED");
366  } else {
367  check(uves_contains_frames_kind(framelist,raw_off,"BIAS_BLUE"),
368  "Found no input frames with tag %s","BIAS_BLUE");
369  }
370 
371  check_nomsg(noff=cpl_frameset_get_size(raw_off));
372  if (noff<1) {
373  uves_msg_error("Found no input bias frames");
374 
375  } else {
376 
377  frame_off=cpl_frameset_get_first(raw_off);
378  next2=cpl_frame_get_nextensions(frame_off);
379  /* check that raw frame and bias are coherent else exit */
380  if(next2 != next1) {
381  uves_msg_error("Raw frames with different number of extensions");
382  uves_msg_error("Something wrong! Exit");
383  goto cleanup;
384  }
385  name2=cpl_frame_get_filename(frame_off);
386  uves_msg("Bias file name =%s",name2);
387  check_nomsg(cpl_image_save(NULL, name_r,CPL_BPP_IEEE_FLOAT,
388  plist1,CPL_IO_DEFAULT));
389 
390  /* subtract bias on each extension */
391  if(next1==0) {
392  /*
393  subtract bias,
394  correct for cosmics,
395  save result
396  */
397 
398  check_nomsg(ima_on=cpl_image_load(name1,CPL_TYPE_FLOAT,0,0));
399  check_nomsg(ima_off=cpl_image_load(name2,CPL_TYPE_FLOAT,0,0));
400  check_nomsg(cpl_image_subtract(ima_on,ima_off));
401 
402 
403  cpl_image_save(ima_on,"image_with_crh.fits",CPL_BPP_IEEE_FLOAT,
404  NULL,CPL_IO_DEFAULT);
405 
406  check(uves_rcosmic(ima_on,&ima_flt,&ima_res,&ima_msk,
407  sky_mean,ron,gain,kappa,nc),
408  "fail to remove CRHs");
409 
410 
411  check_nomsg(cpl_image_add(ima_res,ima_off));
412 
413  check_nomsg(cpl_image_save(ima_res, name_r,CPL_BPP_IEEE_FLOAT,
414  plist1,CPL_IO_DEFAULT));
415  } else {
416  uves_msg("next=%d",next1);
417  /* loop over extensions,
418  subtract bias,
419  correct for cosmics,
420  save result
421  */
422 
423 
424 
425  for(i=1;i<=next1;i++) {
426  uves_msg("name1=%s",name1);
427  uves_msg("name2=%s",name2);
428  check_nomsg(ima_on=cpl_image_load(name1,CPL_TYPE_FLOAT,0,i));
429 
430 
431  check_nomsg(pliste=cpl_propertylist_load(name1,i));
432 
433  if(next2==0) {
434  check_nomsg(ima_off=cpl_image_load(name2,CPL_TYPE_FLOAT,0,0));
435 
436  } else {
437  check_nomsg(ima_off=cpl_image_load(name2,CPL_TYPE_FLOAT,0,i));
438 
439  }
440  uves_msg("ima_on=%p ima_off=%p",ima_on,ima_off);
441  check_nomsg(cpl_image_subtract(ima_on,ima_off));
442 
443  cpl_image_save(ima_on,"image_with_crh.fits",CPL_BPP_IEEE_FLOAT,
444  NULL,CPL_IO_DEFAULT);
445 
446 
447  check(uves_rcosmic(ima_on,&ima_flt,&ima_res,&ima_msk,
448  sky_mean,ron,gain,kappa,nc),
449  "fail to remove CRHs");
450  check_nomsg(cpl_image_add(ima_res,ima_off));
451 
452 
453  if(i>0) {
454  check_nomsg(cpl_image_save(ima_res, name_r,CPL_BPP_IEEE_FLOAT,
455  pliste,CPL_IO_EXTEND));
456  }
457  uves_free_image(&ima_on);
458  uves_free_image(&ima_off);
459  uves_free_image(&ima_flt);
460  uves_free_image(&ima_res);
461  cpl_propertylist_delete(pliste); pliste=NULL;
462 
463 
464  }
465 
466 
467  }
468  }
469 
470  uves_free_frameset(&raw_off);
471  uves_free_frameset(&raw_on);
472 
473 
474  } else {
475  uves_msg("Please, provide a bias frame. Exit.");
476  goto cleanup;
477  }
478 
479 
480 
481  /* HOW TO SAVE A PRODUCT ON DISK */
482  /* Set the file name */
483  name_r = "ima_res.fits" ;
484 
485  /* Create product frame */
486  check_nomsg(product_frame = cpl_frame_new());
487  check_nomsg(cpl_frame_set_filename(product_frame, name_r)) ;
488  check_nomsg(cpl_frame_set_tag(product_frame, "PRODUCT")) ;
489  check_nomsg(cpl_frame_set_type(product_frame, CPL_FRAME_TYPE_IMAGE)) ;
490  check_nomsg(cpl_frame_set_group(product_frame, CPL_FRAME_GROUP_PRODUCT)) ;
491  check(cpl_frame_set_level(product_frame, CPL_FRAME_LEVEL_FINAL),
492  "Error while initialising the product frame") ;
493 
494 
495  /* Add DataFlow keywords */
496  check_nomsg(cpl_propertylist_erase_regexp(plist1, "^ESO PRO CATG",0));
497  /*
498  check(cpl_dfs_setup_product_header(plist1,
499  product_frame,
500  framelist,
501  parlist,
502  "uves_utl_rcosmic",
503  "UVES",
504  DICTIONARY),
505  "Problem in the product DFS-compliance") ;
506  */
507  /* Save the file
508  check(cpl_image_save(ima_res,
509  name_r,
510  CPL_BPP_IEEE_FLOAT,
511  plist1,
512  CPL_IO_DEFAULT),
513  "Could not save product");
514  */
515  cpl_propertylist_delete(plist1) ; plist1=NULL;
516 
517  /* Log the saved file in the input frameset */
518  check_nomsg(cpl_frameset_insert(framelist, product_frame)) ;
519 
520 
521  cleanup:
522  uves_free_frameset(&raw_on);
523  uves_free_frameset(&raw_off);
524  uves_free_image(&ima_on);
525  uves_free_image(&ima_off);
526  /* the following image cannot be erased
527  uves_free_image(&ima_msk);
528  */
529  uves_free_image(&ima_flt);
530  uves_free_image(&ima_res);
531 
532  if(pliste!=NULL) cpl_propertylist_delete(pliste); pliste=NULL;
533 
534  if (plist1!=NULL) cpl_propertylist_delete(plist1);plist1=NULL;
535  if (plist2!=NULL) cpl_propertylist_delete(plist2);plist2=NULL;
536 
537  /* This is usually freed by esorex: but what about if errors occurs?
538  uves_free_frame(&product_frame) ;
539  */
540 
541  if (cpl_error_get_code()) {
542  return -1 ;
543  } else {
544  return 0 ;
545  }
546 
547 }