Index: trunk/psastro/src/psastroMosaicGradients.c
===================================================================
--- trunk/psastro/src/psastroMosaicGradients.c	(revision 10830)
+++ trunk/psastro/src/psastroMosaicGradients.c	(revision 10880)
@@ -1,6 +1,7 @@
 # include "psastro.h"
 
-psArray *psastroMosaicGradients (pmFPA *fpa, psMetadata *recipe) {
+bool psastroMosaicGradients (pmFPA *fpa, psMetadata *recipe) {
 
+    bool status;
     pmChip *chip = NULL;
     pmCell *cell = NULL;
@@ -36,9 +37,32 @@
 
 		// measure the local gradients for this set of stars
-		// XXX update the function prototype to accept an incoming gradient structure to which the new elements are added
 		gradients = pmAstromMeasureGradients (gradients, rawstars, refstars, match, recipe);
 	    }
 	}
     }
-    return (gradients);
+
+    // allocate mosaic-level polynomial transformation and set masks needed by DVO
+    int order = psMetadataLookupF32 (&status, recipe, "PSASTRO.MOSAIC.ORDER");
+    if (!status) {
+	psError(PSASTRO_ERR_UNKNOWN, false, "failed to find single-chip fit order\n");
+        return false;
+    }
+    psFree (fpa->toTPA);
+    fpa->toTPA = psPlaneTransformAlloc (order, order);
+    for (int i = 0; i <= fpa->toTPA->x->nX; i++) {
+        for (int j = 0; j <= fpa->toTPA->x->nY; j++) {
+            if (i + j > order) {
+		fpa->toTPA->x->mask[i][j] = 1;
+		fpa->toTPA->y->mask[i][j] = 1;
+            }
+        }
+    }
+
+    // fit the measured gradients with the telescope distortion model (polynomial order based on toTPA)
+    pmAstromFitDistortion (fpa, gradients, recipe);
+    psastroMosaicSetAstrom (fpa);
+
+    psFree (gradients);
+    psFree (view);
+    return true;
 }
