Index: /trunk/Ohana/src/addstar/src/mkcmf.c
===================================================================
--- /trunk/Ohana/src/addstar/src/mkcmf.c	(revision 39010)
+++ /trunk/Ohana/src/addstar/src/mkcmf.c	(revision 39011)
@@ -22,4 +22,5 @@
 void writeStars_PS1_V1 (FTable *ftable, double *X, double *Y, double *M, int Nstars);
 void writeStars_PS1_SV3 (FTable *ftable, double *X, double *Y, double *M, unsigned int *Flag, int Nstars);
+void writeStars_PS1_DV5 (FTable *ftable, double *X, double *Y, double *M, unsigned int *Flag, int Nstars);
 void writeStars_PS1_DEV_1 (FTable *ftable, double *X, double *Y, double *M, int Nstars);
 void writeStars_PS1_DEV_0 (FTable *ftable, double *X, double *Y, double *M, int Nstars);
@@ -61,4 +62,5 @@
   int isStack = FALSE;
   int isForcedWarp = FALSE;
+  int isDiff  = FALSE;
   int WriteXSRC = FALSE;
   int WriteXFIT = FALSE;
@@ -75,6 +77,14 @@
     isForcedWarp = TRUE;
   }
-
-  if (!isStack && !isForcedWarp) {
+  if ((N = get_argument (argc, argv, "-diff"))) {
+    remove_argument (N, &argc, argv);
+    WriteXSRC = FALSE;
+    WriteXFIT = TRUE;
+    WriteXRAD = FALSE;
+    WriteDETF = TRUE;
+    isDiff = TRUE;
+  }
+  
+  if (!isStack && !isForcedWarp && !isDiff) {
     WriteDETF = TRUE;
   }
@@ -248,5 +258,5 @@
   coords.crpix2 = CRPIX2;
   
-  if (isStack || isForcedWarp) {
+  if (isStack || isForcedWarp || isDiff) {
     coords.cdelt1 = 0.25/3600.0;
     coords.cdelt2 = 0.25/3600.0;
@@ -399,5 +409,13 @@
     gfits_modify (&header, "PHOT_V",                "%s", 1, "38100");
   }
-
+  if (isDiff) {
+    gfits_modify (&header, "HIERARCH FPA.ZP",  "%f", 1, zeroPt);
+    gfits_modify (&header, "HIERARCH PPSUB.INPUT", "%s", 1, "o5076g0214o.93155.wrp.1221054.skycell.2289.079.fits");
+    gfits_modify (&header, "HIERARCH PPSUB.REFERENCE", "%s", 1, "RINGS.V3.skycell.2289.079.stk.4063469.unconv.fits");
+    gfits_modify (&header, "PHOT_V",              "%s", 1, "38100");
+    // CZW There are other fields, but they don't appear to be used by ipp2psps.
+  }
+
+  
   int i;
   for (i = 1; i < 32; i++) {
@@ -443,4 +461,8 @@
   if (!strcmp(type, "PS1_SV3")) {
     writeStars_PS1_SV3 (&ftable, X, Y, M, Flag, Nstars); 
+    found = TRUE;
+  }
+  if (!strcmp(type, "PS1_DV5")) {
+    writeStars_PS1_DV5 (&ftable, X, Y, M, Flag, Nstars);
     found = TRUE;
   }
@@ -1115,4 +1137,119 @@
 }
 
+void writeStars_PS1_DV5 (FTable *ftable, double *X, double *Y, double *M, unsigned int *Flag, int Nstars) {
+
+  int i;
+  CMF_PS1_DV5 *stars;
+  float flux, fSN;
+
+  ALLOCATE(stars, CMF_PS1_DV5, Nstars);
+  for (i = 0; i < Nstars; i++) {
+    flux = pow(10.0, -0.4*M[i]);
+    fSN = 1.0 / sqrt(flux);
+
+    if (ADDNOISE) {
+      X[i] += FX * fSN * rnd_gauss(0.0, 1.0);
+      Y[i] += FY * fSN * rnd_gauss(0.0, 1.0);
+      M[i] += fSN * rnd_gauss(0.0, 1.0);
+      flux = pow(10.0, -0.4 * M[i]);
+      fSN = 1.0 / sqrt(flux);
+    }
+
+    stars[i].detID = i;
+    stars[i].X = X[i];
+    stars[i].Y = Y[i];
+    stars[i].dX = FX * fSN;
+    stars[i].dY = FY * fSN;
+
+    stars[i].posangle = 10.0;
+    stars[i].pltscale = 0.25;
+
+    stars[i].M = M[i];
+    stars[i].dM = fSN;
+
+    stars[i].Flux = flux;
+    stars[i].dFlux = flux * fSN;
+
+    stars[i].Map = M[i] - 0.05;
+    stars[i].MapRaw = M[i] - 0.10;
+
+    stars[i].apRadius = 8.0;
+
+    stars[i].apFlux = pow(10.0, -0.4 * stars[i].Map);
+    stars[i].apFluxErr = stars[i].apFlux * fSN;
+
+    stars[i].Mpeak = M[i] + 1.0;
+    
+    stars[i].Mcalib = M[i] + ZERO_POINT + 2.5 * log10(exptime);
+    stars[i].dMcal  = 0.05;
+
+    XY_to_RD(&stars[i].RA, &stars[i].DEC, X[i], Y[i], &coords);
+
+    stars[i].sky = SKY;
+    stars[i].dSky = DSKY;
+    stars[i].psfChisq = PSFCHI;
+    stars[i].crNsigma = CRN;
+    stars[i].extNsigma = EXTN;
+    stars[i].fx = FX;
+    stars[i].fy = FY;
+    stars[i].df  = DF;
+    
+    if ((BAD_PSFQF_FRAC > 0.0) && (drand48() < BAD_PSFQF_FRAC)) {
+      stars[i].psfQF = 0.25;
+      stars[i].psfQFperf = 0.24;
+    } else {
+      stars[i].psfQF = PSFQUAL;
+      stars[i].psfQFperf = MAX(PSFQUAL - 0.01, 0.0);
+    }
+
+    stars[i].psfNdof = 1;
+    stars[i].psfNpix = 2;
+
+    stars[i].Mxx = FX;
+    stars[i].Mxy = 0.01;
+    stars[i].Myy = FX;
+    stars[i].Mr1 = FX;
+    stars[i].Mrh = FX;
+
+    stars[i].kronFlux = flux * 1.25;
+    stars[i].kronFluxErr = fSN * flux * 1.25;
+
+    stars[i].kronInner = fSN * flux * 0.9;
+    stars[i].kronOuter = fSN * flux * 1.5;
+
+    stars[i].chipNum = 1;
+    stars[i].chipX   = (short) (floor( stars[i].X));
+    stars[i].chipY   = (short) (floor( stars[i].Y));
+    
+    if ((BAD_PSFQF_FRAC > 0.0) && (drand48() < BAD_PSFQF_FRAC)) {
+      stars[i].D_Npos = 1;
+      stars[i].D_Fratio = 0.5;
+      stars[i].D_Nratio_bad = 0.5;
+      stars[i].D_Nratio_mask = 0.0;
+      stars[i].D_Nratio_all = 0.5;
+    }
+    else {
+      stars[i].D_Npos = 2;
+      stars[i].D_Fratio = 1.0;
+      stars[i].D_Nratio_bad = 1.0;
+      stars[i].D_Nratio_mask = 0.0;
+      stars[i].D_Nratio_all = 1.0;
+    }      
+    stars[i].D_Rp = 10.2;
+    stars[i].D_SNp = 844.6;
+    stars[i].D_Rm = 12.24;
+    stars[i].D_SNm = 983.145;
+
+    stars[i].flags = Flag[i];
+    stars[i].flags2 = 0x80;
+
+    stars[i].nFrames = 1;
+  }
+
+  gfits_table_set_CMF_PS1_DV5(ftable, stars, Nstars, TRUE);
+  gfits_modify (ftable->header, "EXTTYPE", "%s", 1, "PS1_DV5");
+}
+    
+    
 void writeStars_PS1_V5_Lensing (FTable *ftable, double *X, double *Y, double *M, unsigned int *Flag, int Nstars) {
 
