Index: /trunk/psLib/psLib.kdevelop.filelist
===================================================================
--- /trunk/psLib/psLib.kdevelop.filelist	(revision 1983)
+++ /trunk/psLib/psLib.kdevelop.filelist	(revision 1984)
@@ -447,2 +447,3 @@
 CVS/Repository
 CVS/Root
+test/image/tst_psImageConvolve.c
Index: /trunk/psLib/psLib.kdevses
===================================================================
--- /trunk/psLib/psLib.kdevses	(revision 1983)
+++ /trunk/psLib/psLib.kdevses	(revision 1984)
@@ -3,32 +3,32 @@
 <KDevPrjSession>
  <DocsAndViews NumberOfDocuments="6" >
-  <Doc0 NumberOfViews="1" URL="file:/home/desonia/psLib/src/image/psImageExtraction.h" >
-   <View0 line="0" Type="???" >
-    <AdditionalSettings Top="1" Width="1138" Attach="1" Height="702" Left="1" MinMaxMode="0" />
+  <Doc0 NumberOfViews="1" URL="file:/home/desonia/psLib/src/image/psImageConvolve.c" >
+   <View0 line="412" Type="???" >
+    <AdditionalSettings Top="2" Width="1181" Attach="1" Height="701" Left="2" MinMaxMode="0" />
    </View0>
   </Doc0>
-  <Doc1 NumberOfViews="1" URL="file:/home/desonia/psLib/src/image/psImageExtraction.c" >
-   <View0 line="151" Type="???" >
-    <AdditionalSettings Top="1" Width="1530" Attach="1" Height="998" Left="1" MinMaxMode="0" />
+  <Doc1 NumberOfViews="1" URL="file:/home/desonia/psLib/src/image/psImageFFT.c" >
+   <View0 line="36" Type="???" >
+    <AdditionalSettings Top="2" Width="1181" Attach="1" Height="701" Left="2" MinMaxMode="0" />
    </View0>
   </Doc1>
-  <Doc2 NumberOfViews="1" URL="file:/home/desonia/psLib/test/image/tst_psImageExtraction.c" >
-   <View0 line="523" Type="???" >
-    <AdditionalSettings Top="1" Width="1138" Attach="1" Height="675" Left="1" MinMaxMode="0" />
+  <Doc2 NumberOfViews="1" URL="file:/home/desonia/psLib/src/dataManip/psVectorFFT.h" >
+   <View0 line="31" Type="???" >
+    <AdditionalSettings Top="2" Width="1181" Attach="1" Height="701" Left="2" MinMaxMode="0" />
    </View0>
   </Doc2>
-  <Doc3 NumberOfViews="1" URL="file:/home/desonia/psLib/test/image/tst_psImageManip.c" >
-   <View0 line="45" Type="???" >
-    <AdditionalSettings Top="1" Width="1138" Attach="1" Height="675" Left="1" MinMaxMode="0" />
+  <Doc3 NumberOfViews="1" URL="file:/home/desonia/psLib/src/image/psImageErrors.dat" >
+   <View0 line="44" Type="???" >
+    <AdditionalSettings Top="2" Width="1181" Attach="1" Height="701" Left="2" MinMaxMode="0" />
    </View0>
   </Doc3>
-  <Doc4 NumberOfViews="1" URL="file:/home/desonia/psLib/test/image/tst_psImage.c" >
-   <View0 line="23" Type="???" >
-    <AdditionalSettings Top="1" Width="1138" Attach="1" Height="675" Left="1" MinMaxMode="0" />
+  <Doc4 NumberOfViews="1" URL="file:/home/desonia/psLib/test/image/tst_psImageConvolve.c" >
+   <View0 line="386" Type="???" >
+    <AdditionalSettings Top="2" Width="1181" Attach="1" Height="701" Left="2" MinMaxMode="0" />
    </View0>
   </Doc4>
-  <Doc5 NumberOfViews="1" URL="file:/home/desonia/psLib/src/image/psImageErrors.dat" >
-   <View0 line="15" Type="???" >
-    <AdditionalSettings Top="1" Width="1532" Attach="1" Height="991" Left="1" MinMaxMode="0" />
+  <Doc5 NumberOfViews="1" URL="file:/home/desonia/psLib/src/collections/psVector.c" >
+   <View0 line="86" Type="???" >
+    <AdditionalSettings Top="2" Width="1181" Attach="1" Height="701" Left="2" MinMaxMode="0" />
    </View0>
   </Doc5>
