Index: /trunk/archive/scripts/src/phase2/papPhase2.c
===================================================================
--- /trunk/archive/scripts/src/phase2/papPhase2.c	(revision 5370)
+++ /trunk/archive/scripts/src/phase2/papPhase2.c	(revision 5371)
@@ -45,5 +45,5 @@
 static psMemId memPrintAlloc(const psMemBlock *mb)
 {
-    printf("Allocated memory block %lld (%lld):\n"
+    printf("Allocated memory block %ld (%ld):\n"
 	   "\tFile %s, line %d, size %d\n"
 	   "\tPosts: %x %x %x\n",
@@ -54,5 +54,5 @@
 static psMemId memPrintFree(const psMemBlock *mb)
 {
-    printf("Freed memory block %lld (%lld):\n"
+    printf("Freed memory block %ld (%ld):\n"
 	   "\tFile %s, line %d, size %d\n"
 	   "\tPosts: %x %x %x\n",
@@ -64,5 +64,5 @@
 {
     psMemBlock *mb = ((psMemBlock*)ptr) - 1;
-    printf("Memory block %lld (%lld):\n"
+    printf("Memory block %ld (%ld):\n"
 	   "\tFile %s, line %d, size %d\n"
 	   "\tPosts: %x %x %x\n",
@@ -75,7 +75,7 @@
 #if 0
     // Hunting memory leaks
-    psMemAllocateCallbackSetID(23289);
-    psMemFreeCallbackSetID(23289);
-    psMemAllocateCallbackSet(memPrintAlloc);
+    psMemAllocCallbackSetID(22367);
+    psMemFreeCallbackSetID(22367);
+    psMemAllocCallbackSet(memPrintAlloc);
     psMemFreeCallbackSet(memPrintFree);
 #endif
@@ -198,7 +198,8 @@
     bool doAstrom = false;		// Astrometry
     pmOverscanAxis overscanMode = PM_OVERSCAN_NONE; // Axis for overscan
-    pmFit overscanFit = PM_FIT_NONE;	// Fit type for overscan
+    pmFit overscanFitType = PM_FIT_NONE; // Fit type for overscan
     int overscanBins = 1;		// Number of pixels per bin for overscan
     psStats *overscanStats = NULL;	// Statistics for overscan
+    void *overscanFit = NULL;		// Overscan fit (polynomial or spline)
 
     if (psMetadataLookupBool(NULL, recipe, "MASK")) {
@@ -243,7 +244,11 @@
 	psString fit = psMetadataLookupString(NULL, recipe, "OVERSCAN.FIT");
 	if (strcasecmp(fit, "POLYNOMIAL") == 0) {
-	    overscanFit = PM_FIT_POLYNOMIAL;
+	    overscanFitType = PM_FIT_POLYNOMIAL;
+	    int order = psMetadataLookupS32(NULL, recipe, "OVERSCAN.ORDER"); // Order of polynomial fit
+	    overscanFit = psPolynomial1DAlloc(order, PS_POLYNOMIAL_ORD);
 	} else if (strcasecmp(fit, "SPLINE") == 0) {
-	    overscanFit = PM_FIT_SPLINE;
+	    overscanFitType = PM_FIT_SPLINE;
+	    int order = psMetadataLookupS32(NULL, recipe, "OVERSCAN.ORDER"); // Order of polynomial fit
+//	    overscanFit = psSpline1DAlloc(order, PS_POLYNOMIAL_ORD);
 	} else if (strcasecmp(fit, "NONE") != 0) {
 	    psLogMsg("phase2", PS_LOG_WARN, "OVERSCAN.FIT (%s) is not one of NONE, POLYNOMIAL, or SPLINE:"
@@ -297,5 +302,5 @@
 #endif
 
-    pmFPAPrint(input);
+    //pmFPAPrint(input);
 
     // Load the calibration frames, if required
@@ -475,5 +480,4 @@
 		pmReadout *inputReadout = inputReadouts->data[k]; // Readout of interest in input image
 		psImage *inputImage = inputReadout->image; // The actual image
-		psList *inputOverscans = inputReadout->overscans; // List of overscan bias regions
 
 		// Mask bad pixels
@@ -656,25 +660,24 @@
 		}
 
-		printf("mode: %d\n", overscanMode);
-
 		if (doBias || doOverscan || doDark) {
-		    void *overscanResult = NULL; // Result of overscan fit
-#ifdef PRODUCTION
-		    (void)pmSubtractBias(inputReadout, overscanResult, inputOverscans, overscanMode,
-					 overscanStats, overscanBins, overscanFit, pedestal);
-#else
-		    (void)pmSubtractBias(inputReadout, overscanResult, inputOverscans, overscanMode,
-					 overscanStats, overscanBins, overscanFit, biasReadout);
-#endif
-		    
+		    psList *inputOverscans = pmReadoutGetBias(inputReadout); // List of overscan bias regions
+#ifdef PRODUCTION
+		    (void)pmSubtractBias(inputReadout, overscanFit, inputOverscans, overscanMode,
+					 overscanStats, overscanBins, overscanFitType, pedestal);
+#else
+		    (void)pmSubtractBias(inputReadout, overscanFit, inputOverscans, overscanMode,
+					 overscanStats, overscanBins, overscanFitType, biasReadout);
+#endif
+		    psFree(inputOverscans);
+
 		    // Output overscan fit results, if required
 		    if (doOverscan) {
-			switch (overscanFit) {
+			switch (overscanFitType) {
 			  case PM_FIT_POLYNOMIAL:
 			    {
-				psPolynomial1D *poly = (psPolynomial1D*)overscanResult;	// The polynomial
+				psPolynomial1D *poly = (psPolynomial1D*)overscanFit;	// The polynomial
 				psString coeffs = NULL;	// String containing the coefficients
 				for (int i = 0; i < poly->n; i++) {
-				    psStringAppend(&coeffs, "%.2f ", poly->coeff[i]);
+				    psStringAppend(&coeffs, "%e ", poly->coeff[i]);
 				}
 				psLogMsg("phase2", PS_LOG_INFO, "Overscan polynomial coefficients:\n%s\n",
@@ -685,5 +688,5 @@
 			  case PM_FIT_SPLINE:
 			    {
-				psSpline1D *spline = (psSpline1D*)overscanResult; // The spline
+				psSpline1D *spline = (psSpline1D*)overscanFit; // The spline
 				psString coeffs = NULL;	// String containing the coefficients
 				for (int i = 0; i < spline->n; i++) {
@@ -691,5 +694,5 @@
 				    psStringAppend(&coeffs, "%d: ", i);
 				    for (int j = 0; j < poly->n; j++) {
-					psStringAppend(&coeffs, "%.2f ", poly->coeff[i]);
+					psStringAppend(&coeffs, "%e ", poly->coeff[i]);
 				    }
 				    psStringAppend(&coeffs, "\n");
@@ -755,4 +758,5 @@
     psFree(dark);
     psFree(flat);
+    psFree(overscanFit);
     psFree(overscanStats);
 
@@ -764,8 +768,10 @@
 #if 1
     for (int i = 0; i < nLeaks; i++) {
-        printf("Memory leak detection: memBlock %lld (%lld)\n"
-	       "\tFile %s, line %d, size %d\n",
-	       leaks[i]->id, leaks[i]->refCounter, leaks[i]->file, leaks[i]->lineno,
-	       leaks[i]->userMemorySize);
+	psMemBlock *mb = leaks[i];
+	printf("Memory leak %ld (%ld):\n"
+	       "\tFile %s, line %d, size %d\n"
+	       "\tPosts: %x %x %x\n",
+	       mb->id, mb->refCounter, mb->file, mb->lineno, mb->userMemorySize, mb->startblock, mb->endblock,
+	       *(void**)((int8_t *)(mb + 1) + mb->userMemorySize));
     }
 #endif
Index: /trunk/archive/scripts/src/phase2/phase2.config
===================================================================
--- /trunk/archive/scripts/src/phase2/phase2.config	(revision 5370)
+++ /trunk/archive/scripts/src/phase2/phase2.config	(revision 5371)
@@ -58,5 +58,6 @@
 # Overscan subtraction
 OVERSCAN.MODE		STR	INDIVIDUAL	# NONE | INDIVIDUAL | ALL
-OVERSCAN.FIT		STR	NONE		# NONE | POLYNOMIAL | SPLINE
-OVERSCAN.BIN		S32	4		# Number of pixels per bin
+OVERSCAN.FIT		STR	SPLINE		# NONE | POLYNOMIAL | SPLINE
+OVERSCAN.ORDER		S32	10		# Order of polynomial fit
+OVERSCAN.BIN		S32	0		# Number of pixels per bin
 OVERSCAN.STAT		STR	MEAN		# MEAN | MEDIAN
Index: /trunk/archive/scripts/src/phase2/pmFPA.c
===================================================================
--- /trunk/archive/scripts/src/phase2/pmFPA.c	(revision 5370)
+++ /trunk/archive/scripts/src/phase2/pmFPA.c	(revision 5371)
@@ -7,24 +7,57 @@
 #include "pmFPA.h"
 
+// Get the bias images for a readout, using the CELL.BIASSEC
+psList *pmReadoutGetBias(pmReadout *readout // Readout for which to get the bias sections
+    )
+{
+    pmCell *cell = readout->parent;	// The parent cell
+    psList *sections = (psList*)psMetadataLookupPtr(NULL, cell->concepts, "CELL.BIASSEC"); // CELL.BIASSEC
+
+    psImage *image = readout->image;	// The image that contains both the biassec and the trimsec
+
+    psList *images = psListAlloc(NULL);	// List of images from bias sections
+    psListIterator *sectionsIter = psListIteratorAlloc(sections, PS_LIST_HEAD, true); // Iterator
+    psRegion *region = NULL;		// Bias region from list
+    while (region = psListGetAndIncrement(sectionsIter)) {
+#if 0
+	// Convert from FITS standard to PS standard
+	// We don't touch the x1 and y1 values because they aren't included by psImageSubset.
+	region->x0 -= 1;
+	region->y0 -= 1;
+#endif
+
+	psImage *bias = psImageSubset(image, *region); // Image from bias section
+	psListAdd(images, PS_LIST_TAIL, bias);
+	psFree(bias);
+    }
+    psFree(sectionsIter);
+
+    return images;
+}
+
 //////////////////////////////////////////////////////////////////////////////////////////////////////////////
 // Allocators
 //////////////////////////////////////////////////////////////////////////////////////////////////////////////
 
-p_pmHDU *p_pmHDUAlloc(const char *extname)
-{
-    p_pmHDU *hdu = psAlloc(sizeof(p_pmHDU));
-    psMemSetDeallocator(hdu, (psFreeFunc)p_pmHDUFree);
-
-    hdu->extname = extname;
-    hdu->pixels = NULL;
-    hdu->header = NULL;
-
-    return hdu;
-}
-
-void p_pmHDUFree(p_pmHDU *hdu)
-{
-    psFree(hdu->pixels);
-    psFree(hdu->header);
+pmPixelData *pmPixelDataAlloc(const char *extname)
+{
+    pmPixelData *pd = psAlloc(sizeof(pmPixelData));
+    psMemSetDeallocator(pd, (psFreeFunc)p_pmPixelDataFree);
+
+    pd->extname = extname;
+    pd->header = NULL;
+    pd->images = NULL;
+    pd->masks = NULL;
+    pd->weights = NULL;
+
+    return pd;
+}
+
+void p_pmPixelDataFree(pmPixelData *pd)
+{
+    psFree(pd->header);
+    psFree(pd->images);
+    psFree(pd->masks);
+    psFree(pd->weights);
 }
 
@@ -44,5 +77,5 @@
     fpa->chips = psArrayAlloc(0);
 
-    fpa->private = NULL;
+    fpa->data = NULL;
 
     return fpa;
@@ -59,5 +92,5 @@
     psFree(fpa->chips);
 
-    psFree(fpa->private);
+    psFree(fpa->data);
 }
 
@@ -86,5 +119,5 @@
     chip->valid = true;    
 
-    chip->private = NULL;
+    chip->data = NULL;
 
     psMetadataAddStr(chip->concepts, PS_LIST_HEAD, "CHIP.NAME", 0, "Chip name added at pmChipAlloc", name);
@@ -101,5 +134,5 @@
     psFree(chip->cells);
 
-    psFree(chip->private);
+    psFree(chip->data);
 
     // We don't free the parent member, since that would generate a circular call.  We don't increment the
@@ -138,5 +171,5 @@
     cell->valid = true;
 
-    cell->private = NULL;
+    cell->data = NULL;
 
     return cell;
@@ -155,5 +188,5 @@
     psFree(cell->readouts);
 
-    psFree(cell->private);
+    psFree(cell->data);
 
     // We don't free the parent member, since that would generate a circular call.  We don't increment the
@@ -163,5 +196,5 @@
 pmReadout *pmReadoutAlloc(pmCell *cell, // Cell to which the readout belongs
 			  psImage *image, // The pixels
-			  psList *overscans, // The overscan images
+			  psImage *mask,// The mask pixels
 			  int col0, int row0, int colParity, int rowParity, int colBin, int rowBin // Data
     )
@@ -173,6 +206,6 @@
     // Set the components
     readout->image = psMemIncrRefCounter(image);
-    readout->mask = NULL;
-    readout->overscans = psMemIncrRefCounter(overscans);
+    readout->mask = psMemIncrRefCounter(mask);
+    readout->weight = NULL;
     
     //readout->concepts = psMetadataAlloc();
@@ -185,4 +218,6 @@
     *(int*)&readout->rowBins = rowBin;
 
+    readout->parent = cell;
+
     return readout;
 }
@@ -191,6 +226,6 @@
 {
     psFree(readout->image);
-    psFree(readout->mask); 
-    psFree(readout->overscans);
+    psFree(readout->mask);
+    psFree(readout->weight);
     //psFree(readout->concepts);
 }
Index: /trunk/archive/scripts/src/phase2/pmFPA.h
===================================================================
--- /trunk/archive/scripts/src/phase2/pmFPA.h	(revision 5370)
+++ /trunk/archive/scripts/src/phase2/pmFPA.h	(revision 5371)
@@ -11,7 +11,9 @@
 typedef struct {
     const char *extname;		// Extension name, if it corresponds to this level
-    psArray *pixels;			// The pixel data, if it corresponds to this level
     psMetadata *header;			// The FITS header, if it corresponds to this level
-} p_pmHDU;
+    psArray *images;			// The pixel data, if it corresponds to this level
+    psArray *masks;			// The mask data, if it corresponds to this level
+    psArray *weights;			// The weight data, if it corresponds to this level
+} pmPixelData;
 
 typedef struct {
@@ -25,5 +27,5 @@
     psMetadata *phu;			// Primary Header
     psArray *chips;			// The chips
-    p_pmHDU *private;			// FITS data
+    pmPixelData *data;			// FITS data
 } pmFPA;
 
@@ -40,5 +42,5 @@
     pmFPA *parent;			// Parent FPA
     bool valid;				// Valid for reading in?
-    p_pmHDU *private;			// FITS data
+    pmPixelData *data;			// FITS data
 } pmChip;
 
@@ -59,5 +61,5 @@
     pmChip *parent;			// Parent chip
     bool valid;				// Valid for operating on?
-    p_pmHDU *private;			// FITS data
+    pmPixelData *data;			// FITS data
 } pmCell;
 
@@ -72,13 +74,19 @@
     const unsigned int rowBins;		// Amount of binning in y-dimension
     // Information
+    psMetadata *concepts;		// Concepts for readouts
+    pmCell *parent;			// Parent cell
     psImage *image;			// The pixels
     psImage *mask;			// Mask image
-    psList *overscans;			// List of subimages containing the overscan regions
-    psMetadata *concepts;		// Concepts for readouts
+    psImage *weight;			// Weight image
 } pmReadout;
 
+
+psList *pmReadoutGetBias(pmReadout *readout // Readout for which to get the bias sections
+    );
+
+
 // Allocators and deallocators
-p_pmHDU *p_pmHDUAlloc(const char *extname);
-void p_pmHDUFree(p_pmHDU *hdu);
+pmPixelData *pmPixelDataAlloc(const char *extname);
+void p_pmPixelDataFree(pmPixelData *pd);
 pmFPA *pmFPAAlloc(const psMetadata *camera // Camera configuration
     );
@@ -96,7 +104,7 @@
 void p_pmCellFree(pmCell *cell);
 
-pmReadout *pmReadoutAlloc(pmCell *cell,	// Cell to which the readout belongs
+pmReadout *pmReadoutAlloc(pmCell *cell, // Cell to which the readout belongs
 			  psImage *image, // The pixels
-			  psList *overscans, // The overscan images
+			  psImage *mask,// The mask pixels
 			  int col0, int row0, int colParity, int rowParity, int colBin, int rowBin // Data
     );
Index: /trunk/archive/scripts/src/phase2/pmFPAConceptsGet.c
===================================================================
--- /trunk/archive/scripts/src/phase2/pmFPAConceptsGet.c	(revision 5370)
+++ /trunk/archive/scripts/src/phase2/pmFPAConceptsGet.c	(revision 5371)
@@ -46,6 +46,6 @@
     if (mdStatus && strlen(keyword) > 0) {
 	// We have a FITS header to look up --- search each level
-	if (cell && cell->private) {
-	    psMetadataItem *cellItem = psMetadataLookup(cell->private->header, keyword);
+	if (cell && cell->data) {
+	    psMetadataItem *cellItem = psMetadataLookup(cell->data->header, keyword);
 	    if (cellItem) {
 		// XXX: Need to clean up before returning
@@ -54,6 +54,6 @@
 	}
 
-	if (chip && chip->private) {
-	    psMetadataItem *chipItem = psMetadataLookup(chip->private->header, keyword);
+	if (chip && chip->data) {
+	    psMetadataItem *chipItem = psMetadataLookup(chip->data->header, keyword);
 	    if (chipItem) {
 		// XXX: Need to clean up before returning
@@ -62,6 +62,6 @@
 	}
 
-	if (fpa->private) {
-	    psMetadataItem *fpaItem = psMetadataLookup(fpa->private->header, keyword);
+	if (fpa->data) {
+	    psMetadataItem *fpaItem = psMetadataLookup(fpa->data->header, keyword);
 	    if (fpaItem) {
 		// XXX: Need to clean up before returning
@@ -653,10 +653,10 @@
 		} else if (strcasecmp(source, "HEADER") == 0) {
 		    psMetadata *header = NULL; // The FITS header
-		    if (cell->private) {
-			header = cell->private->header;
-		    } else if (chip->private) {
-			header = chip->private->header;
-		    } else if (fpa->private) {
-			    header = fpa->private->header;
+		    if (cell->data) {
+			header = cell->data->header;
+		    } else if (chip->data) {
+			header = chip->data->header;
+		    } else if (fpa->data) {
+			    header = fpa->data->header;
 		    }
 		    if (! header) {
@@ -718,10 +718,10 @@
 		    } else if (strcasecmp(source, "HEADER") == 0) {
 			psMetadata *header = NULL; // The FITS header
-			if (cell->private) {
-			    header = cell->private->header;
-			} else if (chip->private) {
-			    header = chip->private->header;
-			} else if (fpa->private) {
-			    header = fpa->private->header;
+			if (cell->data) {
+			    header = cell->data->header;
+			} else if (chip->data) {
+			    header = chip->data->header;
+			} else if (fpa->data) {
+			    header = fpa->data->header;
 			}
 			if (! header) {
@@ -753,4 +753,5 @@
 
 	psMetadataAdd(cell->concepts, PS_LIST_TAIL, "CELL.BIASSEC", PS_META_LIST, "Bias sections", biassecs);
+	psFree(biassecs);
     }
 
@@ -847,10 +848,10 @@
 				// timeString contains headers for the date and time
 				psMetadata *header = NULL; // The FITS header
-				if (cell->private) {
-				    header = cell->private->header;
-				} else if (chip->private) {
-				    header = chip->private->header;
-				} else if (fpa->private) {
-				    header = fpa->private->header;
+				if (cell->data) {
+				    header = cell->data->header;
+				} else if (chip->data) {
+				    header = chip->data->header;
+				} else if (fpa->data) {
+				    header = fpa->data->header;
 				}
 				if (! header) {
@@ -966,5 +967,4 @@
 	psMetadataAdd(cell->concepts, PS_LIST_TAIL, "CELL.TIME", PS_META_UNKNOWN, "Time of exposure", time);
 	psFree(time);
-
     }
 
Index: /trunk/archive/scripts/src/phase2/pmFPAConceptsSet.c
===================================================================
--- /trunk/archive/scripts/src/phase2/pmFPAConceptsSet.c	(revision 5370)
+++ /trunk/archive/scripts/src/phase2/pmFPAConceptsSet.c	(revision 5371)
@@ -130,23 +130,23 @@
 
 	// We have a FITS header to look up --- search each level
-	if (cell && cell->private) {
-	    psMetadataItem *cellItem = psMetadataLookup(cell->private->header, keyword);
+	if (cell && cell->data) {
+	    psMetadataItem *cellItem = psMetadataLookup(cell->data->header, keyword);
 	    if (cellItem) {
 		// XXX: Need to clean up before returning
-		psMetadataAddItem(cell->private->header, headerItem, PS_LIST_TAIL, PS_META_REPLACE);
+		psMetadataAddItem(cell->data->header, headerItem, PS_LIST_TAIL, PS_META_REPLACE);
 		status = true;
 	    }
-	} else if (chip && chip->private) {
-	    psMetadataItem *chipItem = psMetadataLookup(chip->private->header, keyword);
+	} else if (chip && chip->data) {
+	    psMetadataItem *chipItem = psMetadataLookup(chip->data->header, keyword);
 	    if (chipItem) {
 		// XXX: Need to clean up before returning
-		psMetadataAddItem(chip->private->header, headerItem, PS_LIST_TAIL, PS_META_REPLACE);
+		psMetadataAddItem(chip->data->header, headerItem, PS_LIST_TAIL, PS_META_REPLACE);
 		status = true;
 	    }
-	} else if (fpa->private) {
-	    psMetadataItem *fpaItem = psMetadataLookup(fpa->private->header, keyword);
+	} else if (fpa->data) {
+	    psMetadataItem *fpaItem = psMetadataLookup(fpa->data->header, keyword);
 	    if (fpaItem) {
 		// XXX: Need to clean up before returning
-		psMetadataAddItem(fpa->private->header, headerItem, PS_LIST_TAIL, PS_META_REPLACE);
+		psMetadataAddItem(fpa->data->header, headerItem, PS_LIST_TAIL, PS_META_REPLACE);
 		status = true;
 	    }
@@ -571,10 +571,10 @@
 		psString keyword = psMetadataLookupString(NULL, cell->camera, "CELL.TRIMSEC");
 		psMetadata *header = NULL; // The FITS header
-		if (cell->private) {
-		    header = cell->private->header;
-		} else if (chip->private) {
-		    header = chip->private->header;
-		} else if (fpa->private) {
-		    header = fpa->private->header;
+		if (cell->data) {
+		    header = cell->data->header;
+		} else if (chip->data) {
+		    header = chip->data->header;
+		} else if (fpa->data) {
+		    header = fpa->data->header;
 		}
 		if (! header) {
@@ -651,10 +651,10 @@
 		} else {
 		    psMetadata *header = NULL; // The FITS header
-		    if (cell->private) {
-			header = cell->private->header;
-		    } else if (chip->private) {
-			header = chip->private->header;
-		    } else if (fpa->private) {
-			header = fpa->private->header;
+		    if (cell->data) {
+			header = cell->data->header;
+		    } else if (chip->data) {
+			header = chip->data->header;
+		    } else if (fpa->data) {
+			header = fpa->data->header;
 		    }
 		    if (! header) {
@@ -707,10 +707,10 @@
 							     binString);
 	    psMetadata *header = NULL; // The FITS header
-	    if (cell->private) {
-		header = cell->private->header;
-	    } else if (chip->private) {
-		header = chip->private->header;
-	    } else if (fpa->private) {
-		header = fpa->private->header;
+	    if (cell->data) {
+		header = cell->data->header;
+	    } else if (chip->data) {
+		header = chip->data->header;
+	    } else if (fpa->data) {
+		header = fpa->data->header;
 	    }
 	    if (! header) {
@@ -784,10 +784,10 @@
 		// We're working with two separate headers
 		psMetadata *header = NULL; // The FITS header
-		if (cell->private) {
-		    header = cell->private->header;
-		} else if (chip->private) {
-		    header = chip->private->header;
-		} else if (fpa->private) {
-		    header = fpa->private->header;
+		if (cell->data) {
+		    header = cell->data->header;
+		} else if (chip->data) {
+		    header = chip->data->header;
+		} else if (fpa->data) {
+		    header = fpa->data->header;
 		}
 		if (! header) {
Index: /trunk/archive/scripts/src/phase2/pmFPAConstruct.c
===================================================================
--- /trunk/archive/scripts/src/phase2/pmFPAConstruct.c	(revision 5370)
+++ /trunk/archive/scripts/src/phase2/pmFPAConstruct.c	(revision 5371)
@@ -88,5 +88,5 @@
 		psString extName = contentItem->name; // The name of the extension
 		pmChip *chip = pmChipAlloc(fpa, extName); // The chip
-		chip->private = p_pmHDUAlloc(extName); // Prepare chip to receive FITS data
+		chip->data = pmPixelDataAlloc(extName); // Prepare chip to receive FITS data
 		if (contentItem->type != PS_META_STR) {
 		    psLogMsg(__func__, PS_LOG_WARN, "Type of content item (%x) is not string: ignored\n",
@@ -146,5 +146,5 @@
 		    pmCell *cell = pmCellAlloc(chip, cellData, extName); // The cell
 //		    psFree(cellData);
-		    cell->private = p_pmHDUAlloc(extName); // Prepare cell to receive FITS data
+		    cell->data = pmPixelDataAlloc(extName); // Prepare cell to receive FITS data
 
 		    psFree(chip);
@@ -157,5 +157,5 @@
 	} else if (strcasecmp(extType, "NONE") == 0) {
 	    // No extensions; Content contains metadata, each entry is a chip with its component cells
-	    fpa->private = p_pmHDUAlloc("PHU");	// Prepare FPA to receive FITS data
+	    fpa->data = pmPixelDataAlloc("PHU"); // Prepare FPA to receive FITS data
 	    while (contentItem = psMetadataGetAndIncrement(contentsIter)) {
 		psString chipName = contentItem->name; // The name of the chip
@@ -196,5 +196,5 @@
 	if (strcasecmp(extType, "NONE") == 0) {
 	    // There are no extensions --- only the PHU
-	    chip->private = p_pmHDUAlloc("PHU");
+	    chip->data = pmPixelDataAlloc("PHU");
 
 	    const char *contents = psMetadataLookupString(&mdStatus, camera, "CONTENTS");
@@ -247,5 +247,5 @@
 		pmCell *cell = pmCellAlloc(chip, cellData, extName); // The cell
 //		psFree(cellData);
-		cell->private = p_pmHDUAlloc(extName); // Prepare cell to receive FITS data
+		cell->data = pmPixelDataAlloc(extName); // Prepare cell to receive FITS data
 	    } // Iterating through contents
 	    psFree(contentsIter);
@@ -273,8 +273,8 @@
 {
     psTrace(__func__, 0, "FPA:\n");
-    if (fpa->private) {
-	psTrace(__func__, 1, "---> FPA is extension %s.\n", fpa->private->extname);
-	if (! fpa->private->pixels) {
-	    psTrace(__func__, 1, "---> NO PIXELS for extension %s\n", fpa->private->extname);
+    if (fpa->data) {
+	psTrace(__func__, 1, "---> FPA is extension %s.\n", fpa->data->extname);
+	if (! fpa->data->images) {
+	    psTrace(__func__, 1, "---> NO PIXELS for extension %s\n", fpa->data->extname);
 	}
     }
@@ -285,8 +285,8 @@
 	psTrace(__func__, 1, "Chip: %d\n", i);
 	pmChip *chip = chips->data[i]; // The chip
-	if (chip->private) {
-	    psTrace(__func__, 2, "---> Chip is extension %s.\n", chip->private->extname);
-	    if (! chip->private->pixels) {
-		psTrace(__func__, 2, "---> NO PIXELS for extension %s\n", chip->private->extname);
+	if (chip->data) {
+	    psTrace(__func__, 2, "---> Chip is extension %s.\n", chip->data->extname);
+	    if (! chip->data->images) {
+		psTrace(__func__, 2, "---> NO PIXELS for extension %s\n", chip->data->extname);
 	    }
 	}
@@ -296,8 +296,8 @@
 	    psTrace(__func__, 2, "Cell: %d\n", j);
 	    pmCell *cell = cells->data[j]; // The cell
-	    if (cell->private) {
-		psTrace(__func__, 3, "---> Cell is extension %s.\n", cell->private->extname);
-		if (! cell->private->pixels) {
-		    psTrace(__func__, 3, "---> NO PIXELS for extension %s\n", cell->private->extname);
+	    if (cell->data) {
+		psTrace(__func__, 3, "---> Cell is extension %s.\n", cell->data->extname);
+		if (! cell->data->images) {
+		    psTrace(__func__, 3, "---> NO PIXELS for extension %s\n", cell->data->extname);
 		}
 	    }
@@ -311,13 +311,4 @@
 			image->numCols, image->row0, image->row0 + image->numRows, image->numCols,
 			image->numRows);
-		psList *overscans = readout->overscans;	// The list of overscans
-		psListIterator *overscansIter = psListIteratorAlloc(overscans, PS_LIST_HEAD, false);
-		while (image = psListGetAndIncrement(overscansIter)) {
-		    psTrace(__func__, 4, "Overscan: [%d:%d,%d:%d] (%dx%d)\n", image->col0, image->col0 + 
-			    image->numCols, image->row0, image->row0 + image->numRows, image->numCols,
-			    image->numRows);
-		}
-		psFree(overscansIter);
-
 	    } // Iterating over cell
 	} // Iterating over chip
Index: /trunk/archive/scripts/src/phase2/pmFPARead.c
===================================================================
--- /trunk/archive/scripts/src/phase2/pmFPARead.c	(revision 5370)
+++ /trunk/archive/scripts/src/phase2/pmFPARead.c	(revision 5371)
@@ -17,9 +17,9 @@
 
 // Read a FITS extension into a chip
-static bool readExtension(p_pmHDU *hdu,	// HDU to read
+static bool readExtension(pmPixelData *pixelData, // Pixel data into which to read
 			  psFits *fits	// The FITS file from which to read
     )
 {
-    const char *extName = hdu->extname;	// Extension name
+    const char *extName = pixelData->extname; // Extension name
 
     psTrace(__func__, 7, "Moving to extension %s...\n", extName);
@@ -74,4 +74,13 @@
 	if (image->type.type != PS_TYPE_F32) {
 	    pixels->data[i] = psImageCopy(NULL, image, PS_TYPE_F32);
+
+#ifndef PRODUCTION
+	    // XXX: Temporary fix for writing images, until psFits gets cleaned up
+	    psMetadataItem *bitpixItem = psMetadataLookup(header, "BITPIX");
+	    bitpixItem->data.S32 = -32;
+	    psMetadataRemove(header, 0, "BZERO");
+	    psMetadataRemove(header, 0, "BSCALE");
+#endif
+
 	    psFree(image);
 	} else {
@@ -86,58 +95,32 @@
 
     // Update the HDU with the new data
-    hdu->pixels = pixels;
-    hdu->header = header;
+    pixelData->images = pixels;
+    pixelData->header = header;
+
+    // XXX: Insert mask and weight reading here
 
     return true;
 }
 
-
 // Portion out an image into the cell
-static bool portionCell(pmCell *cell,	// The cell that gets its bits
-			psArray *images // Array of images from which the readouts are assigned
+static bool generateReadouts(pmCell *cell, // The cell that gets its bits
+			     pmPixelData *data // Pixel data, containing image, mask, weights
     )
 {
-    bool mdStatus = false;		// Status of MD lookup
-
-    // Get the trim and bias sections
-    psMetadataItem *mdItem = psMetadataLookup(cell->concepts, "CELL.TRIMSEC");
-    psRegion *trimRegion = mdItem->data.V;
-    mdItem = psMetadataLookup(cell->concepts, "CELL.BIASSEC");
-    psList *biasRegionList = mdItem->data.V;
-
+    psArray *images = data->images;	// Array of images (each of which is a readout)
+    psArray *masks = data->masks;	// Array of masks (one for each readout)
     // Iterate over each of the image planes
     for (int i = 0; i < images->n; i++) {
 	psImage *image = images->data[i]; // The i-th plane
-
-	// Convert from FITS standard to PS standard
-	// We don't touch the x1 and y1 values because they aren't included by psImageSubset.
-	//trimRegion->x0 -= 1;
-	//trimRegion->y0 -= 1;
-
-	psImage *trimImage = psImageSubset(image, *trimRegion); // Image from trim section
-
-	psList *biasImages = psListAlloc(NULL);	// List of images from bias sections
-	psListIterator *biasRegionIter = psListIteratorAlloc(biasRegionList, PS_LIST_HEAD, true); // Iterator
-	psRegion *biasRegion = NULL;	// Bias region from list
-	while (biasRegion = psListGetAndIncrement(biasRegionIter)) {
-	    // Convert from FITS standard to PS standard
-	    // We don't touch the x1 and y1 values because they aren't included by psImageSubset.
-	    //biasRegion->x0 -= 1;
-	    //biasRegion->y0 -= 1;
-	    
-	    psImage *biasImage = psImageSubset(image, *biasRegion); // Image from bias section
-	    psListAdd(biasImages, PS_LIST_TAIL, biasImage);
-	    psFree(biasImage);
-	}
-	psFree(biasRegionIter);
-
-	pmReadout *readout = pmReadoutAlloc(cell, trimImage, biasImages, 0,0,0,0,1,1);
+	psImage *mask = NULL;		// The mask
+	if (masks) {
+	    mask = masks->data[i];
+	}
+
+	pmReadout *readout = pmReadoutAlloc(cell, image, mask, 0,0,0,0,1,1);
 	psFree(readout);		// This seems silly, but the alloc registers it with the cell, so we
 					// don't have to do anything with it.  Perhaps we should change
 					// pmReadoutAlloc to pmReadoutAdd?
-	psFree(trimImage);
-	psFree(biasImages);
-    }
-    psFree(biasRegionList);
+    }
 
     return true;
@@ -154,5 +137,5 @@
     )
 {
-    p_pmHDU *hdu = NULL;		// Current HDU from FITS file
+    pmPixelData *pixelData = NULL;	// Pixel data from FITS file
 
     // Read the PHU, if required
@@ -169,9 +152,9 @@
     // Read in....
     psTrace(__func__, 1, "Working on FPA...\n");
-    if (fpa->private) {
-	hdu = fpa->private;
-	psTrace(__func__, 3, "Reading pixels from extension %s into FPA.\n", hdu->extname);
-	if (! readExtension(hdu, fits)) {
-	    psError(PS_ERR_IO, false, "Unable to read pixels from extension %s\n", hdu->extname);
+    if (fpa->data) {
+	pixelData= fpa->data;
+	psTrace(__func__, 3, "Reading pixels from extension %s into FPA.\n", pixelData->extname);
+	if (! readExtension(pixelData, fits)) {
+	    psError(PS_ERR_IO, false, "Unable to read pixels from extension %s\n", pixelData->extname);
 	    return false;
 	}
@@ -191,9 +174,9 @@
 	psTrace(__func__, 2, "Reading in chip %d...\n", i);
 
-	if (chip->private) {
-	    hdu = chip->private;
-	    psTrace(__func__, 3, "Reading pixels from extension %s into chip %d.\n", hdu->extname, i);
-	    if (! readExtension(hdu, fits)) {
-		psError(PS_ERR_IO, false, "Unable to read pixels from extension %s\n", hdu->extname);
+	if (chip->data) {
+	    pixelData = chip->data;
+	    psTrace(__func__, 3, "Reading pixels from extension %s into chip %d.\n", pixelData->extname, i);
+	    if (! readExtension(pixelData, fits)) {
+		psError(PS_ERR_IO, false, "Unable to read pixels from extension %s\n", pixelData->extname);
 		return false;
 	    }
@@ -213,9 +196,11 @@
 	    psTrace(__func__, 3, "Reading in cell %d...\n", j);
 
-	    if (cell->private) {
-		hdu = cell->private;
-		psTrace(__func__, 5, "Reading pixels from extension %s into cell %d.\n", hdu->extname, j);
-		if (! readExtension(hdu, fits)) {
-		    psError(PS_ERR_IO, false, "Unable to read pixels from extension %s\n", hdu->extname);
+	    if (cell->data) {
+		pixelData = cell->data;
+		psTrace(__func__, 5, "Reading pixels from extension %s into cell %d.\n", pixelData->extname,
+			j);
+		if (! readExtension(pixelData, fits)) {
+		    psError(PS_ERR_IO, false, "Unable to read pixels from extension %s\n",
+			    pixelData->extname);
 		    return false;
 		}
@@ -225,5 +210,5 @@
 	    psTrace(__func__, 5, "Allocating readouts for chip %d cell %d...\n",
 		    i, j);
-	    portionCell(cell, hdu->pixels);
+	    generateReadouts(cell, pixelData);
 	}
     }
Index: /trunk/archive/scripts/src/phase2/pmFPAWrite.c
===================================================================
--- /trunk/archive/scripts/src/phase2/pmFPAWrite.c	(revision 5370)
+++ /trunk/archive/scripts/src/phase2/pmFPAWrite.c	(revision 5371)
@@ -7,10 +7,11 @@
 
 static bool writeHDU(psFits *fits,	// FITS file to which to write
-		     p_pmHDU *hdu	// HDU to write
+		     pmPixelData *pixelData // Pixel data to write
     )
 {
     bool status = true;			// Status of write, to return
-    for (int i = 0; i < hdu->pixels->n; i++) {
-	status &= psFitsWriteImage(fits, hdu->header, hdu->pixels->data[i], i);
+    for (int i = 0; i < pixelData->images->n; i++) {
+	status &= psFitsWriteImage(fits, pixelData->header, pixelData->images->data[i], i);
+	// XXX: Insert here the writing on mask and weight images
     }
 
@@ -46,12 +47,12 @@
 		    pmCellOutgestConcepts(cell, db);
 
-		    if (cell->private && strlen(cell->private->extname) > 0) {
-			status &= writeHDU(fits, cell->private);
+		    if (cell->data && strlen(cell->data->extname) > 0) {
+			status &= writeHDU(fits, cell->data);
 		    }
 		}
 	    }
 	    
-	    if (chip->private && strlen(chip->private->extname) > 0) {
-		status &= writeHDU(fits, chip->private);
+	    if (chip->data && strlen(chip->data->extname) > 0) {
+		status &= writeHDU(fits, chip->data);
 	    }
 	}
@@ -59,6 +60,6 @@
     }
 
-    if (fpa->private && strlen(fpa->private->extname) > 0) {
-	status &= writeHDU(fits, fpa->private);
+    if (fpa->data && strlen(fpa->data->extname) > 0) {
+	status &= writeHDU(fits, fpa->data);
     }
 
