Index: /trunk/doc/pslib/psLibSDRS.tex
===================================================================
--- /trunk/doc/pslib/psLibSDRS.tex	(revision 1414)
+++ /trunk/doc/pslib/psLibSDRS.tex	(revision 1415)
@@ -1,3 +1,3 @@
-%%% $Id: psLibSDRS.tex,v 1.62 2004-08-06 19:06:36 eugene Exp $
+%%% $Id: psLibSDRS.tex,v 1.63 2004-08-07 04:11:59 price Exp $
 \documentclass[panstarrs,spec]{panstarrs}
 
@@ -32,4 +32,6 @@
 01 & 2004 May 19 & Extensive modifications, see appendix \\ \hline
 02 & 2004 Jun 22 & Incorporation of Bugzilla PRs (up to 69) \\ \hline
+03 & 2004 Aug 06 & Adding convolution, splines, chebyshevs \\
+   &             & (modified polynomials), ImageTrim for Phase 2 \\ \hline
 \RevisionsEnd
 
@@ -1885,5 +1887,5 @@
 \subsection{Analytical functions}
 
-\subsubsection{General Polynomials}
+\subsubsection{Polynomials}
 
 PSLib provides APIs to represent and interact with polynomials in up
@@ -2630,4 +2632,116 @@
 psImage *psImagePowerSpectrum(psImage *out, const psImage *in);
 \end{verbatim}
+
+%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
+
+\subsubsection{Convolution}
+
+Convolution will be an essential operation for the IPP.  For example,
+if images on the sky are obtained in Orthogonal Transfer (OT) mode,
+then the calibration frames used to correct them must be convolved by
+a kernel derived from the list of OT shifts made during the exposure.
+Also, convolution is also required for object detection and
+PSF-matching.
+
+\subsubsubsection{Kernel definition}
+
+In order to perform a convolution, we need to define the convolution
+kernel.  We need a more general object than a \code{psImage} so that
+we can incorporate the offset from the $(0,0)$ pixel to the $(0,0)$
+value of the kernel.  It might be convenient to allow both positive
+and negative indices to convey the positive and negative shifts.  One
+might consider setting the \code{x0} and \code{y0} members of a
+\code{psImage} to the appropriate offsets, but this is not the purpose
+of these members, and doing so may affect the behavior of other
+\code{psImage} operations.  We define a \code{psKernel}:
+
+\begin{verbatim}
+/** A convolution kernel */
+typedef struct {
+    psImage *data;                      ///< Kernel data, in the form of an image
+    int xMin, yMin;                     ///< Most negative indices
+    int xMax, yMax;                     ///< Most positive indices
+    float **kernelRows;                 ///< Pointer to the rows of the kernel data
+    float **kernel;                     ///< Pointer to  in the kernel data
+} psKernel;
+\end{verbatim}
+
+The kernel data is carried primarily by the \code{data} member which
+is a normal \code{psImage}.  In order to allow negative indices, we
+add two additional members.  \code{kernelRows} is an array of pointers
+to \code{float}; these pointers point into the \code{psImage} data,
+offset by the desired column offset.  \code{kernel} point into the
+\code{kernelRows}, offset by the desired row offset.  For example:
+
+\begin{verbatim}
+    kernelRows = psAlloc(myImage->nRows * sizeof(float));
+    for (int i = 0; i < myImage->nRows; i++) {
+	kernelRows[i] = &rows[i][columnOffset];
+    }
+    kernel = &kernelRows[rowOffset];
+\end{verbatim}
+
+This construction allows the \code{kernel} member to use negative
+indices, while preserving the location of \code{psMemBlock}s relative
+to allocated memory.
+
+The maximum extent of the kernel shifts shall be defined by the
+\code{xMin}, \code{xMax}, \code{yMin} and \code{yMax} members.  Note
+that \code{xMin} and \code{yMin}, under normal circumstances, should
+be negative numbers.  That is, \code{myKernel->kernel[-3][-2]} may be
+defined if \code{yMin} and \code{xMin} are equal to or more negative
+than -3 and -2, respectively.
+
+Of course, we require the appropriate constructor:
+\begin{verbatim}
+psKernel *psKernelAlloc(int xMin, int xMax, int yMin, int yMax);
+\end{verbatim}
+
+\code{psKernelAlloc} shall allocate a kernel.  In the event that one
+of the minimum values is greater than the corresponding maximum value,
+the function shall generate a warning, and the offending values shall
+be exchanged.
+
+\subsubsubsection{Generation of a convolution kernel}
+
+Given a list of values (e.g., shifts made in the course of OT
+guiding), \code{psKernelGenerate} shall return the appropriate kernel.
+The API shall be the following:
+\begin{verbatim}
+psKernel *psKernelGenerate(const psVector *xShifts, const psVector *yShifts);
+\end{verbatim}
+
+The vectors \code{xShifts} and \code{yShifts}, which are a list of
+shifts relative to some starting point, will be supplied by the user.
+The elements of the vectors should be of an integer type; otherwise
+the values shall be truncated to integers.  The output kernel shall be
+normalized such that the sum over the kernel is unity.
+
+If the vectors are not of the same number of elements, then the
+function shall generate a warning shall be generated, following which,
+the longer vector trimmed to the length of the shorter, and the
+function shall continue.
+
+\subsubsubsection{Convolve an image with the kernel}
+
+Given an input image and the convolution kernel,
+\code{psImageConvolve} shall convolve the input image,
+\code{in}, with the kernel, \code{kernel} and return the convolved
+image, \code{out}.  The API shall be the following:
+\begin{verbatim}
+psImage *psImageConvolve(psImage *out, const psImage *in, const psKernel *kernel, bool direct);
+\end{verbatim}
+
+Two methods shall be available for the convolution: if \code{direct}
+is \code{true}, then the convolution shall be performed in real space
+(appropriate for small kernels); otherwise, the convolution shall be
+performed using Fast Fourier Transforms (FFTs; appropriate for larger
+kernels).  The latter option involves padding the input image, copying
+the kernel into an image of the same size as the padded input image,
+performing an FFT on each, multiplying the FFTs, and performing an
+inverse FFT before trimming the image back to the original size.
+
+In the event that \code{out} is \code{NULL}, a new \code{psImage}
+shall be allocated and returned.
 
 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