Index: /trunk/psLib/src/dataManip/psVectorFFT.h
===================================================================
--- /trunk/psLib/src/dataManip/psVectorFFT.h	(revision 1983)
+++ /trunk/psLib/src/dataManip/psVectorFFT.h	(revision 1984)
@@ -7,6 +7,6 @@
  *  @author Robert DeSonia, MHPCC
  *
- *  @version $Revision: 1.14 $ $Name: not supported by cvs2svn $
- *  @date $Date: 2004-08-25 21:10:08 $
+ *  @version $Revision: 1.15 $ $Name: not supported by cvs2svn $
+ *  @date $Date: 2004-10-06 21:40:13 $
  *
  *  Copyright 2004 Maui High Performance Computing Center, University of Hawaii
@@ -24,8 +24,11 @@
 typedef enum {
     /// psImageFFT/psVectorFFT should perform a forward FFT.
-    PS_FFT_FORWARD = (-1),
+    PS_FFT_FORWARD = 1,
 
     /// psImageFFT/psVectorFFT should perform a reverse FFT.
-    PS_FFT_REVERSE = (+1)
+    PS_FFT_REVERSE = 2,
+
+    /// psImageFFT/psVectorFFT should perform a reverse FFT with a real result.
+    PS_FFT_REAL_RESULT = 4
 } psFftDirection;
 
Index: /trunk/psLib/src/fft/psVectorFFT.h
===================================================================
--- /trunk/psLib/src/fft/psVectorFFT.h	(revision 1983)
+++ /trunk/psLib/src/fft/psVectorFFT.h	(revision 1984)
@@ -7,6 +7,6 @@
  *  @author Robert DeSonia, MHPCC
  *
- *  @version $Revision: 1.14 $ $Name: not supported by cvs2svn $
- *  @date $Date: 2004-08-25 21:10:08 $
+ *  @version $Revision: 1.15 $ $Name: not supported by cvs2svn $
+ *  @date $Date: 2004-10-06 21:40:13 $
  *
  *  Copyright 2004 Maui High Performance Computing Center, University of Hawaii
@@ -24,8 +24,11 @@
 typedef enum {
     /// psImageFFT/psVectorFFT should perform a forward FFT.
-    PS_FFT_FORWARD = (-1),
+    PS_FFT_FORWARD = 1,
 
     /// psImageFFT/psVectorFFT should perform a reverse FFT.
-    PS_FFT_REVERSE = (+1)
+    PS_FFT_REVERSE = 2,
+
+    /// psImageFFT/psVectorFFT should perform a reverse FFT with a real result.
+    PS_FFT_REAL_RESULT = 4
 } psFftDirection;
 
Index: /trunk/psLib/src/sys/psType.h
===================================================================
--- /trunk/psLib/src/sys/psType.h	(revision 1983)
+++ /trunk/psLib/src/sys/psType.h	(revision 1984)
@@ -11,6 +11,6 @@
 *  @author Ross Harman, MHPCC
 *
-*  @version $Revision: 1.21 $ $Name: not supported by cvs2svn $
-*  @date $Date: 2004-09-21 22:30:19 $
+*  @version $Revision: 1.22 $ $Name: not supported by cvs2svn $
+*  @date $Date: 2004-10-06 21:40:13 $
 *
 *  Copyright 2004 Maui High Performance Computing Center, University of Hawaii
@@ -50,6 +50,6 @@
 typedef float psF32;                   ///< 32-bit floating point
 typedef double psF64;                  ///< 64-bit floating point
-typedef complex float psC32;           ///< complex with 32-bit floating point Real and Imagary numbers
-typedef complex double psC64;          ///< complex with 64-bit floating point Real and Imagary numbers
+typedef float _Complex psC32;          ///< complex with 32-bit floating point Real and Imagary numbers
+typedef double _Complex psC64;         ///< complex with 64-bit floating point Real and Imagary numbers
 typedef void *psPTR;                   ///< void pointer
 
Index: /trunk/psLib/src/sysUtils/psType.h
===================================================================
--- /trunk/psLib/src/sysUtils/psType.h	(revision 1983)
+++ /trunk/psLib/src/sysUtils/psType.h	(revision 1984)
@@ -11,6 +11,6 @@
 *  @author Ross Harman, MHPCC
 *
-*  @version $Revision: 1.21 $ $Name: not supported by cvs2svn $
-*  @date $Date: 2004-09-21 22:30:19 $
+*  @version $Revision: 1.22 $ $Name: not supported by cvs2svn $
+*  @date $Date: 2004-10-06 21:40:13 $
 *
 *  Copyright 2004 Maui High Performance Computing Center, University of Hawaii
