IPP Software Navigation Tools IPP Links Communication Pan-STARRS Links

Changeset 20095


Ignore:
Timestamp:
Oct 13, 2008, 11:20:36 AM (18 years ago)
Author:
Paul Price
Message:

Allowing CELL.READNOISE to be specified in ADU instead of electrons. This requires updating the parsed value with the gain when it's available. Added a check at the principal (only?) place this value is used (pmReadoutSetWeight) so that errors can be trapped.

Location:
trunk/psModules/src
Files:
5 edited

Legend:

Unmodified
Added
Removed
  • trunk/psModules/src/camera/pmFPAMaskWeight.c

    r19163 r20095  
    212212    if (!mdok || isnan(readnoise)) {
    213213        psError(PS_ERR_IO, true, "CELL.READNOISE is not set --- unable to set weight.\n");
     214        return false;
     215    }
     216    if (psMetadataLookup(cell->concepts, "CELL.READNOISE.UPDATE")) {
     217        psError(PS_ERR_IO, true, "CELL.READNOISE has not yet been updated for the gain");
    214218        return false;
    215219    }
  • trunk/psModules/src/concepts/pmConcepts.c

    r19688 r20095  
    598598        // Install the standard concepts
    599599        conceptRegisterF32("CELL.GAIN", "CCD gain (e/count)", NULL, NULL, true, PM_FPA_LEVEL_CELL);
    600         conceptRegisterF32("CELL.READNOISE", "CCD read noise (e)", NULL, NULL, true, PM_FPA_LEVEL_CELL);
     600        conceptRegisterF32("CELL.READNOISE", "CCD read noise (e)", p_pmConceptParse_CELL_READNOISE, p_pmConceptFormat_CELL_READNOISE, true, PM_FPA_LEVEL_CELL);
    601601        conceptRegisterF32("CELL.SATURATION", "Saturation level (counts)", NULL, NULL, true, PM_FPA_LEVEL_CELL);
    602602        conceptRegisterF32("CELL.BAD", "Bad level (counts)", NULL, NULL, true, PM_FPA_LEVEL_CELL);
  • trunk/psModules/src/concepts/pmConceptsStandard.c

    r19980 r20095  
    4646    return NAN;
    4747}
     48
     49
     50psMetadataItem *p_pmConceptParse_CELL_READNOISE(const psMetadataItem *concept,
     51                                                const psMetadataItem *pattern,
     52                                                pmConceptSource source,
     53                                                const psMetadata *cameraFormat,
     54                                                const pmFPA *fpa,
     55                                                const pmChip *chip,
     56                                                const pmCell *cell)
     57{
     58    assert(concept);
     59    assert(pattern);
     60    assert(cameraFormat);
     61    assert(cell);
     62
     63    float rn = psMetadataItemParseF32(concept); // Read noise
     64    if (isfinite(rn)) {
     65        bool mdok;                      // Status of MD lookup
     66        psMetadata *formats = psMetadataLookupMetadata(&mdok, cameraFormat, "FORMATS");
     67        if (mdok && formats) {
     68            psString format = psMetadataLookupStr(&mdok, formats, pattern->name);
     69            if (mdok && strlen(format) > 0) {
     70                if (strcasecmp(format, "ADU") == 0) {
     71                    float gain = psMetadataLookupF32(NULL, cell->concepts, "CELL.GAIN"); // Gain (e/ADU)
     72                    if (!isfinite(gain)) {
     73                        // Will need to update the readnoise once the gain is available
     74                        psMetadataAddBool(cell->concepts, PS_LIST_TAIL, "CELL.READNOISE.UPDATE",
     75                                          PS_META_REPLACE,
     76                                          "Need to update CELL.READNOISE when the gain is available.", true);
     77                    } else {
     78                        rn *= gain;
     79                    }
     80                } else {
     81                    psError(PS_ERR_BAD_PARAMETER_VALUE, true, "Unrecognised format for CELL.READNOISE: %s",
     82                            format);
     83                    return NULL;
     84                }
     85            }
     86        }
     87    }
     88
     89    return psMetadataItemAllocF32(pattern->name, pattern->comment, rn);
     90}
     91
     92psMetadataItem *p_pmConceptFormat_CELL_READNOISE(const psMetadataItem *concept,
     93                                                 pmConceptSource source,
     94                                                 const psMetadata *cameraFormat,
     95                                                 const pmFPA *fpa,
     96                                                 const pmChip *chip,
     97                                                 const pmCell *cell)
     98{
     99    assert(concept);
     100    assert(cell);
     101    assert(concept->type == PS_TYPE_F32);
     102
     103    float rn = concept->data.F32;       // Read noise
     104    if (isfinite(rn)) {
     105        bool mdok;                      // Status of MD lookup
     106        psMetadata *formats = psMetadataLookupMetadata(&mdok, cameraFormat, "FORMATS");
     107        if (mdok && formats) {
     108            psString format = psMetadataLookupStr(&mdok, formats, concept->name);
     109            if (mdok && strlen(format) > 0) {
     110                if (strcasecmp(format, "ADU") == 0) {
     111                    if (!psMetadataLookup(cell->concepts, "CELL.READNOISE.UPDATE")) {
     112                        // Gain correction has been applied, so we need to reverse it to format
     113                        float gain = psMetadataLookupF32(NULL, cell->concepts, "CELL.GAIN"); // Gain (e/ADU)
     114                        if (!isfinite(gain)) {
     115                            psWarning("CELL.READNOISE is supposed to be in ADU, but CELL.GAIN isn't set");
     116                        }
     117                        rn /= gain;
     118                    }
     119                } else {
     120                    psError(PS_ERR_BAD_PARAMETER_VALUE, true, "Unrecognised format for CELL.READNOISE: %s",
     121                            format);
     122                    return NULL;
     123                }
     124            }
     125        }
     126    }
     127
     128    return psMetadataItemAllocF32(concept->name, concept->comment, rn);
     129}
     130
    48131
    49132// TELTEMPS : parse a list of the form 'X1 X2 X3 X4 X5 ...' : for now use median
  • trunk/psModules/src/concepts/pmConceptsStandard.h

    r15770 r20095  
    44 * @author Paul Price, IfA
    55 *
    6  * @version $Revision: 1.12 $ $Name: not supported by cvs2svn $
    7  * @date $Date: 2007-12-08 03:15:37 $
     6 * @version $Revision: 1.13 $ $Name: not supported by cvs2svn $
     7 * @date $Date: 2008-10-13 21:20:36 $
    88 * Copyright 2005-2006 Institute for Astronomy, University of Hawaii
    99 */
     
    1919    );
    2020
     21/// Parse the CELL.READNOISE concept to do ADU->e correction if required
     22psMetadataItem *p_pmConceptParse_CELL_READNOISE(const psMetadataItem *concept,
     23                                                const psMetadataItem *pattern,
     24                                                pmConceptSource source,
     25                                                const psMetadata *cameraFormat,
     26                                                const pmFPA *fpa,
     27                                                const pmChip *chip,
     28                                                const pmCell *cell);
     29
     30/// Format the CELL.READNOISE concept to do e->ADU correction if required
     31psMetadataItem *p_pmConceptFormat_CELL_READNOISE(const psMetadataItem *concept,
     32                                                 pmConceptSource source,
     33                                                 const psMetadata *cameraFormat,
     34                                                 const pmFPA *fpa,
     35                                                 const pmChip *chip,
     36                                                 const pmCell *cell);
     37
    2138// Parse the TELTEMPS concept : parse a list of the form 'X1 X2 X3 X4 X5 ...' : for now use median
    2239psMetadataItem *p_pmConceptParse_TELTEMPS(const psMetadataItem *concept,
    23                                           const psMetadataItem *pattern,
    24                                           pmConceptSource source,
    25                                           const psMetadata *cameraFormat,
    26                                           const pmFPA *fpa,
    27                                           const pmChip *chip,
    28                                           const pmCell *cell);
     40                                          const psMetadataItem *pattern,
     41                                          pmConceptSource source,
     42                                          const psMetadata *cameraFormat,
     43                                          const pmFPA *fpa,
     44                                          const pmChip *chip,
     45                                          const pmCell *cell);
    2946
    3047/// Parse the FPA.FILTER concept to apply a lookup table
  • trunk/psModules/src/concepts/pmConceptsUpdate.c

    r13034 r20095  
    2525        // Check for cell concepts updates
    2626
    27         bool xStatus, yStatus; // Status of MD lookups
    28         psImageBinning *binning = psImageBinningAlloc();
    29         binning->nXbin = psMetadataLookupS32(&xStatus, cell->concepts, "CELL.XBIN");
    30         binning->nYbin = psMetadataLookupS32(&yStatus, cell->concepts, "CELL.YBIN");
    31         if (!xStatus || !yStatus) {
    32             // XXX should this be an error condition?
    33             psFree (binning);
    34             return true;
    35         }
    36         if (!binning->nXbin || !binning->nXbin) {
    37             // XXX should this be an error condition?
    38             psFree (binning);
    39             return true;
    40         }
     27        // CELL.READNOISE needs to be updated if specified in ADU
     28        if (psMetadataLookup(cell->concepts, "CELL.READNOISE.UPDATE")) {
     29            float gain = psMetadataLookupF32(NULL, cell->concepts, "CELL.GAIN"); // Gain for cell
     30            if (isfinite(gain)) {
     31                psMetadataItem *rn = psMetadataLookup(cell->concepts, "CELL.READNOISE"); // Read noise
     32                psAssert(rn && rn->type == PS_TYPE_F32, "Should be of the correct type");
     33                rn->data.F32 *= gain;
     34                psMetadataRemoveKey(cell->concepts, "CELL.READNOISE.UPDATE");
     35            }
     36        }
     37
     38        bool xStatus, yStatus; // Status of MD lookups
     39        psImageBinning *binning = psImageBinningAlloc();
     40        binning->nXbin = psMetadataLookupS32(&xStatus, cell->concepts, "CELL.XBIN");
     41        binning->nYbin = psMetadataLookupS32(&yStatus, cell->concepts, "CELL.YBIN");
     42        if (!xStatus || !yStatus) {
     43            // XXX should this be an error condition?
     44            psFree (binning);
     45            return true;
     46        }
     47        if (!binning->nXbin || !binning->nXbin) {
     48            // XXX should this be an error condition?
     49            psFree (binning);
     50            return true;
     51        }
    4152
    4253        // CELL.TRIMSEC needs to be updated for the binning
    4354        if (psMetadataLookup(cell->concepts, "CELL.TRIMSEC.UPDATE")) {
    44             psRegion *trimsec = psMetadataLookupPtr(NULL, cell->concepts, "CELL.TRIMSEC"); // Trim section
    45             *trimsec = psImageBinningSetRuffRegion (binning, *trimsec);
    46             // force integer pixels : truncate x0, roundup x1:
    47             trimsec->x0 = (int)trimsec->x0;
    48             if (trimsec->x1 > (int)trimsec->x1) {
    49                 trimsec->x1 = (int)trimsec->x1 + 1;
    50             } else {
    51                 trimsec->x1 = (int)trimsec->x1;
    52             }           
    53             trimsec->y0 = (int)trimsec->y0;
    54             if (trimsec->y1 > (int)trimsec->y1) {
    55                 trimsec->y1 = (int)trimsec->y1 + 1;
    56             } else {
    57                 trimsec->y1 = (int)trimsec->y1;
    58             }           
    59             psMetadataRemoveKey(cell->concepts, "CELL.TRIMSEC.UPDATE");
     55            psRegion *trimsec = psMetadataLookupPtr(NULL, cell->concepts, "CELL.TRIMSEC"); // Trim section
     56            *trimsec = psImageBinningSetRuffRegion (binning, *trimsec);
     57            // force integer pixels : truncate x0, roundup x1:
     58            trimsec->x0 = (int)trimsec->x0;
     59            if (trimsec->x1 > (int)trimsec->x1) {
     60                trimsec->x1 = (int)trimsec->x1 + 1;
     61            } else {
     62                trimsec->x1 = (int)trimsec->x1;
     63            }
     64            trimsec->y0 = (int)trimsec->y0;
     65            if (trimsec->y1 > (int)trimsec->y1) {
     66                trimsec->y1 = (int)trimsec->y1 + 1;
     67            } else {
     68                trimsec->y1 = (int)trimsec->y1;
     69            }
     70            psMetadataRemoveKey(cell->concepts, "CELL.TRIMSEC.UPDATE");
    6071        }
    6172
    6273        // CELL.BIASSEC needs to be updated for the binning
    6374        if (psMetadataLookup(cell->concepts, "CELL.BIASSEC.UPDATE")) {
    64             psList *biassecs = psMetadataLookupPtr(NULL, cell->concepts, "CELL.BIASSEC"); // Bias sections
    65             psListIterator *biassecsIter = psListIteratorAlloc(biassecs, PS_LIST_HEAD, true); // Iterator
    66             psRegion *biassec; // Bias region, from iteration
    67             while ((biassec = psListGetAndIncrement(biassecsIter))) {
    68                 *biassec = psImageBinningSetRuffRegion (binning, *biassec);
    69                 // force integer pixels : truncate x0, roundup x1:
    70                 biassec->x0 = (int)biassec->x0;
    71                 if (biassec->x1 > (int)biassec->x1) {
    72                     biassec->x1 = (int)biassec->x1 + 1;
    73                 } else {
    74                     biassec->x1 = (int)biassec->x1;
    75                 }               
    76                 biassec->y0 = (int)biassec->y0;
    77                 if (biassec->y1 > (int)biassec->y1) {
    78                     biassec->y1 = (int)biassec->y1 + 1;
    79                 } else {
    80                     biassec->y1 = (int)biassec->y1;
    81                 }               
    82             }
    83             psFree(biassecsIter);
    84             psMetadataRemoveKey(cell->concepts, "CELL.BIASSEC.UPDATE");
     75            psList *biassecs = psMetadataLookupPtr(NULL, cell->concepts, "CELL.BIASSEC"); // Bias sections
     76            psListIterator *biassecsIter = psListIteratorAlloc(biassecs, PS_LIST_HEAD, true); // Iterator
     77            psRegion *biassec; // Bias region, from iteration
     78            while ((biassec = psListGetAndIncrement(biassecsIter))) {
     79                *biassec = psImageBinningSetRuffRegion (binning, *biassec);
     80                // force integer pixels : truncate x0, roundup x1:
     81                biassec->x0 = (int)biassec->x0;
     82                if (biassec->x1 > (int)biassec->x1) {
     83                    biassec->x1 = (int)biassec->x1 + 1;
     84                } else {
     85                    biassec->x1 = (int)biassec->x1;
     86                }
     87                biassec->y0 = (int)biassec->y0;
     88                if (biassec->y1 > (int)biassec->y1) {
     89                    biassec->y1 = (int)biassec->y1 + 1;
     90                } else {
     91                    biassec->y1 = (int)biassec->y1;
     92                }
     93            }
     94            psFree(biassecsIter);
     95            psMetadataRemoveKey(cell->concepts, "CELL.BIASSEC.UPDATE");
    8596        }
    86         psFree (binning);
     97        psFree (binning);
    8798    }
    8899
Note: See TracChangeset for help on using the changeset viewer.