Index: /trunk/ppImage/src/ppImage.h
===================================================================
--- /trunk/ppImage/src/ppImage.h	(revision 7620)
+++ /trunk/ppImage/src/ppImage.h	(revision 7621)
@@ -34,10 +34,12 @@
 bool ppImageDetrendNonLinearPolynomial(pmReadout *input, psMetadataItem *dataItem);
 
-bool ppImageRebinReadout (pmConfig *config, pmFPAview *view, char *filename);
+bool ppImageRebinChip (pmConfig *config, pmFPAview *view, char *outName, char *inName);
+bool ppImageRebinReadout (pmReadout *output, pmReadout *input, pmFPAfile *outFile);
 
 bool ppImagePhotom (pmConfig *config, pmFPAview *view);
 bool ppImageAstrom (pmConfig *config);
 
-bool ppImageMosaicChip (pmChip *chip, pmConfig *config, const pmFPAview *view);
+bool ppImageMosaicChip (pmConfig *config, const pmFPAview *view, char *outFile, char *inFile);
+bool ppImageMosaicFPA (pmConfig *config, char *outFile, char *inFile);
 
 #endif
Index: /trunk/ppImage/src/ppImageAstrom.c
===================================================================
--- /trunk/ppImage/src/ppImageAstrom.c	(revision 7620)
+++ /trunk/ppImage/src/ppImageAstrom.c	(revision 7621)
@@ -5,10 +5,14 @@
     bool status;
 
+    // select recipe options supplied on command line
+    // XXX move these options to the "PSASTRO" recipe?
+    psMetadata *recipe  = psMetadataLookupPtr (&status, config->recipes, RECIPE_NAME);
+
     // find or define a pmFPAfile PSPHOT.INPUT
     pmFPAfile *input = psMetadataLookupPtr (&status, config->files, "PSASTRO.INPUT");
     if (!status) {
 
-	// psphotReadout requires a pmFPAfile supplied with the name PSPHOT.INPUT
-	// create a pmFPAfile which points at PPIMAGE.OUTPUT
+	// psphotReadout requires a pmFPAfile supplied with the name PSASTRO.INPUT
+	// create a pmFPAfile which points at PSPHOT.OUTPUT
 	// mode is 'REFERENCE' to prevent double frees of the fpa
 	pmFPAfile *output = psMetadataLookupPtr (&status, config->files, "PSPHOT.OUTPUT");
@@ -17,15 +21,5 @@
 
 	pmFPAfileDefineOutput (config, input->fpa, "PSPHOT.OUTPUT");
-
-	// supply the output name (from cmd-line) to all output (WRITE) files
-	// XXX does this cause trouble with existing files?
-	char *outname = psMetadataLookupPtr(&status, config->arguments, "OUTPUT");
-	pmFPAfileAddFileNames (config->files, "OUTPUT", outname, PM_FPA_MODE_WRITE);
     }
-
-    // we only was to operate on PSPHOT pmFPAfiles here:
-    pmFPAfileActivate (config->files, false, NULL);
-    pmFPAfileActivate (config->files, true, "PSASTRO.INPUT");
-    pmFPAfileActivate (config->files, true, "PSASTRO.OUTPUT");
 
     // interpret the available initial astrometric information
@@ -38,27 +32,11 @@
     psastroMosaicGetRefstars (config, refs); 
 