@@ -50,6 +50,6 @@
 typedef float psF32;                   ///< 32-bit floating point
 typedef double psF64;                  ///< 64-bit floating point
-typedef complex float psC32;           ///< complex with 32-bit floating point Real and Imagary numbers
-typedef complex double psC64;          ///< complex with 64-bit floating point Real and Imagary numbers
+typedef float _Complex psC32;          ///< complex with 32-bit floating point Real and Imagary numbers
+typedef double _Complex psC64;         ///< complex with 64-bit floating point Real and Imagary numbers
 typedef void *psPTR;                   ///< void pointer
 
Index: /trunk/psLib/test/dataManip/verified/tst_psMinimize04.stderr
===================================================================
--- /trunk/psLib/test/dataManip/verified/tst_psMinimize04.stderr	(revision 1983)
+++ /trunk/psLib/test/dataManip/verified/tst_psMinimize04.stderr	(revision 1984)
@@ -2,3 +2,3 @@
     Following should generate an error for null input polynomial.
 <DATE><TIME>|<HOST>|E|psVectorFitPolynomial1D
-    Invalid operation: myPoly or its coeffs is NULL.
+    Unallowable operation: myPoly or its coeffs is NULL.
Index: /trunk/psLib/test/image/tst_psImageConvolve.c
===================================================================
--- /trunk/psLib/test/image/tst_psImageConvolve.c	(revision 1983)
+++ /trunk/psLib/test/image/tst_psImageConvolve.c	(revision 1984)
@@ -5,6 +5,6 @@
  *  @author Robert DeSonia, MHPCC
  *
- *  @version $Revision: 1.3 $ $Name: not supported by cvs2svn $
- *  @date $Date: 2004-10-01 20:58:32 $
+ *  @version $Revision: 1.4 $ $Name: not supported by cvs2svn $
+ *  @date $Date: 2004-10-06 21:40:13 $
  *
  *  Copyright 2004 Maui High Performance Computing Center, University of Hawaii
@@ -22,8 +22,10 @@
 static int testKernelAlloc(void);
 static int testKernelGenerate(void);
+static int testImageConvolve(void);
 
 testDescription tests[] = {
                               {testKernelAlloc,731,"psKernelAlloc",0,false},
                               {testKernelGenerate,732,"psKernelGenerate",0,false},
+                              {testImageConvolve,733,"psImageConvolve",0,false},
                               {NULL}
                           };
@@ -287,2 +289,165 @@
     return 0;
 }
