uves_corrbadpix.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: jmlarsen $
00022  * $Date: 2007/08/21 13:08:26 $
00023  * $Revision: 1.23 $
00024  * $Name: uves-3_9_0 $
00025  * $Log: uves_corrbadpix.c,v $
00026  * Revision 1.23  2007/08/21 13:08:26  jmlarsen
00027  * Removed irplib_access module, largely deprecated by CPL-4
00028  *
00029  * Revision 1.22  2007/07/23 06:37:44  amodigli
00030  * we now support also input data type CPL_TYPE_FLOAT
00031  *
00032  * Revision 1.21  2007/06/06 08:17:33  amodigli
00033  * replace tab with 4 spaces
00034  *
00035  * Revision 1.20  2007/04/24 12:50:29  jmlarsen
00036  * Replaced cpl_propertylist -> uves_propertylist which is much faster
00037  *
00038  * Revision 1.19  2007/01/16 10:26:52  jmlarsen
00039  * Fixed calloc -> cpl_calloc
00040  *
00041  * Revision 1.18  2007/01/15 15:10:01  jmlarsen
00042  * Fixed memory bug in deallocator
00043  *
00044  * Revision 1.17  2007/01/15 13:57:20  jmlarsen
00045  * Fixed crashing BLUE chips
00046  *
00047  * Revision 1.16  2007/01/10 12:35:59  jmlarsen
00048  * Added uves_get_badpix
00049  *
00050  * Revision 1.15  2006/11/15 15:02:14  jmlarsen
00051  * Implemented const safe workarounds for CPL functions
00052  *
00053  * Revision 1.13  2006/11/15 14:04:08  jmlarsen
00054  * Removed non-const version of parameterlist_get_first/last/next which is already
00055  * in CPL, added const-safe wrapper, unwrapper and deallocator functions
00056  *
00057  * Revision 1.12  2006/11/06 15:19:41  jmlarsen
00058  * Removed unused include directives
00059  *
00060  * Revision 1.11  2006/08/17 13:56:52  jmlarsen
00061  * Reduced max line length
00062  *
00063  * Revision 1.10  2006/08/17 09:16:30  jmlarsen
00064  * Removed CPL2 code
00065  *
00066  * Revision 1.9  2006/08/14 12:15:26  jmlarsen
00067  * Update to CPL3
00068  *
00069  * Revision 1.8  2006/08/10 10:49:06  jmlarsen
00070  * Removed workaround for cpl_image_get_bpm
00071  *
00072  * Revision 1.7  2006/08/08 11:27:18  amodigli
00073  * upgrade to CPL3
00074  *
00075  * Revision 1.6  2006/07/07 06:45:23  amodigli
00076  * added doc
00077  *
00078  * Revision 1.5  2006/07/03 14:20:39  jmlarsen
00079  * Exclude bad pixels from order tracing
00080  *
00081  * Revision 1.4  2006/07/03 12:58:34  jmlarsen
00082  * Support flagging instead of interpolating bad pixels
00083  *
00084  * Revision 1.3  2006/04/06 08:29:56  jmlarsen
00085  * Include self
00086  *
00087  * Revision 1.2  2005/12/19 16:17:56  jmlarsen
00088  * Replaced bool -> int
00089  *
00090  * Revision 1.1  2005/11/11 13:18:54  jmlarsen
00091  * Reorganized code, renamed source files
00092  *
00093  */
00094 
00095 #ifdef HAVE_CONFIG_H
00096 #  include <config.h>
00097 #endif
00098 
00099 /*----------------------------------------------------------------------------*/
00105 /*----------------------------------------------------------------------------*/
00108 /*-----------------------------------------------------------------------------
00109                                 Includes
00110  -----------------------------------------------------------------------------*/
00111 
00112 #include "uves_corrbadpix.h"
00113 
00114 #include <uves_pfits.h>
00115 #include <uves_dump.h>
00116 #include <uves_error.h>
00117 #include <uves_msg.h>
00118 
00119 #include <cpl.h>
00120 
00121 #include <stdbool.h>
00122 /*-----------------------------------------------------------------------------
00123                             Functions prototypes
00124  -----------------------------------------------------------------------------*/
00125 static int
00126 uves_correct_badpix(cpl_image *master_bias, uves_propertylist *header, int **badmap,
00127             bool mark_bad);
00128 
00129 /*-----------------------------------------------------------------------------
00130                             Implementation
00131  -----------------------------------------------------------------------------*/
00132 
00133 
00134 /*----------------------------------------------------------------------------*/
00151 /*----------------------------------------------------------------------------*/
00152 int
00153 uves_correct_badpix_all(cpl_image *master_bias, uves_propertylist *mbias_header,
00154             enum uves_chip chip,
00155             int binx, int biny, int mark_bad)
00156 {
00157     int badpixels_cleaned = -1; /* result */
00158 
00159     int **badmap = NULL;
00160 
00161     check( badmap = uves_get_badpix(chip, binx, biny, mark_bad),
00162        "Could not get bad pixel map");
00163 
00164     check( badpixels_cleaned = 
00165        uves_correct_badpix(master_bias, mbias_header, badmap, mark_bad),
00166        "Error cleaning bad pixels");
00167 
00168   cleanup:
00169     uves_badmap_free(&badmap);
00170     return badpixels_cleaned;
00171 }
00172 
00173 
00174 /*----------------------------------------------------------------------------*/
00179 /*----------------------------------------------------------------------------*/
00180 void
00181 uves_badmap_free(int ***badmap)
00182 {
00183     if (badmap != NULL)
00184     {
00185         if (*badmap != NULL)
00186         {
00187             int row;
00188             for (row = 0;
00189              (*badmap)[row][0] != -1;
00190              row++)
00191             {
00192                 cpl_free((*badmap)[row]);
00193             }
00194             cpl_free((*badmap)[row]);
00195 
00196             cpl_free(*badmap);
00197             *badmap = NULL;
00198         }
00199     }
00200 }
00201 
00202 /*----------------------------------------------------------------------------*/
00208 /*----------------------------------------------------------------------------*/
00209 static int **
00210 dup_map(int badmap[][4])
00211 {
00212     int **map = NULL;
00213     int row;
00214     bool finished = false;
00215 
00216     /* The execution time is O(n*n) which is okay, due to the low number
00217        of entries */
00218     
00219     for (row = 0; !finished; row++)
00220     {
00221         map = cpl_realloc(map, (row+1)*sizeof(int *));
00222         /* First time equivalent to: malloc(sizeof(int *)) */
00223 
00224         map[row] = cpl_calloc(4, sizeof(int));
00225         map[row][0] = badmap[row][0];
00226         map[row][1] = badmap[row][1];
00227         map[row][2] = badmap[row][2];
00228         map[row][3] = badmap[row][3];
00229 
00230         finished = (badmap[row][0] == -1);
00231     }
00232     
00233     return map;
00234 }
00235 
00236 
00237 /*----------------------------------------------------------------------------*/
00251 /*----------------------------------------------------------------------------*/
00252 int **
00253 uves_get_badpix(enum uves_chip chip, 
00254         int binx, int biny, int mark_bad)
00255 {
00256     int **map = NULL;
00257 
00258     if (chip == UVES_CHIP_REDL)
00259     {
00260         if (binx == 1 && biny == 1)
00261         {
00262             int badmap[][4] = {{1,4,2088,4},
00263                        {1,63,2282,63},
00264                        {1,108,1778,108},
00265                        {1,176,2443,176},
00266                        {1,196,2021,196},
00267                        {1,285,1974,285},
00268                        {1,352,1942,352},
00269                        {-1,-1,-1,-1}};
00270 
00271             map = dup_map(badmap);
00272         }
00273         else if (binx == 1 && biny == 2)
00274         {
00275             int badmap[][4] = {{1,4,1044,4},
00276                     {1,63,1141,63},
00277                     {1,108,894,108},
00278                     {1,176,1222,176},
00279                     {1,196,1011,196},
00280                     {1,285,988,285},
00281                     {1,352,971,352},
00282                     {-1,-1,-1,-1}};
00283 
00284             map = dup_map(badmap);
00285         }
00286         else if (binx == 2 && biny == 2)
00287         {
00288             int badmap[][4] = {{1,3,1044,3},
00289                        {1,33,1141,33},
00290                        {1,55,894,56},
00291                        {1,89,1222,90},
00292                        {1,99,1011,100},
00293                        {1,144,988,145},
00294                        {1,177,971,178},
00295                        {-1,-1,-1,-1}};
00296             map = dup_map(badmap);
00297         }
00298         else if (binx == 2 && biny == 3)
00299         {
00300             int badmap[][4] = {{1,3,696,3},
00301                        {1,33,761,33},
00302                        {1,55,592,56},
00303                        {1,89,814,90},
00304                        {1,99,674,100},
00305                        {1,144,658,144},
00306                        {1,177,647,178},
00307                        {-1,-1,-1,-1}};
00308             map = dup_map(badmap);
00309         }
00310         else
00311         {
00312             assure( false, CPL_ERROR_ILLEGAL_INPUT,
00313                 "Don't know bad pixel map for %dx%d binning, red, lower chip", 
00314                 binx, biny);
00315         }
00316     }
00317     else if  (chip == UVES_CHIP_REDU)
00318     {
00319         /* Use different bad pixels maps for bias and
00320            orderpos recipes !
00321         */
00322         if (binx == 1 && biny ==1)
00323         {
00324             int badmap[][4] = {{1,2030,1268,2033},
00325                        {1269,2033,4096,2033},
00326                        {1201, 491, 3271, 492},
00327                        {-1,-1,-1,-1}};
00328 
00329             if (!mark_bad)
00330             {
00331                 badmap[2][0] = -1;
00332                 badmap[2][1] = -1;
00333                 badmap[2][2] = -1;
00334                 badmap[2][3] = -1;
00335             }
00336             map = dup_map(badmap);
00337         }
00338         else if (binx == 1 && biny == 2)
00339         {
00340             int badmap[][4] = {{1,2030,634,2033},
00341                        {635,2033,2048,2033},
00342                        {600, 491,1635, 492},
00343                        {-1,-1,-1,-1}};
00344             if (!mark_bad)
00345             {
00346                 badmap[2][0] = -1;
00347                 badmap[2][1] = -1;
00348                 badmap[2][2] = -1;
00349                 badmap[2][3] = -1;
00350             }
00351             map = dup_map(badmap);
00352         }
00353         else if (binx == 2 && biny == 2)
00354         {
00355             int badmap[][4] = {{1,1013,634,1016},
00356                        {635,1015,2048,1016},
00357                        {600, 244,1635, 245},
00358                        {-1,-1,-1,-1}};
00359             if (!mark_bad)
00360             {
00361                 badmap[2][0] = -1;
00362                 badmap[2][1] = -1;
00363                 badmap[2][2] = -1;
00364                 badmap[2][3] = -1;
00365             }
00366             map = dup_map(badmap);
00367         }
00368         else if (binx == 2 && biny == 3)
00369         {
00370             int badmap[][4] = {{1,1013,423,1016},
00371                        {424,1015,1365,1016},
00372                        {400, 244,1090, 245},
00373                        {-1,-1,-1,-1}};
00374             if (!mark_bad)
00375             {
00376                 badmap[2][0] = -1;
00377                 badmap[2][1] = -1;
00378                 badmap[2][2] = -1;
00379                 badmap[2][3] = -1;
00380             }
00381             map = dup_map(badmap);
00382         }
00383         else
00384         {
00385             assure( false, CPL_ERROR_ILLEGAL_INPUT,
00386                 "Don't know bad pixel map for %dx%d binning, red, upper chip", 
00387                 binx, biny);
00388         }
00389     }
00390     else
00391     {
00392         /* No blue chip bad pixels */
00393         int badmap[][4] = {{-1,-1,-1,-1}};
00394         
00395         map = dup_map(badmap);
00396     }
00397 
00398   cleanup:
00399     return map;
00400 }
00401 
00402 
00403 
00404 /*----------------------------------------------------------------------------*/
00419 /*----------------------------------------------------------------------------*/
00420 static int
00421 uves_correct_badpix(cpl_image *master_bias, uves_propertylist *header, int **badmap,
00422             bool mark_bad)
00423 {
00424     int ncorrect = 0;   /* Result */
00425     int xstart, ystart, xend, yend;
00426     int row;
00427     bool finished = false;
00428     int nx, ny;
00429     cpl_mask  *image_bad = NULL;
00430     cpl_binary*image_bpm = NULL;
00431     cpl_type type=0;
00432 
00433     type=cpl_image_get_type(master_bias);
00434     assure( (type == CPL_TYPE_DOUBLE) || (type == CPL_TYPE_FLOAT),
00435         CPL_ERROR_UNSUPPORTED_MODE,
00436         "Image type must be float or double. It is %s",
00437         uves_tostring_cpl_type(cpl_image_get_type(master_bias)));
00438 
00439     image_bad = cpl_image_get_bpm(master_bias);
00440     image_bpm = cpl_mask_get_data(image_bad);
00441 
00442     nx = cpl_image_get_size_x(master_bias);
00443     ny = cpl_image_get_size_y(master_bias);
00444 
00445     row = 0;
00446     while (!finished)
00447     {
00448         xstart = badmap[row][0];
00449         ystart = badmap[row][1];
00450         xend   = badmap[row][2];
00451         yend   = badmap[row][3];
00452 
00453         if (xstart > 0)
00454         {
00455             int ylow, yhigh;
00456             int x, y;
00457             
00458             assure( 1 <= xstart && xstart <= nx &&
00459                 1 <= xend   && xend   <= nx &&
00460                 1 <= ystart && ystart <= ny &&
00461                 1 <= yend   && yend   <= ny, CPL_ERROR_ILLEGAL_INPUT, 
00462                 "Illegal window (%d, %d) - (%d, %d). Image size = %dx%d",
00463                 xstart, ystart, xend, yend, nx, ny);
00464             
00465             if ( ystart < 3 )
00466             {
00467                 assure( yend + 2 <= ny, CPL_ERROR_ILLEGAL_INPUT,
00468                     "Too large range in y: %d - %d", ystart, yend);
00469 
00470                 ylow  = yend + 1;
00471                 yhigh = yend + 2;
00472             }
00473             else if (yend > ny - 3 )
00474             {
00475                 assure( ystart - 2 >= 1, CPL_ERROR_ILLEGAL_INPUT,
00476                     "Too large range in y: %d - %d", ystart, yend);
00477                 
00478                 ylow  = ystart - 2;
00479                 yhigh = ystart - 1;
00480             }
00481             else
00482             {
00483                 ylow  = ystart - 2;
00484                 yhigh = yend + 2;
00485             }
00486             
00487             uves_msg("Correcting window (%d, %d)-(%d, %d)", xstart, ystart, xend, yend);
00488 
00489 
00490             if(type == CPL_TYPE_DOUBLE) {
00491 
00492             for (x = xstart; x <= xend; x++) {
00493             for (y = ystart; y <= yend; y++) {
00494                 int pis_rejected;
00495                 double i1, i2;
00496                 
00497                 if (mark_bad)
00498                 {
00499                     /* This is extremely slow with CPL2:
00500                        cpl_image_reject(master_bias, x, y);
00501                     */
00502                     image_bpm[(x-1) + (y-1)*nx] = CPL_BINARY_1;
00503                 }
00504                 else
00505                 /* interpolate */
00506                 {
00507                     double *master_bias_data;
00508 
00509                     i1 = cpl_image_get(master_bias, x, ylow , &pis_rejected);
00510                     i2 = cpl_image_get(master_bias, x, yhigh, &pis_rejected);
00511                     
00512                     /* Write average */
00513                     
00514                     /* This will make the bpm invalid:
00515                        cpl_image_set(master_bias, x, y, (i1+i2)/2);
00516                     */
00517                     master_bias_data = cpl_image_get_data_double(master_bias);
00518                     master_bias_data[(x-1) + (y-1)*nx] = (i1+i2)/2;
00519                 }
00520                 ncorrect += 1;
00521             }
00522             }
00523 
00524 
00525         } else {
00526 
00527 
00528             for (x = xstart; x <= xend; x++) {
00529             for (y = ystart; y <= yend; y++) {
00530                 int pis_rejected;
00531                 float i1, i2;
00532                 
00533                 if (mark_bad)
00534                 {
00535                     /* This is extremely slow with CPL2:
00536                        cpl_image_reject(master_bias, x, y);
00537                     */
00538                     image_bpm[(x-1) + (y-1)*nx] = CPL_BINARY_1;
00539                 }
00540                 else
00541                 /* interpolate */
00542                 {
00543                     float *master_bias_data;
00544 
00545                     i1 = cpl_image_get(master_bias, x, ylow , &pis_rejected);
00546                     i2 = cpl_image_get(master_bias, x, yhigh, &pis_rejected);
00547                     
00548                     /* Write average */
00549                     
00550                     /* This will make the bpm invalid:
00551                        cpl_image_set(master_bias, x, y, (i1+i2)/2);
00552                     */
00553                     master_bias_data = cpl_image_get_data_float(master_bias);
00554                     master_bias_data[(x-1) + (y-1)*nx] = (i1+i2)/2;
00555                 }
00556                 ncorrect += 1;
00557             }
00558             }
00559 
00560 
00561         }
00562 
00563 
00564         }
00565         else
00566         {
00567             finished = true;
00568         }
00569         row++;
00570     }
00571 
00572     /* Update product header */
00573     if (ncorrect > 0)
00574     {
00575         check( uves_pfits_set_badpixcorr(header, "true"),
00576            "Error updating product header");
00577     }
00578 
00579   cleanup:
00580     return ncorrect;
00581 }

Generated on Fri Apr 18 14:11:41 2008 for UVES Pipeline Reference Manual by  doxygen 1.5.1