-    char *mosastro = psMetadataLookupStr (NULL, config->arguments, "MOSASTRO");
-    if (mosastro == NULL) {
+    if (psMetadataLookupBool (NULL, recipe, "ASTROM.CHIP")) {
 	psastroChipAstrom (config, refs);
-    } else {
+    } 
+    if (psMetadataLookupBool (NULL, recipe, "ASTROM.MOSAIC")) {
 	psastroMosaicAstrom (config, refs);
     }
 
-    psastroDataSave (config);
-
-    // de-activate the PSPHOT image files, activate the PPIMAGE ones
-    pmFPAfileActivate (config->files, false, NULL);
-    pmFPAfileActivate (config->files, true, "PPIMAGE.INPUT");
-    pmFPAfileActivate (config->files, true, "PPIMAGE.BIAS");
-    pmFPAfileActivate (config->files, true, "PPIMAGE.DARK");
-    pmFPAfileActivate (config->files, true, "PPIMAGE.MASK");
-    pmFPAfileActivate (config->files, true, "PPIMAGE.FLAT");
-    pmFPAfileActivate (config->files, true, "PPIMAGE.OUTPUT");
-
-    pmFPAfileActivate (config->files, true, "PPIMAGE.BIN1");
-    pmFPAfileActivate (config->files, true, "PPIMAGE.JPEG1");
-    pmFPAfileActivate (config->files, true, "PPIMAGE.BIN2");
-    pmFPAfileActivate (config->files, true, "PPIMAGE.JPEG2");
-
     return true;
 }
Index: /trunk/ppImage/src/ppImageLoop.c
===================================================================
--- /trunk/ppImage/src/ppImageLoop.c	(revision 7620)
+++ /trunk/ppImage/src/ppImageLoop.c	(revision 7621)
@@ -37,7 +37,4 @@
 		if (!ppImageDetrendReadout (config, options, view)) return false;
 
-		if (options->doBin1) ppImageRebinReadout (config, view, "PPIMAGE.BIN1");
-		if (options->doBin2) ppImageRebinReadout (config, view, "PPIMAGE.BIN2");
-
 		if (!pmFPAfileIOChecks (config, view, PM_FPA_AFTER)) return false;
 	    }
@@ -45,5 +42,7 @@
 	}
 
-	ppImageMosaicChip (chip, config, view);
+	ppImageMosaicChip (config, view, "PPIMAGE.OUTPUT.CHIP", "PPIMAGE.OUTPUT");
+	ppImageRebinChip (config, view, "PPIMAGE.BIN1", "PPIMAGE.OUTPUT.CHIP");
+	ppImageRebinChip (config, view, "PPIMAGE.BIN2", "PPIMAGE.OUTPUT.CHIP");
 
 	// we perform photometry on the readouts of this chip in the output
@@ -53,10 +52,10 @@
     }
 
+    ppImageMosaicFPA (config, "PPIMAGE.OUTPUT.FPA1", "PPIMAGE.BIN1");
+    ppImageMosaicFPA (config, "PPIMAGE.OUTPUT.FPA2", "PPIMAGE.BIN2");
+
     // we perform astrometry on all chips after sources have been detected
-    if (options->doAstrom) ppImageAstrom (config);
+    if (options->doAstromChip || options->doAstromMosaic) ppImageAstrom (config);
     
-    // ppImageFPAMosaic (config, view);
-    // ppImageJpegFPA (config, view);
-
     if (!pmFPAfileIOChecks (config, view, PM_FPA_AFTER)) return false;
 
@@ -67,2 +66,7 @@
 // input image is: PPIMAGE.INPUT
 // output image is: PPIMAGE.OUTPUT
+
+// XXX need to be careful in ppImage in general about which pmFPAfiles are active and when.
+// major phases:
+// - detrend loop
+// - 
Index: /trunk/ppImage/src/ppImageMosaic.c
===================================================================
--- /trunk/ppImage/src/ppImageMosaic.c	(revision 7620)
+++ /trunk/ppImage/src/ppImageMosaic.c	(revision 7621)
@@ -1,9 +1,9 @@
 # include "ppImage.h"
 
