Changeset 24803
- Timestamp:
- Jul 15, 2009, 2:33:17 PM (17 years ago)
- File:
-
- 1 edited
-
trunk/psModules/src/detrend/pmDark.c (modified) (15 diffs)
Legend:
- Unmodified
- Added
- Removed
-
trunk/psModules/src/detrend/pmDark.c
r21183 r24803 2 2 #include <pslib.h> 3 3 #include <string.h> 4 #include <strings.h> 4 5 5 6 #include "psPolynomialMD.h" … … 12 13 #include "pmReadoutStack.h" 13 14 #include "pmDetrendThreads.h" 15 #include "pmErrorCodes.h" 14 16 15 17 #include "pmDark.h" … … 17 19 #define PM_DARK_FITS_EXTNAME "PS_DARK" // FITS extension name for ordinates table 18 20 #define PM_DARK_FITS_NAME "NAME" // Column name for concept name in ordinates table 21 #define PM_DARK_FITS_RULE "RULE" // Column name for concept rule in ordinates table 19 22 #define PM_DARK_FITS_ORDER "ORDER" // Column name for polynomial order in ordinates table 20 23 #define PM_DARK_FITS_SCALE "SCALE" // Column name for scaling option in ordinates table … … 22 25 #define PM_DARK_FITS_MAX "MAX" // Column name for maximum value in ordinates table 23 26 24 25 26 // Look up the value of an ordinate in a readout 27 static bool ordinateLookup(float *value, // Value of ordinate, to return 28 bool *inRange, // is value within min : max range? 29 const char *name, // Name of ordinate (concept name) 30 bool scale, // Scale the value? 31 float min, float max, // Minimum and maximum values for scaling 32 const pmReadout *ro // Readout of interest 33 ) 34 { 35 assert(value); 36 assert(name); 37 assert(ro); 38 39 *inRange = true; 40 41 pmCell *cell = ro->parent; // Parent cell 42 if (!cell) { 43 return false; 44 } 27 static bool ordinateParseConcept(double *value, const pmReadout *readout, const char *name) { 28 29 *value = NAN; 30 31 pmCell *cell = readout->parent; // Parent cell 32 psAssert(cell, "readout is missing cell \n"); 33 45 34 psMetadataItem *item = psMetadataLookup(cell->concepts, name); 46 35 if (!item) { 47 36 pmChip *chip = cell->parent; // Parent chip 48 if (!chip) { 49 return false; 50 } 37 psAssert(chip, "cell is missing chip \n"); 38 51 39 item = psMetadataLookup(chip->concepts, name); 52 40 if (!item) { 53 41 pmFPA *fpa = chip->parent; // Parent FPA 54 if (!fpa) { 55 return false; 56 } 42 psAssert(fpa, "chip is missing fpa \n"); 43 57 44 item = psMetadataLookup(fpa->concepts, name); 58 45 if (!item) { 59 ps Warning("Unable to find concept %s in readout", name);46 psError(PM_ERR_CONFIG, true, "Unable to find concept %s in readout", name); 60 47 return false; 61 48 } … … 63 50 } 64 51 65 *value = psMetadataItemParseF 32(item); // Value of interest52 *value = psMetadataItemParseF64(item); // Value of interest 66 53 if (!isfinite(*value)) { 67 54 psWarning("Non-finite value (%f) of concept %s in readout", *value, name); 68 return false; 69 } 55 } 56 return true; 57 } 58 59 static bool ordinateParseRule(double *value, const pmReadout *readout, const char *name, const char *rule) { 60 61 psAssert(name, "ordinate name is not defined"); 62 psAssert(rule, "ordinate rule is not defined"); 63 64 *value = NAN; 65 66 psArray *words = psStringSplitArray(rule, " ", false); 67 68 // we should have a rule of the form (concept) OP (concept) OP (concept) ... 69 // for now, the only allowed OP is * (eventually, we can steal code from opihi for a better 70 // RPN parser). 71 72 if (words->n % 2 == 0) { 73 psError(PM_ERR_CONFIG, true, "syntax error in DARK.ORDINATE %s rule %s\n", name, rule); 74 psFree(words); 75 return false; 76 } 77 78 for (int i = 1; i < words->n; i+=2) { 79 if (strcmp((char *)words->data[i], "*")) { 80 psError(PM_ERR_CONFIG, true, "syntax error in DARK.ORDINATE %s rule %s\n", name, rule); 81 psFree(words); 82 return false; 83 } 84 } 85 86 if (!ordinateParseConcept(value, readout, words->data[0])) { 87 psError(PM_ERR_CONFIG, false, "syntax error in DARK.ORDINATE %s rule %s\n", name, rule); 88 psFree(words); 89 return false; 90 } 91 92 double value2 = 0.0; 93 for (int i = 2; i < words->n; i+=2) { 94 if (!ordinateParseConcept(&value2, readout, words->data[i])) { 95 psError(PM_ERR_CONFIG, false, "syntax error in DARK.ORDINATE %s rule %s\n", name, rule); 96 psFree(words); 97 return false; 98 } 99 *value *= value2; 100 } 101 psFree(words); 102 return true; 103 } 104 105 // Look up the value of an ordinate in a readout 106 static bool ordinateLookup(double *value, // Value of ordinate, to return 107 bool *inRange, // is value within min : max range? 108 const char *name, // Name of ordinate (concept or abstract name) 109 const char *rule, // Rule for generating the value (if NULL use name as concept) 110 bool scale, // Scale the value? 111 float min, float max, // Minimum and maximum values for scaling 112 const pmReadout *readout // Readout of interest 113 ) 114 { 115 assert(value); 116 assert(name); 117 assert(readout); 118 119 *inRange = true; 120 121 if (rule) { 122 if (!ordinateParseRule(value, readout, name, rule)) { 123 psError(PM_ERR_CONFIG, false, "trouble parsing rule %s for DARK.ORDINATE %s", rule, name); 124 return false; 125 } 126 } else { 127 if (!ordinateParseConcept(value, readout, name)) { 128 psError(PM_ERR_CONFIG, false, "trouble parsing rule %s for DARK.ORDINATE %s", rule, name); 129 return false; 130 } 131 } 132 70 133 if (scale) { 71 134 if (*value < min || *value > max) { … … 82 145 { 83 146 psFree(ord->name); 147 psFree(ord->rule); 84 148 return; 85 149 } … … 91 155 92 156 ord->name = psStringCopy(name); 157 ord->rule = NULL; 93 158 ord->order = order; 94 159 ord->scale = false; … … 118 183 119 184 pmReadout *readout = inputs->data[i]; // Readout of interest 120 float normValue; // Normalisation value 121 if (!ordinateLookup(&normValue, &inRange, normConcept, false, NAN, NAN, readout)) { 122 psWarning("Unable to find value of %s for readout %d", normConcept, i); 185 double normValue; // Normalisation value 186 if (!ordinateLookup(&normValue, &inRange, normConcept, NULL, false, NAN, NAN, readout)) { 187 psError(PM_ERR_CONFIG, false, "problem finding concept %s for DARK.NORM", normConcept); 188 return false; 189 } 190 if (!isfinite(normValue)) { 191 psWarning("Unable to find acceptable value of %s for readout %d", normConcept, i); 123 192 roMask->data.PS_TYPE_VECTOR_MASK_DATA[i] = 0xff; 124 193 norm->data.F32[i] = NAN; … … 140 209 pmDarkOrdinate *ord = ordinates->data[i]; // Ordinate information 141 210 if (ord->order <= 0) { 142 psError(PS_ERR_UNKNOWN, true, "Bad order for concept%s (%d) --- ignored", ord->name, ord->order);211 psError(PS_ERR_UNKNOWN, true, "Bad order for DARK.ORDINATE %s (%d) --- ignored", ord->name, ord->order); 143 212 psFree(values); 144 213 psFree(roMask); … … 157 226 158 227 pmReadout *readout = inputs->data[j]; // Readout of interest 159 float value = NAN; // Value of ordinate 160 if (!ordinateLookup(&value, &inRange, ord->name, ord->scale, ord->min, ord->max, readout)) { 228 double value = NAN; // Value of ordinate 229 if (!ordinateLookup(&value, &inRange, ord->name, ord->rule, ord->scale, ord->min, ord->max, readout)) { 230 psError(PM_ERR_CONFIG, false, "problem finding rule for DARK.ORDINATE %s", ord->name); 231 return false; 232 } 233 if (!isfinite(value)) { 234 psWarning("Unable to find acceptable value of DARK.ORDINATE %s for readout %d", ord->name, i); 161 235 roMask->data.PS_TYPE_VECTOR_MASK_DATA[j] = 0xff; 162 236 val->data.F32[i] = NAN; … … 165 239 } 166 240 if (!inRange) { 241 psWarning("Value of DARK.ORDINATE %s for readout %d is out of range", ord->name, i); 167 242 roMask->data.PS_TYPE_VECTOR_MASK_DATA[j] = 0xff; 168 243 val->data.F32[i] = NAN; … … 447 522 for (int i = 0; i < numOrdinates; i++) { 448 523 pmDarkOrdinate *ord = ordinates->data[i]; // Ordinate of interest 449 floatvalue = NAN; // Value for ordinate450 if (!ordinateLookup(&value, &inRange, ord->name, ord-> scale, ord->min, ord->max, readout)) {451 psError(PS_ERR_UNKNOWN, true, "Unable to find value for %s", ord->name);524 double value = NAN; // Value for ordinate 525 if (!ordinateLookup(&value, &inRange, ord->name, ord->rule, ord->scale, ord->min, ord->max, readout)) { 526 psError(PS_ERR_UNKNOWN, true, "Unable to find value for DARK.ORDINATE %s", ord->name); 452 527 psFree(values); 453 528 return false; 454 529 } 530 if (!isfinite(value)) { 531 psError(PS_ERR_UNKNOWN, true, "Value for DARK.ORDINATE %s is NAN", ord->name); 532 psFree(values); 533 return false; 534 } 455 535 values->data.F32[i] = value; 456 536 } 457 floatnorm = NAN; // Normalisation value537 double norm = NAN; // Normalisation value 458 538 bool doNorm = false; // Do normalisation? 459 539 if (normConcept && strlen(normConcept) > 0) { 460 if (!ordinateLookup(&norm, &inRange, normConcept, false, NAN, NAN, readout)) {540 if (!ordinateLookup(&norm, &inRange, normConcept, NULL, false, NAN, NAN, readout)) { 461 541 psError(PS_ERR_UNKNOWN, true, "Unable to find value for %s", normConcept); 462 542 psFree(values); … … 470 550 pmDarkOrdinate *ord = ordinates->data[i]; // Ordinate information 471 551 if (ord->order <= 0) { 472 psError(PS_ERR_UNKNOWN, true, "Bad order for concept%s (%d) --- ignored", ord->name, ord->order);552 psError(PS_ERR_UNKNOWN, true, "Bad order for DARK.ORDINATE %s (%d) --- ignored", ord->name, ord->order); 473 553 psFree(values); 474 554 psFree(orders); … … 701 781 pmDarkOrdinate *ord = ordinates->data[i]; // Ordinate of interest 702 782 psMetadata *row = psMetadataAlloc(); // FITS table row 703 psMetadataAddStr(row, PS_LIST_TAIL, PM_DARK_FITS_NAME, 0, "Concept name", ord->name); 783 psMetadataAddStr(row, PS_LIST_TAIL, PM_DARK_FITS_NAME, 0, "DARK.ORDINATE name", ord->name); 784 785 // XXX write a dummy value if ord->rule == NULL? (eg, NONE) 786 if (ord->rule) { 787 psMetadataAddStr(row, PS_LIST_TAIL, PM_DARK_FITS_RULE, 0, "DARK.ORDINATE rule", ord->rule); 788 } else { 789 psMetadataAddStr(row, PS_LIST_TAIL, PM_DARK_FITS_RULE, 0, "DARK.ORDINATE rule", "NONE"); 790 } 791 704 792 psMetadataAddS32(row, PS_LIST_TAIL, PM_DARK_FITS_ORDER, 0, "Polynomial order", ord->order); 705 793 psMetadataAddBool(row, PS_LIST_TAIL, PM_DARK_FITS_SCALE, 0, "Scale values?", ord->scale); … … 878 966 ord->max = psMetadataLookupF32(NULL, row, PM_DARK_FITS_MAX); 879 967 968 // load the ordinate rule; it is not an error if this field is missing or NULL 969 // a NULL rule means 'use the name as the single concept' 970 const char *rule = psMetadataLookupStr(&mdok, row, PM_DARK_FITS_RULE); 971 if (!strcasecmp(rule, "NONE")) { 972 ord->rule = NULL; 973 } else { 974 ord->rule = psStringCopy(rule); 975 } 880 976 ordinates->data[i] = ord; 881 977 }
Note:
See TracChangeset
for help on using the changeset viewer.
