IIINSTRUMENT Pipeline Reference Manual  1.3.13
detmon.c
1 /* $Id: detmon.c,v 1.11 2013-07-19 12:00:24 jtaylor Exp $
2  *
3  * This file is part of the irplib package
4  * Copyright (C) 2002, 2003 European Southern Observatory
5  *
6  * This program is free software; you can redistribute it and/or modify
7  * it under the terms of the GNU General Public License as published by
8  * the Free Software Foundation; either version 2 of the License, or
9  * (at your option) any later version.
10  *
11  * This program is distributed in the hope that it will be useful,
12  * but WITHOUT ANY WARRANTY; without even the implied warranty of
13  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14  * GNU General Public License for more details.
15  *
16  * You should have received a copy of the GNU General Public License
17  * along with this program; if not, write to the Free Software
18  * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02111-1307 USA
19  */
20 
21 /*
22  * $Author: jtaylor $
23  * $Date: 2013-07-19 12:00:24 $
24  * $Revision: 1.11 $
25  * $Name: not supported by cvs2svn $
26  */
27 
28 #ifdef HAVE_CONFIG_H
29 #include <config.h>
30 #endif
31 
32 /*---------------------------------------------------------------------------
33  Includes
34  ---------------------------------------------------------------------------*/
35 
36 #include "detmon.h"
37 
38 #include "irplib_ksigma_clip.h"
39 #include "irplib_hist.h"
40 #include "irplib_utils.h"
41 
42 #include <math.h>
43 #include <string.h>
44 #include <assert.h>
45 #include <float.h>
46 
47 
49 /*--------------------------------------------------------------------------*/
50 
51 /*
52  * @defgroup detmon Detector monitoring functions
53  */
54 
55 /*--------------------------------------------------------------------------*/
56 
57 /*---------------------------------------------------------------------------
58  Defines
59  ---------------------------------------------------------------------------*/
60 
61 /* Computes the square of an euclidean distance bet. 2 points */
62 #define pdist(x1,y1,x2,y2) (((x1-x2)*(x1-x2))+((y1-y2)*(y1-y2)))
63 
64 #define cpl_drand() ((double)rand()/(double)RAND_MAX)
65 
66 enum pixeltypes
67 {
68  HOT = 0,
69  DEAD = 1,
70  NOISY = 2
71 };
72 
73 enum stackingtypes
74 {
75  MINMAX = 0,
76  MEAN = 1,
77  MEDIAN = 2,
78  KSIGMA = 3
79 };
80 
81 enum readouts
82 {
83  HORIZONTAL = 1,
84  VERTICAL = 2
85 };
86 
87 #define NIR TRUE
88 #define OPT FALSE
89 
90 /*---------------------------------------------------------------------------
91  Private function prototypes
92  ---------------------------------------------------------------------------*/
93 
94 /* Functions for RON/Bias recipe, detmon_ronbias() */
95 
96 cpl_error_code
97 detmon_rm_bpixs(cpl_image **,
98  const double,
99  int ,
100  int );
101 
102 /*---------------------------------------------------------------------------*/
103 
104 /*
105  * @brief Fill input parameters values
106  * @param parlist parameters list
107  * @param recipe_name recipe name
108  * @param pipeline_name pipeline name
109  * @param npars number of parameters
110 
111  * @return CPL_ERROR_NONE on success.
112  */
113 
114 /*---------------------------------------------------------------------------*/
115 cpl_error_code
116 detmon_fill_parlist(cpl_parameterlist * parlist,
117  const char *recipe_name,
118  const char *pipeline_name,
119  int npars, ...)
120 {
121 
122  va_list ap;
123 
124  char *group_name;
125 
126  int pars_counter = 0;
127 
128  group_name = cpl_sprintf("%s.%s", pipeline_name, recipe_name);
129  assert(group_name != NULL);
130 
131 #define insert_par(PARNAME, PARDESC, PARVALUE, PARTYPE) \
132  do { \
133  char * par_name = cpl_sprintf("%s.%s", group_name, PARNAME); \
134  cpl_parameter * p; \
135  assert(par_name != NULL); \
136  p = cpl_parameter_new_value(par_name, PARTYPE, \
137  PARDESC, group_name, PARVALUE); \
138  cpl_parameter_set_alias(p, CPL_PARAMETER_MODE_CLI, PARNAME); \
139  cpl_parameter_disable(p, CPL_PARAMETER_MODE_ENV); \
140  cpl_parameterlist_append(parlist, p); \
141  cpl_free(par_name); \
142  } while(0);
143 
144 
145  va_start(ap, npars);
146 
147  while(pars_counter < npars) {
148  char *name = va_arg(ap, char *);
149  char *desc = va_arg(ap, char *);
150  char *type = va_arg(ap, char *);
151 
152  if(!strcmp(type, "CPL_TYPE_INT")) {
153  int v1 = va_arg(ap, int);
154 
155  insert_par(name, desc, v1, CPL_TYPE_INT);
156  } else if(!strcmp(type, "CPL_TYPE_BOOL")) {
157  char *v2 = va_arg(ap, char *);
158 
159  if(!strcmp(v2, "CPL_FALSE"))
160  insert_par(name, desc, CPL_FALSE, CPL_TYPE_BOOL);
161  if(!strcmp(v2, "CPL_TRUE"))
162  insert_par(name, desc, CPL_TRUE, CPL_TYPE_BOOL);
163  } else if(!strcmp(type, "CPL_TYPE_STRING")) {
164  char *v2 = va_arg(ap, char *);
165 
166  insert_par(name, desc, v2, CPL_TYPE_STRING);
167  } else if(!strcmp(type, "CPL_TYPE_DOUBLE")) {
168  double v3 = va_arg(ap, double);
169  insert_par(name, desc, v3, CPL_TYPE_DOUBLE);
170  }
171 
172  pars_counter++;
173  }
174 
175  va_end(ap);
176 
177  cpl_free(group_name);
178 
179 #undef insert_par
180  return 0;
181 }
182 
183 /*---------------------------------------------------------------------------*/
184 
185 /*
186  * @brief Retrieve input int parameter
187  * @param pipeline_name Input image
188  * @param recipe_name Input image
189  * @param parlist Shift to apply on the x-axis
190  * @return CPL_ERROR_NONE on success.
191  */
192 
193 /*---------------------------------------------------------------------------*/
194 int
195 detmon_retrieve_par_int(const char *parn,
196  const char *pipeline_name,
197  const char *recipe_name,
198  const cpl_parameterlist * parlist)
199 {
200  char *par_name;
201  const cpl_parameter *par;
202  int value;
203 
204  par_name = cpl_sprintf("%s.%s.%s", pipeline_name, recipe_name, parn);
205  assert(par_name != NULL);
206  par = cpl_parameterlist_find_const(parlist, par_name);
207  value = cpl_parameter_get_int(par);
208  cpl_free(par_name);
209 
210  return value;
211 }
212 
213 /*---------------------------------------------------------------------------*/
214 
215 /*
216  * @brief Retrieve input double parameter
217  * @param pipeline_name Input image
218  * @param recipe_name Input image
219  * @param parlist Shift to apply on the x-axis
220  * @return CPL_ERROR_NONE on success.
221  */
222 
223 /*---------------------------------------------------------------------------*/
224 double
225 detmon_retrieve_par_double(const char *parn,
226  const char *pipeline_name,
227  const char *recipe_name,
228  const cpl_parameterlist * parlist)
229 {
230  char *par_name;
231  const cpl_parameter *par;
232  double value;
233 
234  par_name = cpl_sprintf("%s.%s.%s", pipeline_name, recipe_name, parn);
235  assert(par_name != NULL);
236  par = cpl_parameterlist_find_const(parlist, par_name);
237  value = cpl_parameter_get_double(par);
238  cpl_free(par_name);
239 
240  return value;
241 }
242 
243 
244 /*---------------------------------------------------------------------------*/
245 
246 /*
247  * @brief Retrieve exposure time
248  * @param plist parameter list
249  * @return "EXPTIME" keyword value.
250  */
251 
252 /*---------------------------------------------------------------------------*/
253 
254 double
255 irplib_pfits_get_exptime(const cpl_propertylist * plist)
256 {
257  double exptime;
258 
259  exptime = cpl_propertylist_get_double(plist, "EXPTIME");
260 
261  return exptime;
262 }
263 
264 /*---------------------------------------------------------------------------*/
265 /*
266  * @brief Generate propertylist with product category, type, technique
267  * @param procatg product category
268  * @param protype product type
269  * @param protech product technique
270  * @param proscience switch to identify a science product
271  * @return filled cpl_propertylist (to be deallocated)
272  */
273 /*---------------------------------------------------------------------------*/
274 cpl_propertylist *
275 detmon_fill_prolist(const char * procatg,
276  const char * protype,
277  const char * protech,
278  cpl_boolean proscience)
279 {
280  cpl_propertylist * prolist = cpl_propertylist_new();
281 
282  cpl_propertylist_append_string(prolist, CPL_DFS_PRO_CATG, procatg);
283  cpl_propertylist_append_bool(prolist, CPL_DFS_PRO_SCIENCE, proscience);
284  if (protype) {
285  cpl_propertylist_append_string(prolist, CPL_DFS_PRO_TYPE, protype);
286  }
287  if (protech) {
288  cpl_propertylist_append_string(prolist, CPL_DFS_PRO_TECH, protech);
289  }
290 
291  return prolist;
292 }
293 
294 /*---------------------------------------------------------------------------*/
295 
296 /*
297  * @brief Remove bad pixels
298  * @param image input/output image
299  * @param kappa kappa for kappa-sigma clip
300  * @param nffts number of fft
301  * @param nsamples number of sampling areas
302  * @return CPL_ERROR_NONE on success.
303  */
304 
305 /*---------------------------------------------------------------------------*/
306 
307 
308 cpl_error_code
309 detmon_rm_bpixs(cpl_image ** image,
310  const double kappa, int nffts, int nsamples)
311 {
312  int i, j;
313 
314  float *data = cpl_image_get_data_float(*image);
315  int k = 0;
316  for(i = 0; i < nffts; i++) {
317  for(j = 0; j < nsamples; j++) {
318  float neighbours = 0;
319  int nneighs = 0;
320  float average = 0;
321 
322  /*
323  * Look for the way to optimize this:
324  * Some of the points added to neighbours coincide
325  * in one iteration and the following
326  */
327  if(i > 0) {
328  neighbours += *(data + (i - 1) * nsamples + j);
329  nneighs++;
330  }
331  if(i < nffts - 1) {
332  neighbours += *(data + (i + 1) * nsamples + j);
333  nneighs++;
334  }
335  if(j > 0) {
336  neighbours += *(data + i * nsamples + (j - 1));
337  nneighs++;
338  }
339  if(j < nsamples - 1) {
340  neighbours += *(data + i * nsamples + (j + 1));
341  nneighs++;
342  }
343  average = neighbours / nneighs;
344  if(average > 0) {
345  if(*(data + i * nsamples + j) < average * (-1 * kappa) ||
346  *(data + i * nsamples + j) > average * (kappa)) {
347  k++;
348  *(data + i * nsamples + j) = average;
349  }
350  }
351  if(average < 0) {
352  if(*(data + i * nsamples + j) > average * (-1 * kappa) ||
353  *(data + i * nsamples + j) < average * (kappa)) {
354  k++;
355  *(data + i * nsamples + j) = average;
356  }
357  }
358 
359  }
360  }
361 
362 
363  return cpl_error_get_code();
364 
365 }
366 
367 void
368 detmon_print_rec_status(void) {
369  if(cpl_error_get_code() != CPL_ERROR_NONE) {
370  /* cpl_msg_error(cpl_func,"Function status at %d",val); */
371  cpl_msg_error(cpl_func,"%s",(const char*) cpl_error_get_message());
372  cpl_msg_error(cpl_func,"%s",(const char*) cpl_error_get_where());
373  return;
374  }
375  return;
376 }
377