IPP Software Navigation Tools IPP Links Communication Pan-STARRS Links

Ignore:
Timestamp:
Jun 4, 2008, 3:32:28 PM (18 years ago)
Author:
Paul Price
Message:

I've implemented the chip-dependent concepts. It uses a generalised version of the dependent DEFAULT concepts, which can, unfortunately, make the camera format configuration a bit longer, but it consolidates code and keeps things simple both for the code and the configuration.

In the process, I took care of a couple of other concept bugs that have been sitting in my inbox for nearly a year:

  • FPA.NAME has been replaced with FPA.OBS, which is intended to be an observation identifier (bug 885). You're welcome to change the name, so long as you also volunteer to fix all the camera formats.
  • FPA.CAMERA is automatically set (on construction of the FPA) to the camera name as used by the configuration files (bug 931). I've changed the ppStats REGISTER recipe to use FPA.CAMERA instead of FPA.INSTRUMENT (which is retained in the concepts as the instrument's name according to the instrument, whereas FPA.CAMERA is the instrument's name according to our configuration).
File:
1 edited

Legend:

Unmodified
Added
Removed
  • trunk/psModules/src/concepts/pmConceptsWrite.c

    r12890 r17911  
    66#include <assert.h>
    77#include <string.h>
    8 #include <strings.h>            /* for strn?casecmp */
     8#include <strings.h>            /* for strn?casecmp */
    99#include <pslib.h>
    1010
     
    340340        pmConceptSpec *spec = specItem->data.V; // The specification
    341341        psString name = specItem->name; // The concept name
    342         psMetadataItem *defaultItem = psMetadataLookup(defaults, name); // The item from the DEFAULTS
    343         if (defaultItem) {
    344             psMetadataItem *conceptItem = NULL; // The item from the concepts
    345             if (defaultItem->type == PS_DATA_METADATA) {
    346                 // It's a menu --- need to look up the .DEPEND
    347                 psString dependName = NULL; // The concept name with ".DEPEND" on the end
    348                 psStringAppend(&dependName, "%s.DEPEND", defaultItem->name);
    349                 psString dependKey = psMetadataLookupStr(&mdok, defaults, dependName); // The keyword
    350                 if (!mdok || !dependKey || strlen(dependKey) == 0) {
    351                     psWarning("Can't find %s in the DEFAULTS for %s --- ignored.\n",
    352                              dependName, name);
    353                     psFree(dependName);
    354                     continue;
    355                 }
    356                 psString dependValue = psMetadataLookupStr(&mdok, concepts, dependKey); // The value
    357                 if (!mdok || !dependValue || strlen(dependValue) == 0) {
    358                     psWarning("Concept %s specified by %s isn't of type STR -- "
    359                              "ignored.\n", dependKey, dependName);
    360                     psFree(dependName);
    361                     continue;
    362                 }
    363                 // Get the actual item of interest, and correct the name to match the concept name
    364                 defaultItem = psMetadataLookup(defaultItem->data.md, dependValue);
    365                 if (!defaultItem) {
    366                     psWarning("Concept dependency name %s is not found "
    367                              "in concept table for %s -- ignored.\n", dependValue, dependName);
    368                     psFree(dependName);
    369                     continue;
    370                 }
    371                 defaultItem = psMetadataItemCopy(defaultItem);
    372                 psFree(dependName);
    373                 psFree(defaultItem->name);
    374                 defaultItem->name = psStringCopy(name);
    375             } else {
    376                 psMemIncrRefCounter(defaultItem);
    377             }
    378             conceptItem = psMetadataLookup(concepts, name); // The item from the concepts
    379             psMetadataItem *formatted = conceptFormat(spec, conceptItem, PM_CONCEPT_SOURCE_DEFAULTS,
    380                                                       cameraFormat, fpa, chip, cell);
    381             if (!formatted) {
    382                 continue;
    383             }
    384             if (! compareConcepts(formatted, defaultItem)) {
    385                 psWarning("Concept %s is specified by the DEFAULTS in the camera "
    386                          "format, but the values don't match.\n", name);
    387             }
    388             psFree(defaultItem);
    389             psFree(formatted);
    390         }
     342
     343        psMetadataItem *defaultItem = p_pmConceptsReadSingleFromDefaults(name, defaults, fpa, chip, cell);
     344        if (!defaultItem) {
     345            continue;
     346        }
     347        psMetadataItem *conceptItem = psMetadataLookup(concepts, name); // The item from the concepts
     348        psMetadataItem *formatted = conceptFormat(spec, conceptItem, PM_CONCEPT_SOURCE_DEFAULTS,
     349                                                  cameraFormat, fpa, chip, cell);
     350        if (!formatted) {
     351            continue;
     352        }
     353
     354        if (strcmp(defaultItem->name, name) != 0) {
     355            // Correct the name to match the concept name
     356            defaultItem = psMetadataItemCopy(defaultItem);
     357            psFree(defaultItem->name);
     358            defaultItem->name = psStringCopy(name);
     359        } else {
     360            psMemIncrRefCounter(defaultItem);
     361        }
     362
     363        if (!compareConcepts(formatted, defaultItem)) {
     364            psWarning("Concept %s is specified by the DEFAULTS in the camera "
     365                      "format, but the values don't match.\n", name);
     366        }
     367        psFree(defaultItem);
     368        psFree(formatted);
    391369    }
    392370    psFree(specsIter);
     
    418396        psString name = specItem->name; // The concept name
    419397        psMetadataItem *headerItem = psMetadataLookup(translation, name); // The item from the TRANSLATION
    420         if (headerItem) {
    421             if (headerItem->type != PS_DATA_STRING) {
    422                 psWarning("TRANSLATION keyword for concept %s isn't of type STR ---"
    423                          " ignored.", name);
     398        if (!headerItem) {
     399            continue;
     400        }
     401        if (headerItem->type == PS_DATA_METADATA) {
     402            // This is a menu
     403            psTrace("psModules.concepts", 5, "%s is of type METADATA.\n", name);
     404            headerItem = p_pmConceptsDepend(name, headerItem->data.md, translation, fpa, chip, cell);
     405            if (!headerItem) {
    424406                continue;
    425407            }
    426             psTrace("psModules.concepts", 3, "Writing %s to header %s\n", name, headerItem->data.str);
    427             psMetadataItem *conceptItem = psMetadataLookup(concepts, name); // The item from the concepts
    428             psMetadataItem *formatted = conceptFormat(spec, conceptItem, PM_CONCEPT_SOURCE_HEADER,
    429                                                       cameraFormat, fpa, chip, cell);
    430             if (!formatted) {
    431                 continue;
    432             }
    433             writeHeader(hdu, headerItem->data.V, formatted);
    434             psFree(formatted);
    435         }
     408        }
     409        if (headerItem->type != PS_DATA_STRING) {
     410            psWarning("TRANSLATION keyword for concept %s isn't of type STR --- ignored.", name);
     411            continue;
     412        }
     413        psTrace("psModules.concepts", 3, "Writing %s to header %s\n", name, headerItem->data.str);
     414        psMetadataItem *conceptItem = psMetadataLookup(concepts, name); // The item from the concepts
     415        psMetadataItem *formatted = conceptFormat(spec, conceptItem, PM_CONCEPT_SOURCE_HEADER,
     416                                                  cameraFormat, fpa, chip, cell);
     417        if (!formatted) {
     418            continue;
     419        }
     420        writeHeader(hdu, headerItem->data.V, formatted);
     421        psFree(formatted);
    436422    }
    437423    psFree(specsIter);
     
    470456        psString name = specItem->name; // The concept name
    471457
    472         psMetadataItem *dbItem = psMetadataLookup(database, name); // The item from the DATABASE
    473         if (dbItem) {
    474             if (dbItem->type != PS_DATA_METADATA) {
    475                 psWarning("DATABASE keyword for concept %s isn't of type METADATA "
    476                          "--- ignored.\n", name);
    477                 continue;
    478             }
    479 
    480             psMetadataItem *conceptItem = psMetadataLookup(concepts, name); // The item from the concepts
    481             psMetadataItem *formatted = conceptFormat(spec, conceptItem, PM_CONCEPT_SOURCE_DATABASE,
    482                                                       cameraFormat, fpa, chip, cell);
    483             if (!formatted) {
    484                 continue;
    485             }
    486 
    487             psMetadata *dbLookup = dbItem->data.V; // How to look up the value of interest
    488             // Name of the table
    489             const char *tableName = psMetadataLookupStr(&mdok, dbLookup, "TABLE");
    490             // Name of "where" columns
    491             const char *givenCols = psMetadataLookupStr(&mdok, dbLookup, "GIVENDBCOL");
    492             // Values for "where" columns
    493             const char *givenPS = psMetadataLookupStr(&mdok, dbLookup, "GIVENPS");
    494 
    495             // Now, need to get the "given"s
    496             if (strlen(givenCols) || strlen(givenPS)) {
    497                 psList *cols = psStringSplit(givenCols, ",;", true); // List of column names
    498                 psList *values = psStringSplit(givenPS, ",;", true); // List of value names for the columns
    499                 psMetadata *selection = psMetadataAlloc(); // The stuff to select in the DB
    500                 if (cols->n != values->n) {
    501                     psLogMsg(__func__, PS_LOG_WARN,
    502                              "The GIVENDBCOL and GIVENPS entries for %s do not have "
    503                              "the same number of entries --- ignored.\n", name);
    504                 } else {
    505                     // Iterators for the lists
    506                     psListIterator *colsIter = psListIteratorAlloc(cols, PS_LIST_HEAD, false);
    507                     psListIterator *valuesIter = psListIteratorAlloc(values, PS_LIST_HEAD, false);
    508                     char *column = NULL;    // Name of the column
    509                     while ((column = psListGetAndIncrement(colsIter))) {
    510                         char *dependName = psListGetAndIncrement(valuesIter); // Name for the value
    511                         if (!strlen(column) || !strlen(name)) {
    512                             psWarning("One of the columns or value names for %s is "
    513                                      " empty --- ignored.\n", name);
    514                         } else {
    515                             // Search for the value name
    516                             psMetadataItem *item = NULL; // The value
    517                             if (!item && cell) {
    518                                 item = psMetadataLookup(cell->concepts, dependName);
    519                             }
    520                             if (!item && chip) {
    521                                 item = psMetadataLookup(chip->concepts, dependName);
    522                             }
    523                             if (!item && fpa) {
    524                                 item = psMetadataLookup(fpa->concepts, dependName);
    525                             }
    526                             if (! item) {
    527                                 psLogMsg(__func__, PS_LOG_ERROR,
    528                                          "Unable to find the value name %s for DB "
    529                                          " lookup on %s --- ignored.\n", dependName, name);
    530                             } else {
    531                                 // We need to create a new psMetadataItem.  I don't think we can't simply
    532                                 // hack the existing one, since that could conceivably cause memory leaks
    533                                 psMetadataAddItem(selection, formatted, PS_LIST_TAIL, PS_META_REPLACE);
    534                                 psFree(formatted);
    535                             }
    536                         }
    537                         psFree(dependName);
    538                         psFree(column);
    539                     } // Iterating through the columns
    540                     psFree(colsIter);
    541                     psFree(valuesIter);
    542 
    543                     // Check first to make sure we're only going to touch one row
    544                     psArray *dbResult = psDBSelectRows(db, tableName, selection, 2); // Lookup result
    545                     // Note that we use limit=2 in order to test if there are multiple rows returned
    546                     if (! dbResult || dbResult->n == 0) {
    547                         psWarning("Unable to find any rows in DB for %s --- "
    548                                  "ignored\n", name);
    549                         return false;
    550                     } else {
    551                         if (dbResult->n > 1) {
    552                             psWarning("Multiple rows returned in DB lookup for %s "
    553                                      "--- ignored.\n", name);
    554                         }
    555                         // Update the DB
    556                         psMetadata *update = psMetadataAlloc();
    557                         psMetadataAddItem(update, conceptItem, PS_LIST_HEAD, 0);
    558                         psDBUpdateRows(db, tableName, selection, update);
    559                         psFree(update);
    560                         return true;
    561                     }
    562                 }
    563                 psFree(cols);
    564                 psFree(values);
    565             } // Doing the "given"s.
    566         }
     458        psMetadataItem *dbItem = p_pmConceptsReadSingleFromDatabase(name, database, db, fpa, chip, cell);
     459        if (!dbItem) {
     460            continue;
     461        }
     462
     463        psMetadataItem *conceptItem = psMetadataLookup(concepts, name); // The item from the concepts
     464        psMetadataItem *formatted = conceptFormat(spec, conceptItem, PM_CONCEPT_SOURCE_DATABASE,
     465                                                  cameraFormat, fpa, chip, cell);
     466        if (!formatted) {
     467            continue;
     468        }
     469
     470        if (strcmp(dbItem->name, name) != 0) {
     471            // Correct the name to match the concept name
     472            dbItem = psMetadataItemCopy(dbItem);
     473            psFree(dbItem->name);
     474            dbItem->name = psStringCopy(name);
     475        } else {
     476            psMemIncrRefCounter(dbItem);
     477        }
     478
     479        if (!compareConcepts(formatted, dbItem)) {
     480            psWarning("Concept %s is specified by the DATABASE in the camera "
     481                      "format, but the values don't match.\n", name);
     482        }
     483        psFree(dbItem);
     484        psFree(formatted);
    567485    }
    568486    psFree(specsIter);
     
    570488    #endif
    571489}
    572 
Note: See TracChangeset for help on using the changeset viewer.