Changeset 27840 for branches/simtest_nebulous_branches/ppSub/src
- Timestamp:
- May 3, 2010, 8:50:52 AM (16 years ago)
- Location:
- branches/simtest_nebulous_branches
- Files:
-
- 23 edited
- 2 copied
-
. (modified) (1 prop)
-
ppSub/src (modified) (1 prop)
-
ppSub/src/Makefile.am (modified) (3 diffs)
-
ppSub/src/ppSub.c (modified) (4 diffs)
-
ppSub/src/ppSub.h (modified) (3 diffs)
-
ppSub/src/ppSubArguments.c (modified) (4 diffs)
-
ppSub/src/ppSubBackground.c (modified) (2 diffs)
-
ppSub/src/ppSubCamera.c (modified) (22 diffs)
-
ppSub/src/ppSubConvolve.c (copied) (copied from trunk/ppSub/src/ppSubConvolve.c )
-
ppSub/src/ppSubData.c (modified) (3 diffs)
-
ppSub/src/ppSubDefineOutput.c (modified) (1 diff)
-
ppSub/src/ppSubErrorCodes.dat (modified) (1 diff)
-
ppSub/src/ppSubExit.c (copied) (copied from trunk/ppSub/src/ppSubExit.c )
-
ppSub/src/ppSubFiles.c (modified) (2 diffs)
-
ppSub/src/ppSubLoop.c (modified) (11 diffs)
-
ppSub/src/ppSubMakePSF.c (modified) (4 diffs)
-
ppSub/src/ppSubMatchPSFs.c (modified) (9 diffs)
-
ppSub/src/ppSubReadoutInverse.c (modified) (2 diffs)
-
ppSub/src/ppSubReadoutJpeg.c (modified) (3 diffs)
-
ppSub/src/ppSubReadoutPhotometry.c (modified) (5 diffs)
-
ppSub/src/ppSubReadoutStats.c (modified) (1 diff)
-
ppSub/src/ppSubReadoutSubtract.c (modified) (2 diffs)
-
ppSub/src/ppSubSetMasks.c (modified) (4 diffs)
-
ppSub/src/ppSubThreshold.c (modified) (5 diffs)
-
ppSub/src/ppSubVarianceRescale.c (modified) (1 diff)
Legend:
- Unmodified
- Added
- Removed
-
branches/simtest_nebulous_branches
- Property svn:mergeinfo changed
-
branches/simtest_nebulous_branches/ppSub/src
- Property svn:ignore
-
old new 13 13 ppSubErrorCodes.c 14 14 ppSubVersionDefinitions.h 15 ppSubConvolve
-
- Property svn:ignore
-
branches/simtest_nebulous_branches/ppSub/src/Makefile.am
r24862 r27840 1 bin_PROGRAMS = ppSub ppSubKernel 1 bin_PROGRAMS = ppSub ppSubKernel ppSubConvolve 2 2 3 3 if HAVE_SVNVERSION … … 34 34 ppSubData.c \ 35 35 ppSubErrorCodes.c \ 36 ppSubExit.c \ 36 37 ppSubFiles.c \ 37 38 ppSubLoop.c \ … … 53 54 ppSubKernel_SOURCES = \ 54 55 ppSubKernel.c 56 57 ppSubConvolve_CPPFLAGS = $(PSLIB_CFLAGS) $(PSMODULE_CFLAGS) $(PPSTATS_CFLAGS) $(PSPHOT_CFLAGS) $(PPSUB_CFLAGS) 58 ppSubConvolve_LDFLAGS = $(PSLIB_LIBS) $(PSMODULE_LIBS) $(PPSTATS_LIBS) $(PSPHOT_LIBS) $(PPSUB_LIBS) 59 60 ppSubConvolve_SOURCES = \ 61 ppSubConvolve.c \ 62 ppSubExit.c \ 63 ppSubVersion.c 55 64 56 65 noinst_HEADERS = \ -
branches/simtest_nebulous_branches/ppSub/src/ppSub.c
r23753 r27840 24 24 int main(int argc, char *argv[]) 25 25 { 26 ps Exit exitValue = PS_EXIT_SUCCESS; // Exit value26 psLibInit(NULL); 27 27 psTimerStart("ppSub"); 28 psLibInit(NULL); 28 29 pmErrorRegister(); 30 ppSubErrorRegister(); 31 psphotErrorRegister(); 29 32 30 33 ppSubData *data = NULL; // Processing data 31 34 pmConfig *config = pmConfigRead(&argc, argv, PPSUB_RECIPE); // Configuration 32 35 if (!config) { 33 psErrorStackPrint(stderr, "Error reading configuration.");34 exitValue = PS_EXIT_CONFIG_ERROR;35 36 goto die; 36 37 } … … 39 40 40 41 if (!pmModelClassInit()) { 41 psErrorStackPrint(stderr, "Error initialising model classes.\n"); 42 exitValue = PS_EXIT_PROG_ERROR; 42 psError(PPSUB_ERR_PROG, false, "Unable to initialise model classes."); 43 43 psFree(config); 44 44 goto die; … … 46 46 47 47 if (!psphotInit()) { 48 psErrorStackPrint(stderr, "Error initialising psphot.\n"); 49 exitValue = PS_EXIT_PROG_ERROR; 48 psError(PPSUB_ERR_PROG, false, "Error initialising psphot."); 50 49 psFree(config); 51 50 goto die; … … 55 54 56 55 if (!ppSubArguments(argc, argv, data)) { 57 psErrorStackPrint(stderr, "Error reading arguments.\n"); 58 exitValue = PS_EXIT_CONFIG_ERROR; 56 psError(psErrorCodeLast(), false, "Error reading arguments."); 59 57 goto die; 60 58 } 61 59 62 60 if (!ppSubCamera(data)) { 63 psErrorStackPrint(stderr, "Error setting up camera.\n");64 exitValue = PS_EXIT_CONFIG_ERROR;65 61 goto die; 66 62 } 67 63 68 64 if (!ppSubLoop(data)) { 69 psErrorStackPrint(stderr, "Error performing subtraction.\n");70 exitValue = PS_EXIT_SYS_ERROR;71 65 goto die; 72 66 } 73 67 74 68 die: 75 psTrace("ppSub", 1, "Finished at %f sec\n", psTimerMark("ppSub"));76 psTimerStop();69 { 70 psExit exitValue = ppSubExitCode(PS_EXIT_SUCCESS); // Exit code 77 71 78 psFree(data); 72 if (data && data->stats && data->statsFile) { 73 psString stats = psMetadataConfigFormat(data->stats); // Statistics to output 74 if (!stats || strlen(stats) == 0) { 75 psError(PPSUB_ERR_IO, false, "Unable to format statistics file"); 76 } else if (fprintf(data->statsFile, "%s", stats) != strlen(stats)) { 77 psError(PPSUB_ERR_IO, true, "Unable to write statistics file"); 78 } 79 psFree(stats); 80 if (fclose(data->statsFile) == EOF) { 81 psError(PPSUB_ERR_IO, true, "Unable to close statistics file"); 82 } 83 data->statsFile = NULL; 84 pmConfigRunFilenameAddWrite(data->config, "STATS", data->statsName); 85 exitValue = ppSubExitCode(exitValue); 86 } 79 87 80 pmVisualClose(); //close plot windows, if -visual is set 81 pmModelClassCleanup(); 82 pmConfigDone(); 83 psLibFinalize(); 88 if (config && !ppSubFilesIterateUp(config, PPSUB_FILES_ALL)) { 89 psError(psErrorCodeLast(), false, "Unable to close files."); 90 exitValue = ppSubExitCode(exitValue); 91 pmFPAfileFreeSetStrict(false); 92 } 84 93 85 exit(exitValue); 94 if (data) { 95 psString dump_file = psMetadataLookupStr(NULL, data->config->arguments, "-dumpconfig"); 96 if (dump_file) { 97 if (!pmConfigDump(data->config, dump_file)) { 98 psError(PPSUB_ERR_IO, false, "Unable to dump configuration."); 99 exitValue = ppSubExitCode(exitValue); 100 } 101 } 102 psFree(data); 103 } 104 105 psTrace("ppSub", 1, "Finished at %f sec\n", psTimerMark("ppSub")); 106 psTimerStop(); 107 108 pmVisualClose(); //close plot windows, if -visual is set 109 pmModelClassCleanup(); 110 pmConfigDone(); 111 psLibFinalize(); 112 113 exitValue = ppSubExitCode(exitValue); 114 exit(exitValue); 115 } 86 116 } -
branches/simtest_nebulous_branches/ppSub/src/ppSub.h
r24862 r27840 45 45 bool photometry; // Perform photometry? 46 46 bool inverse; // Output inverse subtraction as well? 47 bool saveInConv; // Save convolved input? 48 bool saveRefConv; // Save convolved reference? 47 49 psString stamps; // Stamps file 48 50 pmPSF *psf; // Point Spread Function … … 152 154 ); 153 155 156 /// Generate JPEG images 157 bool ppSubResidualSampleJpeg(pmConfig *config); 158 154 159 /// Generate inverse subtraction 155 160 bool ppSubReadoutInverse(pmConfig *config // Configuration … … 160 165 bool psMetadataCopySingle(psMetadata *target, psMetadata *source, const char *name); 161 166 167 bool ppSubCopyPSF (pmFPAfile *output, pmFPAfile *input, pmFPAview *view); 168 169 /// Return appropriate exit code 170 psExit ppSubExitCode(psExit exitValue // Current exit value 171 ); 172 162 173 ///@} 163 174 #endif -
branches/simtest_nebulous_branches/ppSub/src/ppSubArguments.c
r24833 r27840 86 86 psMetadataAddS32(arguments, PS_LIST_TAIL, "-convolve", 0, "Image to convolve [1 or 2]", 0); 87 87 psMetadataAddBool(arguments, PS_LIST_TAIL, "-photometry", 0, "Perform photometry?", NULL); 88 psMetadataAddBool(arguments, PS_LIST_TAIL, "-inverse", 0, "Generate inverse subtractions?", NULL); 88 psMetadataAddF32(arguments, PS_LIST_TAIL, "-zp", 0, "Zero point for photometry", NAN); 89 psMetadataAddBool(arguments, PS_LIST_TAIL, "-inverse", 0, "Generate inverse subtractions?", false); 90 psMetadataAddBool(arguments, PS_LIST_TAIL, "-save-inconv", 0, "Save input convolved images?", false); 91 psMetadataAddBool(arguments, PS_LIST_TAIL, "-save-refconv", 0, "Save reference convolved images?", false); 89 92 psMetadataAddBool(arguments, PS_LIST_TAIL, "-visual", 0, "Show diagnostic plots", NULL); 90 93 … … 140 143 if (data->statsName && strlen(data->statsName) > 0) { 141 144 psString resolved = pmConfigConvertFilename(data->statsName, config, true, true); // Resolved filename 145 if (!resolved) { 146 psError(psErrorCodeLast(), false, "Unable to resolve statistics file: %s", data->statsName); 147 return false; 148 } 142 149 data->statsFile = fopen(resolved, "w"); 143 150 if (!data->statsFile) { … … 149 156 } 150 157 158 data->saveInConv = psMetadataLookupBool(NULL, arguments, "-save-inconv"); 159 data->saveRefConv = psMetadataLookupBool(NULL, arguments, "-save-refconv"); 160 151 161 if (psMetadataLookupBool(NULL, arguments, "-visual")) { 152 162 pmVisualSetVisual(true); … … 156 166 if (threads > 0) { 157 167 if (!psThreadPoolInit(threads)) { 158 psError( PS_ERR_UNKNOWN, false, "Unable to setup %d threads", threads);168 psError(psErrorCodeLast(), false, "Unable to setup %d threads", threads); 159 169 return false; 160 170 } -
branches/simtest_nebulous_branches/ppSub/src/ppSubBackground.c
r23740 r27840 42 42 if (!modelRO) { 43 43 // Create the background model 44 if (!psphotModelBackground (config, view, "PPSUB.OUTPUT")) {45 psError( PS_ERR_UNKNOWN, false, "Unable to model background");44 if (!psphotModelBackgroundReadoutFileIndex(config, view, "PPSUB.OUTPUT", 0)) { 45 psError(psErrorCodeLast(), false, "Unable to model background"); 46 46 psFree(view); 47 47 return false; … … 50 50 modelRO = pmFPAfileThisReadout(config->files, view, "PSPHOT.BACKMDL"); 51 51 if (!modelRO) { 52 psError( PS_ERR_UNEXPECTED_NULL, true, "Unable to find background model");52 psError(psErrorCodeLast(), false, "Unable to find background model"); 53 53 psFree(view); 54 54 return false; -
branches/simtest_nebulous_branches/ppSub/src/ppSubCamera.c
r24261 r27840 23 23 24 24 // Define an input file 25 static pmFPAfile *defineInputFile(pmConfig *config,// Configuration 25 static pmFPAfile *defineInputFile(bool *success, 26 pmConfig *config,// Configuration 26 27 pmFPAfile *bind, // File to which to bind, or NULL 27 28 char *filerule, // Name of file rule … … 32 33 bool status; 33 34 34 // look for the file on the RUN metadata 35 pmFPAfile *file = pmFPAfileDefineFromRun(&status, bind, config, filerule); // File to return 35 *success = false; 36 37 pmFPAfile *file = NULL; 38 39 // look for the file on the argument list 40 if (bind) { 41 file = pmFPAfileBindFromArgs(&status, bind, config, filerule, argname); 42 } else { 43 file = pmFPAfileDefineFromArgs(&status, config, filerule, argname); 44 } 45 36 46 if (!status) { 37 psError( PS_ERR_UNKNOWN, false, "Failed to load file definition for %s", filerule);38 return NULL;47 psError(psErrorCodeLast(), false, "Failed to load file definition for %s", filerule); 48 return false; 39 49 } 40 50 if (!file) { 41 // look for the file on the argument list 42 if (bind) { 43 file = pmFPAfileBindFromArgs(&status, bind, config, filerule, argname); 44 } else { 45 file = pmFPAfileDefineFromArgs(&status, config, filerule, argname); 46 } 51 // look for the file on the RUN metadata 52 file = pmFPAfileDefineFromRun(&status, bind, config, filerule); // File to return 47 53 if (!status) { 48 psError( PS_ERR_UNKNOWN, false, "Failed to load file definition for %s", filerule);49 return false;54 psError(psErrorCodeLast(), false, "Failed to load file definition for %s", filerule); 55 return NULL; 50 56 } 51 57 } 52 58 53 59 if (!file) { 60 // no file defined 61 *success = true; 54 62 return NULL; 55 63 } 56 64 57 65 if (file->type != fileType) { 58 psError(PS_ERR_UNKNOWN, true, "%s is not of type %s", filerule, pmFPAfileStringFromType(fileType)); 59 return NULL; 60 } 61 66 psError(PPSUB_ERR_CONFIG, true, "%s is not of type %s", filerule, pmFPAfileStringFromType(fileType)); 67 return NULL; 68 } 69 70 *success = true; 62 71 return file; 63 72 } … … 75 84 pmFPAfileDefineOutput(config, template->fpa, filerule); 76 85 if (!file) { 77 psError( PS_ERR_IO, false, _("Unable to generate output file from %s"), filerule);86 psError(psErrorCodeLast(), false, _("Unable to generate output file from %s"), filerule); 78 87 return NULL; 79 88 } 80 89 if (file->type != fileType) { 81 psError(P S_ERR_IO, true, "%s is not of type %s", filerule, pmFPAfileStringFromType(fileType));90 psError(PPSUB_ERR_CONFIG, true, "%s is not of type %s", filerule, pmFPAfileStringFromType(fileType)); 82 91 return NULL; 83 92 } … … 92 101 pmFPAfile *bind, // File to which to bind, or NULL 93 102 char *filerule, // Name of file rule 103 const char *argname, // Argument name for file 94 104 pmFPAfileType fileType // Type of file 95 105 ) … … 98 108 99 109 // look for the file on the RUN metadata 100 pmFPAfile *file = pmFPAfileDefineFromRun(&status, bind, config, filerule); // File to return110 pmFPAfile *file = pmFPAfileDefineFromRun(&status, NULL, config, filerule); // File to return 101 111 if (!status) { 102 psError(PS_ERR_UNKNOWN, false, "Failed to load file definition for %s", filerule); 112 psError(psErrorCodeLast(), false, "Failed to load file definition for %s", filerule); 113 return NULL; 114 } 115 file = pmFPAfileBindFromArgs(&status, bind, config, filerule, argname); 116 if (!status) { 117 psError(psErrorCodeLast(), false, "Failed to load file definition for %s", filerule); 103 118 return NULL; 104 119 } … … 112 127 file = pmFPAfileDefineOutput(config, bind ? bind->fpa : NULL, filerule); 113 128 if (!status) { 114 psError( PS_ERR_UNKNOWN, false, "Failed to load file definition for %s", filerule);129 psError(psErrorCodeLast(), false, "Failed to load file definition for %s", filerule); 115 130 return false; 116 131 } … … 126 141 127 142 if (file->type != fileType) { 128 psError(P S_ERR_UNKNOWN, true, "%s is not of type %s", filerule, pmFPAfileStringFromType(fileType));143 psError(PPSUB_ERR_CONFIG, true, "%s is not of type %s", filerule, pmFPAfileStringFromType(fileType)); 129 144 return NULL; 130 145 } … … 136 151 bool ppSubCamera(ppSubData *data) 137 152 { 153 bool success = true; 154 138 155 psAssert(data, "Require processing data"); 139 156 pmConfig *config = data->config; … … 141 158 142 159 // Input image 143 pmFPAfile *input = defineInputFile(config, NULL, "PPSUB.INPUT", "INPUT", PM_FPA_FILE_IMAGE); 144 if (!input) { 145 psError(PS_ERR_IO, false, "Failed to build FPA from PPSUB.INPUT"); 146 return false; 147 } 148 defineInputFile(config, input, "PPSUB.INPUT.MASK", "INPUT.MASK", PM_FPA_FILE_MASK); 149 pmFPAfile *inVar = defineInputFile(config, input, "PPSUB.INPUT.VARIANCE", "INPUT.VARIANCE", 150 PM_FPA_FILE_VARIANCE); 151 defineInputFile(config, NULL, "PPSUB.INPUT.SOURCES", "INPUT.SOURCES", PM_FPA_FILE_CMF); 160 pmFPAfile *input = defineInputFile(&success, config, NULL, "PPSUB.INPUT", "INPUT", PM_FPA_FILE_IMAGE); 161 if (!success) { 162 psError(psErrorCodeLast(), false, "Failed to build FPA from PPSUB.INPUT"); 163 return false; 164 } 165 166 defineInputFile(&success, config, input, "PPSUB.INPUT.MASK", "INPUT.MASK", PM_FPA_FILE_MASK); 167 if (!success) { 168 psError(psErrorCodeLast(), false, "Failed to build FPA from PPSUB.INPUT.MASK"); 169 return false; 170 } 171 172 pmFPAfile *inVar = defineInputFile(&success, config, input, "PPSUB.INPUT.VARIANCE", "INPUT.VARIANCE", PM_FPA_FILE_VARIANCE); 173 if (!success) { 174 psError(psErrorCodeLast(), false, "Failed to build FPA from PPSUB.INPUT.VARIANCE"); 175 return false; 176 } 177 178 defineInputFile(&success, config, NULL, "PPSUB.INPUT.SOURCES", "INPUT.SOURCES", PM_FPA_FILE_CMF); 179 if (!success) { 180 psError(psErrorCodeLast(), false, "Failed to build FPA from PPSUB.INPUT.SOURCES"); 181 return false; 182 } 152 183 153 184 // Reference image 154 pmFPAfile *ref = defineInputFile(config, NULL, "PPSUB.REF", "REF", PM_FPA_FILE_IMAGE); 155 if (!ref) { 156 psError(PS_ERR_IO, false, "Failed to build FPA from PPSUB.REF"); 157 return false; 158 } 159 defineInputFile(config, ref, "PPSUB.REF.MASK", "REF.MASK", PM_FPA_FILE_MASK); 160 pmFPAfile *refVar = defineInputFile(config, ref, "PPSUB.REF.VARIANCE", "REF.VARIANCE", 161 PM_FPA_FILE_VARIANCE); 162 defineInputFile(config, NULL, "PPSUB.REF.SOURCES", "REF.SOURCES", PM_FPA_FILE_CMF); 163 185 pmFPAfile *ref = defineInputFile(&success, config, NULL, "PPSUB.REF", "REF", PM_FPA_FILE_IMAGE); 186 if (!success) { 187 psError(psErrorCodeLast(), false, "Failed to build FPA from PPSUB.REF"); 188 return false; 189 } 190 191 defineInputFile(&success, config, ref, "PPSUB.REF.MASK", "REF.MASK", PM_FPA_FILE_MASK); 192 if (!success) { 193 psError(psErrorCodeLast(), false, "Failed to build FPA from PPSUB.REF.MASK"); 194 return false; 195 } 196 197 pmFPAfile *refVar = defineInputFile(&success, config, ref, "PPSUB.REF.VARIANCE", "REF.VARIANCE", PM_FPA_FILE_VARIANCE); 198 if (!success) { 199 psError(psErrorCodeLast(), false, "Failed to build FPA from PPSUB.REF.VARIANCE"); 200 return false; 201 } 202 203 defineInputFile(&success, config, NULL, "PPSUB.REF.SOURCES", "REF.SOURCES", PM_FPA_FILE_CMF); 204 if (!success) { 205 psError(psErrorCodeLast(), false, "Failed to build FPA from PPSUB.REF.SOURCES"); 206 return false; 207 } 164 208 165 209 // Now that the camera has been determined, we can read the recipe 166 210 psMetadata *recipe = psMetadataLookupMetadata(NULL, config->recipes, PPSUB_RECIPE); // Recipe for ppSim 167 211 if (!recipe) { 168 psError(P S_ERR_UNEXPECTED_NULL, false, "Unable to find recipe %s", PPSUB_RECIPE);212 psError(PPSUB_ERR_CONFIG, false, "Unable to find recipe %s", PPSUB_RECIPE); 169 213 return false; 170 214 } … … 180 224 data->inverse = psMetadataLookupBool(NULL, recipe, "INVERSE"); 181 225 data->photometry = psMetadataLookupBool(NULL, recipe, "PHOTOMETRY"); 182 183 bool mdok; // Status of MD lookup184 bool saveConv = psMetadataLookupBool(&mdok, recipe, "SAVE.CONVOLVED"); // Save convolved images?185 226 186 227 // Convolved input image … … 189 230 PM_FPA_FILE_MASK); 190 231 if (!inConvImage || !inConvMask) { 191 psError(PS_ERR_UNKNOWN, false, "Unable to define output files"); 192 return false; 193 } 194 if (saveConv) { 195 inConvImage->save = true; 196 inConvMask->save = true; 197 } 232 psError(psErrorCodeLast(), false, "Unable to define output files"); 233 return false; 234 } 235 inConvImage->save = data->saveInConv; 236 inConvMask->save = data->saveInConv; 198 237 if (inVar) { 199 238 pmFPAfile *inConvVar = defineOutputFile(config, inConvImage, false, "PPSUB.INPUT.CONV.VARIANCE", 200 239 PM_FPA_FILE_VARIANCE); 201 240 if (!inConvVar) { 202 psError(PS_ERR_UNKNOWN, false, "Unable to define output files"); 203 return false; 204 } 205 if (saveConv) { 206 inConvVar->save = true; 207 } 241 psError(psErrorCodeLast(), false, "Unable to define output files"); 242 return false; 243 } 244 inConvVar->save = data->saveInConv; 208 245 } 209 246 … … 213 250 PM_FPA_FILE_MASK); 214 251 if (!refConvImage || !refConvMask) { 215 psError(PS_ERR_UNKNOWN, false, "Unable to define output files"); 216 return false; 217 } 218 if (saveConv) { 219 refConvImage->save = true; 220 refConvMask->save = true; 221 } 252 psError(psErrorCodeLast(), false, "Unable to define output files"); 253 return false; 254 } 255 refConvImage->save = data->saveRefConv; 256 refConvMask->save = data->saveRefConv; 222 257 if (refVar) { 223 258 pmFPAfile *refConvVar = defineOutputFile(config, refConvImage, false, "PPSUB.REF.CONV.VARIANCE", 224 259 PM_FPA_FILE_VARIANCE); 225 260 if (!refConvVar) { 226 psError(PS_ERR_UNKNOWN, false, "Unable to define output files"); 227 return false; 228 } 229 if (saveConv) { 230 refConvVar->save = true; 231 } 261 psError(psErrorCodeLast(), false, "Unable to define output files"); 262 return false; 263 } 264 refConvVar->save = data->saveRefConv; 232 265 } 233 266 … … 236 269 pmFPAfile *outMask = defineOutputFile(config, output, false, "PPSUB.OUTPUT.MASK", PM_FPA_FILE_MASK); 237 270 if (!output || !outMask) { 238 psError( PS_ERR_UNKNOWN, false, "Unable to define output files");271 psError(psErrorCodeLast(), false, "Unable to define output files"); 239 272 return false; 240 273 } … … 245 278 PM_FPA_FILE_VARIANCE); 246 279 if (!outVar) { 247 psError( PS_ERR_UNKNOWN, false, "Unable to define output files");280 psError(psErrorCodeLast(), false, "Unable to define output files"); 248 281 return false; 249 282 } … … 258 291 PM_FPA_FILE_MASK); 259 292 if (!inverse || !invMask) { 260 psError( PS_ERR_UNKNOWN, false, "Unable to define output files");293 psError(psErrorCodeLast(), false, "Unable to define output files"); 261 294 return false; 262 295 } … … 267 300 PM_FPA_FILE_VARIANCE); 268 301 if (!invVar) { 269 psError( PS_ERR_UNKNOWN, false, "Unable to define output files");302 psError(psErrorCodeLast(), false, "Unable to define output files"); 270 303 return false; 271 304 } … … 278 311 pmFPAfile *jpeg1 = pmFPAfileDefineOutput(config, NULL, "PPSUB.OUTPUT.JPEG1"); 279 312 if (!jpeg1) { 280 psError( PS_ERR_IO, false, _("Unable to generate output file from PPSUB.OUTPUT.JPEG1"));313 psError(psErrorCodeLast(), false, _("Unable to generate output file from PPSUB.OUTPUT.JPEG1")); 281 314 return false; 282 315 } 283 316 if (jpeg1->type != PM_FPA_FILE_JPEG) { 284 psError( PS_ERR_IO, true, "PPSUB.OUTPUT.JPEG1 is not of type JPEG");317 psError(psErrorCodeLast(), true, "PPSUB.OUTPUT.JPEG1 is not of type JPEG"); 285 318 return false; 286 319 } … … 288 321 pmFPAfile *jpeg2 = pmFPAfileDefineOutput(config, NULL, "PPSUB.OUTPUT.JPEG2"); 289 322 if (!jpeg2) { 290 psError( PS_ERR_IO, false, _("Unable to generate output file from PPSUB.OUTPUT.JPEG2"));323 psError(psErrorCodeLast(), false, _("Unable to generate output file from PPSUB.OUTPUT.JPEG2")); 291 324 return false; 292 325 } 293 326 if (jpeg2->type != PM_FPA_FILE_JPEG) { 294 psError( PS_ERR_IO, true, "PPSUB.OUTPUT.JPEG2 is not of type JPEG");327 psError(psErrorCodeLast(), true, "PPSUB.OUTPUT.JPEG2 is not of type JPEG"); 295 328 return false; 296 329 } 297 330 jpeg2->save = true; 298 331 332 // Output residual JPEG 333 pmFPAfile *jpeg3 = pmFPAfileDefineOutput(config, NULL, "PPSUB.OUTPUT.RESID.JPEG"); 334 if (!jpeg3) { 335 psError(psErrorCodeLast(), false, _("Unable to generate output file from PPSUB.OUTPUT.RESID.JPEG")); 336 return false; 337 } 338 if (jpeg3->type != PM_FPA_FILE_JPEG) { 339 psError(psErrorCodeLast(), true, "PPSUB.OUTPUT.RESID.JPEG is not of type JPEG"); 340 return false; 341 } 342 jpeg3->save = true; 343 299 344 // Output subtraction kernel 300 pmFPAfile *kernel = defineCalcFile(config, output, "PPSUB.OUTPUT.KERNELS", PM_FPA_FILE_SUBKERNEL); 345 pmFPAfile *kernel = defineCalcFile(config, output, "PPSUB.OUTPUT.KERNELS", "KERNEL", 346 PM_FPA_FILE_SUBKERNEL); 301 347 if (!kernel) { 302 348 psError(PS_ERR_UNEXPECTED_NULL, false, "Unable to define file PPSUB.OUTPUT.KERNELS"); … … 305 351 306 352 // psPhot input 307 if (data->photometry ) {353 if (data->photometry || 1) { 308 354 psphotModelClassInit(); // load implementation-specific models 309 355 310 356 pmFPAfile *psphot = pmFPAfileDefineFromFPA(config, output->fpa, 1, 1, "PSPHOT.INPUT"); 311 357 if (!psphot) { 312 psError( PS_ERR_IO, false, "Failed to build FPA from PSPHOT.INPUT");358 psError(psErrorCodeLast(), false, "Failed to build FPA from PSPHOT.INPUT"); 313 359 return false; 314 360 } 315 361 if (psphot->type != PM_FPA_FILE_IMAGE) { 316 psError(PS_ERR_IO, true, "PSPHOT.INPUT is not of type IMAGE"); 317 return false; 318 } 362 psError(psErrorCodeLast(), true, "PSPHOT.INPUT is not of type IMAGE"); 363 return false; 364 } 365 // specify the number of psphot input images 366 psMetadataAddS32 (config->arguments, PS_LIST_TAIL, "PSPHOT.INPUT.NUM", PS_META_REPLACE, "number of inputs", 1); 319 367 pmFPAfileActivate(config->files, false, "PSPHOT.INPUT"); 320 368 321 // Internal -ishfile for getting the PSF from the minuend322 pmFPAfile *psf = pmFPAfileDefine OutputFromFile(config, psphot, "PSPHOT.PSF.LOAD");369 // Internal file for getting the PSF from the minuend 370 pmFPAfile *psf = pmFPAfileDefineFromFPA(config, output->fpa, 1, 1, "PSPHOT.PSF.LOAD"); 323 371 if (!psf) { 324 psError( PS_ERR_IO, false, "Failed to build FPA from PSPHOT.PSF.LOAD");372 psError(psErrorCodeLast(), false, "Failed to build FPA from PSPHOT.PSF.LOAD"); 325 373 return false; 326 374 } 327 375 if (psf->type != PM_FPA_FILE_PSF) { 328 psError( PS_ERR_IO, true, "PSPHOT.PSF.LOAD is not of type PSF");376 psError(psErrorCodeLast(), true, "PSPHOT.PSF.LOAD is not of type PSF"); 329 377 return false; 330 378 } … … 332 380 333 381 if (!psphotDefineFiles(config, psphot)) { 334 psError( PS_ERR_UNKNOWN, false, "Unable to set up psphot files.");382 psError(psErrorCodeLast(), false, "Unable to set up psphot files."); 335 383 return false; 336 384 } … … 343 391 PM_FPA_FILE_CMF); 344 392 if (!outSources) { 345 psError( PS_ERR_UNKNOWN, false, "Unable to set up output source file.");393 psError(psErrorCodeLast(), false, "Unable to set up output source file."); 346 394 return false; 347 395 } … … 352 400 PM_FPA_FILE_CMF); 353 401 if (!invSources) { 354 psError( PS_ERR_UNKNOWN, false, "Unable to set up inverse source file.");402 psError(psErrorCodeLast(), false, "Unable to set up inverse source file."); 355 403 return false; 356 404 } -
branches/simtest_nebulous_branches/ppSub/src/ppSubData.c
r23753 r27840 13 13 static void subDataFree(ppSubData *data) 14 14 { 15 if (data->statsFile) { 16 psString stats = psMetadataConfigFormat(data->stats); // Statistics to output 17 if (!stats || strlen(stats) == 0) { 18 psWarning("Unable to generate statistics file."); 19 } else { 20 fprintf(data->statsFile, "%s", stats); 21 } 22 psFree(stats); 23 fclose(data->statsFile); 24 pmConfigRunFilenameAddWrite(data->config, "STATS", data->statsName); 25 } 15 psAssert(!data->statsFile, "Statistics file still open."); 26 16 psFree(data->statsName); 27 17 psFree(data->stamps); … … 29 19 psFree(data->stats); 30 20 31 psString dump_file = psMetadataLookupStr(NULL, data->config->arguments, "-dumpconfig");32 if (dump_file) {33 pmConfigDump(data->config, dump_file);34 }35 21 psFree(data->config); 36 22 … … 47 33 data->photometry = false; 48 34 data->inverse = false; 35 data->saveInConv = false; 36 data->saveRefConv = false; 49 37 data->stamps = NULL; 50 38 data->psf = NULL; -
branches/simtest_nebulous_branches/ppSub/src/ppSubDefineOutput.c
r23740 r27840 51 51 bool mdok; // Status of MD lookup 52 52 psMetadata *analysis = inConv->analysis; // Analysis metadata with kernel information 53 pmSubtractionKernels *kernels = psMetadataLookupPtr(&mdok, analysis, 54 PM_SUBTRACTION_ANALYSIS_KERNEL); // Subtraction kernel 53 pmHDU *hdu = pmHDUFromCell(inConv->parent); 54 pmSubtractionKernels *kernels = psMetadataLookupPtr(&mdok, analysis, PM_SUBTRACTION_ANALYSIS_KERNEL); // Subtraction kernel 55 55 56 if (!kernels) { 57 hdu = pmHDUFromCell(refConv->parent); 56 58 analysis = refConv->analysis; 57 59 kernels = psMetadataLookupPtr(&mdok, analysis, PM_SUBTRACTION_ANALYSIS_KERNEL); 58 60 } 59 61 if (!kernels) { 60 psError(P S_ERR_UNEXPECTED_NULL, true, "Unable to find SUBTRACTION.KERNEL");62 psError(PPSUB_ERR_UNKNOWN, true, "Unable to find SUBTRACTION.KERNEL"); 61 63 psFree(outRO); 62 64 return false; 63 65 } 64 psMetadataAddStr(outHDU->header, PS_LIST_TAIL, "PPSUB.KERNEL", 0, "Subtraction kernel", 65 kernels->description); 66 psAssert (hdu, "unable to find HDU"); 67 psMetadataAddStr(outHDU->header, PS_LIST_TAIL, "PPSUB.KERNEL", 0, "Subtraction kernel", kernels->description); 68 outHDU->header = psMetadataCopy(outHDU->header, hdu->header); 66 69 67 70 // Add additional data to the header -
branches/simtest_nebulous_branches/ppSub/src/ppSubErrorCodes.dat
r23740 r27840 10 10 DATA Problem in data values 11 11 NO_OVERLAP No overlap between input and skycell 12 PROG Programming error -
branches/simtest_nebulous_branches/ppSub/src/ppSubFiles.c
r23740 r27840 23 23 // Subtraction files 24 24 static const char *subFiles[] = { "PPSUB.OUTPUT", "PPSUB.OUTPUT.MASK", "PPSUB.OUTPUT.VARIANCE", 25 "PPSUB.OUTPUT.JPEG1", "PPSUB.OUTPUT.JPEG2", 25 "PPSUB.OUTPUT.JPEG1", "PPSUB.OUTPUT.JPEG2", "PPSUB.OUTPUT.RESID.JPEG", 26 26 NULL }; 27 27 … … 183 183 } 184 184 185 psFree(view); 186 187 // Disable writing of data now that we've written things out 188 if (files & PPSUB_FILES_CONV) { 189 pmFPAview *view = ppSubViewReadout(); // View to readout 190 { 191 pmReadout *ro = pmFPAfileThisReadout(config->files, view, "PPSUB.INPUT.CONV"); 192 if (ro) { 193 ro->data_exists = ro->parent->data_exists = ro->parent->parent->data_exists = false; 194 } 195 } 196 { 197 pmReadout *ro = pmFPAfileThisReadout(config->files, view, "PPSUB.REF.CONV"); 198 if (ro) { 199 ro->data_exists = ro->parent->data_exists = ro->parent->parent->data_exists = false; 200 } 201 } 202 psFree(view); 203 } 204 if (files & PPSUB_FILES_SUB) { 205 pmFPAview *view = ppSubViewReadout(); // View to readout 206 pmReadout *ro = pmFPAfileThisReadout(config->files, view, "PPSUB.OUTPUT"); 207 if (ro) { 208 ro->data_exists = ro->parent->data_exists = ro->parent->parent->data_exists = false; 209 } 210 psFree(view); 211 } 212 // Disable writing of data now that we've written things out 213 if (files & PPSUB_FILES_INV) { 214 pmFPAview *view = ppSubViewReadout(); // View to readout 215 pmReadout *ro = pmFPAfileThisReadout(config->files, view, "PPSUB.INVERSE"); 216 if (ro) { 217 ro->data_exists = ro->parent->data_exists = ro->parent->parent->data_exists = false; 218 } 219 psFree(view); 220 } 221 185 222 ppSubFilesActivate(config, PPSUB_FILES_ALL, false); 186 223 -
branches/simtest_nebulous_branches/ppSub/src/ppSubLoop.c
r24862 r27840 27 27 28 28 pmConfigCamerasCull(config, NULL); 29 pmConfigRecipesCull(config, "PPSUB,PPSTATS,PSPHOT, MASKS,JPEG");29 pmConfigRecipesCull(config, "PPSUB,PPSTATS,PSPHOT,PSASTRO,MASKS,JPEG"); 30 30 31 31 … … 43 43 44 44 if (!ppSubSetMasks(config)) { 45 psError( PS_ERR_UNKNOWN, false, "Unable to set masks.");45 psError(psErrorCodeLast(), false, "Unable to set masks."); 46 46 return false; 47 47 } 48 48 49 49 if (!ppSubMatchPSFs(data)) { 50 psError( PS_ERR_UNKNOWN, false, "Unable to match PSFs.");50 psError(psErrorCodeLast(), false, "Unable to match PSFs."); 51 51 return false; 52 52 } … … 55 55 return true; 56 56 } 57 // generate the residual stamp grid for visualization 58 if (!ppSubResidualSampleJpeg(config)) { 59 psError(psErrorCodeLast(), false, "Unable to update."); 60 return false; 61 } 57 62 58 63 psMetadataAddF32(data->stats, PS_LIST_TAIL, "TIME_MATCH", 0, "Time to match PSFs", … … 66 71 67 72 if (!ppSubLowThreshold(data)) { 68 psError( PS_ERR_UNKNOWN, false, "Unable to threshold images.");73 psError(psErrorCodeLast(), false, "Unable to threshold images."); 69 74 return false; 70 75 } … … 77 82 78 83 if (!ppSubDefineOutput("PPSUB.OUTPUT", config)) { 79 psError( PS_ERR_UNKNOWN, false, "Unable to define output.");84 psError(psErrorCodeLast(), false, "Unable to define output."); 80 85 return false; 81 86 } 82 87 83 88 if (!data->quality && !ppSubMakePSF(data)) { 84 psError(PS_ERR_UNKNOWN, false, "Unable to generate PSF."); 85 return false; 89 psError(psErrorCodeLast(), false, "Unable to generate PSF."); 90 return false; 91 } 92 93 // Now we've got a PSF, blow away detections in case they're confused with real output detections 94 { 95 pmFPAview *view = ppSubViewReadout(); // View to readout 96 pmReadout *out = pmFPAfileThisReadout(config->files, view, "PPSUB.OUTPUT"); 97 if (psMetadataLookup(out->analysis, "PSPHOT.DETECTIONS")) { 98 psMetadataRemoveKey(out->analysis, "PSPHOT.DETECTIONS"); 99 } 100 psFree(view); 86 101 } 87 102 88 103 if (!ppSubReadoutSubtract(config)) { 89 psError( PS_ERR_UNKNOWN, false, "Unable to subtract images.");104 psError(psErrorCodeLast(), false, "Unable to subtract images."); 90 105 return false; 91 106 } … … 99 114 // Higher order background subtraction using psphot 100 115 if (!ppSubBackground(config)) { 101 psError( PS_ERR_UNKNOWN, false, "Unable to subtract background.");116 psError(psErrorCodeLast(), false, "Unable to subtract background."); 102 117 return false; 103 118 } … … 105 120 // Perform Variance correction (rescale within a modest range) 106 121 if (!ppSubVarianceRescale(config)) { 107 psError( PS_ERR_UNKNOWN, false, "Unable to rescale variance.");122 psError(psErrorCodeLast(), false, "Unable to rescale variance."); 108 123 return false; 109 124 } … … 115 130 116 131 if (!data->quality && !ppSubReadoutPhotometry("PPSUB.OUTPUT", data)) { 117 psError( PS_ERR_UNKNOWN, false, "Unable to perform photometry.");132 psError(psErrorCodeLast(), false, "Unable to perform photometry."); 118 133 return false; 119 134 } … … 126 141 // Perform statistics on the cell 127 142 if (!ppSubReadoutStats(data)) { 128 psError(PS_ERR_UNKNOWN, false, "Unable to collect statistics"); 129 return false; 130 } 131 143 psError(psErrorCodeLast(), false, "Unable to collect statistics"); 144 return false; 145 } 146 147 // generate the binned image used to write the jpeg 132 148 if (!ppSubReadoutJpeg(config)) { 133 psError( PS_ERR_UNKNOWN, false, "Unable to update.");149 psError(psErrorCodeLast(), false, "Unable to update."); 134 150 return false; 135 151 } … … 143 159 144 160 if (data->inverse && !ppSubDefineOutput("PPSUB.INVERSE", config)) { 145 psError( PS_ERR_UNKNOWN, false, "Unable to define inverse.");161 psError(psErrorCodeLast(), false, "Unable to define inverse."); 146 162 return false; 147 163 } 148 164 149 165 if (!ppSubReadoutInverse(config)) { 150 psError( PS_ERR_UNKNOWN, false, "Unable to invert images.");166 psError(psErrorCodeLast(), false, "Unable to invert images."); 151 167 return false; 152 168 } … … 164 180 165 181 if (!data->quality && !ppSubReadoutPhotometry("PPSUB.INVERSE", data)) { 166 psError( PS_ERR_UNKNOWN, false, "Unable to perform photometry.");182 psError(psErrorCodeLast(), false, "Unable to perform photometry."); 167 183 return false; 168 184 } -
branches/simtest_nebulous_branches/ppSub/src/ppSubMakePSF.c
r23763 r27840 21 21 22 22 #include "ppSub.h" 23 24 psArray *ppSubSelectPSFSources(psArray *sources); 23 25 24 26 bool ppSubMakePSF(ppSubData *data) … … 57 59 pmFPAfile *photFile = psMetadataLookupPtr(&mdok, config->files, "PSPHOT.INPUT"); // Photometry file 58 60 if (!pmFPACopy(photFile->fpa, minuendFile->fpa)) { 59 psError(P S_ERR_UNKNOWN, false, "Unable to copy FPA for photometry");61 psError(PPSUB_ERR_CONFIG, false, "Unable to copy FPA for photometry"); 60 62 psFree(view); 61 63 return false; 62 64 } 65 63 66 pmReadout *photRO = pmFPAviewThisReadout(view, photFile->fpa); // Readout to photometer 64 if (psMetadataLookup(photRO->analysis, "PSPHOT.SOURCES")) { 65 psMetadataRemoveKey(photRO->analysis, "PSPHOT.SOURCES"); 67 68 // we need to remove any existing PSPHOT.DETECTIONS (why not do this in psphot?) 69 if (psMetadataLookup(photRO->analysis, "PSPHOT.DETECTIONS")) { 70 psMetadataRemoveKey(photRO->analysis, "PSPHOT.DETECTIONS"); 66 71 } 72 if (psMetadataLookup(photRO->parent->parent->analysis, "PSPHOT.PSF")) { 73 psMetadataRemoveKey(photRO->parent->parent->analysis, "PSPHOT.PSF"); 74 } 75 76 # ifdef TESTING 77 // XXX for testing, dump these images: 78 psphotSaveImage (NULL, photRO->image, "findpsf.im.fits"); 79 psphotSaveImage (NULL, photRO->variance, "findpsf.wt.fits"); 80 psphotSaveImage (NULL, photRO->mask, "findpsf.mk.fits"); 81 # endif 67 82 68 83 // Extract the loaded sources from the associated readout, and generate PSF 69 84 // Here, we assume the image is background-subtracted 70 psArray *sources = psMetadataLookupPtr(&mdok, minuend->analysis, "PSPHOT.SOURCES"); 71 if (!psphotReadoutFindPSF(config, view, sources)) { 85 pmDetections *detections = psMetadataLookupPtr(&mdok, minuend->analysis, "PSPHOT.DETECTIONS"); 86 if (!detections || !detections->allSources) { 87 psError(PPSUB_ERR_CONFIG, true, "No sources from which to determine PSF."); 88 return false; 89 } 90 psArray *sources = detections->allSources; 91 92 // XXX filter sources? limit the total number and return only brighter objects? 93 // use flags to toss totally bogus entries? 94 psArray *goodSources = ppSubSelectPSFSources (sources); 95 if (!psphotReadoutFindPSF(config, view, goodSources)) { 72 96 // This is likely a data quality issue 73 97 // XXX Split into multiple cases using error codes? … … 76 100 ppSubDataQuality(data, PSPHOT_ERR_PSF, PPSUB_FILES_PHOT_SUB | PPSUB_FILES_PHOT_INV); 77 101 psFree(view); 102 psFree(goodSources); 78 103 return true; 104 } 105 106 // save the resulting PSF information on the pmFPAfile PSPHOT.PSF.LOAD 107 pmFPAfile *psfFile = psMetadataLookupPtr(&mdok, config->files, "PSPHOT.PSF.LOAD"); // PSF file 108 if (!ppSubCopyPSF(psfFile, photFile, view)) { 109 psErrorStackPrint(stderr, "PSF was not generated"); 110 psWarning("PSF was not generated --- suspect bad data quality."); 111 ppSubDataQuality(data, psErrorCodeLast(), PPSUB_FILES_PHOT_SUB | PPSUB_FILES_PHOT_INV); 79 112 } 80 113 … … 82 115 psMetadataRemoveKey(photRO->analysis, "PSPHOT.HEADER"); 83 116 84 if (!data->quality) { 85 data->psf = psMemIncrRefCounter(psMetadataLookupPtr(NULL, photRO->parent->parent->analysis, 86 "PSPHOT.PSF")); 87 } 88 117 psFree(goodSources); 89 118 psFree(view); 90 119 91 120 return true; 92 121 } 122 123 bool ppSubCopyPSF(pmFPAfile *output, pmFPAfile *input, pmFPAview *view) 124 { 125 pmChip *inputChip = pmFPAviewThisChip(view, input->fpa); // Chip with PSF info 126 pmChip *outputChip = pmFPAviewThisChip(view, output->fpa); // Chip to store PSF info 127 128 pmReadout *inputRO = pmFPAviewThisReadout(view, input->fpa); // Readout with PSF info 129 pmReadout *outputRO = pmFPAviewThisReadout(view, output->fpa); // Readout to store PSF info 130 131 if (!outputRO) { 132 pmCell *outputCell = pmFPAviewThisCell(view, output->fpa); 133 outputRO = pmReadoutAlloc(outputCell); 134 outputRO->image = psMemIncrRefCounter(inputRO->image); 135 } 136 137 // Copy the PSF-related data 138 psMetadataIterator *iter = psMetadataIteratorAlloc(inputRO->analysis, PS_LIST_HEAD, "^PSF\\.CLUMP.*"); 139 psMetadataItem *item; // Item from iteration 140 while ((item = psMetadataGetAndIncrement(iter))) { 141 psMetadataAddItem(outputRO->analysis, item, PS_LIST_TAIL, PS_META_REPLACE); 142 } 143 psFree(iter); 144 145 // copy the PSF model data 146 pmPSF *psf = psMetadataLookupPtr(NULL, inputChip->analysis, "PSPHOT.PSF"); // PSF for photometry 147 if (!psf) { 148 psErrorStackPrint(stderr, "No PSF available"); 149 return false; 150 } 151 152 psMetadataAddPtr(outputChip->analysis, PS_LIST_TAIL, "PSPHOT.PSF", PS_DATA_UNKNOWN | PS_META_REPLACE, 153 "PSF from ppSubMakePSF", psf); 154 155 return true; 156 } 157 158 159 // XXX hardwired MAX for now 160 # define MAX_NPSF 500 161 162 psArray *ppSubSelectPSFSources(psArray *sources){ 163 164 sources = psArraySort (sources, pmSourceSortBySN); 165 166 psArray *subset = psArrayAllocEmpty(MAX_NPSF); 167 168 int nPSF = 0; 169 for (int i = 0; (nPSF < MAX_NPSF) && (i < sources->n); i++) { 170 171 pmSource *source = sources->data[i]; 172 if (!source) continue; 173 174 // skip non-astronomical objects (very likely defects) 175 if (source->type == PM_SOURCE_TYPE_DEFECT) continue; 176 if (source->type == PM_SOURCE_TYPE_SATURATED) continue; 177 if (source->mode & PM_SOURCE_MODE_SATSTAR) continue; 178 179 psArrayAdd (subset, 100, source); 180 nPSF++; 181 } 182 183 return subset; 184 } -
branches/simtest_nebulous_branches/ppSub/src/ppSubMatchPSFs.c
r24862 r27840 18 18 #include <pslib.h> 19 19 #include <psmodules.h> 20 #include <psphot.h> 20 21 21 22 #include "ppSub.h" 23 24 #define COVAR_FRAC 0.01 // Truncation fraction for covariance matrix 22 25 23 26 // Normalise a region on an image … … 37 40 } 38 41 42 // Measure the PSF for an image 43 static float subImagePSF(ppSubData *data, // Processing data 44 const pmReadout *ro, // Readout for which to measure PSF 45 psArray *sources // Sources with positions at which to measure PSF 46 ) 47 { 48 psAssert(data, "Require processing data"); 49 pmConfig *config = data->config; // Configuration 50 psAssert(config, "Require configuration"); 51 52 psAssert(ro, "Need readout"); 53 psAssert(sources, "Need sources."); 54 55 pmFPAfile *photFile = psMetadataLookupPtr(NULL, config->files, "PSPHOT.INPUT"); // Photometry file 56 psAssert(photFile, "Need photometry file."); 57 if (!pmFPACopy(photFile->fpa, ro->parent->parent->parent)) { 58 psError(PPSUB_ERR_CONFIG, false, "Unable to copy FPA for photometry"); 59 return false; 60 } 61 62 pmFPAview *view = ppSubViewReadout(); // View to readout 63 pmReadout *photRO = pmFPAviewThisReadout(view, photFile->fpa); // Readout to photometer 64 65 if (psMetadataLookup(photRO->analysis, "PSPHOT.DETECTIONS")) { 66 psMetadataRemoveKey(photRO->analysis, "PSPHOT.DETECTIONS"); 67 } 68 if (psMetadataLookup(photRO->parent->parent->analysis, "PSPHOT.PSF")) { 69 psMetadataRemoveKey(photRO->parent->parent->analysis, "PSPHOT.PSF"); 70 } 71 72 // Extract the loaded sources from the associated readout, and generate PSF 73 // Here, we assume the image is background-subtracted 74 if (!psphotReadoutFindPSF(config, view, sources)) { 75 psErrorStackPrint(stderr, "Unable to determine PSF"); 76 psWarning("Unable to determine PSF."); 77 psFree(view); 78 return true; 79 } 80 81 psFree(view); 82 83 psMetadata *header = psMetadataLookupMetadata(NULL, photRO->analysis, "PSPHOT.HEADER"); 84 psAssert(header, "Require header."); 85 float fwhm = psMetadataLookupF32(NULL, header, "FWHM_MAJ"); 86 87 if (psMetadataLookup(photRO->analysis, "PSPHOT.DETECTIONS")) { 88 psMetadataRemoveKey(photRO->analysis, "PSPHOT.DETECTIONS"); 89 } 90 if (psMetadataLookup(photRO->parent->parent->analysis, "PSPHOT.PSF")) { 91 psMetadataRemoveKey(photRO->parent->parent->analysis, "PSPHOT.PSF"); 92 } 93 94 return fwhm; 95 } 96 97 // Scale the kernel parameters according to the PSFs 98 static bool subScaleKernel(ppSubData *data, // Processing data 99 psVector *kernelWidths, // Widths for kernel 100 int *kernelSize, // Size of kernel 101 int *stampSize // Size of stamps (footprint) 102 ) 103 { 104 psAssert(data, "Require processing data"); 105 pmConfig *config = data->config; // Configuration 106 psAssert(config, "Require configuration"); 107 108 // Nothing to do if pre-calculated kernel exists 109 pmFPAview *view = ppSubViewReadout(); // View to readout 110 pmReadout *kernelRO = pmFPAfileThisReadout(config->files, view, "PPSUB.OUTPUT.KERNELS"); // RO with kernel 111 if (kernelRO) { 112 psFree(view); 113 return true; 114 } 115 116 // Look up recipe values 117 psMetadata *recipe = psMetadataLookupMetadata(NULL, config->recipes, PPSUB_RECIPE); // Recipe for ppSim 118 psAssert(recipe, "We checked this earlier, so it should be here."); 119 if (!psMetadataLookupBool(NULL, recipe, "SCALE")) { 120 // No scaling requested 121 psFree(view); 122 return true; 123 } 124 125 // Input images 126 pmReadout *inRO = pmFPAfileThisReadout(config->files, view, "PPSUB.INPUT"); // Input readout 127 pmReadout *refRO = pmFPAfileThisReadout(config->files, view, "PPSUB.REF"); // Reference readout 128 129 // Input sources 130 pmReadout *inSourceRO = pmFPAfileThisReadout(config->files, view, "PPSUB.INPUT.SOURCES"); 131 pmReadout *refSourceRO = pmFPAfileThisReadout(config->files, view, "PPSUB.REF.SOURCES"); 132 if (!inSourceRO || !refSourceRO) { 133 psWarning("Unable to scale kernel, since no sources were provided."); 134 return true; 135 } 136 137 pmDetections *inDetections = psMetadataLookupPtr(NULL, inSourceRO->analysis, "PSPHOT.DETECTIONS"); // Input sources 138 pmDetections *refDetections = psMetadataLookupPtr(NULL, refSourceRO->analysis, "PSPHOT.DETECTIONS"); // Ref sources 139 140 psFree(view); 141 142 if (!inDetections || !refDetections) { 143 psWarning("Unable to scale kernel, since no sources were provided."); 144 return true; 145 } 146 147 psArray *inSources = inDetections->allSources; 148 psAssert (inSources, "missing inSources?"); 149 150 psArray *refSources = refDetections->allSources; 151 psAssert (refSources, "missing refSources?"); 152 153 float inFWHM = psMetadataLookupF32(NULL, inRO->parent->parent->concepts, "CHIP.SEEING"); // FWHM for input 154 if (!isfinite(inFWHM) || inFWHM == 0.0) { 155 inFWHM = subImagePSF(data, inRO, inSources); 156 } 157 float refFWHM = psMetadataLookupF32(NULL, refRO->parent->parent->concepts, "CHIP.SEEING"); // FWHM for ref 158 if (!isfinite(refFWHM) || refFWHM == 0.0) { 159 refFWHM = subImagePSF(data, refRO, refSources); 160 } 161 psLogMsg("ppSub", PS_LOG_INFO, "Input FWHM: %f\nReference FWHM: %f\n", inFWHM, refFWHM); 162 if (!isfinite(inFWHM) || !isfinite(refFWHM)) { 163 psWarning("Unable to scale kernel, since unable to measure PSFs."); 164 return true; 165 } 166 167 float scaleRef = psMetadataLookupF32(NULL, recipe, "SCALE.REF"); // Reference for scaling 168 float scaleMin = psMetadataLookupF32(NULL, recipe, "SCALE.MIN"); // Minimum for scaling 169 float scaleMax = psMetadataLookupF32(NULL, recipe, "SCALE.MAX"); // Maximum for scaling 170 if (!isfinite(scaleRef) || !isfinite(scaleMin) || !isfinite(scaleMax)) { 171 psError(PPSUB_ERR_ARGUMENTS, false, 172 "Scale parameters (SCALE.REF=%f, SCALE.MIN=%f, SCALE.MAX=%f) not set in recipe.", 173 scaleRef, scaleMin, scaleMax); 174 return false; 175 } 176 177 if (!pmSubtractionParamsScale(kernelSize, stampSize, kernelWidths, inFWHM, refFWHM, 178 scaleRef, scaleMin, scaleMax)) { 179 psError(PPSUB_ERR_DATA, false, "Unable to scale parameters."); 180 return false; 181 } 182 183 return true; 184 } 185 39 186 40 187 bool ppSubMatchPSFs(ppSubData *data) … … 71 218 pmReadout *kernelRO = pmFPAfileThisReadout(config->files, view, "PPSUB.OUTPUT.KERNELS"); // RO with kernel 72 219 73 psFree(view);74 75 220 // Sources in image, used for stamps: these must be loaded from previous analysis stages 76 221 pmReadout *inSourceRO = pmFPAfileThisReadout(config->files, view, "PPSUB.INPUT.SOURCES"); 77 222 pmReadout *refSourceRO = pmFPAfileThisReadout(config->files, view, "PPSUB.REF.SOURCES"); 78 psArray *inSources = inSourceRO ? psMetadataLookupPtr(&mdok, inSourceRO->analysis, "PSPHOT.SOURCES") : 79 NULL; // Source list from input image 80 psArray *refSources = refSourceRO ? psMetadataLookupPtr(&mdok, refSourceRO->analysis, "PSPHOT.SOURCES") : 81 NULL ; // Source list from reference image 82 83 psArray *sources = NULL; // Merged list of sources 84 if (inSources && refSources) { 223 224 pmDetections *inDetections = inSourceRO ? psMetadataLookupPtr(&mdok, inSourceRO->analysis, "PSPHOT.DETECTIONS") : NULL; // Input sources 225 pmDetections *refDetections = refSourceRO ? psMetadataLookupPtr(&mdok, refSourceRO->analysis, "PSPHOT.DETECTIONS") : NULL; // Ref sources 226 227 psFree(view); 228 229 pmDetections *detections = NULL; // Merged detection set 230 if (inDetections && refDetections) { 231 psArray *inSources = inDetections->allSources; 232 psArray *refSources = refDetections->allSources; 233 234 psAssert (inSources, "missing in sources?"); 235 psAssert (refSources, "missing ref sources?"); 236 237 detections = pmDetectionsAlloc(); 85 238 float radius = psMetadataLookupF32(NULL, recipe, "SOURCE.RADIUS"); // Matching radius 86 239 psArray *lists = psArrayAlloc(2); // Source lists 87 240 lists->data[0] = psMemIncrRefCounter(inSources); 88 241 lists->data[1] = psMemIncrRefCounter(refSources); 89 sources = pmSourceMatchMerge(lists, radius);242 detections->allSources = pmSourceMatchMerge(lists, radius); 90 243 psFree(lists); 91 if (!sources) { 92 psError(PS_ERR_UNKNOWN, false, "Unable to merge source lists"); 244 if (!detections->allSources) { 245 psError(PPSUB_ERR_DATA, false, "Unable to merge source lists"); 246 psFree(detections); 93 247 return false; 94 248 } 95 } else if (inSources) {96 sources = psMemIncrRefCounter(inSources);97 } else if (refSources) {98 sources = psMemIncrRefCounter(refSources);99 }100 101 psMetadataAddArray(inConv->analysis, PS_LIST_TAIL, "PSPHOT.SOURCES", PS_META_REPLACE,102 "Merged source list", sources); 103 psMetadataAdd Array(refConv->analysis, PS_LIST_TAIL, "PSPHOT.SOURCES", PS_META_REPLACE,104 "Merged source list", sources);105 psFree( sources); // Drop reference249 } 250 if (!detections && inDetections) { 251 detections = psMemIncrRefCounter(inDetections); 252 } 253 if (!detections && refDetections) { 254 detections = psMemIncrRefCounter(refDetections); 255 } 256 257 psMetadataAddPtr(inConv->analysis, PS_LIST_TAIL, "PSPHOT.DETECTIONS", PS_META_REPLACE | PS_DATA_UNKNOWN, "Merged source list", detections); 258 psMetadataAddPtr(refConv->analysis, PS_LIST_TAIL, "PSPHOT.DETECTIONS", PS_META_REPLACE | PS_DATA_UNKNOWN, "Merged source list", detections); 259 psFree(detections); // Drop reference 106 260 107 261 int footprint = psMetadataLookupS32(NULL, recipe, "STAMP.FOOTPRINT"); // Stamp half-size … … 115 269 pmSubtractionKernelsType type = pmSubtractionKernelsTypeFromString(typeStr); // Type of kernel 116 270 if (type == PM_SUBTRACTION_KERNEL_NONE) { 117 psError(P S_ERR_BAD_PARAMETER_VALUE, true, "Unrecognised kernel type: %s", typeStr);271 psError(PPSUB_ERR_ARGUMENTS, true, "Unrecognised kernel type: %s", typeStr); 118 272 return false; 119 273 } … … 130 284 int iter = psMetadataLookupS32(NULL, recipe, "ITER"); // Rejection iterations 131 285 float rej = psMetadataLookupF32(NULL, recipe, "REJ"); // Rejection threshold 132 float sys = psMetadataLookupF32(NULL, recipe, "SYS"); // Relative systematic error in kernel 286 float kernelErr = psMetadataLookupF32(NULL, recipe, "KERNEL.ERR"); // Relative systematic error in kernel 287 float normFrac = psMetadataLookupF32(NULL, recipe, "NORM.FRAC"); // Fraction of window for normalisn windw 288 float sysErr = psMetadataLookupF32(NULL, recipe, "SYS.ERR"); // Relative systematic error in images 289 float skyErr = psMetadataLookupF32(NULL, recipe, "SKY.ERR"); // Additional error in sky 290 float covarFrac = psMetadataLookupF32(NULL, recipe, "COVAR.FRAC"); // Fraction for covariance calculation 133 291 134 292 float badFrac = psMetadataLookupF32(NULL, recipe, "BADFRAC"); // Maximum bad fraction … … 168 326 break; 169 327 default: 170 psError StackPrint(stderr, "Invalid value for -convolve");328 psError(PPSUB_ERR_ARGUMENTS, false, "Invalid value for -convolve"); 171 329 return false; 172 330 } 173 331 } 174 332 333 if (!subScaleKernel(data, widths, &size, &footprint)) { 334 psError(PPSUB_ERR_DATA, false, "Unable to scale kernel parameters"); 335 return false; 336 } 337 175 338 int threads = psMetadataLookupS32(NULL, config->arguments, "-threads"); // Number of threads 176 339 if (threads > 0) { 177 pmSubtractionThreadsInit(inRO, refRO); 178 } 340 pmSubtractionThreadsInit(); 341 } 342 343 if (inRO->covariance) { 344 psImageCovarianceTruncate(inRO->covariance, COVAR_FRAC); 345 } 346 if (refRO->covariance) { 347 psImageCovarianceTruncate(refRO->covariance, COVAR_FRAC); 348 } 349 350 // Data doesn't exist until it's created in pmSubtraction... 351 inConv->data_exists = inConv->parent->data_exists = inConv->parent->parent->data_exists = false; 352 refConv->data_exists = refConv->parent->data_exists = refConv->parent->parent->data_exists = false; 179 353 180 354 // Match the PSFs … … 182 356 if (kernelRO) { 183 357 success = pmSubtractionMatchPrecalc(inConv, refConv, inRO, refRO, kernelRO->analysis, 184 stride, sys, maskVal, maskBad, maskPoor, poorFrac, badFrac); 358 stride, kernelErr, covarFrac, maskVal, maskBad, maskPoor, 359 poorFrac, badFrac); 185 360 } else { 186 361 success = pmSubtractionMatch(inConv, refConv, inRO, refRO, footprint, stride, regionSize, 187 spacing, threshold, sources, data->stamps, type, size, order, 188 widths, orders, inner, ringsOrder, binning, penalty, optimum, 189 optWidths, optOrder, optThresh, iter, rej, sys, maskVal, 190 maskBad, maskPoor, poorFrac, badFrac, subMode); 191 } 362 spacing, threshold, detections ? detections->allSources : NULL, 363 data->stamps, type, size, order, widths, orders, inner, ringsOrder, 364 binning, penalty, optimum, optWidths, optOrder, optThresh, iter, rej, 365 normFrac, sysErr, skyErr, kernelErr, covarFrac, 366 maskVal, maskBad, maskPoor, poorFrac, badFrac, subMode); 367 } 368 369 # ifdef TESTING 370 // XXX for testing 371 psphotSaveImage (NULL, refRO->image, "refRO.im.fits"); 372 psphotSaveImage (NULL, refRO->variance, "refRO.wt.fits"); 373 psphotSaveImage (NULL, refRO->mask, "refRO.mk.fits"); 374 375 psphotSaveImage (NULL, inRO->image, "inRO.im.fits"); 376 psphotSaveImage (NULL, inRO->variance, "inRO.wt.fits"); 377 psphotSaveImage (NULL, inRO->mask, "inRO.mk.fits"); 378 379 psphotSaveImage (NULL, inConv->image, "inConv.im.fits"); 380 psphotSaveImage (NULL, inConv->variance, "inConv.wt.fits"); 381 psphotSaveImage (NULL, inConv->mask, "inConv.mk.fits"); 382 383 psphotSaveImage (NULL, refConv->image, "refConv.im.fits"); 384 psphotSaveImage (NULL, refConv->variance, "refConv.wt.fits"); 385 psphotSaveImage (NULL, refConv->mask, "refConv.mk.fits"); 386 # endif 192 387 193 388 psFree(optWidths); 194 pmSubtractionThreadsFinalize( inRO, refRO);389 pmSubtractionThreadsFinalize(); 195 390 196 391 if (!success) { … … 207 402 return true; 208 403 } else { 209 psError(P S_ERR_UNKNOWN, false, "Unable to match images.");404 psError(PPSUB_ERR_DATA, false, "Unable to match images."); 210 405 return false; 211 406 } … … 260 455 pmConceptsCopyFPA(refConv->parent->parent->parent, refRO->parent->parent->parent, true, true); 261 456 262 psImageCovarianceTransfer(inConv->variance, inConv->covariance); 263 psImageCovarianceTransfer(refConv->variance, refConv->covariance); 457 if (inConv->covariance) { 458 psImageCovarianceTruncate(inConv->covariance, COVAR_FRAC); 459 } 460 if (refConv->covariance) { 461 psImageCovarianceTruncate(refConv->covariance, COVAR_FRAC); 462 } 463 464 if (inConv->variance) { 465 psImageCovarianceTransfer(inConv->variance, inConv->covariance); 466 } 467 if (refConv->variance) { 468 psImageCovarianceTransfer(refConv->variance, refConv->covariance); 469 } 264 470 265 471 return true; -
branches/simtest_nebulous_branches/ppSub/src/ppSubReadoutInverse.c
r24255 r27840 20 20 invRO->variance = psMemIncrRefCounter(outRO->variance); 21 21 invRO->covariance = psMemIncrRefCounter(outRO->covariance); 22 invRO->analysis = psMetadataCopy(invRO->analysis, outRO->analysis); 22 23 23 24 invRO->data_exists = invRO->parent->data_exists = invRO->parent->parent->data_exists = true; … … 34 35 pmHDU *invHDU = invFPA->hdu; // Inverse HDU 35 36 if (!pmAstromWriteWCS(invHDU->header, outFPA, outChip, WCS_TOLERANCE)) { 36 psError( PS_ERR_UNKNOWN, false, "Unable to write WCS astrometry to PPSUB.INVERSE.");37 psError(psErrorCodeLast(), false, "Unable to write WCS astrometry to PPSUB.INVERSE."); 37 38 return false; 38 39 } 39 40 // Read from newly written astrometry so that it exists in the "inverse" FPA (for sources) 40 41 if (!pmAstromReadWCS(invFPA, invChip, invHDU->header, 1.0)) { 41 psError( PS_ERR_UNKNOWN, false, "Unable to read WCS astrometry.");42 psError(psErrorCodeLast(), false, "Unable to read WCS astrometry."); 42 43 return false; 43 44 } -
branches/simtest_nebulous_branches/ppSub/src/ppSubReadoutJpeg.c
r23740 r27840 33 33 pmReadout *ro1 = pmReadoutAlloc(cell1), *ro2 = pmReadoutAlloc(cell2); // Binned readouts 34 34 if (!pmReadoutRebin(ro1, outRO, maskBad, bin1, bin1)) { 35 psError(P S_ERR_UNKNOWN, false, "Unable to bin output (1st binning)");35 psError(PPSUB_ERR_DATA, false, "Unable to bin output (1st binning)"); 36 36 psFree(ro1); 37 37 psFree(ro2); … … 39 39 } 40 40 if (!pmReadoutRebin(ro2, ro1, 0, bin2, bin2)) { 41 psError(P S_ERR_UNKNOWN, false, "Unable to bin output (2nd binning)");41 psError(PPSUB_ERR_DATA, false, "Unable to bin output (2nd binning)"); 42 42 psFree(ro1); 43 43 psFree(ro2); … … 49 49 return true; 50 50 } 51 52 bool ppSubResidualSampleJpeg(pmConfig *config) 53 { 54 return true; 55 56 pmFPAview *view = ppSubViewReadout(); // View to readout 57 58 // we save sample difference stamps on the convolved image readout->analysis metadata 59 pmReadout *inConv = pmFPAfileThisReadout(config->files, view, "PPSUB.INPUT.CONV"); // Input convolved 60 61 psArray *samples = psArrayAllocEmpty(16); // Array of sample stamp images 62 63 // we may have multiple entries with the same name; pull them off into a separate array: 64 psString regex = NULL; // Regular expression 65 psStringAppend(®ex, "^%s$", "SUBTRACTION.SAMPLE.STAMP.SET"); 66 psMetadataIterator *iter = psMetadataIteratorAlloc(inConv->analysis, PS_LIST_HEAD, regex); // Iterator 67 psFree(regex); 68 69 psMetadataItem *item = NULL;// Item from iteration 70 while ((item = psMetadataGetAndIncrement(iter))) { 71 assert(item->type == PS_DATA_ARRAY); 72 psArray *sampleStamps = item->data.V; 73 samples = psArrayAdd(samples, 16, sampleStamps); 74 } 75 psFree(iter); 76 psAssert (samples, "no sample stamps?"); 77 psAssert (samples->n, "no sample stamps?"); 78 79 // get the kernel sizes 80 psArray *kernels = samples->data[0]; 81 psAssert (kernels, "no valid kernel?"); 82 psAssert (kernels->n, "no valid kernel?"); 83 84 psImage *kernel = kernels->data[0]; 85 psAssert (kernel, "missing valid kernel?"); 86 87 int DX = kernel->numCols; 88 int DY = kernel->numRows; 89 90 // each array contains up to 9 sample stamps. generate an image mosaicking these together in 3x3 blocks. 91 int innerBorder = 1; 92 int outerBorder = 2; 93 int NXblock = sqrt(samples->n); 94 int NYblock = samples->n / NXblock; 95 if (samples->n % NXblock) NYblock ++; 96 97 int NXpix = NXblock * (3 * (DX + innerBorder) + outerBorder); 98 int NYpix = NYblock * (3 * (DY + innerBorder) + outerBorder); 99 100 // output cell 101 pmCell *cell = pmFPAfileThisCell(config->files, view, "PPSUB.OUTPUT.RESID.JPEG"); 102 pmReadout *readout = pmReadoutAlloc(cell); 103 readout->image = psImageAlloc(NXpix, NYpix, PS_TYPE_F32); 104 105 cell->data_exists = true; 106 cell->parent->data_exists = true; 107 108 psImageInit (readout->image, 0.0); 109 110 for (int i = 0; i < samples->n; i++) { 111 112 int xBlock = i % NXblock; 113 int yBlock = i / NYblock; 114 115 psArray *kernels = samples->data[i]; 116 117 for (int j = 0; j < kernels->n; j++) { 118 119 psImage *kernel = kernels->data[j]; 120 121 int xSub = j % 3; 122 int ySub = j / 3; 123 124 int xPix = xBlock * (3 * (DX + innerBorder) + outerBorder) + xSub * (DX + innerBorder); 125 int yPix = yBlock * (3 * (DX + innerBorder) + outerBorder) + ySub * (DY + innerBorder); 126 127 for (int y = 0; y < kernel->numRows; y++) { 128 for (int x = 0; x < kernel->numCols; x++) { 129 readout->image->data.F32[y + yPix][x + xPix] = kernel->data.F32[y][x]; 130 } 131 } 132 } 133 } 134 135 { 136 psFits *fits = psFitsOpen ("resid.stamps.fits", "w"); 137 psFitsWriteImage (fits, NULL, readout->image, 0, NULL); 138 psFitsClose (fits); 139 } 140 141 return true; 142 } -
branches/simtest_nebulous_branches/ppSub/src/ppSubReadoutPhotometry.c
r24932 r27840 24 24 bool ppSubReadoutPhotometry(const char *name, ppSubData *data) 25 25 { 26 bool mdok = false; 27 26 28 psAssert(data, "Require processing data"); 27 29 pmConfig *config = data->config; // Configuration … … 42 44 } 43 45 44 // The PSF (measured in ppSubMakePSF) is stored on the chip->analysis of PSPHOT.INPUT 45 // In order to use an incoming PSF, it must be stored on the chip->analysis of PSPHOT.PSF.LOAD 46 // select the view of interest 46 47 pmFPAview *view = ppSubViewReadout(); // View to readout 47 pmChip *psfInputChip = pmFPAfileThisChip(config->files, view, "PSPHOT.INPUT"); // Chip with PSF48 psAssert (psfInputChip, "should have been generated for ppSubMakePSF");49 pmChip *psfLoadChip = pmFPAfileThisChip(config->files, view, "PSPHOT.PSF.LOAD"); // Chip to have PSF50 psAssert (psfLoadChip, "PSPHOT.PSF.LOAD should have been defined in ppSubCamera");51 pmPSF *psf = psMetadataLookupPtr(NULL, psfInputChip->analysis, "PSPHOT.PSF"); // PSF for photometry52 if (!psf) {53 psErrorStackPrint(stderr, "No PSF available");54 psWarning("No PSF available --- suspect bad data quality.");55 ppSubDataQuality(data, psErrorCodeLast(), PPSUB_FILES_PHOT_SUB | PPSUB_FILES_PHOT_INV);56 return true;57 }58 psMetadataAddPtr(psfLoadChip->analysis, PS_LIST_TAIL, "PSPHOT.PSF", PS_DATA_UNKNOWN | PS_META_REPLACE,59 "PSF from ppSubMakePSF", psf);60 61 bool mdok = false;62 48 63 49 // psphotReadoutMinimal performs the photometry analysis on PSPHOT.INPUT; we need to move 64 // around the pointers so PSPHOT.INPUT corresponds to the output image; previously, it was 65 // equivalent to the minuend image. 66 pmReadout *inRO = pmFPAfileThisReadout(config->files, view, name); // Readout with image and sources 67 if (psMetadataLookup(inRO->analysis, "PSPHOT.SOURCES")) { 68 psMetadataRemoveKey(inRO->analysis, "PSPHOT.SOURCES"); 69 } 70 50 // around the pointers so PSPHOT.INPUT corresponds to the output image of interest (on one 51 // pass this is the subtraction image, in another it is negative of the subtraction 71 52 pmFPAfile *photFile = psMetadataLookupPtr(&mdok, config->files, "PSPHOT.INPUT"); // Photometry file 72 53 pmFPAfile *inFile = psMetadataLookupPtr(&mdok, config->files, name); // Input file 73 54 if (!pmFPACopy(photFile->fpa, inFile->fpa)) { 74 psError(P S_ERR_UNKNOWN, false, "Unable to copy FPA for photometry");55 psError(PPSUB_ERR_CONFIG, false, "Unable to copy FPA for photometry"); 75 56 psFree(view); 76 57 return false; 77 58 } 59 60 // drop references to PSPHOT.DETECTIONS on both of these (why is this needed for both??) 78 61 pmReadout *photRO = pmFPAviewThisReadout(view, photFile->fpa); // Readout to photometer 79 if (psMetadataLookup(photRO->analysis, "PSPHOT.SOURCES")) { 80 psMetadataRemoveKey(photRO->analysis, "PSPHOT.SOURCES"); 62 if (psMetadataLookup(photRO->analysis, "PSPHOT.DETECTIONS")) { 63 psMetadataRemoveKey(photRO->analysis, "PSPHOT.DETECTIONS"); 64 } 65 pmReadout *inRO = pmFPAfileThisReadout(config->files, view, name); // Readout with image and sources 66 if (psMetadataLookup(inRO->analysis, "PSPHOT.DETECTIONS")) { 67 psMetadataRemoveKey(inRO->analysis, "PSPHOT.DETECTIONS"); 81 68 } 82 69 83 psMetadataAddPtr(photRO->parent->parent->analysis, PS_LIST_TAIL, "PSPHOT.PSF", 84 PS_META_REPLACE | PS_DATA_UNKNOWN, "Point-spread function", data->psf); 70 // grab the PSF information from the pmFPAfile PSPHOT.PSF.LOAD 71 pmFPAfile *psfFile = psMetadataLookupPtr(&mdok, config->files, "PSPHOT.PSF.LOAD"); // PSF file 72 ppSubCopyPSF (photFile, psfFile, view); 85 73 86 psFree(photRO->analysis); 87 photRO->analysis = psMetadataAlloc(); 74 // psphotSaveImage (photFile->fpa->hdu->header, photRO->image, "findsrc.im.fits"); 75 // psphotSaveImage (photFile->fpa->hdu->header, photRO->variance, "findsrc.wt.fits"); 76 // psphotSaveImage (photFile->fpa->hdu->header, photRO->mask, "findsrc.mk.fits"); 77 78 // erase the overlays from a previous psphot-related step 79 if (pmVisualIsVisual()) { 80 // psphotVisualEraseOverlays (1, "all"); 81 } 88 82 89 83 if (!psphotReadoutMinimal(config, view)) { … … 96 90 97 91 // If no sources were found, there's no error, but we want to trigger 'bad quality' 98 p sArray *sources = psMetadataLookupPtr(NULL, photRO->analysis, "PSPHOT.SOURCES"); // Sources99 if (! sources) {92 pmDetections *detections = psMetadataLookupPtr(NULL, photRO->analysis, "PSPHOT.DETECTIONS"); // Sources 93 if (!detections) { 100 94 ppSubDataQuality(data, PSPHOT_ERR_DATA, PPSUB_FILES_PHOT_SUB | PPSUB_FILES_PHOT_INV); 101 95 } 96 psArray *sources = detections->allSources; 97 psAssert (sources, "missing sources?"); 102 98 103 99 if (data->stats) { … … 114 110 115 111 if (!data->quality) { 116 if (!psMetadataCopySingle(inRO->analysis, photRO->analysis, "PSPHOT. SOURCES")) {117 psError(P S_ERR_UNEXPECTED_NULL, false, "Unable to copy PSPHOT.SOURCES");112 if (!psMetadataCopySingle(inRO->analysis, photRO->analysis, "PSPHOT.DETECTIONS")) { 113 psError(PPSUB_ERR_PROG, false, "Unable to copy PSPHOT.DETECTIONS"); 118 114 return false; 119 115 } 120 116 if (!psMetadataCopySingle(inRO->analysis, photRO->analysis, "PSPHOT.HEADER")) { 121 psError(P S_ERR_UNEXPECTED_NULL, false, "Unable to copy PSPHOT.HEADER");117 psError(PPSUB_ERR_PROG, false, "Unable to copy PSPHOT.HEADER"); 122 118 return false; 119 } 120 if (!psMetadataCopySingle(inRO->analysis, photRO->analysis, PM_DETEFF_ANALYSIS)) { 121 psError(PPSUB_ERR_PROG, false, "Unable to copy Detection Efficiency"); 122 return false; 123 } 124 125 // Ensure photometry information is put in the header 126 pmHDU *hdu = pmHDUFromReadout(inRO); // HDU for readout 127 if (hdu) { 128 psMetadata *photHeader = psMetadataLookupMetadata(NULL, inRO->analysis, "PSPHOT.HEADER"); // Header 129 hdu->header = psMetadataCopy(hdu->header, photHeader); 123 130 } 124 131 } … … 130 137 } 131 138 132 133 134 135 136 139 #ifdef TESTING 137 140 // Record data about sources: not everything gets into the output CMF files 138 141 { 139 142 pmReadout *photRO = pmFPAviewThisReadout(view, photFile->fpa); // Readout with the sources 140 psArray *sources = psMetadataLookupPtr(NULL, photRO->analysis, "PSPHOT.SOURCES"); // Sources 143 pmDetections *detections = psMetadataLookupPtr(NULL, photRO->analysis, "PSPHOT.DETECTIONS"); // Sources 144 psArray *sources = detections->allSources; 141 145 FILE *sourceFile = fopen("sources.dat", "w"); // File for sources 142 146 fprintf(sourceFile, -
branches/simtest_nebulous_branches/ppSub/src/ppSubReadoutStats.c
r23939 r27840 23 23 pmFPAfile *output = psMetadataLookupPtr(NULL, config->files, "PPSUB.OUTPUT"); // Output file 24 24 if (!output) { 25 psError(P S_ERR_UNEXPECTED_NULL, true, "Unable to find file PPSUB.OUTPUT.\n");25 psError(PPSUB_ERR_PROG, true, "Unable to find file PPSUB.OUTPUT.\n"); 26 26 return false; 27 27 } -
branches/simtest_nebulous_branches/ppSub/src/ppSubReadoutSubtract.c
r24862 r27840 71 71 pmFPA *outFPA = outFile->fpa; // Output FPA 72 72 if (!pmConceptsCopyFPA(outFPA, inFPA, true, true)) { 73 psError(P S_ERR_UNKNOWN, false, "Unable to copy concepts from input to output.");73 psError(PPSUB_ERR_CONFIG, false, "Unable to copy concepts from input to output."); 74 74 psFree(outRO); 75 75 psFree(view); … … 84 84 psFree(view); 85 85 if (!outHDU || !inHDU) { 86 psError(P S_ERR_UNKNOWN, false, "Unable to find HDU at FPA level to copy astrometry.");86 psError(PPSUB_ERR_PROG, true, "Unable to find HDU at FPA level to copy astrometry."); 87 87 return false; 88 88 } 89 89 if (!pmAstromReadWCS(outFPA, outChip, inHDU->header, 1.0)) { 90 psError( PS_ERR_UNKNOWN, false, "Unable to read WCS astrometry from input FPA.");90 psError(psErrorCodeLast(), false, "Unable to read WCS astrometry from input FPA."); 91 91 return false; 92 92 } 93 93 if (!pmAstromWriteWCS(outHDU->header, outFPA, outChip, WCS_TOLERANCE)) { 94 psError( PS_ERR_UNKNOWN, false, "Unable to write WCS astrometry to output FPA.");94 psError(psErrorCodeLast(), false, "Unable to write WCS astrometry to output FPA."); 95 95 return false; 96 96 } -
branches/simtest_nebulous_branches/ppSub/src/ppSubSetMasks.c
r23740 r27840 28 28 psImageMaskType maskValue, markValue; // Mask values 29 29 if (!pmConfigMaskSetBits(&maskValue, &markValue, config)) { 30 psError(P S_ERR_UNKNOWN, false, "Unable to determine mask value.");30 psError(PPSUB_ERR_CONFIG, false, "Unable to determine mask value."); 31 31 return false; 32 32 } 33 33 34 34 // Set the mask bits needed by psphot (in psphot recipe) 35 psphotSetMaskRecipe (config, maskValue, markValue);35 psphotSetMaskRecipe(config, maskValue, markValue); 36 36 37 37 // Look up recipe values … … 79 79 // Mask the NAN values 80 80 if (!pmReadoutMaskNonfinite(inRO, satValue)) { 81 psError(P S_ERR_UNKNOWN, false, "Unable to mask non-finite pixels in input.");81 psError(PPSUB_ERR_DATA, false, "Unable to mask non-finite pixels in input."); 82 82 return false; 83 83 } 84 84 if (!pmReadoutMaskNonfinite(refRO, satValue)) { 85 psError(P S_ERR_UNKNOWN, false, "Unable to mask non-finite pixels in reference.");85 psError(PPSUB_ERR_DATA, false, "Unable to mask non-finite pixels in reference."); 86 86 return false; 87 87 } … … 94 94 psImageInterpolateMode interpMode = psImageInterpolateModeFromString(interpModeStr); // Interp 95 95 if (interpMode == PS_INTERPOLATE_NONE) { 96 psError(P S_ERR_BAD_PARAMETER_VALUE, false, "Unknown interpolation mode: %s", interpModeStr);96 psError(PPSUB_ERR_CONFIG, false, "Unknown interpolation mode: %s", interpModeStr); 97 97 return false; 98 98 } … … 104 104 // Interpolate over bad pixels, so the bad pixels don't explode 105 105 if (!pmReadoutInterpolateBadPixels(inRO, maskVal, interpMode, poorFrac, maskPoor, maskBad)) { 106 psError(P S_ERR_UNKNOWN, false, "Unable to interpolate bad pixels for input image.");106 psError(PPSUB_ERR_DATA, false, "Unable to interpolate bad pixels for input image."); 107 107 return false; 108 108 } 109 109 if (!pmReadoutInterpolateBadPixels(refRO, maskVal, interpMode, poorFrac, maskPoor, maskBad)) { 110 psError(P S_ERR_UNKNOWN, false, "Unable to interpolate bad pixels for reference image.");110 psError(PPSUB_ERR_DATA, false, "Unable to interpolate bad pixels for reference image."); 111 111 return false; 112 112 } -
branches/simtest_nebulous_branches/ppSub/src/ppSubThreshold.c
r24862 r27840 27 27 psImageMaskType maskIgnore, // Ignore pixels with this mask 28 28 psImageMaskType maskThresh, // Give pixels this mask if below threshold 29 psRegion *region, // Region of interest 29 30 const char *description // Description of image 30 31 ) … … 37 38 psImage *image = ro->image; // Image 38 39 psImage *mask = ro->mask; // Mask 39 int numCols = ro->image->numCols, numRows = ro->image->numRows; // Size of image 40 41 psImage *subImage = psImageSubset(image, *region); // Image with region of interest 42 psImage *subMask = psImageSubset(mask, *region); // Maks with region of interest 40 43 41 44 psStats *stats = psStatsAlloc(PS_STAT_ROBUST_MEDIAN | PS_STAT_ROBUST_STDEV); // Statistics 42 45 psRandom *rng = psRandomAlloc(PS_RANDOM_TAUS); // Random number generator 43 if (!psImageBackground(stats, NULL, image, mask, maskIgnore, rng)) {44 psError(P S_ERR_UNKNOWN, false, "Unable to determine threshold.");46 if (!psImageBackground(stats, NULL, subImage, subMask, maskIgnore, rng)) { 47 psError(PPSUB_ERR_DATA, false, "Unable to determine threshold."); 45 48 psFree(rng); 46 49 psFree(stats); … … 49 52 psFree(rng); 50 53 54 psFree(subImage); 55 psFree(subMask); 56 51 57 float threshold = stats->robustMedian - thresh * stats->robustStdev; // Threshold below which to clip 52 58 psFree(stats); 53 59 psLogMsg("ppSub", PS_LOG_INFO, "Masking pixels below %f in %s", threshold, description); 54 60 55 for (int y = 0; y < numRows; y++) {56 for (int x = 0; x < numCols; x++) {61 for (int y = region->y0; y < region->y1; y++) { 62 for (int x = region->x0; x < region->x1; x++) { 57 63 if (mask->data.PS_TYPE_IMAGE_MASK_DATA[y][x] & maskIgnore) { 58 64 continue; … … 91 97 pmReadout *in = pmFPAfileThisReadout(config->files, view, "PPSUB.INPUT.CONV"); // Input image 92 98 if (!in) { 93 psError(PS_ERR_UNEXPECTED_NULL, false, "Unable to find readout."); 94 return false; 95 } 96 if (!lowThreshold(in, thresh, maskVal, maskThresh, "input convolved image")) { 97 psError(PS_ERR_UNKNOWN, false, "Unable to threshold input image."); 99 psError(PPSUB_ERR_UNKNOWN, false, "Unable to find readout."); 98 100 return false; 99 101 } … … 101 103 pmReadout *ref = pmFPAfileThisReadout(config->files, view, "PPSUB.REF.CONV"); // Reference image 102 104 if (!ref) { 103 psError(P S_ERR_UNEXPECTED_NULL, false, "Unable to find readout.");105 psError(PPSUB_ERR_UNKNOWN, false, "Unable to find readout."); 104 106 return false; 105 107 } 106 if (!lowThreshold(ref, thresh, maskVal, maskThresh, "reference convolved image")) { 107 psError(PS_ERR_UNKNOWN, false, "Unable to threshold input image."); 108 return false; 108 109 psMetadataIterator *regIter = psMetadataIteratorAlloc(in->analysis, PS_LIST_HEAD, 110 "^" PM_SUBTRACTION_ANALYSIS_REGION "$"); 111 psMetadataItem *regItem; // Item with region 112 while ((regItem = psMetadataGetAndIncrement(regIter))) { 113 psAssert(regItem->type == PS_DATA_REGION && regItem->data.V, "Expect region type"); 114 psRegion *region = regItem->data.V; // Region of interest 115 if (!lowThreshold(in, thresh, maskVal, maskThresh, region, "input convolved image")) { 116 psError(psErrorCodeLast(), false, "Unable to threshold input image."); 117 return false; 118 } 119 if (!lowThreshold(ref, thresh, maskVal, maskThresh, region, "reference convolved image")) { 120 psError(psErrorCodeLast(), false, "Unable to threshold input image."); 121 return false; 122 } 109 123 } 124 psFree(regIter); 110 125 111 126 psFree(view); -
branches/simtest_nebulous_branches/ppSub/src/ppSubVarianceRescale.c
r24672 r27840 28 28 bool mdok; // Status of metadata lookups 29 29 30 psMetadata * ppSubRecipe = psMetadataLookupPtr(NULL, config->recipes, PPSUB_RECIPE); // Recipe for ppSub31 psAssert( ppSubRecipe, "Need PPSUB recipe");30 psMetadata *recipe = psMetadataLookupPtr(NULL, config->recipes, PPSUB_RECIPE); // Recipe for ppSub 31 psAssert(recipe, "Need PPSUB recipe"); 32 32 33 if (!psMetadataLookupBool(&mdok, ppSubRecipe, "VARIANCE.RESCALE")) return true; 33 if (!psMetadataLookupBool(&mdok, recipe, "RENORM")) return true; 34 35 int num = psMetadataLookupS32(&mdok, recipe, "RENORM.NUM"); 36 if (!mdok) { 37 psError(PPSUB_ERR_ARGUMENTS, true, "RENORM.NUM is not set in the recipe"); 38 return false; 39 } 40 float minValid = psMetadataLookupF32(&mdok, recipe, "RENORM.MIN"); 41 if (!mdok) { 42 psError(PPSUB_ERR_ARGUMENTS, true, "RENORM.MIN is not set in the recipe"); 43 return false; 44 } 45 float maxValid = psMetadataLookupF32(&mdok, recipe, "RENORM.MAX"); 46 if (!mdok) { 47 psError(PPSUB_ERR_ARGUMENTS, true, "RENORM.MAX is not set in the recipe"); 48 return false; 49 } 34 50 35 51 psImageMaskType maskBad = pmConfigMaskGet("BLANK", config); // Bits to mask 36 52 37 53 pmFPAview *view = ppSubViewReadout(); // View to readout 38 pmReadout * outRO= pmFPAfileThisReadout(config->files, view, "PPSUB.OUTPUT"); // Output image54 pmReadout *readout = pmFPAfileThisReadout(config->files, view, "PPSUB.OUTPUT"); // Output image 39 55 40 psImage *image = outRO->image; // Image of interest 41 psImage *variance = outRO->variance; // Variance image 42 psImage *mask = outRO->mask; // Mask of interest 43 44 psRandom *rng = psRandomAlloc(PS_RANDOM_TAUS); 45 46 psLogMsg("psLib.psImageBackground", PS_LOG_DETAIL, "Generating the signal-to-noise image"); 47 48 // generate an image representing the signal/noise: 49 psImage *SN = psImageCopy (NULL, outRO->image, PS_TYPE_F32); 50 51 int nx = image->numCols; // Size of image 52 int ny = image->numRows; // Size of image 53 54 for (int y = 0; y < ny; y++) { 55 for (int x = 0; x < nx; x++) { 56 if (mask && mask->data.PS_TYPE_IMAGE_MASK_DATA[y][x] & maskBad) { 57 SN->data.F32[y][x] = 0.0; 58 continue; 59 } 60 if (!isfinite(image->data.F32[y][x])) { 61 SN->data.F32[y][x] = 0.0; 62 continue; 63 } 64 if (!isfinite(variance->data.F32[y][x]) || (variance->data.F32[y][x] < 0.0)) { 65 SN->data.F32[y][x] = 0.0; 66 continue; 67 } 68 SN->data.F32[y][x] = image->data.F32[y][x] / sqrt(variance->data.F32[y][x]); 69 } 56 if (!readout->variance) { 57 // Nothing to renormalise 58 psWarning("Renormalisation of the variance requested, but no variance provided."); 59 return true; 70 60 } 71 61 72 // these should not be chosen by the user: only a ROBUST version makes sense 73 psStats *stats = psStatsAlloc (PS_STAT_ROBUST_MEDIAN | PS_STAT_ROBUST_STDEV); 74 75 int Nsubset = psMetadataLookupS32(&mdok, ppSubRecipe, "VARIANCE.RESCALE.NSAMPLE"); 76 psAssert (mdok, "missing VARIANCE.RESCALE.NSAMPLE in ppSub recipe"); 77 78 const int Npixels = nx*ny; // Total number of pixels 79 Nsubset = PS_MIN(Nsubset, Npixels); // Number of pixels in subset 80 psLogMsg("psLib.psImageBackground", PS_LOG_DETAIL, "Searching for %d pixels in S/N image", Nsubset); 81 82 psVector *values = psVectorAllocEmpty(Nsubset, PS_TYPE_F32); // Vector containing subsample 83 84 // Minimum and maximum values 85 float min = +PS_MAX_F32; 86 float max = -PS_MAX_F32; 87 88 // select a subset of the image pixels to measure the stats 89 long n = 0; // Number of actual pixels in subset 90 if (Nsubset >= Npixels) { 91 // if we have an image smaller than Nsubset, just loop over the image pixels 92 for (int iy = 0; iy < ny; iy++) { 93 for (int ix = 0; ix < nx; ix++) { 94 if (!isfinite(image->data.F32[iy][ix]) || (mask && mask->data.PS_TYPE_IMAGE_MASK_DATA[iy][ix] & maskBad)) { 95 continue; 96 } 97 98 float value = SN->data.F32[iy][ix]; 99 min = PS_MIN(value, min); 100 max = PS_MAX(value, max); 101 values->data.F32[n] = value; 102 n++; 103 } 104 } 105 } else { 106 for (long i = 0; i < Nsubset; i++) { 107 double frnd = psRandomUniform(rng); 108 int pixel = Npixels * frnd; 109 int ix = pixel % nx; 110 int iy = pixel / nx; 111 112 if (!isfinite(image->data.F32[iy][ix]) || (mask && mask->data.PS_TYPE_IMAGE_MASK_DATA[iy][ix] & maskBad)) { 113 continue; 114 } 115 116 float value = SN->data.F32[iy][ix]; 117 min = PS_MIN(value, min); 118 max = PS_MAX(value, max); 119 values->data.F32[n] = value; 120 n++; 121 } 122 } 123 if (n < 0.01*Nsubset) { 124 psLogMsg("psLib.psImageBackground", PS_LOG_DETAIL, "Unable to measure image background: too few data points (%ld)", n); 125 psFree(values); 126 return false; 127 } 128 values->n = n; 129 psFree (SN); 130 131 psLogMsg("psLib.psImageBackground", PS_LOG_DETAIL, "Using for %ld pixels in S/N image", values->n); 132 133 if (!psVectorStats (stats, values, NULL, NULL, 0)) { 134 if (psTraceGetLevel("psLib.imageops") >= 5) { 135 FILE *f = fopen ("vector.dat", "w"); 136 int fd = fileno(f); 137 p_psVectorPrint (fd, values, "values"); 138 fclose (f); 139 } 140 psError(PS_ERR_UNKNOWN, false, "Unable to measure statistics for image background " 141 "(%dx%d, (row0,col0) = (%d,%d)", 142 image->numRows, image->numCols, image->row0, image->col0); 143 psFree(values); 144 return false; 145 } 146 if (psTraceGetLevel("psLib.imageops") >= 6) { 147 FILE *f = fopen ("vector.dat", "w"); 148 int fd = fileno(f); 149 p_psVectorPrint (fd, values, "values"); 150 fclose (f); 151 } 152 psFree (values); 153 psLogMsg ("ppSub", PS_LOG_INFO, "background stdev %f\n", stats->robustStdev); 154 155 float minValid = psMetadataLookupF32(&mdok, ppSubRecipe, "VARIANCE.RESCALE.MIN.VALID"); 156 psAssert (mdok, "missing VARIANCE.RESCALE.MIN.VALID in ppSub recipe"); 157 158 float maxValid = psMetadataLookupF32(&mdok, ppSubRecipe, "VARIANCE.RESCALE.MAX.VALID"); 159 psAssert (mdok, "missing VARIANCE.RESCALE.MAX.VALID in ppSub recipe"); 160 161 psLogMsg("psLib.psImageBackground", PS_LOG_DETAIL, "Stdev of S/N image: %f (mean: %f)", stats->robustStdev, stats->robustMedian); 162 163 // valid range of correction; 0.66 to 1.5 (skip if in range 0.98 to 1.02) 164 if ((stats->robustStdev < minValid) || (stats->robustStdev > maxValid)) { 165 psWarning ("background stdev (%f) is out of allowed range; not correcting\n", stats->robustStdev); 166 // XXX set quality to poor 167 psFree (stats); 168 return true; 169 } 170 171 // valid range of correction; 0.66 to 1.5 (skip if in range 0.98 to 1.02) 172 // if ((stats->robustStdev > 0.98) && (stats->robustStdev > 1.02)) { 173 // psLogMsg ("ppSub", PS_LOG_INFO, "background stdev (%f) is close to 1.0; do not modify variance\n", stats->robustStdev); 174 // // XXX set quality to poor 175 // psFree (stats); 176 // return true; 177 // } 178 179 float varianceFactor = PS_SQR(stats->robustStdev); 180 psLogMsg ("ppSub", PS_LOG_INFO, "background stdev is not 1.0: multiplying variance by %f\n", varianceFactor); 181 for (int y = 0; y < ny; y++) { 182 for (int x = 0; x < nx; x++) { 183 if (mask && mask->data.PS_TYPE_IMAGE_MASK_DATA[y][x] & maskBad) { 184 continue; 185 } 186 if (!isfinite(image->data.F32[y][x])) { 187 continue; 188 } 189 if (!isfinite(variance->data.F32[y][x]) || (variance->data.F32[y][x] < 0.0)) { 190 continue; 191 } 192 variance->data.F32[y][x] *= varianceFactor; 193 } 194 } 195 196 pmFPA *outFPA = outRO->parent->parent->parent; 197 pmHDU *outHDU = outFPA->hdu; // Output HDU 198 199 char history[80]; 200 snprintf (history, 80, "Rescaled variance by %6.4f (stdev by %6.4f)", varianceFactor, stats->robustStdev); 201 psMetadataAddStr(outHDU->header, PS_LIST_TAIL, "HISTORY", PS_META_DUPLICATE_OK, NULL, history); 202 203 psFree (stats); 204 return true; 62 return pmReadoutVarianceRenormalise(readout, maskBad, num, minValid, maxValid); 205 63 }
Note:
See TracChangeset
for help on using the changeset viewer.