-bool ppImageMosaicChip (pmChip *chip, pmConfig *config, const pmFPAview *view) {
+bool ppImageMosaicChip (pmConfig *config, const pmFPAview *view, char *outFile, char *inFile) {
 
     bool status;
 
-    pmFPAfile *outByChip = psMetadataLookupPtr (&status, config->files, "PPIMAGE.OUTPUT.CHIP");
+    pmFPAfile *in = psMetadataLookupPtr (&status, config->files, inFile);
     if (!status) {
 	psErrorStackPrint(stderr, "Can't find required I/O file!\n");
@@ -11,8 +11,40 @@
     }
 
-    pmFPAAddSourceFromView (outByChip->fpa, view, outByChip->format);
-    pmChip *outChip = pmFPAviewThisChip (view, outByChip->fpa);
-    pmChipMosaic (outChip, chip);
+    pmFPAfile *out = psMetadataLookupPtr (&status, config->files, outFile);
+    if (!status) {
+	psErrorStackPrint(stderr, "Can't find required I/O file!\n");
+	exit(EXIT_FAILURE);
+    }
+
+    pmFPAAddSourceFromView (out->fpa, view, out->format);
+    pmChip *outChip = pmFPAviewThisChip (view, out->fpa);
+    pmChip *inChip = pmFPAviewThisChip (view, in->fpa);
+
+    pmChipMosaic (outChip, inChip);
 
     return true;
 }
+
+bool ppImageMosaicFPA (pmConfig *config, char *outFile, char *inFile) {
+
+    bool status;
+
+    pmFPAfile *in = psMetadataLookupPtr (&status, config->files, inFile);
+    if (!status) {
+	psErrorStackPrint(stderr, "Can't find required I/O file!\n");
+	exit(EXIT_FAILURE);
+    }
+
+    pmFPAfile *out = psMetadataLookupPtr (&status, config->files, outFile);
+    if (!status) {
+	psErrorStackPrint(stderr, "Can't find required I/O file!\n");
+	exit(EXIT_FAILURE);
+    }
+
+    pmFPAview *view = pmFPAviewAlloc (0);
+    pmFPAAddSourceFromView (out->fpa, view, out->format);
+    pmFPAMosaic (out->fpa, in->fpa);
+
+    psFree (view);
+    return true;
+}
Index: /trunk/ppImage/src/ppImageOptions.c
===================================================================
--- /trunk/ppImage/src/ppImageOptions.c	(revision 7620)
+++ /trunk/ppImage/src/ppImageOptions.c	(revision 7621)
@@ -29,10 +29,16 @@
     options->doFringe 	= false;	// Fringe subtraction
     options->doPhotom 	= false;	// Source identification and photometry
-    options->doAstrom 	= false;	// Astrometry
+    options->doAstromChip = false;	// Astrometry
+    options->doAstromMosaic = false;	// Astrometry
 
-    options->doBin1 	= false;	// create binned image (scale 1)
-    options->doBin2 	= false;	// create binned image (scale 2)
-    options->doBin1JPG 	= false;	// create jpg of binned image (scale 1)
-    options->doBin2JPG 	= false;	// create jpg of binned image (scale 2)
+    options->BaseFITS 	= false;	// create binned image (scale 1)
+    options->ChipFITS 	= false;	// create binned image (scale 1)
+    options->FPA1FITS 	= false;	// create binned image (scale 1)
+    options->FPA2FITS 	= false;	// create binned image (scale 1)
+
+    options->Bin1FITS 	= false;	// create binned image (scale 1)
+    options->Bin2FITS 	= false;	// create binned image (scale 2)
+    options->Bin1JPEG 	= false;	// create jpeg of binned image (scale 1)
+    options->Bin2JPEG 	= false;	// create jpeg of binned image (scale 2)
 
     // Overscan defaults
@@ -164,21 +170,18 @@
     if (!status) options->yBin1 = 16;
 
-    options->doBin1 = psMetadataLookupBool(NULL, recipe, "BIN1.FITS");
-    options->doBin1JPG = psMetadataLookupBool(NULL, recipe, "BIN1.JPEG");
-    if (options->doBin1JPG && !options->doBin1) {
-	psLogMsg(__func__, PS_LOG_ERROR, "Invalid Phase2 Options: cannot make JPG of Bin1 image without Bin1 image");
-	exit(EXIT_FAILURE);
-    }
+    options->BaseFITS = psMetadataLookupBool(NULL, recipe, "BASE.FITS");
+    options->ChipFITS = psMetadataLookupBool(NULL, recipe, "CHIP.FITS");
+    options->FPA1FITS = psMetadataLookupBool(NULL, recipe, "FPA1.FITS");
+    options->FPA2FITS = psMetadataLookupBool(NULL, recipe, "FPA2.FITS");
 
-    options->doBin2 = psMetadataLookupBool(NULL, recipe, "BIN2.FITS");
-    options->doBin2JPG = psMetadataLookupBool(NULL, recipe, "BIN2.JPEG");
-    if (options->doBin2JPG && !options->doBin2) {
-	psLogMsg(__func__, PS_LOG_ERROR, "Invalid Phase2 Options: cannot make JPG of Bin2 image without Bin2 image");
-	exit(EXIT_FAILURE);
-    }
+    options->Bin1FITS = psMetadataLookupBool(NULL, recipe, "BIN1.FITS");
+    options->Bin1JPEG = psMetadataLookupBool(NULL, recipe, "BIN1.JPEG");
+    options->Bin2FITS = psMetadataLookupBool(NULL, recipe, "BIN2.FITS");
+    options->Bin2JPEG = psMetadataLookupBool(NULL, recipe, "BIN2.JPEG");
     
     options->doPhotom = psMetadataLookupBool(NULL, recipe, "PHOTOM");
-    options->doAstrom = psMetadataLookupBool(NULL, recipe, "ASTROM");
-    if (options->doAstrom && !options->doPhotom) {
+    options->doAstromChip = psMetadataLookupBool(NULL, recipe, "ASTROM.CHIP");
+    options->doAstromMosaic = psMetadataLookupBool(NULL, recipe, "ASTROM.MOSAIC");
+    if ((options->doAstromChip || options->doAstromMosaic) && !options->doPhotom) {
 	psLogMsg(__func__, PS_LOG_ERROR, "Invalid Phase2 Options: cannot do ASTROMetry without PHOTOMetry");
 	exit(EXIT_FAILURE);
Index: /trunk/ppImage/src/ppImageOptions.h
===================================================================
--- /trunk/ppImage/src/ppImageOptions.h	(revision 7620)
+++ /trunk/ppImage/src/ppImageOptions.h	(revision 7621)
@@ -12,5 +12,6 @@
     bool doFringe;                      // Fringe subtraction
     bool doPhotom;                      // Source identification and photometry
-    bool doAstrom;                      // Astrometry
+    bool doAstromChip;                  // per-chip Astrometry
+    bool doAstromMosaic;                // full-mosaic Astrometry
 
     bool doOverscan;                    // Overscan subtraction
@@ -22,10 +23,15 @@
     void *nonLinearSource;
 
-    bool doBin1;
-    bool doBin1JPG;
+    bool BaseFITS;
+    bool ChipFITS;
+    bool FPA1FITS;
+    bool FPA2FITS;
+
+    bool Bin1FITS;
+    bool Bin1JPEG;
     int xBin1, yBin1;
 
-    bool doBin2;
-    bool doBin2JPG;
+    bool Bin2FITS;
+    bool Bin2JPEG;
     int xBin2, yBin2;
 
Index: /trunk/ppImage/src/ppImageParseCamera.c
===================================================================
--- /trunk/ppImage/src/ppImageParseCamera.c	(revision 7620)
+++ /trunk/ppImage/src/ppImageParseCamera.c	(revision 7621)
@@ -6,5 +6,5 @@
     bool status = false;
 
-    // the input image defines the camera
+    // the input image defines the camera, and all recipes and options the follow
     pmFPAfile *input = pmFPAfileDefineFromArgs (&status, config, "PPIMAGE.INPUT", "INPUT");
     if (!status) {
@@ -14,5 +14,5 @@
 
     // add recipe options supplied on command line
-    psMetadata *recipe  = psMetadataLookupPtr (&status, config->recipes,   "PHASE2");
+    psMetadata *recipe  = psMetadataLookupPtr (&status, config->recipes, "PHASE2");
     psMetadata *arglist = psMetadataLookupPtr (&status, config->arguments, "PPIMAGE.OPTIONS");
     psMetadataCopy (recipe, arglist);
@@ -20,8 +20,4 @@
     // parse the options from the metadata format to the ppImageOptions structure
     ppImageOptions *options = ppImageOptionsParse (config);
-
-    // the following files are output targets
-    pmFPAfileDefineOutput (config, input->fpa, "PPIMAGE.OUTPUT");
-    pmFPAfileDefineNewCamera (config, "PPIMAGE.OUTPUT.CHIP");
 
     // the following are defined from the argument list, if given, 
@@ -56,22 +52,54 @@
 	if (!status) psAbort ("ppImageParseDetrend", "can't find a flat image source");
     }
-    if (options->doBin1) {
-	pmFPAfile *file = pmFPAfileDefineFromFPA (config, input->fpa, options->xBin1, options->yBin1, "PPIMAGE.BIN1");
-	if (options->doBin1JPG) {
-	    pmFPAfileDefineOutput (config, file->fpa, "PPIMAGE.JPEG1");
+
+    // the following files are output targets
+    pmFPAfile *output = pmFPAfileDefineOutput (config, input->fpa, "PPIMAGE.OUTPUT");
+    pmFPAfile *byChip = pmFPAfileDefineNewCamera (config, "PPIMAGE.OUTPUT.CHIP");
+    pmFPAfile *byFPA1 = pmFPAfileDefineNewCamera (config, "PPIMAGE.OUTPUT.FPA1");
+    pmFPAfile *byFPA2 = pmFPAfileDefineNewCamera (config, "PPIMAGE.OUTPUT.FPA2");
+
+    // save any of these files?
+    output->save = options->BaseFITS;
+    byChip->save = options->ChipFITS;
+    byFPA1->save = options->FPA1FITS;
+    byFPA2->save = options->FPA2FITS;
+
+    // output is used as a carrier: input to byChip
+    output->freeLevel = PM_FPA_LEVEL_CHIP; 
+
+    // define the binned target files (which may just be carriers for some camera configurations)
+    pmFPAfile *bin1 = pmFPAfileDefineFromFPA (config, byChip->fpa, options->xBin1, options->yBin1, "PPIMAGE.BIN1");
+    pmFPAfile *bin2 = pmFPAfileDefineFromFPA (config, byChip->fpa, options->xBin2, options->yBin2, "PPIMAGE.BIN2");
+
+    // set the CELL.XBIN and CELL.YBIN for the output mosaiced FPAs
+    for (int i = 0; i < byFPA1->fpa->chips->n; i++) {
+	pmChip *chip = byFPA1->fpa->chips->data[i];
+	for (int j = 0; j < chip->cells->n; j++) {
+	    pmCell *cell = chip->cells->data[j];
+            psMetadataAddF32 (cell->concepts, PS_LIST_TAIL, "CELL.XBIN", PS_META_REPLACE, "", options->xBin1);
+            psMetadataAddF32 (cell->concepts, PS_LIST_TAIL, "CELL.YBIN", PS_META_REPLACE, "", options->yBin1);
 	}
     }
-    if (options->doBin2) {
-	pmFPAfile *file = pmFPAfileDefineFromFPA (config, input->fpa, options->xBin2, options->yBin2, "PPIMAGE.BIN2");
-	if (options->doBin2JPG) {
-	    pmFPAfileDefineOutput (config, file->fpa, "PPIMAGE.JPEG2");
+    for (int i = 0; i < byFPA2->fpa->chips->n; i++) {
+	pmChip *chip = byFPA2->fpa->chips->data[i];
+	for (int j = 0; j < chip->cells->n; j++) {
+	    pmCell *cell = chip->cells->data[j];
+            psMetadataAddF32 (cell->concepts, PS_LIST_TAIL, "CELL.XBIN", PS_META_REPLACE, "", options->xBin2);
+            psMetadataAddF32 (cell->concepts, PS_LIST_TAIL, "CELL.YBIN", PS_META_REPLACE, "", options->yBin2);
 	}
     }
 
-    // ppImage is supplied with an output name, which may be used by multiple
-    // output files to construct the output names.  supply this value to the
-    // files which are write types.
-    char *output = psMetadataLookupPtr(&status, config->arguments, "OUTPUT");
-    pmFPAfileAddFileNames (config->files, "OUTPUT", output, PM_FPA_MODE_WRITE);
+    // bin1 and bin2 are used as carriers: input for byFPA1, byFPA2
+    bin1->freeLevel = PM_FPA_LEVEL_FPA;
+    bin2->freeLevel = PM_FPA_LEVEL_FPA;
+
+    pmFPAfile *jpg1 = pmFPAfileDefineOutput (config, byFPA1->fpa, "PPIMAGE.JPEG1");
+    pmFPAfile *jpg2 = pmFPAfileDefineOutput (config, byFPA2->fpa, "PPIMAGE.JPEG2");
+
+    // XXX we could potentially not define these pmFPAfiles if no output is requested...
+    bin1->save = options->Bin1FITS;
+    bin2->save = options->Bin2FITS;
+    jpg1->save = options->Bin1JPEG;
+    jpg2->save = options->Bin2JPEG;
 
     // Chip selection: turn on only the chips specified (pass status to suppress missing-key log msg)
Index: /trunk/ppImage/src/ppImagePhotom.c
===================================================================
--- /trunk/ppImage/src/ppImagePhotom.c	(revision 7620)
+++ /trunk/ppImage/src/ppImagePhotom.c	(revision 7621)
@@ -24,58 +24,82 @@
     pmFPAfile *input = psMetadataLookupPtr (&status, config->files, "PSPHOT.INPUT");
     if (!status) {
-
 	// psphotReadout requires a pmFPAfile supplied with the name PSPHOT.INPUT
-	// create a pmFPAfile which points at PPIMAGE.OUTPUT
+	// create a pmFPAfile which points to PPIMAGE.OUTPUT.CHIP (guaranteed to be mosaiced by chip)
 	// mode is 'REFERENCE' to prevent double frees of the fpa
-	pmFPAfile *output = psMetadataLookupPtr (&status, config->files, "PPIMAGE.OUTPUT");
+	pmFPAfile *output = psMetadataLookupPtr (&status, config->files, "PPIMAGE.OUTPUT.CHIP");
 	input = pmFPAfileDefineInput (config, output->fpa, "PSPHOT.INPUT");
 	input->mode = PM_FPA_MODE_REFERENCE;
 
 	pmFPAfileDefineOutput (config, input->fpa, "PSPHOT.OUTPUT");
-
-	// supply the output name (from cmd-line) to all output (WRITE) files
-	// XXX does this cause trouble with existing files?
-	char *outname = psMetadataLookupPtr(&status, config->arguments, "OUTPUT");
-	pmFPAfileAddFileNames (config->files, "OUTPUT", outname, PM_FPA_MODE_WRITE);
     }
 
-    // XXX add the option output files here
+    // optionally save the residual image 
+    if (psMetadataLookupBool(NULL, recipe, "SAVE.RESID")) {
+	pmFPAfileDefineOutput (config, input->fpa, "PSPHOT.RESID");
+    }
 
-    // int DX = psMetadataLookupS32 (&status, recipe, "BACKGROUND.XBIN");
-    // int DY = psMetadataLookupS32 (&status, recipe, "BACKGROUND.YBIN");
+    int DX = psMetadataLookupS32 (&status, recipe, "BACKGROUND.XBIN");
+    int DY = psMetadataLookupS32 (&status, recipe, "BACKGROUND.YBIN");
 
-    // we only was to operate on PSPHOT pmFPAfiles here:
-    pmFPAfileActivate (config->files, false, NULL);
-    pmFPAfileActivate (config->files, true, "PSPHOT.INPUT");
-    pmFPAfileActivate (config->files, true, "PSPHOT.RESID");
-    pmFPAfileActivate (config->files, true, "PSPHOT.OUTPUT");
+    // these calls construct a new fpa for the I/O handle 
 
-    pmFPAfileActivate (config->files, true, "PSPHOT.BACKSUB");
-    pmFPAfileActivate (config->files, true, "PSPHOT.BACKGND");
-    pmFPAfileActivate (config->files, true, "PSPHOT.BACKMDL");
+    // optionally save the background model (small FITS image)
+    if (psMetadataLookupBool(NULL, recipe, "SAVE.BACKMDL")) {
+	pmFPAfileDefineFromFPA (config, input->fpa, DX, DY, "PSPHOT.BACKMDL");
+    }
+    // optionally save the full background image
+    if (psMetadataLookupBool(NULL, recipe, "SAVE.BACKGND")) {
+	pmFPAfileDefineFromFPA (config, input->fpa,  1,  1, "PSPHOT.BACKGND");
+    }
+    // optionally save the background-subtracted image
+    if (psMetadataLookupBool(NULL, recipe, "SAVE.BACKSUB")) {
+	pmFPAfileDefineFromFPA (config, input->fpa,  1,  1, "PSPHOT.BACKSUB");
+    }
+    // optionally save the PSF Model
+    if (psMetadataLookupBool(NULL, recipe, "SAVE.PSF")) {
+	pmFPAfileDefineOutput (config, input->fpa, "PSPHOT.PSF.SAVE");
+    }
+    // optionally load the PSF Model
+    if (psMetadataLookupBool(NULL, recipe, "LOAD.PSF")) {
+	pmFPAfileDefineInput (config, input->fpa, "PSPHOT.PSF.LOAD");
+    }
 
+    // XXX not tested (or defined?)
+    // pmFPAfileConstruct (config->files, format, config->camera, "PSPHOT.PSF_SAMPLE");
 
+    // view->cell = -1;
     // iterate over the cells in the current chip
-    // view->cell = -1;
-
     while ((cell = pmFPAviewNextCell (view, input->fpa, 1)) != NULL) {
 	psLogMsg ("ppImagePhot", 4, "Cell %d: %x %x\n", view->cell, cell->file_exists, cell->process);
 	if (! cell->process || ! cell->file_exists) { continue; }
-	pmFPAfileIOChecks (config, view, PM_FPA_BEFORE);
 
 	// process each of the readouts
 	while ((readout = pmFPAviewNextReadout (view, input->fpa, 1)) != NULL) {
-	    pmFPAfileIOChecks (config, view, PM_FPA_BEFORE);
 	    if (! readout->data_exists) { continue; }
 
 	    // run the actual photometry analysis
 	    psphotReadout (config, view);
+	}
+    }
+    return true;
+}
 
-	    pmFPAfileIOChecks (config, view, PM_FPA_AFTER);
-	}
-	pmFPAfileIOChecks (config, view, PM_FPA_AFTER);
-    }
+    // we only want to operate on PSPHOT pmFPAfiles here:
+    // XXX is this necessary?  why invoke I/O during this function?
+    // the psphot constructed files, if chosen, will be saved at the chip level
+    // in the next call outside of this function.
+    // XXX there could be an issue if those files are set for 'cell' or 'readout'
+    // pmFPAfileActivate (config->files, false, NULL);
+    // pmFPAfileActivate (config->files, true, "PSPHOT.INPUT");
+    // pmFPAfileActivate (config->files, true, "PSPHOT.RESID");
+    // pmFPAfileActivate (config->files, true, "PSPHOT.OUTPUT");
+    // pmFPAfileActivate (config->files, true, "PSPHOT.BACKSUB");
+    // pmFPAfileActivate (config->files, true, "PSPHOT.BACKGND");
+    // pmFPAfileActivate (config->files, true, "PSPHOT.BACKMDL");
+
+
 
     // de-activate the PSPHOT image files, activate the PPIMAGE ones
+    # if 0
     pmFPAfileActivate (config->files, false, NULL);
     pmFPAfileActivate (config->files, true, "PPIMAGE.INPUT");
@@ -85,10 +109,8 @@
     pmFPAfileActivate (config->files, true, "PPIMAGE.FLAT");
     pmFPAfileActivate (config->files, true, "PPIMAGE.OUTPUT");
-
     pmFPAfileActivate (config->files, true, "PPIMAGE.BIN1");
     pmFPAfileActivate (config->files, true, "PPIMAGE.JPEG1");
     pmFPAfileActivate (config->files, true, "PPIMAGE.BIN2");
     pmFPAfileActivate (config->files, true, "PPIMAGE.JPEG2");
+    # endif
 
-    return true;
-}
Index: /trunk/ppImage/src/ppImageRebinReadout.c
===================================================================
--- /trunk/ppImage/src/ppImageRebinReadout.c	(revision 7620)
+++ /trunk/ppImage/src/ppImageRebinReadout.c	(revision 7621)
@@ -1,19 +1,42 @@
 #include "ppImage.h"
 
-bool ppImageRebinReadout (pmConfig *config, pmFPAview *view, char *filename)
+bool ppImageRebinChip (pmConfig *config, pmFPAview *view, char *outName, char *inName) {
+
+    pmCell *cell;
+    pmReadout *inReadout, *outReadout;
+
+    pmFPAfile *inFile = psMetadataLookupPtr (NULL, config->files, inName);
+    if (inFile == NULL) return NULL;
+
+    pmFPAfile *outFile = psMetadataLookupPtr (NULL, config->files, outName);
+    if (outFile == NULL) return NULL;
+
+    // XXX double check that chip != -1?
+
+    pmChip *inChip = pmFPAviewThisChip (view, inFile->fpa);
+    pmChip *outChip = pmFPAviewThisChip (view, outFile->fpa);
+    pmChipCopyStructure (outChip, inChip, outFile->xBin, outFile->yBin);
+
+    while ((cell = pmFPAviewNextCell (view, inFile->fpa, 1)) != NULL) {
+	psLogMsg ("ppImageRebinChip", 4, "Cell %d: %x %x\n", view->cell, cell->file_exists, cell->process);
+	if (! cell->process || ! cell->file_exists) { continue; }
+
+	// process each of the readouts
+	while ((inReadout = pmFPAviewNextReadout (view, inFile->fpa, 1)) != NULL) {
+	    if (! inReadout->data_exists) { continue; }
+
+	    outReadout = pmFPAviewThisReadout (view, outFile->fpa);
+
+	    // run the rebin code
+	    ppImageRebinReadout (outReadout, inReadout, outFile);
+	}
+    }
+    return true;
+}
+
+bool ppImageRebinReadout (pmReadout *output, pmReadout *input, pmFPAfile *outFile)
 {
-    bool status;
     psF32 value;
     psS32 nPix;
-
-    // find the currently selected readout
-    pmReadout *input = pmFPAfileThisReadout (config->files, view, "PPIMAGE.INPUT");
-
-    // set up the readouts for dark and bias
-    pmReadout  *output = pmFPAfileThisReadout (config->files, view, filename);
-
-    // we need the file for the binning factors as well
-    pmFPAfile *file = psMetadataLookupPtr (&status, config->files, filename);
-    if (file == NULL) return NULL;
 
     // the binning process must not change the size of the output image...
@@ -22,6 +45,6 @@
     // psFree (stats);
 
-    int dX = file->xBin;
-    int dY = file->yBin;
+    int dX = outFile->xBin;
+    int dY = outFile->yBin;
 
     int nX = input->image->numCols;
