00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023
00024
00025
00026
00027
00028
00029
00030 #ifdef HAVE_CONFIG_H
00031 #include <config.h>
00032 #endif
00033
00034 #include <math.h>
00035 #include <cpl.h>
00036
00037 #include "vircam_utils.h"
00038 #include "vircam_pfits.h"
00039 #include "vircam_stats.h"
00040 #include "vircam_fits.h"
00041 #include "vircam_mods.h"
00042
00043
00044
00045 #define FATAL_ERR(_f,_a) {cpl_msg_error(_f,"%s",_a); tidy(); *status = VIR_FATAL; return(*status);}
00046 #define WARN_ERR(_f,_a) {cpl_msg_error(_f,"%s",_a); tidy(); *status = VIR_WARN; return(VIR_WARN);}
00047 #define INFO_ERR(_f,_a) {cpl_msg_info(_f,"%s",_a);}
00048 #define MEDIANCALC 1
00049 #define MEANCALC 2
00050 #define SZBUF 1024
00051
00052
00053
00054
00055 typedef struct {
00056 vir_fits *frame;
00057 float exptime;
00058 float expfudge;
00059 float skylevel;
00060 float skynoise;
00061 float skyfudge;
00062 float skyrenorm;
00063 } litestruct;
00064
00065
00066
00067 static litestruct *fileptrs = NULL;
00068 static float **datas = NULL;
00069 static cpl_binary **masks = NULL;
00070 static float *odata;
00071 static cpl_binary *omask;
00072 static long npts;
00073 static int nf;
00074 static float oskylevel;
00075 static long nx;
00076 static long ny;
00077 static unsigned char *rmask = NULL;
00078 static unsigned char *rplus = NULL;
00079
00080
00081
00082 static void skyest(float *data, cpl_binary *bpm, float thresh, float *skymed,
00083 float *skynoise);
00084 static void medcalc(float, float, int);
00085 static void meancalc(float, float, int);
00086 static void xclip_med(float thresh, int scaletype);
00087 static void xclip_mean(float thresh, int scaletype);
00088
00089 static void tidy(void);
00090
00093
00153
00154
00155 extern int vircam_imcombine(vir_fits **fset, int nfits, int combtype,
00156 int scaletype, int xrej, float thresh,
00157 cpl_image **outimage, unsigned char **rejmask,
00158 unsigned char **rejplus, cpl_propertylist **drs,
00159 int *status) {
00160 int i,k,j;
00161 const char *ic_fctid = "vircam_imcombine";
00162 char msg[SZBUF];
00163 float sumsky,sumsig,texp1,texp2,expfudge,skylevel,skynoise,oskynoise;
00164 float *dat,*work;
00165 litestruct *ff;
00166 cpl_image *im;
00167 cpl_propertylist *plist_p;
00168
00169
00170
00171 *rejmask = NULL;
00172 *rejplus = NULL;
00173 *drs = NULL;
00174 *outimage = NULL;
00175 if (*status != VIR_OK)
00176 return(*status);
00177
00178
00179
00180 nf = nfits;
00181 if (nf == 0)
00182 WARN_ERR(ic_fctid,"No files to combine")
00183
00184
00185
00186 fileptrs = cpl_calloc(nf,sizeof(litestruct));
00187
00188
00189
00190 datas = cpl_malloc(nf*sizeof(float *));
00191 npts = vircam_getnpts(vircam_fits_get_image(fset[0]));
00192 for (k = 0; k < nf; k++)
00193 datas[k] = cpl_malloc(npts*sizeof(float));
00194 masks = cpl_malloc(nf*sizeof(cpl_binary *));
00195
00196
00197
00198 for (k = 0; k < nf; k++) {
00199 im = vircam_fits_get_image(fset[k]);
00200 dat = cpl_image_get_data_float(im);
00201 if (dat == NULL) {
00202 snprintf(msg,SZBUF,"Failed to load data from extension %d in %s",
00203 vircam_fits_get_nexten(fset[k]),
00204 vircam_fits_get_filename(fset[k]));
00205 FATAL_ERR(ic_fctid,msg)
00206 }
00207 for (i = 0; i < npts; i++)
00208 datas[k][i] = dat[i];
00209 masks[k] = cpl_mask_get_data(cpl_image_get_bpm(im));
00210 }
00211
00212
00213
00214
00215 for (i = 0; i < nf; i++) {
00216 ff = fileptrs + i;
00217 ff->frame = fset[i];
00218
00219
00220
00221
00222 if (i == 0) {
00223 nx = cpl_image_get_size_x(vircam_fits_get_image(fset[0]));
00224 ny = cpl_image_get_size_y(vircam_fits_get_image(fset[0]));
00225 npts = nx*ny;
00226 }
00227
00228
00229
00230 plist_p = vircam_fits_get_phu(ff->frame);
00231 if (plist_p == NULL) {
00232 snprintf(msg,SZBUF,"Failed to load primary property list %s",
00233 vircam_fits_get_filename(ff->frame));
00234 INFO_ERR(ic_fctid,msg)
00235 texp2 = 1.0;
00236 } else {
00237 if (vircam_pfits_get_exptime(plist_p,&texp2) != VIR_OK) {
00238 texp2 = 1.0;
00239 snprintf(msg,SZBUF,"Failed to get exposure time from %s",
00240 vircam_fits_get_filename(ff->frame));
00241 INFO_ERR(ic_fctid,msg)
00242 }
00243 }
00244
00245
00246
00247 ff->exptime = texp2;
00248 texp1 = fileptrs->exptime;
00249 expfudge = texp1/texp2;
00250 ff->expfudge = expfudge;
00251
00252
00253
00254
00255
00256 if (scaletype == 3 && i > 0) {
00257 for (j = 0; j < npts; j++)
00258 datas[i][j] *= ff->expfudge;
00259 }
00260
00261
00262
00263 skyest(datas[i],masks[i],thresh,&skylevel,&skynoise);
00264 ff->skylevel = skylevel;
00265 ff->skynoise = skynoise;
00266 }
00267
00268
00269
00270
00271 work = cpl_malloc(nf*sizeof(float));
00272 for (i = 0; i < nf; i++)
00273 work[i] = (fileptrs+i)->skylevel;
00274 sumsky = vircam_med(work,NULL,(long)nf);
00275 for (i = 0; i < nf; i++)
00276 work[i] = (fileptrs+i)->skynoise;
00277 sumsig = vircam_med(work,NULL,(long)nf);
00278 cpl_free(work);
00279 switch (scaletype) {
00280 case 1:
00281 for (i = 0; i < nf; i++)
00282 (fileptrs+i)->skyfudge = sumsky - (fileptrs+i)->skylevel;
00283 break;
00284 case 2:
00285 for (i = 0; i < nf; i++)
00286 (fileptrs+i)->skyfudge = sumsky/(fileptrs+i)->skylevel;
00287 break;
00288 case 3:
00289 for (i = 0; i < nf; i++)
00290 (fileptrs+i)->skyfudge = sumsky - (fileptrs+i)->skylevel;
00291 break;
00292 default:
00293 for (i = 0; i < nf; i++)
00294 (fileptrs+i)->skyfudge = 0.0;
00295 break;
00296 }
00297
00298
00299
00300 *outimage = cpl_image_new(nx,ny,CPL_TYPE_FLOAT);
00301 odata = cpl_image_get_data_float(*outimage);
00302 omask = cpl_mask_get_data(cpl_image_get_bpm(*outimage));
00303 if (*outimage == NULL || odata == NULL)
00304 FATAL_ERR(ic_fctid,"Couldn't create output image")
00305 *rejmask = cpl_calloc(npts,sizeof(*rejmask));
00306 rmask = *rejmask;
00307 *rejplus = cpl_calloc(npts,sizeof(*rejplus));
00308 rplus = *rejplus;
00309
00310
00311
00312 switch (combtype) {
00313 case MEDIANCALC:
00314 medcalc(thresh,sumsig,scaletype);
00315 break;
00316 case MEANCALC:
00317 meancalc(thresh,sumsig,scaletype);
00318 break;
00319 }
00320
00321
00322
00323 if (xrej) {
00324
00325
00326
00327 skyest(odata,omask,thresh,&oskylevel,&oskynoise);
00328
00329
00330
00331
00332
00333 for (i = 0; i < nf; i++) {
00334 ff = fileptrs + i;
00335 ff->skyrenorm = ff->skylevel/oskylevel;
00336 switch (scaletype) {
00337 case 1:
00338 for (k = 0; k < npts; k++)
00339 datas[i][k] -= (odata[k] - oskylevel);
00340 break;
00341 case 2:
00342 for (k = 0; k < npts; k++)
00343 datas[i][k] -= (odata[k] - oskylevel)*ff->skyrenorm;
00344 break;
00345 case 3:
00346 for (k = 0; k < npts; k++)
00347 datas[i][k] -= (odata[k] - oskylevel);
00348 break;
00349 case 0:
00350 for (k = 0; k < npts; k++)
00351 datas[i][k] -= (odata[k] - oskylevel);
00352 break;
00353 }
00354
00355
00356
00357 skyest(datas[i],masks[i],thresh,&skylevel,&skynoise);
00358 ff->skynoise = skynoise;
00359 }
00360
00361
00362
00363 switch (combtype) {
00364 case MEDIANCALC:
00365 xclip_med(thresh,scaletype);
00366 break;
00367 case MEANCALC:
00368 xclip_mean(thresh,scaletype);
00369 break;
00370 }
00371 }
00372
00373
00374
00375 *drs = cpl_propertylist_new();
00376 vircam_prov(*drs,fset,nfits);
00377
00378
00379
00380 tidy();
00381 return(VIR_OK);
00382 }
00383
00384
00406
00407
00408 static void xclip_med(float thresh, int scaletype) {
00409 int nf1,nf2,nfm,nrejmax,is_even,k,is_even2,nrej,nremain,nm,nmm,nplus;
00410 int nminus,nn,j;
00411 float **work,*dork,value,cliplev;
00412 long i;
00413 litestruct *ff;
00414
00415
00416
00417 work = cpl_malloc(3*sizeof(float *));
00418 for (i = 0; i < 3; i++)
00419 work[i] = cpl_malloc(nf*sizeof(float));
00420 dork = cpl_malloc(nf*sizeof(float));
00421
00422
00423
00424 for (i = 0; i < npts; i++) {
00425 if (omask[i])
00426 continue;
00427
00428
00429
00430 nn = 0;
00431 switch (scaletype) {
00432 case 0:
00433 for (k = 0; k < nf; k++) {
00434 if (masks[k][i])
00435 continue;
00436 ff = fileptrs + k;
00437 work[0][nn] = datas[k][i];
00438 work[1][nn] = ff->skynoise;
00439 work[2][nn++] = datas[k][i] + odata[i] - oskylevel;
00440 }
00441 break;
00442 case 1:
00443 for (k = 0; k < nf; k++) {
00444 if (masks[k][i])
00445 continue;
00446 ff = fileptrs + k;
00447 work[0][nn] = datas[k][i] + ff->skyfudge;
00448 work[1][nn] = ff->skynoise;
00449 work[2][nn++] = datas[k][i] + odata[i] - oskylevel +
00450 ff->skyfudge;
00451 }
00452 break;
00453 case 2:
00454 for (k = 0; k < nf; k++) {
00455 if (masks[k][i])
00456 continue;
00457 ff = fileptrs + k;
00458 work[0][nn] = datas[k][i]*ff->skyfudge;
00459 work[1][nn] = ff->skynoise*ff->skyfudge;
00460 work[2][nn++] = (datas[k][i] + odata[i]*ff->skyrenorm -
00461 ff->skylevel)*ff->skyfudge;
00462 }
00463 break;
00464 case 3:
00465 for (k = 0; k < nf; k++) {
00466 if (masks[k][i])
00467 continue;
00468 ff = fileptrs + k;
00469 work[0][nn] = datas[k][i] + ff->skyfudge;
00470 work[1][nn] = ff->skynoise;
00471 work[2][nn++] = datas[k][i] + odata[i] - oskylevel +
00472 ff->skyfudge;
00473 }
00474 break;
00475 }
00476
00477
00478
00479 nf1 = nn/2 - 1;
00480 nf2 = nf1 + 1;
00481 nfm = (nn + 1)/2 - 1;
00482 nrejmax = nn/2;
00483 is_even = !(nn & 1);
00484
00485
00486
00487 vircam_sort(work,nn,3);
00488 if (is_even)
00489 value = 0.5*(work[0][nf1] + work[0][nf2]);
00490 else
00491 if (nn < 5)
00492 value = work[0][nfm];
00493 else
00494 value = 0.25*(work[0][nfm-1] + work[0][nfm+1]) + 0.5*work[0][nfm];
00495
00496
00497
00498 nplus = 0;
00499 cliplev = value + thresh*work[1][nn-1];
00500 while (nplus < nrejmax && work[0][nn-nplus-1] > cliplev)
00501 nplus++;
00502 nminus = 0;
00503 cliplev = value - thresh*work[1][nn-1];
00504 while ((nplus+nminus) < nrejmax && work[0][nminus] < cliplev)
00505 nminus++;
00506 nrej = nplus + nminus;
00507
00508
00509
00510 if (nrej > 0) {
00511 nremain = nn - nrej;
00512 if (nremain != 0) {
00513 nm = nremain/2 - 1;
00514 for (j = 0; j < nremain; j++)
00515 dork[j] = work[2][j+nminus];
00516 nmm = (nremain + 1)/2 - 1;
00517 is_even2 = !(nremain & 1);
00518 vircam_sort(&dork,nm,1);
00519 if (is_even2)
00520 value = 0.5*(dork[nm] + dork[nm+1]);
00521 else
00522 if (nremain < 3)
00523 value = dork[nmm];
00524 else
00525 value = 0.5*dork[nmm] + 0.25*(dork[nmm-1] + dork[nmm+1]);
00526 }
00527
00528
00529
00530 odata[i] = value;
00531 rmask[i] = min(255,nrej);
00532 rplus[i] = min(255,nplus);
00533 } else {
00534 rmask[i] = 0;
00535 rplus[i] = 0;
00536 }
00537 }
00538
00539
00540
00541 for (i = 0; i < 3; i++)
00542 cpl_free(work[i]);
00543 cpl_free(work);
00544 cpl_free(dork);
00545 }
00546
00547
00569
00570
00571 static void xclip_mean(float thresh, int scaletype) {
00572 int k,nf2,nrej,nplus,kk,krem;
00573 float *work[3],value,value2,nrejmax,resid,maxresid;
00574 long i,nn;
00575 litestruct *ff;
00576 unsigned char *iflag;
00577
00578
00579
00580 for (i = 0; i < 3; i++)
00581 work[i] = cpl_malloc(nf*sizeof(float));
00582 iflag = cpl_malloc(nf*sizeof(unsigned char));
00583
00584
00585
00586 nrejmax = nf/2;
00587 for (i = 0; i < npts; i++) {
00588 if (omask[i])
00589 continue;
00590
00591
00592
00593 nn = 0;
00594 switch (scaletype) {
00595 case 0:
00596 for (k = 0; k < nf; k++) {
00597 if (masks[k][i])
00598 continue;
00599 ff = fileptrs + k;
00600 work[0][nn] = datas[k][i];
00601 work[1][nn] = ff->skynoise;
00602 work[2][nn] = datas[k][i] + odata[i] - oskylevel;
00603 iflag[nn++] = 0;
00604 }
00605 break;
00606 case 1:
00607 for (k = 0; k < nf; k++) {
00608 if (masks[k][i])
00609 continue;
00610 ff = fileptrs + k;
00611 work[0][nn] = datas[k][i] + ff->skyfudge;
00612 work[1][nn] = ff->skynoise;
00613 work[2][nn] = datas[k][i] + odata[i] - oskylevel + ff->skyfudge;
00614 iflag[nn++] = 0;
00615 }
00616 break;
00617 case 2:
00618 for (k = 0; k < nf; k++) {
00619 if (masks[k][i])
00620 continue;
00621 ff = fileptrs + k;
00622 work[0][nn] = datas[k][i]*ff->skyfudge;
00623 work[1][nn] = ff->skynoise*ff->skyfudge;
00624 work[2][nn] = (datas[k][i] + odata[i]*ff->skyrenorm -
00625 ff->skylevel)*ff->skyfudge;
00626 iflag[nn++] = 0;
00627 }
00628 break;
00629 case 3:
00630 for (k = 0; k < nf; k++) {
00631 if (masks[k][i])
00632 continue;
00633 ff = fileptrs + k;
00634 work[0][nn] = datas[k][i] + ff->skyfudge;
00635 work[1][nn] = ff->skynoise;
00636 work[2][nn] = datas[k][i] + odata[i] - oskylevel + ff->skyfudge;
00637 iflag[nn++] = 0;
00638 }
00639 break;
00640 }
00641
00642
00643
00644 value = 0.0;
00645 for (k = 0; k < nn; k++)
00646 value += work[0][k];
00647 value /= (float)nn;
00648
00649
00650
00651 nplus = 0;
00652 nrej = 0;
00653 for (kk = 0; kk < nrejmax; kk++) {
00654 maxresid = 0.0;
00655 krem = -1;
00656 for (k = 0; k < nn; k++) {
00657 if (iflag[k] == 1)
00658 continue;
00659 resid = fabs(work[0][k] - value);
00660 if (resid > thresh*work[1][k]) {
00661 if (resid > maxresid) {
00662 krem = k;
00663 maxresid = resid;
00664 }
00665 }
00666 }
00667
00668
00669
00670 if (krem == -1)
00671 break;
00672
00673
00674
00675 iflag[krem] = 1;
00676 if ((work[0][krem] - value) > 0.0)
00677 nplus++;
00678 nrej++;
00679
00680
00681
00682 nf2 = 0;
00683 value2 = 0;
00684 for (k = 0; k < nn; k++) {
00685 if (iflag[k] == 0) {
00686 value2 += work[0][k];
00687 nf2++;
00688 }
00689 }
00690 if (nf2 != 0)
00691 value = value2/(float)nf2;
00692 else
00693 break;
00694 }
00695
00696
00697
00698 if (nrej > 0)
00699 odata[i] = value;
00700 rmask[i] = min(255,nrej);
00701 rplus[i] = min(255,nplus);
00702 }
00703
00704
00705
00706 for (k = 0; k < 3; k++)
00707 cpl_free(work[k]);
00708 cpl_free(iflag);
00709 }
00710
00711
00712
00735
00736
00737 static void medcalc(float thresh, float avskynoise, int scaletype) {
00738 int nf1,nf2,nfm,nrejmax,is_even,nrej,nremain,nm,nmm,is_even2,k,nminus;
00739 int nplus,nn;
00740 long i;
00741 float value,cliplev,*work;
00742
00743
00744
00745 work = cpl_malloc(nf*sizeof(*work));
00746
00747
00748
00749 for (i = 0; i < npts; i++) {
00750
00751
00752
00753 nn = 0;
00754 switch (scaletype) {
00755 case 0:
00756 for (k = 0; k < nf; k++) {
00757 if (masks[k][i])
00758 continue;
00759 work[nn++] = datas[k][i];
00760 }
00761 break;
00762 case 1:
00763 for (k = 0; k < nf; k++) {
00764 if (masks[k][i])
00765 continue;
00766 work[nn++] = datas[k][i] + (fileptrs+k)->skyfudge;
00767 }
00768 break;
00769 case 2:
00770 for (k = 0; k < nf; k++) {
00771 if (masks[k][i])
00772 continue;
00773 work[nn++] = datas[k][i]*(fileptrs+k)->skyfudge;
00774 }
00775 break;
00776 case 3:
00777 for (k = 0; k < nf; k++) {
00778 if (masks[k][i])
00779 continue;
00780 work[nn++] = datas[k][i] + (fileptrs+k)->skyfudge;
00781 }
00782 break;
00783 }
00784
00785
00786
00787 if (nn == 0) {
00788 odata[i] = 0;
00789 omask[i] = 1;
00790 rmask[i] = 0;
00791 rplus[i] = 0;
00792 continue;
00793 }
00794
00795
00796
00797 nf1 = nn/2 - 1;
00798 nf2 = nf1 + 1;
00799 nfm = (nn + 1)/2 - 1;
00800 nrejmax = nn/2;
00801 is_even = !(nn & 1);
00802
00803
00804
00805 vircam_sort(&work,nn,1);
00806 if (is_even)
00807 value = 0.5*(work[nf1] + work[nf2]);
00808 else
00809 if (nn < 5)
00810 value = work[nfm];
00811 else
00812 value = 0.25*(work[nfm-1] + work[nfm+1]) + 0.5*work[nfm];
00813
00814
00815
00816 nplus = 0;
00817 cliplev = value + thresh*avskynoise;
00818 while (nplus < nrejmax && work[nn-nplus-1] > cliplev)
00819 nplus++;
00820 nminus = 0;
00821 cliplev = value - thresh*avskynoise;
00822 while ((nplus+nminus) < nrejmax && work[nminus] < cliplev)
00823 nminus++;
00824 nrej = nplus + nminus;
00825
00826
00827
00828 if (nrej > 0) {
00829 nremain = nn - nrej;
00830 nm = nremain/2 - 1 + nminus;
00831 nmm = (nremain + 1)/2 - 1 + nminus;
00832 is_even2 = !(nremain & 1);
00833 if (is_even2)
00834 value = 0.5*(work[nm] + work[nm+1]);
00835 else
00836 if (nremain < 3)
00837 value = work[nmm];
00838 else
00839 value = 0.5*work[nmm] + 0.25*(work[nmm-1] + work[nmm+1]);
00840 }
00841
00842
00843
00844 odata[i] = value;
00845 omask[i] = 0;
00846 rmask[i] = min(255,nrej);
00847 rplus[i] = min(255,nplus);
00848 }
00849
00850
00851
00852 cpl_free(work);
00853 }
00854
00855
00878
00879
00880 static void meancalc(float thresh, float avskynoise, int scaletype) {
00881 int nf2,k,nrej,nplus,nrejmax,kk,krem;
00882 long i,nn;
00883 float *work,value,value2,maxresid,resid,fresid,cliplev;
00884 unsigned char *iflag;
00885
00886
00887
00888 work = cpl_malloc(nf*sizeof(*work));
00889 iflag = cpl_malloc(nf*sizeof(unsigned char));
00890
00891
00892
00893 cliplev = thresh*avskynoise;
00894 for (i = 0; i < npts; i++) {
00895
00896
00897
00898 nn = 0;
00899 switch (scaletype) {
00900 case 0:
00901 for (k = 0; k < nf; k++) {
00902 if (masks[k][i])
00903 continue;
00904 work[nn++] = datas[k][i];
00905 }
00906 break;
00907 case 1:
00908 for (k = 0; k < nf; k++) {
00909 if (masks[k][i])
00910 continue;
00911 work[nn++] = datas[k][i] + (fileptrs+k)->skyfudge;
00912 }
00913 break;
00914 case 2:
00915 for (k = 0; k < nf; k++) {
00916 if (masks[k][i])
00917 continue;
00918 work[nn++] = datas[k][i]*(fileptrs+k)->skyfudge;
00919 }
00920 break;
00921 case 3:
00922 for (k = 0; k < nf; k++) {
00923 if (masks[k][i])
00924 continue;
00925 work[nn++] = datas[k][i] + (fileptrs+k)->skyfudge;
00926 }
00927 break;
00928 }
00929
00930
00931
00932 if (nn == 0) {
00933 odata[i] = 0;
00934 omask[i] = 1;
00935 rmask[i] = 0;
00936 rplus[i] = 0;
00937 continue;
00938 }
00939
00940
00941
00942 value = 0.0;
00943 for (k = 0; k < nn; k++) {
00944 value += work[k];
00945 iflag[k] = 0;
00946 }
00947 value /= (float)nn;
00948
00949
00950
00951 nrejmax = nn - 1;
00952 nplus = 0;
00953 nf2 = 0;
00954 for (kk = 0; kk < nrejmax; kk++) {
00955 maxresid = 0.0;
00956 krem = -1;
00957 for (k = 0; k < nn; k++) {
00958 if (iflag[k] == 1)
00959 continue;
00960 resid = work[k] - value;
00961 fresid = (float)fabs((double)resid);
00962 if (fresid > cliplev) {
00963 if (fresid > maxresid) {
00964 krem = k;
00965 maxresid = fresid;
00966 }
00967 }
00968 }
00969 if (krem == -1)
00970 break;
00971 if ((work[krem] - value) > 0.0)
00972 nplus++;
00973 value2 = 0.0;
00974 iflag[krem] = 1;
00975 nf2 = 0;
00976 for (k = 0; k < nn; k++) {
00977 if (iflag[k] == 0) {
00978 value2 += work[k];
00979 nf2 += 1;
00980 }
00981 }
00982 value = value2/(float)nf2;
00983 }
00984
00985
00986
00987 nrej = nn - nf2;
00988
00989
00990
00991 odata[i] = value;
00992 omask[i] = 0;
00993 rmask[i] = min(255,nrej);
00994 rplus[i] = min(255,nplus);
00995 }
00996
00997
00998
00999 cpl_free(work);
01000 cpl_free(iflag);
01001 }
01002
01003
01028
01029
01030 static void skyest(float *data, cpl_binary *mask, float thresh, float *skymed,
01031 float *skynoise) {
01032 unsigned char *bpm;
01033
01034
01035
01036 bpm = (unsigned char *)mask;
01037
01038
01039
01040 vircam_qmedsig(data,bpm,npts,thresh,3,-65535.0,65535.0,skymed,
01041 skynoise);
01042
01043 }
01044
01045
01049
01050
01051 static void tidy(void) {
01052 int i;
01053
01054
01055
01056 freespace(fileptrs);
01057 for (i = 0; i < nf; i++)
01058 freespace(datas[i]);
01059 freespace(datas);
01060 freespace(masks);
01061 }
01062
01066
01067
01068
01069
01070
01071
01072
01073
01074
01075
01076
01077
01078
01079
01080
01081
01082
01083
01084
01085
01086
01087
01088
01089
01090
01091
01092
01093
01094
01095
01096
01097
01098
01099
01100
01101
01102
01103
01104
01105
01106
01107
01108
01109
01110
01111
01112
01113
01114
01115
01116
01117
01118
01119
01120
01121
01122
01123
01124
01125
01126
01127
01128
01129
01130
01131
01132
01133
01134
01135
01136
01137
01138
01139
01140
01141
01142
01143
01144
01145
01146
01147
01148
01149
01150
01151
01152
01153
01154
01155
01156
01157
01158