+
+static int testImageConvolve(void)
+{
+    const int r = 200;
+    const int c = 300;
+    int sum;
+
+    // approximate a normalized gaussian kernel.
+    psKernel* g = psKernelAlloc(-1,1,-1,1);
+    g->kernel[-1][-1] =
+        g->kernel[-1][1] =
+            g->kernel[1][-1] =
+                g->kernel[1][1] = 0.0113;
+    g->kernel[1][0] =
+        g->kernel[-1][0] =
+            g->kernel[0][-1] =
+                g->kernel[0][1] = 0.0838;
+    g->kernel[0][0] = 0.6193;
+
+    // create a normalized non-symetric kernel.
+    psKernel* nsk = psKernelAlloc(0,2,0,2);
+    sum = 0.0;
+    for (int i=0;i<2;i++) {
+        for (int j=0;j<2;j++) {
+            nsk->kernel[i][j] = i+j;
+            sum = i+j;
+        }
+    }
+    for (int i=0;i<2;i++) {
+        for (int j=0;j<2;j++) {
+            nsk->kernel[i][j] /= sum;
+        }
+    }
+
+
+    psImage* img = psImageAlloc(c,r,PS_TYPE_F32);
+    memset(img->data.F32[0],0,c*r*PSELEMTYPE_SIZEOF(PS_TYPE_F32));
+    img->data.F32[0][0] = 1.0f;
+    img->data.F32[r/2][c/2] = 1.0f;
+    img->data.F32[r-1][c/2] = 1.0f;
+
+    // test spacial convolution of gaussian
+    psLogMsg(__func__,PS_LOG_INFO,"Testing direct gaussian convolution");
+    psImage* out = psImageConvolve(NULL, img, g, true);
+
+    if (out == NULL) {
+        psError(__func__, "psImageConvolve returned a NULL for direct gaussian case.");
+        return 1;
+    }
+
+    if (out->numCols != c || out->numRows != r) {
+        psError(__func__, "psImageConvolve result image is %dx%d, but expected %dx%d.",
+                out->numCols, out->numRows,
+                c,r);
+        return 2;
+    }
+
+    if (out->type.type != PS_TYPE_F32) {
+        char* typeStr;
+        PS_TYPE_NAME(typeStr,out->type.type);
+        psError(__func__, "psImageConvolve result image is of type %s, not psF32.",
+                typeStr);
+        return 3;
+    }
+
+    // test values
+    for (int i=-1;i<1;i++) {
+        for (int j=-1;j<1;j++) {
+            if (fabsf(out->data.F32[r/2+i][c/2+j] - g->kernel[i][j]) > 0.0001) {
+                psError(__func__,"Convolved image wrong at %d,%d.  Value is %g, expected %g.",
+                        c/2+j,r/2+i,
+                        out->data.F32[r/2+i][c/2+j], g->kernel[i][j]);
+                return 4;
+            }
+            if (i >= 0 && j >= 0 && fabsf(out->data.F32[i][j] - g->kernel[i][j]) > 0.0001) {
+                psError(__func__,"Convolved image wrong at %d,%d.  Value is %g, expected %g.",
+                        j,i,
+                        out->data.F32[i][j], g->kernel[i][j]);
+                return 5;
+            }
+            if (i <= 0 && fabsf(out->data.F32[r-1+i][c/2+j] - g->kernel[i][j]) > 0.0001) {
+                psError(__func__,"Convolved image wrong at %d,%d.  Value is %g, expected %g.",
+                        c/2+j,r-1+i,
+                        out->data.F32[r-1+i][c/2+j], g->kernel[i][j]);
+                return 6;
+            }
+        }
+    }
+
+    // test fourier convolution of gaussian
+    psLogMsg(__func__,PS_LOG_INFO,"Testing fourier gaussian convolution");
+    psKernel* gg = psKernelAlloc(1,3,1,3);
+    gg->kernel[1][1] =
+        gg->kernel[1][3] =
+            gg->kernel[3][1] =
+                gg->kernel[3][3] = 0.0113;
+    gg->kernel[3][2] =
+        gg->kernel[1][2] =
+            gg->kernel[2][1] =
+                gg->kernel[2][3] = 0.0838;
+    gg->kernel[2][2] = 0.6193;
+    img->data.F32[0][0] = 0.0f;
+    img->data.F32[r/2][c/2] = 1.0f;
+    img->data.F32[r-1][c/2] = 0.0f;
+    psImage* out2 = psImageConvolve(out, img, gg, false);
+
+    if (out == NULL) {
+        psError(__func__, "psImageConvolve returned a NULL for gaussian case.");
+        return 10;
+    }
+
+    if (out != out2) {
+        psError(__func__, "psImageConvolve didn't recycle the supplied out image struct.");
+        return 11;
+    }
+
+    if (out->numCols != c || out->numRows != r) {
+        psError(__func__, "psImageConvolve result image is %dx%d, but expected %dx%d.",
+                out->numCols, out->numRows,
+                c,r);
+        return 12;
+    }
+
+    if (out->type.type != PS_TYPE_F32) {
+        char* typeStr;
+        PS_TYPE_NAME(typeStr,out->type.type);
+        psError(__func__, "psImageConvolve result image is of type %s, not psF32.",
+                typeStr);
+        return 13;
+    }
+
+    psImageWriteSection(out2,0,0,0,NULL,0,"out2.fits");
+    // test values
+    for (int i=-1;i<1;i++) {
+        for (int j=-1;j<1;j++) {
+            if (fabsf(out->data.F32[r/2+i][c/2+j] - g->kernel[i][j]) > 0.0001) {
+                psError(__func__,"Convolved image wrong at %d,%d.  Value is %g, expected %g.",
+                        c/2+j,r/2+i,
+                        out->data.F32[r/2+i][c/2+j], g->kernel[i][j]);
+                psImageWriteSection(out,0,0,0,NULL,0,"problem.fits");
+                return 14;
+            }
+            if (i >= 0 && j >= 0 && fabsf(out->data.F32[i][j] - g->kernel[i][j]) > 0.0001) {
+                psError(__func__,"Convolved image wrong at %d,%d.  Value is %g, expected %g.",
+                        j,i,
+                        out->data.F32[i][j], g->kernel[i][j]);
+                return 15;
+            }
+            if (i <= 0 && fabsf(out->data.F32[r-1+i][c/2+j] - g->kernel[i][j]) > 0.0001) {
+                psError(__func__,"Convolved image wrong at %d,%d.  Value is %g, expected %g.",
+                        c/2+j,r-1+i,
+                        out->data.F32[r-1+i][c/2+j], g->kernel[i][j]);
+                return 16;
+            }
+        }
+    }
+
+    psFree(g);
+    psFree(img);
+    psFree(nsk);
+    psFree(out);
+    return 0;
+}
Index: /trunk/psLib/test/image/tst_psImageFFT.c
===================================================================
--- /trunk/psLib/test/image/tst_psImageFFT.c	(revision 1983)
+++ /trunk/psLib/test/image/tst_psImageFFT.c	(revision 1984)
@@ -6,6 +6,6 @@
  *  @author Robert DeSonia, MHPCC
  *
