Index: trunk/Ohana/src/relphot/Makefile
===================================================================
--- trunk/Ohana/src/relphot/Makefile	(revision 17215)
+++ trunk/Ohana/src/relphot/Makefile	(revision 17242)
@@ -39,4 +39,5 @@
 $(SRC)/reload_catalogs.$(ARCH).o \
 $(SRC)/relphot.$(ARCH).o	 \
+$(SRC)/relphot_objects.$(ARCH).o	 \
 $(SRC)/select_images.$(ARCH).o	 \
 $(SRC)/setExclusions.$(ARCH).o 	 \
Index: trunk/Ohana/src/relphot/include/relphot.h
===================================================================
--- trunk/Ohana/src/relphot/include/relphot.h	(revision 17215)
+++ trunk/Ohana/src/relphot/include/relphot.h	(revision 17242)
@@ -78,4 +78,5 @@
 int    USE_GRID;
 int    PLOTDELAY;
+int    UpdateAverages;
 
 int    RELPHOT_GRID_X;
@@ -191,4 +192,5 @@
 void          setMrelFinal        PROTO((Catalog *catalog));
 int           setMrelOutput       PROTO((Catalog *catalog, int Ncatalog, int mark));
+int           setMave             PROTO((Catalog *catalog, int Ncatalog));
 void          set_ZP              PROTO((double ZERO));
 int           setrefcode          PROTO((Image *image, int Nimage)); 
Index: trunk/Ohana/src/relphot/src/StarOps.c
===================================================================
--- trunk/Ohana/src/relphot/src/StarOps.c	(revision 17215)
+++ trunk/Ohana/src/relphot/src/StarOps.c	(revision 17242)
@@ -146,4 +146,62 @@
 }
 
+// for each average object, set the average mags based on existing equiv photometry
+int setMave (Catalog *catalog, int Ncatalog) {
+
+  int i, j, k, m, Ns, Nsecfilt, N, Nmax, Nc;
+  float Msys;
+  double *list, *dlist;
+  StatType stats;
+  PhotCode *code;
+
+  // pre-allocate a list for stats purposes
+  Nmax = 0;
+  for (i = 0; i < Ncatalog; i++) {
+    for (j = 0; j < catalog[i].Naverage; j++) {
+      Nmax = MAX (Nmax, catalog[i].average[j].Nmeasure);
+    }
+  }
+  ALLOCATE (list, double, MAX (1, Nmax));
+  ALLOCATE (dlist, double, MAX (1, Nmax));
+
+  Nsecfilt = catalog[0].Nsecfilt;
+
+  for (i = 0; i < Ncatalog; i++) {
+    for (j = 0; j < catalog[i].Naverage; j++) {
+      for (Ns = 0; Ns < Nsecfilt; Ns++) {
+
+	code = GetPhotcodebyNsec (Ns);
+	Nc = code[0].code;
+	
+	N = 0;
+	m = catalog[i].average[j].measureOffset;
+	for (k = 0; k < catalog[i].average[j].Nmeasure; k++, m++) {
+	  if (catalog[i].measure[m].dbFlags & MEAS_BAD) continue;
+	  if (GetPhotcodeEquivCodebyCode (catalog[i].measure[m].photcode) != Nc) continue;
+
+	  Msys = PhotSys (&catalog[i].measure[m], &catalog[i].average[j], &catalog[i].secfilt[j*PhotNsec]);
+	  list[N] = Msys - catalog[i].measure[m].Mcal;
+	  dlist[N] = MAX (catalog[i].measure[m].dM, MIN_ERROR);
+	  N++;
+	}
+	if (N < 1) continue;
+
+	liststats (list, dlist, N, &stats);
+
+	/* use sigma or error in dM for output? */
+	catalog[i].secfilt[Nsecfilt*j+Ns].M  = stats.mean;
+	catalog[i].secfilt[Nsecfilt*j+Ns].dM = MAX (stats.error, stats.sigma);
+	catalog[i].secfilt[Nsecfilt*j+Ns].Xm = (stats.Nmeas > 1) ? 100.0*log10(stats.chisq) : NAN_S_SHORT;
+	catalog[i].secfilt[Nsecfilt*j+Ns].Ncode = N;
+	catalog[i].secfilt[Nsecfilt*j+Ns].Nused = stats.Nmeas;
+      }
+    }
+  }
+
+  free (list);
+  free (dlist);
+  return (TRUE);
+}
+
 /* set measure.Mcal for all measures except ID_MEAS_NOCAL and ID_IMAGE_NOCAL */
 int setMcalOutput (Catalog *catalog, int Ncatalog) {
Index: trunk/Ohana/src/relphot/src/args.c
===================================================================
--- trunk/Ohana/src/relphot/src/args.c	(revision 17215)
+++ trunk/Ohana/src/relphot/src/args.c	(revision 17242)
@@ -181,6 +181,13 @@
   }
 
-  if ( UserPatchSelect && (argc != 2)) usage ();
-  if (!UserPatchSelect && (argc != 3)) usage ();
+  UpdateAverages = FALSE;
+  if ((N = get_argument (argc, argv, "-averages"))) {
+    remove_argument (N, &argc, argv);
+    UpdateAverages = TRUE;
+  }
+
+  if (UpdateAverages && (argc == 1)) return TRUE;
+  if (UserPatchSelect && (argc == 2)) return TRUE;
+  if (argc != 3) usage ();
 
   return TRUE;
