hawki_cal_dark.c

00001 /* $Id: hawki_cal_dark.c,v 1.18 2009/12/16 15:17:40 cgarcia Exp $
00002  *
00003  * This file is part of the HAWKI Pipeline
00004  * Copyright (C) 2002,2003 European Southern Observatory
00005  *
00006  * This program is free software; you can redistribute it and/or modify
00007  * it under the terms of the GNU General Public License as published by
00008  * the Free Software Foundation; either version 2 of the License, or
00009  * (at your option) any later version.
00010  *
00011  * This program is distributed in the hope that it will be useful,
00012  * but WITHOUT ANY WARRANTY; without even the implied warranty of
00013  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
00014  * GNU General Public License for more details.
00015  *
00016  * You should have received a copy of the GNU General Public License
00017  * along with this program; if not, write to the Free Software
00018  * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
00019  */
00020 
00021 /*
00022  * $Author: cgarcia $
00023  * $Date: 2009/12/16 15:17:40 $
00024  * $Revision: 1.18 $
00025  * $Name: hawki-1_7_2 $
00026  */
00027 
00028 #ifdef HAVE_CONFIG_H
00029 #include <config.h>
00030 #endif
00031 
00032 /*-----------------------------------------------------------------------------
00033                                 Includes
00034  -----------------------------------------------------------------------------*/
00035 
00036 #include <math.h>
00037 #include <cpl.h>
00038 
00039 #include "irplib_utils.h"
00040 
00041 #include "hawki_utils.h"
00042 #include "hawki_image_stats.h"
00043 #include "hawki_pfits.h"
00044 #include "hawki_dfs.h"
00045 #include "hawki_load.h"
00046 #include "hawki_save.h"
00047 #include "hawki_variance.h"
00048 
00049 /*-----------------------------------------------------------------------------
00050                             Functions prototypes
00051  -----------------------------------------------------------------------------*/
00052 
00053 static int hawki_cal_dark_create(cpl_plugin *) ;
00054 static int hawki_cal_dark_exec(cpl_plugin *) ;
00055 static int hawki_cal_dark_destroy(cpl_plugin *) ;
00056 static int hawki_cal_dark(cpl_parameterlist *, cpl_frameset *) ;
00057 
00058 void hawki_cal_dark_initialise_qc(void);
00059 static int hawki_cal_dark_retrieve_input_param
00060 (cpl_parameterlist * parlist);
00061 static double hawki_cal_dark_ron(const cpl_image *, const cpl_image *, int) ;
00062 static int hawki_cal_dark_save
00063 (const cpl_imagelist *   dark,
00064  const cpl_imagelist *   master_dark_err,
00065  const cpl_imagelist *   bpmdark,
00066  cpl_table           **  raw_dark_stats,
00067  const cpl_vector    **  rons,
00068  const cpl_frameset  *   used_frames,
00069  cpl_parameterlist   *   parlist,
00070  cpl_frameset        *   set);
00071 
00072 /*-----------------------------------------------------------------------------
00073                             Static variables
00074  -----------------------------------------------------------------------------*/
00075 
00076 static struct {
00077     /* Inputs */
00078     int         hsize ;
00079     int         nsamples ;
00080     double      sigma ;
00081     int         llx ;
00082     int         lly ;
00083     int         urx ;
00084     int         ury ;
00085     double      gain;
00086     double      ron;
00087     int         error_tracking;
00088 } hawki_cal_dark_config ;
00089 
00090 static struct {
00091     /* Outputs */
00092     int         nb_badpix[HAWKI_NB_DETECTORS] ;
00093     double      master_dark_mean[HAWKI_NB_DETECTORS] ;
00094     double      master_dark_med[HAWKI_NB_DETECTORS] ;
00095     double      master_dark_stdev[HAWKI_NB_DETECTORS] ;
00096     double      master_dark_error_mean[HAWKI_NB_DETECTORS] ;
00097     double      master_dark_error_med[HAWKI_NB_DETECTORS] ;
00098     double      master_dark_error_stdev[HAWKI_NB_DETECTORS] ;
00099     double      vc_mean[HAWKI_NB_DETECTORS][HAWKI_NB_VC] ;
00100     double      vc_med[HAWKI_NB_DETECTORS][HAWKI_NB_VC] ;
00101     double      vc_stdev[HAWKI_NB_DETECTORS][HAWKI_NB_VC] ;
00102 } hawki_cal_dark_outputs;
00103 
00104 static char hawki_cal_dark_description[] =
00105 "hawki_cal_dark -- Dark recipe\n"
00106 "The files listed in the Set Of Frames (sof-file) must be tagged:\n"
00107 "raw-file.fits "HAWKI_CAL_DARK_RAW" or\n"
00108 "raw-file.fits "HAWKI_TEC_FLAT_RAW".\n" ;
00109 
00110 /*-----------------------------------------------------------------------------
00111                                 Functions code
00112  -----------------------------------------------------------------------------*/
00113 
00114 /*----------------------------------------------------------------------------*/
00123 /*----------------------------------------------------------------------------*/
00124 int cpl_plugin_get_info(cpl_pluginlist * list)
00125 {
00126     cpl_recipe  *   recipe = cpl_calloc(1, sizeof *recipe ) ;
00127     cpl_plugin  *   plugin = &recipe->interface ;
00128 
00129     cpl_plugin_init(plugin,
00130                     CPL_PLUGIN_API,
00131                     HAWKI_BINARY_VERSION,
00132                     CPL_PLUGIN_TYPE_RECIPE,
00133                     "hawki_cal_dark",
00134                     "Dark recipe",
00135                     hawki_cal_dark_description,
00136                     "Cesar Enrique Garcia Dabo",
00137                     "cgarcia@eso.org",
00138                     hawki_get_license(),
00139                     hawki_cal_dark_create,
00140                     hawki_cal_dark_exec,
00141                     hawki_cal_dark_destroy) ;
00142 
00143     cpl_pluginlist_append(list, plugin) ;
00144     
00145     return 0;
00146 }
00147 
00148 /*----------------------------------------------------------------------------*/
00156 /*----------------------------------------------------------------------------*/
00157 static int hawki_cal_dark_create(cpl_plugin * plugin)
00158 {
00159     cpl_recipe      *   recipe ;
00160     cpl_parameter   *   p ;
00161         
00162     /* Check that the plugin is part of a valid recipe */
00163     if (cpl_plugin_get_type(plugin) == CPL_PLUGIN_TYPE_RECIPE) 
00164         recipe = (cpl_recipe *)plugin ;
00165     else return -1 ;
00166 
00167     /* Create the parameters list in the cpl_recipe object */
00168     recipe->parameters = cpl_parameterlist_new() ; 
00169 
00170     /* Fill the parameters list */
00171     /* --sigma */
00172     p = cpl_parameter_new_value("hawki.hawki_cal_dark.sigma",
00173             CPL_TYPE_DOUBLE, "sigma for hot bad pixels detection",
00174             "hawki.hawki_cal_dark", 10.0) ;
00175     cpl_parameter_set_alias(p, CPL_PARAMETER_MODE_CLI, "sigma") ;
00176     cpl_parameter_disable(p, CPL_PARAMETER_MODE_ENV) ;
00177     cpl_parameterlist_append(recipe->parameters, p) ;
00178     /* --nsamples */
00179     p = cpl_parameter_new_value("hawki.hawki_cal_dark.nsamples",
00180             CPL_TYPE_INT, "number of samples for RON computation",
00181             "hawki.hawki_cal_dark", 100) ;
00182     cpl_parameter_set_alias(p, CPL_PARAMETER_MODE_CLI, "nsamples") ;
00183     cpl_parameter_disable(p, CPL_PARAMETER_MODE_ENV) ;
00184     cpl_parameterlist_append(recipe->parameters, p) ;
00185     /* --hsize */
00186     p = cpl_parameter_new_value("hawki.hawki_cal_dark.hsize",
00187             CPL_TYPE_INT, "half size of the window for RON computation",
00188             "hawki.hawki_cal_dark", 6) ;
00189     cpl_parameter_set_alias(p, CPL_PARAMETER_MODE_CLI, "hsize") ;
00190     cpl_parameter_disable(p, CPL_PARAMETER_MODE_ENV) ;
00191     cpl_parameterlist_append(recipe->parameters, p) ;
00192     /* --zone */
00193     p = cpl_parameter_new_value("hawki.hawki_cal_dark.zone",
00194                                 CPL_TYPE_STRING,
00195                                 "Stats zone",
00196                                 "hawki.hawki_cal_dark",
00197                                 "512,512,1536,1536") ;
00198     cpl_parameter_set_alias(p, CPL_PARAMETER_MODE_CLI, "zone") ;
00199     cpl_parameter_disable(p, CPL_PARAMETER_MODE_ENV) ;
00200     cpl_parameterlist_append(recipe->parameters, p) ;
00201     /* --gain */
00202     p = cpl_parameter_new_value("hawki.hawki_cal_dark.gain",
00203                                 CPL_TYPE_DOUBLE,
00204                                 "Detector nominal gain (e-/ADU)",
00205                                 "hawki.hawki_cal_dark",
00206                                 -1.);
00207     cpl_parameter_set_alias(p, CPL_PARAMETER_MODE_CLI, "gain") ;
00208     cpl_parameter_disable(p, CPL_PARAMETER_MODE_ENV) ;
00209     cpl_parameterlist_append(recipe->parameters, p) ;
00210     /* --ron */
00211     p = cpl_parameter_new_value("hawki.hawki_cal_dark.ron",
00212                                 CPL_TYPE_DOUBLE,
00213                                 "Detector nominal RON for a single readout (ADU)",
00214                                 "hawki.hawki_cal_dark",
00215                                 -1.);
00216     cpl_parameter_set_alias(p, CPL_PARAMETER_MODE_CLI, "ron") ;
00217     cpl_parameter_disable(p, CPL_PARAMETER_MODE_ENV) ;
00218     cpl_parameterlist_append(recipe->parameters, p) ;
00219 
00220     /* Return */
00221     return 0;
00222 }
00223 
00224 /*----------------------------------------------------------------------------*/
00230 /*----------------------------------------------------------------------------*/
00231 static int hawki_cal_dark_exec(cpl_plugin * plugin)
00232 {
00233     cpl_recipe  *   recipe ;
00234     
00235     /* Get the recipe out of the plugin */
00236     if (cpl_plugin_get_type(plugin) == CPL_PLUGIN_TYPE_RECIPE) 
00237         recipe = (cpl_recipe *)plugin ;
00238     else return -1 ;
00239 
00240     /* Issue a banner */
00241     hawki_print_banner();
00242 
00243     return hawki_cal_dark(recipe->parameters, recipe->frames) ;
00244 }
00245 
00246 /*----------------------------------------------------------------------------*/
00252 /*----------------------------------------------------------------------------*/
00253 static int hawki_cal_dark_destroy(cpl_plugin * plugin)
00254 {
00255     cpl_recipe  *   recipe ;
00256     
00257     /* Get the recipe out of the plugin */
00258     if (cpl_plugin_get_type(plugin) == CPL_PLUGIN_TYPE_RECIPE) 
00259         recipe = (cpl_recipe *)plugin ;
00260     else return -1 ;
00261 
00262     cpl_parameterlist_delete(recipe->parameters) ; 
00263     return 0 ;
00264 }
00265 
00266 /*----------------------------------------------------------------------------*/
00273 /*----------------------------------------------------------------------------*/
00274 static int hawki_cal_dark(
00275         cpl_parameterlist   *   parlist, 
00276         cpl_frameset        *   frameset)
00277 {
00278     cpl_frameset        *   rawframes ;
00279     cpl_frame           *   ref_frame ;
00280     cpl_propertylist    *   plist ;
00281     double                  dit;
00282     int                     ndit;
00283     int                     ndsamples;
00284     cpl_imagelist       *   darks_raw ;
00285     cpl_imagelist       *   master_dark;
00286     cpl_imagelist       *   master_dark_err;
00287     cpl_imagelist       *   bpmdark;
00288     cpl_image           *   bpm ;
00289     cpl_image           *   ima_curr ;
00290     cpl_image           *   ima_next ;
00291     cpl_image           *   ima_accu ;
00292     cpl_image           *   ima_accu_err = NULL;
00293     int                     nframes ;
00294     cpl_vector          *   rons[HAWKI_NB_DETECTORS] ;
00295     cpl_table           **  raw_dark_stats;
00296     double                  ron ;
00297     int                     vc_urx, vc_ury, vc_llx, vc_lly ;
00298     int                     j, k ;
00299     int                     idet;
00300     cpl_errorstate          error_prevstate;      
00301     
00302     /* Initialise */
00303     rawframes = NULL ;
00304     ima_accu = NULL ;
00305     ima_next = NULL ;
00306     master_dark_err = NULL;
00307     hawki_cal_dark_initialise_qc();
00308 
00309     /* Retrieve input parameters */
00310     if(hawki_cal_dark_retrieve_input_param(parlist))
00311     {
00312         cpl_msg_error(__func__, "Wrong parameters");
00313         return -1;
00314     }
00315  
00316     /* Identify the RAW and CALIB frames in the input frameset */
00317     if (hawki_dfs_set_groups(frameset)) {
00318         cpl_msg_error(__func__, "Cannot identify RAW and CALIB frames") ;
00319         return -1 ;
00320     }
00321         
00322     /* Retrieve raw frames */
00323     rawframes = hawki_extract_frameset(frameset, HAWKI_CAL_DARK_RAW) ;
00324 
00325     /* Test if raw frames have been found */
00326     if (rawframes == NULL) {
00327         cpl_msg_error(__func__, "No raw frame in input") ;
00328         return -1 ;
00329     }
00330 
00331     /* At least 3 frames */
00332     if (cpl_frameset_get_size(rawframes) < 3) {
00333         cpl_msg_error(__func__, "Not enough input frames");
00334         cpl_frameset_delete(rawframes) ;
00335         return -1 ;
00336     }
00337     
00338     /* Get DIT / NDIT from the header */
00339     error_prevstate = cpl_errorstate_get();
00340     ref_frame = cpl_frameset_get_frame(rawframes, 0) ;
00341     if ((plist=cpl_propertylist_load(cpl_frame_get_filename(ref_frame),
00342                     0)) == NULL) {
00343         cpl_msg_error(__func__, "Cannot get header from frame");
00344         cpl_msg_indent_less() ;
00345         cpl_frameset_delete(rawframes) ;
00346         return -1 ;
00347     }
00348     dit = hawki_pfits_get_dit(plist) ;
00349     ndit = hawki_pfits_get_ndit(plist) ;
00350     ndsamples = hawki_pfits_get_ndsamples(plist);
00351     cpl_propertylist_delete(plist) ;
00352     if(!cpl_errorstate_is_equal(error_prevstate))
00353     {
00354         cpl_msg_error(__func__, "Cannot get the DIT/NDIT from the header") ;
00355         cpl_msg_indent_less() ;
00356         cpl_frameset_delete(rawframes) ;
00357         return -1 ;
00358     }
00359     cpl_msg_info(__func__, "DIT value: %g sec.", dit) ;
00360     cpl_msg_info(__func__, "NDIT value: %d", ndit) ;
00361     cpl_msg_info(__func__, "NDSAMPLES value: %d", ndsamples) ;
00362 
00363     /* Number of frames */
00364     nframes = cpl_frameset_get_size(rawframes) ;
00365 
00366     /* Create the statistics table */
00367     raw_dark_stats = cpl_malloc(HAWKI_NB_DETECTORS * sizeof(cpl_table *));
00368     for( idet=0 ; idet<HAWKI_NB_DETECTORS ; idet++)
00369     {
00370         raw_dark_stats[idet] = cpl_table_new(nframes);
00371     }
00372     hawki_image_stats_initialize(raw_dark_stats);
00373     
00374     /* Loop on the detectors */
00375     master_dark = cpl_imagelist_new();
00376     if(hawki_cal_dark_config.error_tracking)
00377         master_dark_err = cpl_imagelist_new();
00378     bpmdark = cpl_imagelist_new();
00379     cpl_msg_info(__func__, "Dark computation");
00380     cpl_msg_indent_more() ;
00381     for (idet=0 ; idet<HAWKI_NB_DETECTORS ; idet++) {
00382         cpl_msg_info(__func__, "Handle chip number %d", idet+1) ;
00383 
00384         /* Create the rons vectors */
00385         rons[idet] = cpl_vector_new(nframes) ;
00386         
00387         /* Load the input data */
00388         darks_raw = hawki_load_detector(rawframes, idet+1, CPL_TYPE_FLOAT) ;
00389 
00390         /* Loop on the frames */
00391         for (j=0 ; j<nframes ; j++) {
00392             /* Load the current and next images */
00393             if (j==nframes-1) {
00394                 ima_curr = cpl_imagelist_get(darks_raw, j) ;
00395                 ima_next = cpl_imagelist_get(darks_raw, 0) ;
00396             } else {
00397                 ima_curr = cpl_imagelist_get(darks_raw, j) ;
00398                 ima_next = cpl_imagelist_get(darks_raw, j+1) ;
00399             }
00400 
00401             /* Compute the dark stats and store in table */
00402             if(hawki_image_stats_fill_from_image
00403                 (raw_dark_stats,
00404                  ima_curr,
00405                  hawki_cal_dark_config.llx,
00406                  hawki_cal_dark_config.lly,
00407                  hawki_cal_dark_config.urx,
00408                  hawki_cal_dark_config.ury,
00409                  idet,
00410                  j) != 0)
00411             {
00412                 cpl_msg_error(__func__, "Cannot compute statistics") ;
00413                 cpl_msg_indent_less() ; 
00414                 cpl_frameset_delete(rawframes) ;
00415                 cpl_imagelist_delete(master_dark);
00416                 if(hawki_cal_dark_config.error_tracking)
00417                     cpl_imagelist_delete(master_dark_err);                
00418                 cpl_imagelist_delete(darks_raw); 
00419                 cpl_imagelist_delete(bpmdark) ;
00420                 for (k=0 ; k<=idet ; k++) 
00421                     cpl_vector_delete(rons[k]) ;
00422                 for( idet=0 ; idet<HAWKI_NB_DETECTORS ; idet++) 
00423                     cpl_table_delete(raw_dark_stats[idet]);
00424                 cpl_free(raw_dark_stats);
00425                 return -1 ;
00426             }
00427            
00428             /* Compute the RON */
00429             ron = hawki_cal_dark_ron(ima_curr, ima_next, ndit) ;
00430             cpl_vector_set(rons[idet], j, ron);
00431         }
00432         
00433         /* Collapse */
00434         if (nframes > 2)
00435         {
00436             ima_accu = cpl_imagelist_collapse_minmax_create(darks_raw, 0, 1) ;
00437             if(hawki_cal_dark_config.error_tracking)
00438             {
00439                 cpl_imagelist * variances;
00440                 cpl_image     * accu_var;
00441                 cpl_msg_info(__func__, "Computing the uncertainty in dark");
00442                 variances = hawki_imglist_create_variances_and_delete
00443                     (darks_raw, hawki_cal_dark_config.gain, 
00444                      hawki_cal_dark_config.ron, ndit, ndsamples);
00445                 /* The variances are collapsed, like the dark_raw. Given that
00446                  * the variances are a monotically increasing function with
00447                  * respect to the dark_raw, the minmax algorithm will select
00448                  * the same values as for the dark_raw 
00449                  * The nframes - 1 is because only one frame is being rejected*/  
00450                 accu_var = cpl_imagelist_collapse_minmax_create(variances,0,1);
00451                 cpl_image_divide_scalar(accu_var, nframes - 1);
00452                 ima_accu_err = cpl_image_duplicate(accu_var);
00453                 cpl_image_power(ima_accu_err, 0.5);
00454                 cpl_imagelist_delete(variances);
00455                 cpl_image_delete(accu_var);
00456             }
00457 
00458         } else {
00459             ima_accu = cpl_imagelist_collapse_create(darks_raw) ;
00460             if(hawki_cal_dark_config.error_tracking)
00461             {
00462                 cpl_imagelist * variances;
00463                 cpl_image     * accu_var;
00464                 cpl_msg_info(__func__, "Computing the uncertainty in dark");
00465                 variances = hawki_imglist_create_variances_and_delete 
00466                     (darks_raw, hawki_cal_dark_config.gain, 
00467                      hawki_cal_dark_config.ron, ndit, ndsamples);
00468                 accu_var = cpl_imagelist_collapse_create(variances);                
00469                 cpl_image_divide_scalar(accu_var, nframes); 
00470                 ima_accu_err = cpl_image_duplicate(accu_var);
00471                 cpl_image_power(ima_accu_err, 0.5);
00472                 cpl_imagelist_delete(variances);
00473                 cpl_image_delete(accu_var);
00474             }
00475         }
00476         if (ima_accu == NULL) {
00477             cpl_msg_error(__func__, "Cannot compute the average") ;
00478             cpl_frameset_delete(rawframes) ;
00479             cpl_imagelist_delete(bpmdark) ;
00480             cpl_imagelist_delete(master_dark) ;
00481             if(ima_accu_err != NULL)
00482                 cpl_image_delete(ima_accu_err);
00483             cpl_imagelist_delete(darks_raw); 
00484             for (idet=0 ; idet<HAWKI_NB_DETECTORS ; idet++)
00485                 cpl_vector_delete(rons[idet]) ;
00486             for( idet=0 ; idet<HAWKI_NB_DETECTORS ; idet++) 
00487                  cpl_table_delete(raw_dark_stats[idet]);
00488             cpl_free(raw_dark_stats);
00489             return -1 ;
00490         }
00491         cpl_imagelist_delete(darks_raw) ;
00492 
00493         /* Put the result in the list */
00494         cpl_imagelist_set(master_dark, ima_accu, idet) ;
00495         if(hawki_cal_dark_config.error_tracking)
00496             cpl_imagelist_set(master_dark_err, ima_accu_err, idet) ;
00497 
00498         /* Compute the dark_med and stdev */
00499         hawki_cal_dark_outputs.master_dark_med[idet]=
00500             cpl_image_get_median(ima_accu) / dit;
00501         hawki_cal_dark_outputs.master_dark_mean[idet] =
00502             cpl_image_get_mean(ima_accu) / dit;
00503         hawki_cal_dark_outputs.master_dark_stdev[idet] =
00504             cpl_image_get_stdev(ima_accu) / dit;
00505         if(hawki_cal_dark_config.error_tracking)
00506         {
00507             hawki_cal_dark_outputs.master_dark_error_med[idet]=
00508                 cpl_image_get_median(ima_accu_err) / dit;
00509             hawki_cal_dark_outputs.master_dark_error_mean[idet] =
00510                 cpl_image_get_mean(ima_accu_err) / dit;
00511             hawki_cal_dark_outputs.master_dark_error_stdev[idet] =
00512                 cpl_image_get_stdev(ima_accu_err) / dit;
00513         }
00514 
00515         /* Compute the Video Channels stats */
00516         vc_lly = 973 ;
00517         vc_ury = 1036 ;
00518         for (j=0 ; j<HAWKI_NB_VC ; j++) {
00519             vc_llx = j*(2048/HAWKI_NB_VC) + 1 ;
00520             vc_urx = (j+1)*(2048/HAWKI_NB_VC) ;
00521 
00522             hawki_cal_dark_outputs.vc_mean[idet][j] =
00523                 cpl_image_get_mean_window(ima_accu, vc_llx, vc_lly,
00524                         vc_urx, vc_ury) ;
00525 
00526             hawki_cal_dark_outputs.vc_med[idet][j] =
00527                 cpl_image_get_median_window(ima_accu, vc_llx, vc_lly,
00528                         vc_urx, vc_ury) ;
00529 
00530             hawki_cal_dark_outputs.vc_stdev[idet][j] =
00531                 cpl_image_get_stdev_window(ima_accu, vc_llx, vc_lly,
00532                         vc_urx, vc_ury) ;
00533         }
00534 
00535         /* Compute the HOT pixels map */
00536         cpl_msg_info(__func__, "Compute the BPM from the dark") ;
00537         cpl_msg_indent_more() ;
00538         if ((bpm=hawki_compute_darkbpm(ima_accu, 
00539                         hawki_cal_dark_config.sigma)) == NULL) {
00540             cpl_msg_error(__func__, "Cannot compute the hot pixels") ;
00541             cpl_msg_indent_less() ; 
00542             cpl_frameset_delete(rawframes) ;
00543             cpl_imagelist_delete(bpmdark) ;
00544             cpl_imagelist_delete(master_dark);
00545             if(hawki_cal_dark_config.error_tracking)
00546                 cpl_imagelist_delete(master_dark_err);
00547             for (idet=0 ; idet<HAWKI_NB_DETECTORS ; idet++)
00548                 cpl_vector_delete(rons[idet]) ;
00549             for (idet=0 ; idet<HAWKI_NB_DETECTORS ; idet++) 
00550                 cpl_table_delete(raw_dark_stats[idet]);
00551             cpl_free(raw_dark_stats);
00552             return -1 ;
00553         }
00554         cpl_imagelist_set(bpmdark, bpm, idet) ;
00555         hawki_cal_dark_outputs.nb_badpix[idet]=(int)cpl_image_get_flux(bpm);
00556         cpl_msg_indent_less() ;
00557     }
00558     cpl_msg_indent_less() ;
00559     
00560     /* Divide by DIT */
00561     cpl_msg_info(__func__, "Division by DIT") ;
00562     cpl_imagelist_divide_scalar(master_dark, dit);
00563     if(hawki_cal_dark_config.error_tracking)
00564         cpl_imagelist_divide_scalar(master_dark_err, dit);
00565 
00566     /* Save the product */
00567     cpl_msg_info(__func__, "Save the products") ;
00568     cpl_msg_indent_more() ;
00569     if (hawki_cal_dark_save(master_dark, master_dark_err,
00570                             bpmdark, raw_dark_stats, 
00571                             (const cpl_vector **)rons,
00572                             rawframes,
00573                             parlist, frameset)) 
00574         cpl_msg_warning(__func__,"Some data could not be saved. "
00575                                  "Check permisions or disk space");
00576 
00577     /* Free */
00578     cpl_frameset_delete(rawframes) ;
00579     for (idet=0 ; idet<HAWKI_NB_DETECTORS ; idet++)
00580         cpl_vector_delete(rons[idet]) ;
00581     cpl_imagelist_delete(master_dark) ;
00582     if(hawki_cal_dark_config.error_tracking)
00583         cpl_imagelist_delete(master_dark_err);
00584     cpl_imagelist_delete(bpmdark) ;
00585     cpl_msg_indent_less() ;
00586     for( idet=0 ; idet<HAWKI_NB_DETECTORS ; idet++) 
00587          cpl_table_delete(raw_dark_stats[idet]);
00588     cpl_free(raw_dark_stats);
00589 
00590     /* Return */
00591     if (cpl_error_get_code()) return -1 ;
00592     else return 0 ;
00593 }
00594 
00595 /*----------------------------------------------------------------------------*/
00603 /*----------------------------------------------------------------------------*/
00604 static double hawki_cal_dark_ron(
00605         const cpl_image     *   ima1, 
00606         const cpl_image     *   ima2, 
00607         int                     ndit) 
00608 {
00609     cpl_image       *   ima ;
00610     double              norm ;
00611     double              ron ;
00612 
00613     /* Test entries */
00614     if (ima1 == NULL)   return -1.0 ;
00615     if (ima2 == NULL)   return -1.0 ;
00616     if (ndit < 1)       return -1.0 ;
00617 
00618     /* Compute norm */
00619     norm = 0.5 * ndit ;
00620     norm = sqrt(norm) ;
00621 
00622     /* Subtraction */
00623     if ((ima = cpl_image_subtract_create(ima2, ima1)) == NULL) return -1.0 ;
00624    
00625     /* RON measurement */
00626     cpl_flux_get_noise_window(ima, NULL, hawki_cal_dark_config.hsize,
00627             hawki_cal_dark_config.nsamples, &ron, NULL) ;
00628     cpl_image_delete(ima) ;
00629     return norm*ron ;
00630 }
00631 
00632 /*----------------------------------------------------------------------------*/
00642 /*----------------------------------------------------------------------------*/
00643 static int hawki_cal_dark_save
00644 (const cpl_imagelist *   master_dark,
00645  const cpl_imagelist *   master_dark_err,
00646  const cpl_imagelist *   bpmdark,
00647  cpl_table           **  raw_dark_stats,
00648  const cpl_vector    **  rons,
00649  const cpl_frameset  *   used_frames,
00650  cpl_parameterlist   *   parlist,
00651  cpl_frameset        *   set)
00652 {
00653     cpl_propertylist    **  qclists ;
00654     const cpl_frame     *   ref_frame ;
00655     char                    sval[32] ;
00656     cpl_propertylist    *   inputlist ;
00657     int                     ext_nb ;
00658     const char          *   recipe_name = "hawki_cal_dark" ;
00659     int                     i, j ;
00660     cpl_errorstate          error_prevstate = cpl_errorstate_get();
00661     
00662 
00663     /* Get the reference frame */
00664     ref_frame = irplib_frameset_get_first_from_group(set, CPL_FRAME_GROUP_RAW) ;
00665 
00666     /* Create the QC lists */
00667     qclists = cpl_malloc(HAWKI_NB_DETECTORS * sizeof(cpl_propertylist*)) ;
00668     for (i=0 ; i<HAWKI_NB_DETECTORS ; i++) {
00669         qclists[i] = cpl_propertylist_new() ;
00670         cpl_propertylist_append_int(qclists[i], "ESO QC DARK NBADPIX",
00671                 hawki_cal_dark_outputs.nb_badpix[i]) ;
00672         cpl_propertylist_append_double(qclists[i], "ESO QC DARK MEAN",
00673                 hawki_cal_dark_outputs.master_dark_mean[i]) ;
00674         cpl_propertylist_append_double(qclists[i], "ESO QC DARK MED",
00675                 hawki_cal_dark_outputs.master_dark_med[i]) ;
00676         cpl_propertylist_append_double(qclists[i], "ESO QC DARK STDEV",
00677                 hawki_cal_dark_outputs.master_dark_stdev[i]) ;
00678         if(hawki_cal_dark_config.error_tracking)
00679         {
00680             cpl_propertylist_append_double(qclists[i], "ESO QC DARK ERR MEAN",
00681                  hawki_cal_dark_outputs.master_dark_mean[i]) ;
00682             cpl_propertylist_append_double(qclists[i], "ESO QC DARK ERR MED",
00683                  hawki_cal_dark_outputs.master_dark_med[i]) ;
00684             cpl_propertylist_append_double(qclists[i], "ESO QC DARK ERR STDEV",
00685                  hawki_cal_dark_outputs.master_dark_stdev[i]) ;
00686         }
00687         for (j=0 ; j<HAWKI_NB_VC ; j++) {
00688             sprintf(sval, "ESO QC DARK VC%d MEAN", j+1) ;
00689             cpl_propertylist_append_double(qclists[i], sval,
00690                     hawki_cal_dark_outputs.vc_mean[i][j]) ;
00691             sprintf(sval, "ESO QC DARK VC%d MED", j+1) ;
00692             cpl_propertylist_append_double(qclists[i], sval,
00693                     hawki_cal_dark_outputs.vc_med[i][j]) ;
00694             sprintf(sval, "ESO QC DARK VC%d STDEV", j+1) ;
00695             cpl_propertylist_append_double(qclists[i], sval,
00696                     hawki_cal_dark_outputs.vc_stdev[i][j]) ;
00697         }
00698         for (j=0 ; j<cpl_vector_get_size(rons[i]) ; j++) {
00699             sprintf(sval, "ESO QC RON%d", j+1) ;
00700             cpl_propertylist_append_double(qclists[i], sval,
00701                     cpl_vector_get(rons[i], j)) ;
00702         } 
00703         cpl_propertylist_append_double(qclists[i], "ESO QC RON MEAN",
00704                 cpl_vector_get_mean(rons[i])) ;
00705         cpl_propertylist_append_double(qclists[i], "ESO QC RON MED",
00706                 cpl_vector_get_median_const(rons[i])) ;
00707         cpl_propertylist_append_double(qclists[i], "ESO QC RON STDEV",
00708                 cpl_vector_get_stdev(rons[i])) ;
00709         cpl_propertylist_append_double(qclists[i], "ESO QC DATANCOM",
00710                 cpl_frameset_get_size(set)) ;
00711        
00712         /* Propagate some keywords from input raw frame extensions */
00713         ext_nb=hawki_get_ext_from_detector(cpl_frame_get_filename(ref_frame), i+1);
00714         inputlist = cpl_propertylist_load_regexp(
00715                 cpl_frame_get_filename(ref_frame), ext_nb, 
00716                 HAWKI_HEADER_EXT_FORWARD, 0) ;
00717         cpl_propertylist_append(qclists[i], inputlist) ; 
00718         cpl_propertylist_delete(inputlist) ;
00719     }
00720     /* Statistics of the raw images in the QC */
00721     hawki_image_stats_stats(raw_dark_stats, qclists);
00722 
00723     /* Write the dark image */
00724     hawki_imagelist_save(set,
00725                          parlist,
00726                          used_frames, 
00727                          master_dark, 
00728                          recipe_name,
00729                          HAWKI_CALPRO_DARK, 
00730                          HAWKI_PROTYPE_DARK,
00731                          NULL,
00732                          (const cpl_propertylist**)qclists,
00733                          "hawki_cal_dark.fits") ;
00734 
00735     /* Write the dark image error */
00736     if(master_dark_err != NULL)
00737     {
00738         hawki_imagelist_save(set,
00739                              parlist,
00740                              used_frames, 
00741                              master_dark_err, 
00742                              recipe_name,
00743                              HAWKI_CALPRO_DARK_ERR, 
00744                              HAWKI_PROTYPE_DARK_ERR,
00745                              NULL,
00746                              NULL,
00747                              "hawki_cal_dark_err.fits") ;
00748     }
00749 
00750     /* Write the bpmdark pixels image */
00751     hawki_imagelist_save(set,
00752                          parlist,
00753                          used_frames, 
00754                          bpmdark, 
00755                          recipe_name,
00756                          HAWKI_CALPRO_BPM_HOT, 
00757                          HAWKI_PROTYPE_BPM,
00758                          NULL,
00759                          NULL,
00760                          "hawki_cal_dark_bpmdark.fits") ;
00761 
00762     
00763     /* Write the table with the statistics */
00764     hawki_tables_save(set,
00765                       parlist,
00766                       used_frames,
00767                       (const cpl_table **)raw_dark_stats,
00768                       recipe_name,
00769                       HAWKI_CALPRO_DARK_STATS,
00770                       HAWKI_PROTYPE_DARK_STATS,
00771                       NULL,
00772                       NULL,
00773                       "hawki_cal_dark_stats.fits") ;
00774 
00775     /* Free and return */
00776     for (i=0 ; i<HAWKI_NB_DETECTORS ; i++) {
00777         cpl_propertylist_delete(qclists[i]) ;
00778     }
00779     cpl_free(qclists) ;
00780     if(!cpl_errorstate_is_equal(error_prevstate))
00781     {
00782         cpl_errorstate_set(CPL_ERROR_NONE);
00783         return -1;
00784     }
00785     return  0;
00786 }
00787 
00788 static int hawki_cal_dark_retrieve_input_param
00789 (cpl_parameterlist * parlist)
00790 {
00791     cpl_parameter       *   par ;
00792     const char          *   sval ;
00793     cpl_errorstate          error_prevstate = cpl_errorstate_get();
00794     
00795     /* Retrieve input parameters */
00796     par = cpl_parameterlist_find(parlist, "hawki.hawki_cal_dark.sigma") ;
00797     hawki_cal_dark_config.sigma = cpl_parameter_get_double(par) ;
00798     par = cpl_parameterlist_find(parlist, "hawki.hawki_cal_dark.hsize") ;
00799     hawki_cal_dark_config.hsize = cpl_parameter_get_int(par) ;
00800     par = cpl_parameterlist_find(parlist, "hawki.hawki_cal_dark.nsamples") ;
00801     hawki_cal_dark_config.nsamples = cpl_parameter_get_int(par) ;
00802     par = cpl_parameterlist_find(parlist, "hawki.hawki_cal_dark.zone") ;
00803     sval = cpl_parameter_get_string(par) ;
00804     if (sscanf(sval, "%d,%d,%d,%d",
00805                     &hawki_cal_dark_config.llx,
00806                     &hawki_cal_dark_config.lly,
00807                     &hawki_cal_dark_config.urx,
00808                     &hawki_cal_dark_config.ury)!=4) {
00809         return -1 ;
00810     }
00811     par = cpl_parameterlist_find(parlist, "hawki.hawki_cal_dark.gain") ;
00812     hawki_cal_dark_config.gain = cpl_parameter_get_double(par);
00813     par = cpl_parameterlist_find(parlist, "hawki.hawki_cal_dark.ron") ;
00814     hawki_cal_dark_config.ron = cpl_parameter_get_double(par);
00815     hawki_cal_dark_config.error_tracking = 0; 
00816     if(hawki_cal_dark_config.gain > 0 && hawki_cal_dark_config.ron > 0)
00817         hawki_cal_dark_config.error_tracking = 1; 
00818     
00819     if(!cpl_errorstate_is_equal(error_prevstate))
00820         return -1;
00821 
00822     return 0;
00823 }
00824 
00825 void hawki_cal_dark_initialise_qc(void)
00826 {
00827     int idet;
00828     int j;
00829     
00830     for(idet=0; idet<HAWKI_NB_DETECTORS; idet++) 
00831     {
00832         hawki_cal_dark_outputs.nb_badpix[idet] = -1 ;
00833         hawki_cal_dark_outputs.master_dark_mean[idet] = -1.0 ;
00834         hawki_cal_dark_outputs.master_dark_med[idet] = -1.0 ;
00835         hawki_cal_dark_outputs.master_dark_stdev[idet] = -1.0 ;
00836         hawki_cal_dark_outputs.master_dark_error_mean[idet] = -1.0 ;
00837         hawki_cal_dark_outputs.master_dark_error_med[idet] = -1.0 ;
00838         hawki_cal_dark_outputs.master_dark_error_stdev[idet] = -1.0 ;
00839         for (j=0 ; j<HAWKI_NB_VC ; j++) 
00840         {
00841             hawki_cal_dark_outputs.vc_mean[idet][j] = -1.0 ;
00842             hawki_cal_dark_outputs.vc_med[idet][j] = -1.0 ;
00843             hawki_cal_dark_outputs.vc_stdev[idet][j] = -1.0 ;
00844         }
00845     }
00846 }

Generated on 10 Jun 2010 for HAWKI Pipeline Reference Manual by  doxygen 1.6.1