uves_reduce_mflat.c

00001 /*                                                                              *
00002  *   This file is part of the ESO UVES Pipeline                                 *
00003  *   Copyright (C) 2004,2005 European Southern Observatory                      *
00004  *                                                                              *
00005  *   This library is free software; you can redistribute it and/or modify       *
00006  *   it under the terms of the GNU General Public License as published by       *
00007  *   the Free Software Foundation; either version 2 of the License, or          *
00008  *   (at your option) any later version.                                        *
00009  *                                                                              *
00010  *   This program is distributed in the hope that it will be useful,            *
00011  *   but WITHOUT ANY WARRANTY; without even the implied warranty of             *
00012  *   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the              *
00013  *   GNU General Public License for more details.                               *
00014  *                                                                              *
00015  *   You should have received a copy of the GNU General Public License          *
00016  *   along with this program; if not, write to the Free Software                *
00017  *   Foundation, 51 Franklin St, Fifth Floor, Boston, MA  02111-1307  USA       *
00018  *                                                                              */
00019 
00020 /*
00021  * $Author: amodigli $
00022  * $Date: 2007/10/05 16:01:45 $
00023  * $Revision: 1.29 $
00024  * $Name: uves-3_4_5 $
00025  * $Log: uves_reduce_mflat.c,v $
00026  * Revision 1.29  2007/10/05 16:01:45  amodigli
00027  * using proces_chip parameter to process or not a given RED chip
00028  *
00029  * Revision 1.28  2007/09/11 12:55:37  amodigli
00030  * uses uves_frameset_extract to get the SFLAT raw frames
00031  *
00032  * Revision 1.26  2007/08/21 13:08:26  jmlarsen
00033  * Removed irplib_access module, largely deprecated by CPL-4
00034  *
00035  * Revision 1.25  2007/06/28 12:03:32  jmlarsen
00036  * In FLAMES mode, remove any UVES frames from input frameset
00037  *
00038  * Revision 1.24  2007/06/28 09:28:07  jmlarsen
00039  * Insert MASTER_SFLAT into recipe frameset
00040  *
00041  * Revision 1.23  2007/06/22 09:29:02  jmlarsen
00042  * Changed interface of uves_save_image
00043  *
00044  * Revision 1.22  2007/06/06 08:17:33  amodigli
00045  * replace tab with 4 spaces
00046  *
00047  * Revision 1.21  2007/05/22 11:31:35  jmlarsen
00048  * Removed image plotting functionality
00049  *
00050  * Revision 1.20  2007/04/24 16:45:17  amodigli
00051  * changed interface of calls to uves_load_ordertable to match new interface
00052  *
00053  * Revision 1.19  2007/04/24 12:50:29  jmlarsen
00054  * Replaced cpl_propertylist -> uves_propertylist which is much faster
00055  *
00056  * Revision 1.18  2007/04/03 06:29:29  amodigli
00057  * changed interface to uves_load_ordertable
00058  *
00059  * Revision 1.17  2007/02/09 13:40:55  jmlarsen
00060  * Enable calling from uves_mkmaster_sflat
00061  *
00062  * Revision 1.16  2007/02/09 08:59:05  jmlarsen
00063  * Include <float.h>
00064  *
00065  * Revision 1.15  2007/02/09 08:14:16  jmlarsen
00066  * Do not use CPL_PIXEL_MAXVAL which works only for integer images
00067  *
00068  * Revision 1.14  2007/01/10 14:17:13  jmlarsen
00069  * Do not threshold master flat to zero
00070  *
00071  * Revision 1.13  2006/12/07 08:23:23  jmlarsen
00072  * uves_load_raw_imagelist: support FLAMES
00073  *
00074  * Revision 1.12  2006/12/01 12:30:15  jmlarsen
00075  * Load FLAMES order table oshift/yshift
00076  *
00077  * Revision 1.11  2006/11/16 14:12:21  jmlarsen
00078  * Changed undefined trace number from 0 to -1, to support zero as an actual 
00079  * trace number
00080  *
00081  * Revision 1.10  2006/11/15 15:02:15  jmlarsen
00082  * Implemented const safe workarounds for CPL functions
00083  *
00084  * Revision 1.8  2006/11/15 14:04:08  jmlarsen
00085  * Removed non-const version of parameterlist_get_first/last/next which is 
00086  * already in CPL, added const-safe wrapper, unwrapper and deallocator functions
00087  *
00088  * Revision 1.7  2006/11/13 12:47:39  jmlarsen
00089  * Don't subtract background for FLAMES reduction
00090  *
00091  * Revision 1.6  2006/11/06 15:19:41  jmlarsen
00092  * Removed unused include directives
00093  *
00094  * Revision 1.5  2006/10/24 14:08:16  jmlarsen
00095  * Added flames flag when loading frames
00096  *
00097  * Revision 1.4  2006/10/09 13:04:58  jmlarsen
00098  * Use macro to define recipe interface functions
00099  *
00100  * Revision 1.3  2006/10/02 08:38:16  jmlarsen
00101  * Added REF_TFLAT computation
00102  *
00103  * Revision 1.2  2006/09/27 15:08:45  jmlarsen
00104  * Fixed doc. bug
00105  *
00106  * Revision 1.1  2006/09/27 13:22:04  jmlarsen
00107  * Factored out flat reduction
00108  *
00109  * Revision 1.4  2006/08/17 13:56:52  jmlarsen
00110  * Reduced max line length
00111  *
00112  * Revision 1.3  2005/12/19 16:17:56  jmlarsen
00113  * Replaced bool -> int
00114  *
00115  */
00116 
00117 #ifdef HAVE_CONFIG_H
00118 #  include <config.h>
00119 #endif
00120 
00121 /*----------------------------------------------------------------------------*/
00126 /*----------------------------------------------------------------------------*/
00131 /*-----------------------------------------------------------------------------
00132                                 Includes
00133  -----------------------------------------------------------------------------*/
00134 #include <uves_reduce_mflat.h>
00135 
00136 #include <uves.h>
00137 #include <uves_backsub.h>
00138 #include <uves_chip.h>
00139 #include <uves_dfs.h>
00140 #include <uves_pfits.h>
00141 #include <uves_parameters.h>
00142 #include <uves_utils.h>
00143 #include <uves_utils_wrappers.h>
00144 #include <uves_qclog.h>
00145 #include <uves_error.h>
00146 #include <uves_msg.h>
00147 
00148 #include <cpl.h>
00149 #include <float.h>
00150 
00151 /*-----------------------------------------------------------------------------
00152                             Functions prototypes
00153  -----------------------------------------------------------------------------*/
00154 
00155 static void uves_mflat_qclog(const cpl_imagelist* raw_images,
00156                      cpl_table* qclog);
00157 
00158 static cpl_error_code uves_msflats(cpl_frameset * set, const cpl_parameterlist *parameters,
00159                    const char *recipe_id,
00160                    const char *starttime);
00161 static void uves_mflat_one(cpl_frameset *frames,
00162                const cpl_parameterlist *parameters, 
00163                bool flames,
00164                const char *recipe_id,
00165                const char *starttime,
00166                const char* prefix);
00167 
00168 static cpl_error_code
00169 uves_mflat_at_ypos(cpl_frameset* set,
00170            const cpl_parameterlist* parameters,
00171            const char *recipe_id,
00172            const char *starttime,
00173                    const cpl_frameset* raw,
00174                    const cpl_frameset* cdb,
00175                    const int ref_x1enc,
00176                    const int ref_x2enc,
00177            const int set_no);
00178 
00179 static void uves_reduce_mflat(cpl_frameset *frames, const cpl_parameterlist *parameters,
00180                   bool flames,
00181                   const char *recipe_id, 
00182                   const char *starttime,
00183                   const char *prefix);
00184 
00185 /*-----------------------------------------------------------------------------
00186                             Implementation
00187  -----------------------------------------------------------------------------*/
00188 const char * const uves_mflat_desc =
00189 "This recipe creates a master flat frame by 1) subtracting the master bias\n"
00190 "frame from each flat field frame, 2) dividing each flat field frame by the\n"
00191 " exposure time for that frame, 3) taking the median of all bias subtracted,\n"
00192 " normalized raw\n flat frames, 4) optionally subtracting the master dark \n"
00193 "frame, and 5) subtracting\n the background to get the bias subtracted, \n"
00194 "optionally dark subtracted, normalized, background subtracted master \n"
00195 "flat-field frame. Symbolically,\n"
00196 " masterflat = median( (flat_i - masterbias)/exptime_i ) - masterdark/exptime\n"
00197 "            - background.\n"
00198 "\n"
00199 "The input flat field frames must have same tag which must match\n"
00200 "(I|D|S|T|SCREEN|)FLAT_(BLUE|RED), for example TFLAT_BLUE or FLAT_RED. Also, a\n"
00201 "master bias (MASTER_BIAS_xxxx) and ordertable (ORDER_TABLE_xxxx) must be\n"
00202 "provided for each chip (xxxx = BLUE, REDL, REDU). A master dark frame\n"
00203 "(MASTER_(P)DARK_xxxx) may optionally be provided. On blue input the recipe\n"
00204 "computes one master flat field frame; on red input the recipe produces a\n"
00205 "master flat field frame for each chip (MASTER_FLAT_xxxx, MASTER_IFLAT_xxxx,\n"
00206 "MASTER_DFLAT_xxxx, MASTER_TFLAT_xxxx or MASTER_SCREEN_FLAT_xxxx).";
00207 
00208 /*----------------------------------------------------------------------------*/
00215 /*----------------------------------------------------------------------------*/
00216 int
00217 uves_mflat_define_parameters_body(cpl_parameterlist *parameters, 
00218                   const char *recipe_id)
00219 {
00220     /*****************
00221      *    General    *
00222      *****************/
00223     if (uves_define_global_parameters(parameters) != CPL_ERROR_NONE)
00224     {
00225         return -1;
00226     }
00227 
00228     
00229     /****************************
00230      *  Spline back.sub.        *
00231      ****************************/
00232     
00233     if (uves_propagate_parameters_step(UVES_BACKSUB_ID, parameters, 
00234                        recipe_id, NULL) != 0)
00235     {
00236         return -1;
00237     }
00238 
00239     return (cpl_error_get_code() != CPL_ERROR_NONE);
00240 }
00241 
00242 /*----------------------------------------------------------------------------*/
00280 /*----------------------------------------------------------------------------*/
00281 static cpl_image *
00282 uves_mflat_process_chip(const cpl_imagelist *raw_images, uves_propertylist **raw_headers, 
00283             uves_propertylist *master_flat_header,
00284             const cpl_image *master_bias,
00285             const cpl_image *master_dark, const uves_propertylist *mdark_header, 
00286             const cpl_table *ordertable, const polynomial *order_locations,
00287             bool flames,
00288             const cpl_parameterlist *parameters,
00289             enum uves_chip chip,
00290             const char *recipe_id,
00291             bool DEBUG,
00292             cpl_image **background)
00293 
00294 {
00295     cpl_image *master_flat        = NULL; /* Result */
00296     cpl_image *current_flat       = NULL;
00297     cpl_imagelist *preproc_images = NULL;
00298     int i;
00299 
00300     /* First process each input image and store the results in a new image list */
00301 
00302     preproc_images = cpl_imagelist_new();
00303     for (i = 0; i < cpl_imagelist_get_size(raw_images); i++)
00304     {
00305         double exposure_time = 0.0;
00306 
00307         const uves_propertylist *current_header = NULL;
00308 
00309         current_flat   = cpl_image_duplicate(cpl_imagelist_get_const(raw_images, i));
00310         current_header = raw_headers[i];
00311         
00312         /* Subtract master bias */
00313         if (master_bias != NULL)
00314         {
00315             uves_msg("Subtracting master bias");
00316             check( uves_subtract_bias(current_flat, master_bias), 
00317                "Error subtracting master bias");
00318         }
00319         else
00320         {
00321             uves_msg("Skipping bias subtraction");
00322         }
00323         
00324         /* Normalize to unit exposure time */
00325         check( exposure_time = uves_pfits_get_exptime(current_header), 
00326            "Error reading exposure time");
00327         
00328         uves_msg("Normalizing flat from %f s to unit exposure time", exposure_time);
00329         check( cpl_image_divide_scalar(current_flat, exposure_time),
00330            "Error normalizing flat field");
00331         check( uves_pfits_set_exptime(master_flat_header, 1.0),
00332            "Error writing master frame exposure time");
00333         
00334         /* Append to imagelist */
00335         check( cpl_imagelist_set(preproc_images,     /* Image list */
00336                      current_flat,       /* Image to insert */
00337                      i),                 /* Position (number_of_images=>append) */
00338            "Could not insert image into image list");
00339         
00340         /* Don't deallocate the image. It will be deallocated when
00341            the image list is deallocated */
00342         current_flat = NULL;
00343     }
00344     
00345     /* Take median of all input flats */
00346     uves_msg("Calculating stack median");
00347     check( master_flat = cpl_imagelist_collapse_median_create(preproc_images), 
00348        "Error computing median");
00349     
00350     /* Subtract master dark if present */
00351     if (master_dark != NULL)
00352     {
00353         uves_msg("Subtracting master dark");
00354         check( uves_subtract_dark(master_flat, master_flat_header,
00355                       master_dark, mdark_header), 
00356            "Error subtracting master dark");
00357     }
00358     else
00359     {
00360         uves_msg("Skipping dark subtraction");
00361     }
00362 
00363     if (DEBUG && !flames)
00364     {
00365         check( uves_save_image_local("Pre-background subtracted master flat", "pre",
00366                                      master_flat, chip, -1, -1, master_flat_header, true), 
00367            "Error saving image");
00368     }
00369     
00370     /* Subtract background from master flat */
00371     if (!flames)
00372     {
00373         uves_msg("Subtracting background");
00374         
00375         check( uves_backsub_spline(master_flat, 
00376                        /* Info about chip (wavelength, ...) is 
00377                       stored in any raw header,
00378                       so just pass the first one   */
00379                        raw_headers[0],                
00380                        ordertable, order_locations, 
00381                        parameters, recipe_id,
00382                        chip,
00383                        true,     /* Use flat-field parameters? */
00384                        background),
00385            "Error subtracting background from master flat");
00386     }
00387     else
00388     {
00389         uves_msg("Skipping background subtraction");
00390     }
00391         
00392   cleanup:
00393     uves_free_imagelist(&preproc_images);
00394     uves_free_image(&current_flat);
00395     if (cpl_error_get_code() != CPL_ERROR_NONE)
00396     {
00397         uves_free_image(&master_flat);
00398     }
00399     
00400     return master_flat;
00401 }
00402 
00403 /*----------------------------------------------------------------------------*/
00415 /*----------------------------------------------------------------------------*/
00416 void
00417 uves_mflat_exe_body(cpl_frameset *frames, 
00418                     const cpl_parameterlist *parameters,
00419                     const char *starttime,
00420                     const char *recipe_id)
00421 {
00422     /* Do FLAMES reduction if SFLAT frame is given */
00423     if (cpl_frameset_find(frames, UVES_SFLAT(false)) != NULL) {
00424   
00425         check(uves_msflats(frames, parameters, recipe_id, starttime),
00426               "find same sflats failed");
00427     }
00428     else {
00429         bool flames = false;
00430         check(uves_mflat_one(frames, parameters, flames, recipe_id, 
00431                              starttime, ""),
00432               "Master flat one failed");
00433     }
00434     
00435  cleanup:
00436     return;
00437 }
00438 
00439 /*----------------------------------------------------------------------------*/
00445 /*----------------------------------------------------------------------------*/
00446 static cpl_error_code
00447 uves_msflats(cpl_frameset * set, const cpl_parameterlist *parameters,
00448          const char *recipe_id,
00449          const char *starttime)
00450 {
00451   /* Pseudocode:
00452      extract raw frames from set
00453      extract cdb frames from set
00454      identifies how many different Y position we have 
00455      for each Y pos:
00456          extract from the raw_set the raw frames corresponding to each Y pos 
00457          merge in a new wrk_set the cdb_set 
00458          computes the corresponding master flat 
00459          put the products in the final set 
00460      endfor 
00461   */
00462   cpl_frameset* raw=NULL;
00463   cpl_frameset* cdb=NULL;
00464   cpl_frameset* pro=NULL;
00465   int status=0;
00466   int x1enc=0;
00467   int x2enc=0;
00468 
00469   cpl_table* encoder_tbl=NULL;
00470   int nset=0;
00471   int i=0;
00472 
00473   //Extracts SFLAT raw frames 
00474   check(raw=uves_frameset_extract(set,UVES_SFLAT(false)),
00475                   "Extract %s frames failed",
00476                   UVES_SFLAT(false));
00477 
00478   check(uves_extract_frames_group_type(set,&cdb,CPL_FRAME_GROUP_CALIB),
00479     "Extract cdb frames failed");
00480   check(uves_sflats_get_encoder_steps(raw,&encoder_tbl,&nset),
00481     "Get encoder steps failed");
00482   uves_msg("Check Slit Flat Field Y nominal positions within each set");
00483   for(i=0;i<nset;i++) {
00484 
00485          uves_msg("Slit Flat field set %d: x1enc = %d x2enc = %d",
00486               i+1,
00487               cpl_table_get_int(encoder_tbl,"x1enc",i,&status),
00488               cpl_table_get_int(encoder_tbl,"x2enc",i,&status));
00489 
00490   }
00491 
00492   for(i=0;i<nset;i++) {
00493     x1enc=cpl_table_get_int(encoder_tbl,"x1enc",i,&status);
00494     x2enc=cpl_table_get_int(encoder_tbl,"x2enc",i,&status);
00495 
00496     uves_msg("Processing set %d", i+1);
00497    
00498     check(uves_mflat_at_ypos(set,parameters,recipe_id,starttime,raw,cdb,x1enc,x2enc,i+1),
00499       "Master flat one failed");
00500   }
00501 
00502   cleanup:
00503   uves_free_table(&encoder_tbl);
00504   uves_free_frameset(&raw);
00505   uves_free_frameset(&cdb);
00506   uves_free_frameset(&pro);
00507 
00508     return cpl_error_get_code();
00509 }
00510 
00511 
00512 /*----------------------------------------------------------------------------*/
00518 /*----------------------------------------------------------------------------*/
00519 static cpl_error_code
00520 uves_mflat_at_ypos(cpl_frameset* set,
00521            const cpl_parameterlist* parameters,
00522            const char *recipe_id,
00523            const char *starttime,
00524                    const cpl_frameset* raw,
00525                    const cpl_frameset* cdb,
00526                    const int ref_x1enc,
00527                    const int ref_x2enc,
00528                    const int set_no)
00529 {
00530 
00531     const cpl_frame* frm_tmp=NULL;
00532   char* file=NULL;
00533   uves_propertylist* plist=NULL;
00534   int i=0;
00535   const int threshold = 5;
00536   cpl_frame* frm_dup=NULL;
00537   cpl_frameset* tmp=NULL;
00538   cpl_frameset* pro=NULL;
00539   int x1enc=0;
00540   int x2enc=0;
00541   char prefix[255];
00542   bool flames = true;
00543 
00544   check_nomsg(tmp=cpl_frameset_new());
00545    for(i=0;i<cpl_frameset_get_size(raw);i++)
00546     {
00547     check_nomsg(frm_tmp=cpl_frameset_get_frame_const(raw,i));
00548     check_nomsg(file=cpl_strdup(cpl_frame_get_filename(frm_tmp)));
00549     check_nomsg(plist=uves_propertylist_load(file,0));
00550     check_nomsg(x1enc=uves_pfits_get_slit3_x1encoder(plist));
00551     check_nomsg(x2enc=uves_pfits_get_slit3_x2encoder(plist));
00552     
00553     if( (fabs(x1enc - ref_x1enc) <= threshold) &&
00554         (fabs(x2enc - ref_x2enc) <= threshold) ) {
00555       uves_msg_debug("file=%s x1enc=%d x2enc=%d",file,x1enc,x2enc);
00556       check(frm_dup = cpl_frame_duplicate(frm_tmp),"duplicate");
00557       check(cpl_frameset_insert(tmp,frm_dup),"insert");
00558     }
00559     cpl_free(file);
00560     uves_free_propertylist(&plist);
00561     }
00562    check_nomsg(uves_frameset_merge(tmp,cdb));
00563    sprintf(prefix,"%s%d%s","set",set_no,"_");
00564    check(uves_mflat_one(tmp,parameters, flames, recipe_id, starttime,prefix),"Master flat one failed");
00565    check_nomsg(uves_extract_frames_group_type(tmp,&pro,CPL_FRAME_GROUP_PRODUCT));
00566    check_nomsg(uves_frameset_merge(set,pro));
00567 
00568  cleanup:
00569    uves_free_frameset(&tmp);
00570    uves_free_frameset(&pro);
00571    uves_free_propertylist(&plist);
00572   
00573     return cpl_error_get_code();
00574 }
00575 /*----------------------------------------------------------------------------*/
00588 /*----------------------------------------------------------------------------*/
00589 static void
00590 uves_mflat_one(cpl_frameset *frames,
00591            const cpl_parameterlist *parameters, 
00592            bool flames,
00593            const char *recipe_id,
00594            const char *starttime,
00595                const char* prefix)
00596 {
00597     /* Do flat-fielding */
00598     check_nomsg( uves_reduce_mflat(frames, parameters, 
00599                    flames, recipe_id,
00600                    starttime, prefix) );
00601 
00602   cleanup:
00603     return;
00604 }
00605 
00606 /*----------------------------------------------------------------------------*/
00617 /*----------------------------------------------------------------------------*/
00618 static void
00619 uves_reduce_mflat(cpl_frameset *frames, const cpl_parameterlist *parameters,
00620           bool flames,
00621           const char *recipe_id, 
00622           const char *starttime,
00623           const char *prefix)
00624 {
00625     bool DEBUG;
00626 
00627     /* Input */
00628     cpl_imagelist       *raw_images[2] = {NULL, NULL}; /* An image list for both chips */
00629     uves_propertylist  **raw_headers[2] = {NULL, NULL}; /* Two arrays of pointers */
00630 
00631     /* Master bias */
00632     cpl_image *master_bias               = NULL;
00633     uves_propertylist *master_bias_header = NULL;
00634 
00635     /* Master dark */
00636     cpl_image *master_dark               = NULL;
00637     uves_propertylist *master_dark_header = NULL;
00638 
00639     /* Order table */
00640     cpl_table        *ordertable            = NULL;
00641     uves_propertylist *ordertable_header     = NULL;
00642     polynomial       *order_locations       = NULL;
00643     cpl_table        *traces                = NULL;
00644     
00645     /* Reference master flat */
00646     cpl_image        *ref_flat              = NULL;
00647     uves_propertylist *ref_flat_header       = NULL;
00648 
00649     /* Output */
00650     cpl_table *qclog[]                  = {NULL, NULL};
00651     cpl_image *master_flat              = NULL;
00652     cpl_image *background               = NULL;
00653     uves_propertylist *product_header[]  = {NULL, NULL};
00654     cpl_image *ratio                    = NULL;
00655     
00656     /* Local variables */
00657     char *product_filename = NULL;
00658     char pro_filename[255];
00659     const char *product_tag[2] = {NULL, NULL};
00660     bool blue;
00661     enum uves_chip chip;
00662     const char* PROCESS_CHIP=NULL;
00663 
00664     /* Read recipe parameters */
00665     {
00666     /* General */
00667     check( uves_get_parameter(parameters, NULL, "uves", "debug", CPL_TYPE_BOOL  , &DEBUG ), 
00668            "Could not read parameter");
00669     }
00670     check( uves_get_parameter(parameters, NULL, "uves", "process_chip", CPL_TYPE_STRING, &PROCESS_CHIP), "Could not read parameter");
00671 
00672     /* Load and check raw flat images and headers, identify arm (blue/red) */
00673     /* On success, 'raw_headers' will be an array with the same size as 'raw_images' */
00674     /* Set product tags to match input tag */
00675     
00676     if (cpl_frameset_find(frames, UVES_FLAT(true )) != NULL ||
00677     cpl_frameset_find(frames, UVES_FLAT(false)) != NULL)
00678     {
00679         check( uves_load_raw_imagelist(frames, 
00680                        flames,
00681                        UVES_FLAT(true), UVES_FLAT(false),
00682                        CPL_TYPE_DOUBLE,
00683                        raw_images, raw_headers, product_header, 
00684                        &blue), "Error loading raw flat frames");
00685         
00686         for (chip = uves_chip_get_first(blue); chip != UVES_CHIP_INVALID; 
00687          chip = uves_chip_get_next(chip))
00688         {
00689             product_tag[uves_chip_get_index(chip)] = UVES_MASTER_FLAT(chip);
00690         }
00691     }
00692     else if (cpl_frameset_find(frames, UVES_DFLAT(true )) != NULL ||
00693          cpl_frameset_find(frames, UVES_DFLAT(false)) != NULL)
00694     {
00695         check( uves_load_raw_imagelist(frames, 
00696                        flames,
00697                        UVES_DFLAT(true), UVES_DFLAT(false),
00698                        CPL_TYPE_DOUBLE,
00699                        raw_images, raw_headers, product_header, 
00700                        &blue), "Error loading raw flat frames");
00701         for (chip = uves_chip_get_first(blue); 
00702          chip != UVES_CHIP_INVALID; 
00703          chip = uves_chip_get_next(chip))
00704         {
00705             product_tag[uves_chip_get_index(chip)] = UVES_MASTER_DFLAT(chip);
00706         }
00707     }
00708     else if  (cpl_frameset_find(frames, UVES_IFLAT(true )) != NULL ||
00709           cpl_frameset_find(frames, UVES_IFLAT(false)) != NULL)
00710     {
00711         check( uves_load_raw_imagelist(frames, 
00712                        flames,
00713                        UVES_IFLAT(true), UVES_IFLAT(false),
00714                        CPL_TYPE_DOUBLE,
00715                        raw_images, raw_headers, product_header, 
00716                        &blue), "Error loading raw flat frames");
00717         for (chip = uves_chip_get_first(blue); 
00718          chip != UVES_CHIP_INVALID; 
00719          chip = uves_chip_get_next(chip))
00720         {
00721             product_tag[uves_chip_get_index(chip)] = UVES_MASTER_IFLAT(chip);
00722         }
00723     }
00724     else if  (cpl_frameset_find(frames, UVES_TFLAT(true )) != NULL ||
00725           cpl_frameset_find(frames, UVES_TFLAT(false)) != NULL)
00726     {
00727         check( uves_load_raw_imagelist(frames, 
00728                        flames,
00729                        UVES_TFLAT(true), UVES_TFLAT(false),
00730                        CPL_TYPE_DOUBLE,
00731                        raw_images, raw_headers, product_header, 
00732                        &blue), "Error loading raw flat frames");
00733         for (chip = uves_chip_get_first(blue); 
00734          chip != UVES_CHIP_INVALID; 
00735          chip = uves_chip_get_next(chip))
00736         {
00737             product_tag[uves_chip_get_index(chip)] = UVES_MASTER_TFLAT(chip);
00738         }
00739     }
00740     else if  (cpl_frameset_find(frames, UVES_SCREEN_FLAT(true )) != NULL ||
00741           cpl_frameset_find(frames, UVES_SCREEN_FLAT(false)) != NULL)
00742     {
00743         check( uves_load_raw_imagelist(frames, 
00744                        flames,
00745                        UVES_SCREEN_FLAT(true), UVES_SCREEN_FLAT(false),
00746                        CPL_TYPE_DOUBLE,
00747                        raw_images, raw_headers, product_header, 
00748                        &blue), "Error loading raw flat frames");
00749         for (chip = uves_chip_get_first(blue); 
00750          chip != UVES_CHIP_INVALID; 
00751          chip = uves_chip_get_next(chip))
00752         {
00753             product_tag[uves_chip_get_index(chip)] = UVES_MASTER_SCREEN_FLAT(chip);
00754         }
00755     }
00756     else if  (cpl_frameset_find(frames, UVES_SFLAT(true )) != NULL ||
00757           cpl_frameset_find(frames, UVES_SFLAT(false)) != NULL)
00758     {
00759         check( uves_load_raw_imagelist(frames, 
00760                        flames,
00761                        UVES_SFLAT(true), UVES_SFLAT(false),
00762                        CPL_TYPE_DOUBLE,
00763                        raw_images, raw_headers, product_header, 
00764                        &blue), "Error loading raw flat frames");
00765         for (chip = uves_chip_get_first(blue); 
00766          chip != UVES_CHIP_INVALID; 
00767          chip = uves_chip_get_next(chip))
00768         {
00769             product_tag[uves_chip_get_index(chip)] = UVES_MASTER_SFLAT(chip);
00770         }
00771     }
00772     else 
00773     {
00774         assure(false, CPL_ERROR_DATA_NOT_FOUND,
00775            "Missing input flat frame: "
00776            "%s, %s, %s, %s, %s, %s, %s, %s, %s, %s, %s or %s expected",
00777            UVES_FLAT(true) , UVES_FLAT(false),
00778            UVES_DFLAT(true), UVES_DFLAT(false),
00779            UVES_IFLAT(true), UVES_IFLAT(false),
00780            UVES_TFLAT(true), UVES_TFLAT(false),
00781            UVES_SCREEN_FLAT(true), UVES_SCREEN_FLAT(false),
00782            UVES_SFLAT(true), UVES_SFLAT(false));
00783     }
00784 
00785     /* Loop over one or two chips */
00786     for (chip = uves_chip_get_first(blue); 
00787      chip != UVES_CHIP_INVALID; 
00788      chip = uves_chip_get_next(chip))
00789     {
00790 
00791       if(strcmp(PROCESS_CHIP,"redu") == 0) {
00792     chip = uves_chip_get_next(chip);
00793       }
00794 
00795 
00796         const char *ordertable_filename = "";
00797         const char *master_bias_filename = "";
00798         const char *master_dark_filename = "";
00799         const char *chip_name = "";
00800         
00801         int raw_index = uves_chip_get_index(chip);
00802         
00803         uves_msg("Processing %s chip", uves_chip_tostring_upper(chip));
00804 
00805         /* Chip name of first input frame */
00806         check_nomsg( chip_name = uves_pfits_get_chipid(raw_headers[raw_index][0], chip));
00807 
00808         /* Load master bias, set pointer to NULL if not present */
00809         uves_free_image(&master_bias);
00810         uves_free_propertylist(&master_bias_header);
00811         if (cpl_frameset_find(frames, UVES_MASTER_BIAS(chip)) != NULL)
00812         {
00813             uves_free_image(&master_bias);
00814             uves_free_propertylist(&master_bias_header);
00815             check( uves_load_mbias(frames,
00816                        chip_name,
00817                        &master_bias_filename, &master_bias,
00818                        &master_bias_header, chip), 
00819                "Error loading master bias");
00820             
00821             uves_msg_low("Using master bias in '%s'", master_bias_filename);
00822         }
00823         else
00824         {
00825             uves_msg_low("No master bias in SOF. Bias subtraction not done");
00826         }
00827     
00828         /* Load master dark, set pointer to NULL if not present */
00829         uves_free_image(&master_dark);
00830         uves_free_propertylist(&master_dark_header);
00831         if (cpl_frameset_find(frames, UVES_MASTER_DARK(chip))  != NULL ||
00832         cpl_frameset_find(frames, UVES_MASTER_PDARK(chip)) != NULL)
00833         {
00834             uves_free_image(&master_dark);
00835             uves_free_propertylist(&master_dark_header);
00836             check( uves_load_mdark(frames, chip_name,
00837                        &master_dark_filename, &master_dark,
00838                        &master_dark_header, chip), 
00839                "Error loading master dark");
00840             
00841             uves_msg_low("Using master dark in '%s'", master_dark_filename);
00842         }
00843         else
00844         {
00845             uves_msg_low("No master dark in SOF. Dark subtraction not done");
00846         }
00847     
00848         /* Load the order table for this chip */
00849         if (flames)
00850         /* FLAMES does not do background subtraction (here)
00851            and therefore does not need an ordertable */
00852         {
00853             if (cpl_frameset_find(frames, UVES_ORDER_TABLE(flames, chip)) != NULL)
00854             {
00855                 uves_msg_warning("Order table (%s) is not used in FLAMES reduction",
00856                          UVES_ORDER_TABLE(flames, chip));
00857             }
00858         }
00859         else
00860         {
00861             uves_free_table       (&ordertable);
00862             uves_free_propertylist(&ordertable_header);
00863             uves_polynomial_delete(&order_locations);
00864             uves_free_table       (&traces);
00865             
00866             check( uves_load_ordertable(frames,
00867                         flames,
00868                         chip_name,
00869                         &ordertable_filename, 
00870                                                 &ordertable,
00871                         &ordertable_header, 
00872                                                 NULL,
00873                                                 &order_locations,
00874                         &traces, NULL, NULL,
00875                                        NULL, NULL, /* fibre_pos,fibre_mask */
00876                         chip,
00877                         false),
00878                "Could not load order table");
00879             uves_msg("Using order table in '%s'", ordertable_filename);
00880         }
00881         
00882         /* Process chip */
00883         uves_free_image(&master_flat);
00884         uves_free_image(&background);
00885         check( master_flat = uves_mflat_process_chip(
00886                raw_images[raw_index], raw_headers[raw_index],
00887                product_header[raw_index],
00888                master_bias,
00889                master_dark, master_dark_header,
00890                ordertable, order_locations,
00891                flames,
00892                parameters,
00893                chip,
00894                recipe_id,
00895                DEBUG,
00896                &background),
00897            "Error processing chip");
00898 
00899         /* Finished. Compute QC parameters and save */
00900         uves_msg("Computing QC parameters");
00901             uves_qclog_delete(&qclog[0]);
00902             qclog[0] = uves_qclog_init(raw_headers[raw_index][0], chip);
00903 
00904             check(uves_mflat_qclog(raw_images[raw_index],
00905                    qclog[0]),"error computing qclog");
00906     
00907         uves_msg("Saving products");
00908     
00909         cpl_free(product_filename);
00910         check( product_filename = uves_masterflat_filename(chip), 
00911                "Error getting filename");
00912         strcpy(pro_filename,prefix);
00913         strcat(pro_filename,product_filename);
00914         check( uves_frameset_insert(
00915                    frames,
00916                    master_flat,
00917                    CPL_FRAME_GROUP_PRODUCT,
00918                    CPL_FRAME_TYPE_IMAGE,
00919                    CPL_FRAME_LEVEL_INTERMEDIATE,
00920                    pro_filename,
00921                    product_tag[raw_index],
00922                    raw_headers[raw_index][0],
00923                    product_header[raw_index],
00924                    NULL,
00925                    parameters,
00926                    recipe_id,
00927                    PACKAGE "/" PACKAGE_VERSION, qclog,
00928                    starttime, true, UVES_ALL_STATS),
00929                "Could not add master flat %s %s to frameset", 
00930                product_filename, product_tag[raw_index]);
00931         uves_msg("Master flat %s %s added to frameset", 
00932                  pro_filename, product_tag[raw_index]);
00933 
00934         /* Save background image */
00935         if (!flames)
00936         {
00937             cpl_free(product_filename);
00938             check( product_filename = uves_masterflat_bkg_filename(chip), 
00939                "Error getting filename");
00940             strcpy(pro_filename,prefix);
00941             strcat(pro_filename,product_filename);
00942             
00943             check( uves_frameset_insert(frames,
00944                         background,
00945                         CPL_FRAME_GROUP_PRODUCT,
00946                         CPL_FRAME_TYPE_IMAGE,
00947                         CPL_FRAME_LEVEL_INTERMEDIATE,
00948                         pro_filename,
00949                         UVES_BKG_FLAT(chip),
00950                         raw_headers[raw_index][0],
00951                         product_header[raw_index],
00952                         NULL,
00953                         parameters,
00954                         recipe_id,
00955                         PACKAGE "/" PACKAGE_VERSION, NULL,
00956                         starttime, false, 
00957                         CPL_STATS_MIN | CPL_STATS_MAX),
00958                "Could not add background image '%s' to frameset", 
00959                product_filename);
00960             uves_msg("Master flat background '%s' added to frameset", 
00961                  product_filename);
00962                 }
00963 
00964         /* Compute and save ratio MASTER_TFLAT / REF_TFLAT */
00965         if (strcmp(recipe_id, make_str(UVES_TFLAT_ID)) == 0)
00966         {
00967             const char *ref_flat_filename;
00968 
00969             uves_free_image(&ref_flat);
00970             uves_free_propertylist(&ref_flat_header);
00971 
00972             check( uves_load_ref_flat(frames, chip_name, &ref_flat_filename, 
00973                           &ref_flat, &ref_flat_header, 
00974                           chip),
00975                "Error loading reference flat field");
00976             
00977             uves_msg("Using reference flat field in '%s'", ref_flat_filename);
00978 
00979             check( ratio = cpl_image_divide_create(master_flat, ref_flat),
00980                "Error computing ratio of master and reference flat");
00981 
00982             cpl_free(product_filename);
00983             check( product_filename = uves_flat_ratio_filename(chip), 
00984                "Error getting filename");
00985             
00986             check( uves_frameset_insert(frames,
00987                         ratio,
00988                         CPL_FRAME_GROUP_PRODUCT,
00989                         CPL_FRAME_TYPE_IMAGE,
00990                         CPL_FRAME_LEVEL_INTERMEDIATE,
00991                         product_filename,
00992                         UVES_RATIO_TFLAT(chip),
00993                         raw_headers[raw_index][0],
00994                         product_header[raw_index],
00995                         NULL,
00996                         parameters,
00997                         recipe_id,
00998                         PACKAGE "/" PACKAGE_VERSION,
00999                         qclog,
01000                         starttime, false, 
01001                         UVES_ALL_STATS),
01002                "Could not add ratio image '%s' to frameset", product_filename);
01003 
01004             uves_msg("Master flat ratio '%s' added to frameset", product_filename);
01005         }
01006 
01007 
01008       if(strcmp(PROCESS_CHIP,"redl") == 0) {
01009     chip = uves_chip_get_next(chip);
01010       }
01011 
01012     
01013     } /* For each chip */
01014     
01015   cleanup:
01016     /* Input */
01017     if (raw_images[0] != NULL)
01018     {
01019         int i;
01020         for (i = 0; i < cpl_imagelist_get_size(raw_images[0]); i++) 
01021         {
01022             if (raw_headers[0] != NULL) uves_free_propertylist(&raw_headers[0][i]);
01023             if (raw_headers[1] != NULL) uves_free_propertylist(&raw_headers[1][i]);
01024         }
01025         cpl_free(raw_headers[0]); raw_headers[0] = NULL;
01026         cpl_free(raw_headers[1]); raw_headers[1] = NULL;
01027     }
01028 
01029     uves_free_imagelist(&raw_images[0]);
01030     uves_free_imagelist(&raw_images[1]);
01031 
01032     /* Master bias */
01033     uves_free_image(&master_bias);
01034     uves_free_propertylist(&master_bias_header);
01035 
01036     /* Master dark */
01037     uves_free_image(&master_dark);
01038     uves_free_propertylist(&master_dark_header);
01039 
01040     /* Order table */
01041     uves_free_table(&ordertable);
01042     uves_free_propertylist(&ordertable_header);
01043     uves_polynomial_delete(&order_locations);
01044     uves_free_table(&traces);
01045 
01046     /* Reference master flat */
01047     uves_free_image(&ref_flat);
01048     uves_free_propertylist(&ref_flat_header);
01049     
01050     /* Output */
01051     uves_qclog_delete(&qclog[0]);
01052     uves_free_image(&master_flat);
01053     uves_free_image(&background);
01054     uves_free_image(&ratio);
01055     uves_free_propertylist(&product_header[0]);
01056     uves_free_propertylist(&product_header[1]);
01057     cpl_free(product_filename);
01058     
01059     return;
01060 }
01061 
01062 
01063 /*----------------------------------------------------------------------------*/
01069 /*----------------------------------------------------------------------------*/
01070 
01071 static void
01072 uves_mflat_qclog(const cpl_imagelist* raw_images,
01073          cpl_table* qclog)
01074 {
01075   int nraw=0;
01076 
01077   check_nomsg(uves_qclog_add_string(qclog,
01078                         "QC TEST1 ID",
01079                         "Test-on-Master-Flat",
01080                         "Name of QC test",
01081                         "%s"));
01082   check_nomsg(nraw=cpl_imagelist_get_size(raw_images));
01083 
01084   check_nomsg(uves_qclog_add_int(qclog,
01085                         "PRO DATANCOM",
01086                         nraw,
01087                         "Number of frames combined",
01088                         "%d"));
01089  cleanup:
01090   return;
01091 }

Generated on Thu Nov 15 14:32:30 2007 for UVES Pipeline Reference Manual by  doxygen 1.5.1