Index: /trunk/Ohana/src/opihi/dvo/avextract.c
===================================================================
--- /trunk/Ohana/src/opihi/dvo/avextract.c	(revision 16935)
+++ /trunk/Ohana/src/opihi/dvo/avextract.c	(revision 16936)
@@ -100,7 +100,9 @@
 
     for (j = 0; (j < catalog.Naverage) && !interrupt; j++) {
-      m = catalog.average[j].measureOffset;
       // extract the relevant values
       // XXX for measure values, this could be optimized for one loop over measures...
+
+      m = catalog.average[j].measureOffset;
+      dbExtractAveragesInit (); // reset counters for saved fields 
       for (n = 0; n < Nfields; n++) {
 	values[n] = dbExtractAverages (&catalog.average[j], &catalog.secfilt[j*Nsecfilt], &catalog.measure[m], &fields[n]);
Index: /trunk/Ohana/src/opihi/dvo/dbExtractAverages.c
===================================================================
--- /trunk/Ohana/src/opihi/dvo/dbExtractAverages.c	(revision 16935)
+++ /trunk/Ohana/src/opihi/dvo/dbExtractAverages.c	(revision 16936)
@@ -1,3 +1,41 @@
 # include "dvoshell.h"
+
+static CoordTransform *celestial_to_galactic = NULL;
+static CoordTransform *celestial_to_ecliptic = NULL;
+
+static int haveGalactic = FALSE;
+static double GLON = 0.0;
+static double GLAT = 0.0;
+
+static int haveEcliptic = FALSE;
+static double ELON = 0.0;
+static double ELAT = 0.0;
+
+// define a locally-static transform
+int dbExtractAveragesInitTransform (CoordTransformSystem target) {
+
+  // galactic transform is kept forever
+  if (target == COORD_GALACTIC) {
+    if (celestial_to_galactic != NULL) return (TRUE);
+    celestial_to_galactic = InitTransform (COORD_CELESTIAL, target);
+    return (TRUE);
+  }
+
+  // ecliptic transform must be updated (is weakly time-dependent)
+  if (target == COORD_ECLIPTIC) {
+    if (celestial_to_ecliptic != NULL) {
+      free (celestial_to_ecliptic);
+    }
+    celestial_to_ecliptic = InitTransform (COORD_CELESTIAL, target);
+    return (TRUE);
+  }
+  return (FALSE);
+}
+
+int dbExtractAveragesInit () {
+  haveGalactic = FALSE;
+  haveEcliptic = FALSE;
+  return (TRUE);
+}
 
 /* return average.field based on the selection */
@@ -16,4 +54,32 @@
     case AVE_DEC:
       value = average[0].D;
+      break;
+    case AVE_GLON:
+      if (!haveGalactic) {
+	ApplyTransform (&GLON, &GLAT, average[0].R, average[0].D, celestial_to_galactic);
+	haveGalactic = TRUE;
+      }
+      value = GLON;
+      break;
+    case AVE_GLAT:
+      if (!haveGalactic) {
+	ApplyTransform (&GLON, &GLAT, average[0].R, average[0].D, celestial_to_galactic);
+	haveGalactic = TRUE;
+      }
+      value = GLAT;
+      break;
+    case AVE_ELON:
+      if (!haveEcliptic) {
+	ApplyTransform (&ELON, &ELAT, average[0].R, average[0].D, celestial_to_ecliptic);
+	haveEcliptic = TRUE;
+      }
+      value = ELON;
+      break;
+    case AVE_ELAT:
+      if (!haveEcliptic) {
+	ApplyTransform (&ELON, &ELAT, average[0].R, average[0].D, celestial_to_ecliptic);
+	haveEcliptic = TRUE;
+      }
+      value = ELAT;
       break;
     case AVE_RA_ERR:
Index: /trunk/Ohana/src/opihi/dvo/dbExtractMeasures.c
===================================================================
--- /trunk/Ohana/src/opihi/dvo/dbExtractMeasures.c	(revision 16935)
+++ /trunk/Ohana/src/opihi/dvo/dbExtractMeasures.c	(revision 16936)
@@ -10,6 +10,58 @@
 static int TimeFormat;
 
+static CoordTransform *celestial_to_galactic = NULL;
+static CoordTransform *celestial_to_ecliptic = NULL;
+
+static int haveGalacticAve = FALSE;
+static double GLON_AVE = 0.0;
+static double GLAT_AVE = 0.0;
+
+static int haveEclipticAve = FALSE;
+static double ELON_AVE = 0.0;
+static double ELAT_AVE = 0.0;
+
+static int haveGalacticMeas = FALSE;
+static double GLON_MEAS = 0.0;
+static double GLAT_MEAS = 0.0;
+
+static int haveEclipticMeas = FALSE;
+static double ELON_MEAS = 0.0;
+static double ELAT_MEAS = 0.0;
+
 void dbExtractMeasuresInit () {
   GetTimeFormat (&TimeReference, &TimeFormat);
+}
+
+// define a locally-static transform
+int dbExtractMeasuresInitTransform (CoordTransformSystem target) {
+
+  // galactic transform is kept forever
+  if (target == COORD_GALACTIC) {
+    if (celestial_to_galactic != NULL) return (TRUE);
+    celestial_to_galactic = InitTransform (COORD_CELESTIAL, target);
+    return (TRUE);
+  }
+
+  // ecliptic transform must be updated (is weakly time-dependent)
+  if (target == COORD_ECLIPTIC) {
+    if (celestial_to_ecliptic != NULL) {
+      free (celestial_to_ecliptic);
+    }
+    celestial_to_ecliptic = InitTransform (COORD_CELESTIAL, target);
+    return (TRUE);
+  }
+  return (FALSE);
+}
+
+int dbExtractMeasuresInitAve () {
+  haveGalacticAve = FALSE;
+  haveEclipticAve = FALSE;
+  return (TRUE);
+}
+
+int dbExtractMeasuresInitMeas () {
+  haveGalacticMeas = FALSE;
+  haveEclipticMeas = FALSE;
+  return (TRUE);
 }
 
@@ -88,4 +140,63 @@
       value = average[0].D;
       break;
+
+    case MEAS_GLON:
+      if (!haveGalacticMeas) {
+	ApplyTransform (&GLON_MEAS, &GLAT_MEAS, average[0].R - measure[0].dR / 3600.0, average[0].D - measure[0].dD / 3600.0, celestial_to_galactic);
+	haveGalacticMeas = TRUE;
+      }
+      value = GLON_MEAS;
+      break;
+    case MEAS_GLAT:
+      if (!haveGalacticMeas) {
+	ApplyTransform (&GLON_MEAS, &GLAT_MEAS, average[0].R - measure[0].dR / 3600.0, average[0].D - measure[0].dD / 3600.0, celestial_to_galactic);
+	haveGalacticMeas = TRUE;
+      }
+      value = GLAT_MEAS;
+      break;
+    case MEAS_ELON:
+      if (!haveEclipticMeas) {
+	ApplyTransform (&ELON_MEAS, &ELAT_MEAS, average[0].R - measure[0].dR / 3600.0, average[0].D - measure[0].dD / 3600.0, celestial_to_ecliptic);
+	haveEclipticMeas = TRUE;
+      }
+      value = ELON_MEAS;
+      break;
+    case MEAS_ELAT:
+      if (!haveEclipticMeas) {
+	ApplyTransform (&ELON_MEAS, &ELAT_MEAS, average[0].R - measure[0].dR / 3600.0, average[0].D - measure[0].dD / 3600.0, celestial_to_ecliptic);
+	haveEclipticMeas = TRUE;
+      }
+      value = ELAT_MEAS;
+      break;
+
+    case MEAS_GLON_AVE:
+      if (!haveGalacticAve) {
+	ApplyTransform (&GLON_AVE, &GLAT_AVE, average[0].R, average[0].D, celestial_to_galactic);
+	haveGalacticAve = TRUE;
+      }
+      value = GLON_AVE;
+      break;
+    case MEAS_GLAT_AVE:
+      if (!haveGalacticAve) {
+	ApplyTransform (&GLON_AVE, &GLAT_AVE, average[0].R, average[0].D, celestial_to_galactic);
+	haveGalacticAve = TRUE;
+      }
+      value = GLAT_AVE;
+      break;
+    case MEAS_ELON_AVE:
+      if (!haveEclipticAve) {
+	ApplyTransform (&ELON_AVE, &ELAT_AVE, average[0].R, average[0].D, celestial_to_ecliptic);
+	haveEclipticAve = TRUE;
+      }
+      value = ELON_AVE;
+      break;
+    case MEAS_ELAT_AVE:
+      if (!haveEclipticAve) {
+	ApplyTransform (&ELON_AVE, &ELAT_AVE, average[0].R, average[0].D, celestial_to_ecliptic);
+	haveEclipticAve = TRUE;
+      }
+      value = ELAT_AVE;
+      break;
+
     case MEAS_RA_AVE_ERR: /* OK */
       value = average[0].dR;
Index: /trunk/Ohana/src/opihi/dvo/dbFields.c
===================================================================
--- /trunk/Ohana/src/opihi/dvo/dbFields.c	(revision 16935)
+++ /trunk/Ohana/src/opihi/dvo/dbFields.c	(revision 16936)
@@ -103,4 +103,38 @@
   field->name  = strcreate (fieldName);
 
+  if (!strcasecmp (fieldName, "GLON"))       {
+    dbExtractMeasuresInitTransform (COORD_GALACTIC);
+    ESCAPE (MEAS_GLON, MAG_NONE);
+  }
+  if (!strcasecmp (fieldName, "GLAT")) {
+    dbExtractMeasuresInitTransform (COORD_GALACTIC);
+    ESCAPE (MEAS_GLAT, MAG_NONE);
+  }
+  if (!strcasecmp (fieldName, "GLON:AVE")) {
+    dbExtractMeasuresInitTransform (COORD_GALACTIC);
+    ESCAPE (MEAS_GLON_AVE, MAG_NONE);
+  }
+  if (!strcasecmp (fieldName, "GLAT:AVE")) {
+    dbExtractMeasuresInitTransform (COORD_GALACTIC);
+    ESCAPE (MEAS_GLAT_AVE, MAG_NONE);
+  }
+
+  if (!strcasecmp (fieldName, "ELON"))       {
+    dbExtractMeasuresInitTransform (COORD_ECLIPTIC);
+    ESCAPE (MEAS_ELON, MAG_NONE);
+  }
+  if (!strcasecmp (fieldName, "ELAT")) {
+    dbExtractMeasuresInitTransform (COORD_ECLIPTIC);
+    ESCAPE (MEAS_ELAT, MAG_NONE);
+  }
+  if (!strcasecmp (fieldName, "ELON:AVE")) {
+    dbExtractMeasuresInitTransform (COORD_ECLIPTIC);
+    ESCAPE (MEAS_ELON_AVE, MAG_NONE);
+  }
+  if (!strcasecmp (fieldName, "ELAT:AVE")) {
+    dbExtractMeasuresInitTransform (COORD_ECLIPTIC);
+    ESCAPE (MEAS_ELAT_AVE, MAG_NONE);
+  }
+
   if (!strcasecmp (fieldName, "RA"))         ESCAPE (MEAS_RA,   	MAG_NONE);
   if (!strcasecmp (fieldName, "DEC"))        ESCAPE (MEAS_DEC,  	MAG_NONE);
@@ -109,4 +143,5 @@
   if (!strcasecmp (fieldName, "RA:ERR"))     ESCAPE (MEAS_RA_AVE_ERR,  	MAG_NONE);
   if (!strcasecmp (fieldName, "DEC:ERR"))    ESCAPE (MEAS_DEC_AVE_ERR, 	MAG_NONE);
+
   if (!strcasecmp (fieldName, "uRA"))        ESCAPE (MEAS_U_RA,        	MAG_NONE);
   if (!strcasecmp (fieldName, "uDEC"))       ESCAPE (MEAS_U_DEC,       	MAG_NONE);
@@ -175,4 +210,26 @@
   field->name  = strcreate (fieldName);
 
+  // if either GLON or GLAT is requested, we set up a static tranformation 
+  // at prepare to calculate the values only once for each row
+  if (!strcasecmp (fieldName, "GLON"))  { 
+    dbExtractAveragesInitTransform (COORD_GALACTIC);
+    ESCAPE (AVE_GLON, MAG_NONE);
+  }
+  if (!strcasecmp (fieldName, "GLAT"))  {
+    dbExtractAveragesInitTransform (COORD_GALACTIC);
+    ESCAPE (AVE_GLAT, MAG_NONE);
+  }
+
+  // if either ELON or ELAT is requested, we set up a static tranformation 
+  // at prepare to calculate the values only once for each row
+  if (!strcasecmp (fieldName, "ELON"))  { 
+    dbExtractAveragesInitTransform (COORD_ECLIPTIC);
+    ESCAPE (AVE_ELON, MAG_NONE);
+  }
+  if (!strcasecmp (fieldName, "ELAT"))  {
+    dbExtractAveragesInitTransform (COORD_ECLIPTIC);
+    ESCAPE (AVE_ELAT, MAG_NONE);
+  }
+
   if (!strcasecmp (fieldName, "RA"))    ESCAPE (AVE_RA,        MAG_NONE);
   if (!strcasecmp (fieldName, "DEC"))   ESCAPE (AVE_DEC,       MAG_NONE);
Index: /trunk/Ohana/src/opihi/dvo/mextract.c
===================================================================
--- /trunk/Ohana/src/opihi/dvo/mextract.c	(revision 16935)
+++ /trunk/Ohana/src/opihi/dvo/mextract.c	(revision 16936)
@@ -121,7 +121,10 @@
     for (j = 0; (j < catalog.Naverage) && !interrupt; j++) {
       m = catalog.average[j].measureOffset;
+      dbExtractMeasuresInitAve (); // reset counters for saved fields 
+
       for (k = 0; (k < catalog.average[j].Nmeasure); k++, m++) {
 
 	// extract the relevant values for this measurement
+	dbExtractMeasuresInitMeas (); // reset counters for saved fields 
 	for (n = 0; n < Nfields; n++) {
 	  values[n] = dbExtractMeasures (&catalog.average[j], &catalog.secfilt[j*Nsecfilt], &catalog.measure[m], &fields[n]);
Index: /trunk/Ohana/src/opihi/include/dvoshell.h
===================================================================
--- /trunk/Ohana/src/opihi/include/dvoshell.h	(revision 16935)
+++ /trunk/Ohana/src/opihi/include/dvoshell.h	(revision 16936)
@@ -23,4 +23,12 @@
 /* measure fields */
 enum {MEAS_ZERO, 
+      MEAS_GLON, 
+      MEAS_GLAT, 
+      MEAS_GLON_AVE, 
+      MEAS_GLAT_AVE,
+      MEAS_ELON, 
+      MEAS_ELAT, 
+      MEAS_ELON_AVE, 
+      MEAS_ELAT_AVE,
       MEAS_RA, 
       MEAS_DEC, 
@@ -84,4 +92,8 @@
       AVE_RA_ERR, 
       AVE_DEC_ERR, 
+      AVE_GLON, 
+      AVE_GLAT, 
+      AVE_ELON, 
+      AVE_ELAT, 
       AVE_U_RA, 
       AVE_U_DEC, 
@@ -241,3 +253,10 @@
 int wordhash (char *word);
 
+int dbExtractAverageInitTransform (CoordTransformSystem target);
+int dbExtractAverageInit ();
+
+int dbExtractMeasuresInitTransform (CoordTransformSystem target);
+int dbExtractMeasuresInitAve ();
+int dbExtractMeasuresInitMeas ();
+
 # endif