- *  @version $Revision: 1.9 $ $Name: not supported by cvs2svn $
- *  @date $Date: 2004-10-06 19:36:30 $
+ *  @version $Revision: 1.10 $ $Name: not supported by cvs2svn $
+ *  @date $Date: 2004-10-06 21:40:13 $
  *
  *  Copyright 2004 Maui High Performance Computing Center, University of Hawaii
@@ -88,4 +88,9 @@
         return 1;
     }
+    if (img2->numCols != m || img2->numRows != n) {
+        psError(__func__,"FFT didn't produce proper size result (%dx%d vs. expected %dx%d).",
+                img2->numCols,img2->numRows,m,n);
+        return 2;
+    }
 
     // 3. verify that the only significant component cooresponds to the freqency of the input in step 1.
@@ -99,4 +104,5 @@
                         && ! (row == 0 && (col==1 || col == n-1)) ) {
                     psError(__func__,"Result invalid at %d,%d (%.2f)",col,row,mag);
+                    return 3;
                 }
             } else
@@ -104,4 +110,5 @@
                         || (row == 0 && (col==1 || col == n-1)) ) {
                     psError(__func__,"Result invalid at %d,%d (%.2f)",col,row,mag);
+                    return 4;
                 }
         }
@@ -114,5 +121,11 @@
     if (img3->type.type != PS_TYPE_C32) {
         psError(__func__,"FFT didn't produce complex values?");
-        return 4;
+        return 5;
+    }
+
+    if (img3->numCols != m || img3->numRows != n) {
+        psError(__func__,"FFT didn't produce proper size result (%dx%d vs. expected %dx%d).",
+                img3->numCols,img3->numRows,m,n);
+        return 6;
     }
 
@@ -125,7 +138,49 @@
                 psError(__func__,"Reverse FFT didn't give original image back (%d,%d %.2f vs %.2f)",
                         col,row,pixel,imgRow[col]);
-                return 5;
-            }
-        }
+                return 7;
+            }
+        }
+    }
+
+    // 4. perform a reverse transform to real result
+    img3 = psImageFFT(img3,img2,PS_FFT_REVERSE|PS_FFT_REAL_RESULT);
+
+    if (img3->type.type != PS_TYPE_F32) {
+        char* typeStr;
+        PS_TYPE_NAME(typeStr,img3->type.type)
+        psError(__func__,"FFT asked to make real result, but I got a %s type image?",typeStr);
+        return 8;
+    }
+
+    if (img3->numCols != m || img3->numRows != n) {
+        psError(__func__,"FFT didn't produce proper size result (%dx%d vs. expected %dx%d).",
+                img3->numCols,img3->numRows,m,n);
+        return 9;
+    }
+
+    for (unsigned int row=0;row<n;row++) {
+        psF32* img3Row = img3->data.F32[row];
+        psF32* imgRow = img->data.F32[row];
+        for (unsigned int col=0;col<m;col++) {
+            psF32 pixel = img3Row[col]/m/n;
+            if (fabsf(pixel-imgRow[col]) > 0.1) {
+                psError(__func__,"Reverse FFT didn't give original image back (%d,%d %.2f vs %.2f)",
+                        col,row,pixel,imgRow[col]);
+                return 10;
+            }
+        }
+    }
+
+    // check if error occurs if FORWARD and REVERSE are both given.
+    psLogMsg(__func__,PS_LOG_INFO,"Following should be an error.");
+    if (psImageFFT(NULL,img2,PS_FFT_REVERSE|PS_FFT_FORWARD) != NULL) {
+        psError(__func__,"PS_FFT_REVERSE|PS_FFT_FORWARD option produced something?");
+        return 11;
+    }
+
+    psLogMsg(__func__,PS_LOG_INFO,"Following should be an error.");
+    if (psImageFFT(NULL,img2,PS_FFT_FORWARD|PS_FFT_REAL_RESULT) != NULL) {
+        psError(__func__,"PS_FFT_FORWARD|PS_FFT_REAL_RESULT option produced something?");
+        return 12;
     }
 