@@ -190,4 +197,5 @@
   fprintf (stderr, "ERROR: USAGE: relphot (region) (photcode)\n");
   fprintf (stderr, "       or:    relphot (photcode) -region RA RA DEC DEC\n");
+  fprintf (stderr, "       or:    relphot -averages -region RA RA DEC DEC\n");
   fprintf (stderr, "  options: \n");
   fprintf (stderr, "  -time (start) (stop)\n");
Index: trunk/Ohana/src/relphot/src/initialize.c
===================================================================
--- trunk/Ohana/src/relphot/src/initialize.c	(revision 17215)
+++ trunk/Ohana/src/relphot/src/initialize.c	(revision 17242)
@@ -8,16 +8,20 @@
   args (argc, argv);
 
-  N = UserPatchSelect ? 1 : 2;
-  if ((photcode = GetPhotcodebyName (argv[N])) == NULL) {
-    fprintf (stderr, "ERROR: photcode %s not found in photcode table\n", argv[N]);
-    exit (1);
-  }
-  if (photcode[0].type != PHOT_SEC) {
-    fprintf (stderr, "photcode %s is not a primary or secondary filter\n", argv[N]);
-    exit (1);
+  if (!UpdateAverages) {
+
+    N = UserPatchSelect ? 1 : 2;
+
+    if ((photcode = GetPhotcodebyName (argv[N])) == NULL) {
+      fprintf (stderr, "ERROR: photcode %s not found in photcode table\n", argv[N]);
+      exit (1);
+    }
+    if (photcode[0].type != PHOT_SEC) {
+      fprintf (stderr, "photcode %s is not a primary or secondary filter\n", argv[N]);
+      exit (1);
+    }
+    PhotSec = GetPhotcodeNsec (photcode[0].code);
   }
 
   PhotNsec = GetPhotcodeNsecfilt ();
-  PhotSec = GetPhotcodeNsec (photcode[0].code);
 
   initstats (STATMODE);
Index: trunk/Ohana/src/relphot/src/relphot.c
===================================================================
--- trunk/Ohana/src/relphot/src/relphot.c	(revision 17215)
+++ trunk/Ohana/src/relphot/src/relphot.c	(revision 17242)
@@ -11,4 +11,10 @@
   /* get configuration info, args */
   initialize (argc, argv);
+
+  /* the object analysis is a separate process iterating over catalogs */
+  if (UpdateAverages) {
+    relphot_objects ();
+    exit (0);
+  }
 
   /* register database handle with shutdown procedure */
Index: trunk/Ohana/src/relphot/src/relphot_objects.c
===================================================================
--- trunk/Ohana/src/relphot/src/relphot_objects.c	(revision 17242)
+++ trunk/Ohana/src/relphot/src/relphot_objects.c	(revision 17242)
@@ -0,0 +1,65 @@
+# include "relphot.h"
+
+int relphot_objects () {
+
+  int i, j, k, m;
+
+  SkyTable *sky = NULL;
+  SkyList *skylist = NULL;
+  Catalog catalog;
+
+  // load the current sky table (layout of all SkyRegions) 
+  sky = SkyTableLoadOptimal (CATDIR, SKY_TABLE, GSCFILE, SKY_DEPTH, VERBOSE);
+  SkyTableSetFilenames (sky, CATDIR, "cpt");
+  
+  // determine the populated SkyRegions overlapping the requested area (default depth)
+  skylist = SkyListByPatch (sky, -1, &UserPatch);
+
+  // load data from each region file, only use bright stars
+  for (i = 0; i < skylist[0].Nregions; i++) {
+
+    // set up the basic catalog info
+    catalog.filename  = skylist[0].filename[i];
+    catalog.catformat = dvo_catalog_catformat (CATFORMAT);    // set the default catformat from config data
+    catalog.catmode   = dvo_catalog_catmode (CATMODE);        // set the default catmode from config data
+    catalog.catflags  = LOAD_AVES | LOAD_MEAS | LOAD_MISS | LOAD_SECF;
+    catalog.Nsecfilt  = GetPhotcodeNsecfilt ();
+
+    if (!dvo_catalog_open (&catalog, skylist[0].regions[i], VERBOSE, "w")) {
+      fprintf (stderr, "ERROR: failure reading catalog %s\n", catalog.filename);
+      exit (1);
+    }
+    if (!catalog.Naves_disk) {
+      if (VERBOSE) fprintf (stderr, "no data in %s, skipping\n", catalog.filename);
+      dvo_catalog_unlock (&catalog);
+      dvo_catalog_free (&catalog);
+      continue;
+    }
+
+    // XXX consider what gets reset (only PHOTOM flags)
+    if (RESET) {
+      for (j = 0; j < catalog.Naverage; j++) {
+	catalog.average[j].code = 0;
+	m = catalog.average[j].measureOffset;
+	for (k = 0; k < catalog.average[j].Nmeasure; k++) {
+	  catalog.measure[m+k].dbFlags = 0;
+	}
+      }
+    }
+
+    setMave (&catalog, 1);
+
+    if (!UPDATE) {
+      dvo_catalog_unlock (&catalog);
+      dvo_catalog_free (&catalog);
+      continue;
+    }
+    
+    if (VERBOSE) fprintf (stderr, "saving catalog %s\n", catalog.filename);
+    dvo_catalog_save (&catalog, VERBOSE); 
+    dvo_catalog_unlock (&catalog);
+    dvo_catalog_free (&catalog);
+  }
+  
+  return (TRUE);
+}
