 /*
  * Khoros: $Id: lmat2viff.c,v 1.4 1992/03/20 23:35:27 dkhoros Exp $
  */

#if !defined(lint) && !defined(SABER)
static char rcsid[] = "Khoros: $Id: lmat2viff.c,v 1.4 1992/03/20 23:35:27 dkhoros Exp $";
#endif

 /*
  * $Log: lmat2viff.c,v $
 * Revision 1.4  1992/03/20  23:35:27  dkhoros
 * VirtualPatch5
 *
  */

/*
 *----------------------------------------------------------------------
 *
 * Copyright 1992, University of New Mexico.  All rights reserved.
 * Permission to copy and modify this software and its documen-
 * tation only for internal use in your organization is hereby
 * granted, provided that this notice is retained thereon and
 * on all copies.  UNM makes no representations as to the sui-
 * tability and operability of this software for any purpose.
 * It is provided "as is" without express or implied warranty.
 * 
 * UNM DISCLAIMS ALL WARRANTIES WITH REGARD TO THIS SOFTWARE,
 * INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND FIT-
 * NESS.  IN NO EVENT SHALL UNM BE LIABLE FOR ANY SPECIAL,
 * INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY OTHER DAMAGES WHAT-
 * SOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER
 * IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS
 * ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR PER-
 * FORMANCE OF THIS SOFTWARE.
 * 
 * No other rights, including, for example, the right to redis-
 * tribute this software and its documentation or the right to
 * prepare derivative works, are granted unless specifically
 * provided in a separate license agreement.
 *---------------------------------------------------------------------
 */

#include "unmcopyright.h"        /* Copyright 1992 by UNM */

/*>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>  <<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<
 >>>>
 >>>>         File Name: lmat2viff.c
 >>>>
 >>>>      Program Name: mat2viff
 >>>>
 >>>> Date Last Updated: Thu Mar 19 17:33:08 1992 
 >>>>
 >>>>          Routines: lmat2viff - the library call for mat2viff
 >>>>
 >>>>>>>>>>>>>>>>>>>>>>>>>>>>>>   <<<<<<<<<<<<<<<<<<<<<<<<<<<<<<*/


#include "vinclude.h"


/* -library_includes */
double *real=NULL, *imag=NULL;
int p_rows,p_cols;
kfile *kflptr;
/* -library_includes_end */


/****************************************************************
*
* Routine Name: lmat2viff - library call for mat2viff
*
* Purpose:
*    
*    converts a matrix to an image
*    
*    

* Input:
*    
*    image          pointer to VIFF structure containing image data to
*                   be processed.
*    
*    procdir        process direction:  0  indicated  vector  oriented
*                   processing, 1 indicates band oriented processing.
*    
*    

* Output:
*    
*    image          pointer to VIFF structure  containing  image  data
*                   after processing.
*    
*    Return Value:  1 on success, 0 on failure.
*    
*    

*
* Written By: Jeremy Worley
*    
*    B. Martensson and J. Worley 9 Aug  1991 10:52 MDT
*              explicitly set matrix to null so that  readmatrix  does
*              not get confused.
*    
*    Jeremy Worley 19 Mar 1992 17:32 MST
*              changed code so that transport stuff in vgparm was used
*              instead of FILE oriented operations.
*    
*    

****************************************************************/


/* -library_def */
int lmat2viff(image,filename)
  struct xvimage **image;
  char *filename;
/* -library_def_end */

/* -library_code */
{
  int rows,cols,type,errnum;
  double *matrix=NULL;
  char *comment = "no comment..."; 

  readmatrix(filename,&matrix,&rows,&cols,&type,&errnum);

  if(*image==NULL){
     *image = createimage(0,0,(type?VFF_TYP_DCOMPLEX:VFF_TYP_DOUBLE),
                           1,1,comment,
                           (unsigned long)0, /* map_row_size */
                           (unsigned long)0, /* map_col_size */
                           (unsigned long)VFF_MS_NONE,
                           (unsigned long)VFF_MAPTYP_NONE,
                           (unsigned long)VFF_LOC_IMPLICIT,
                           (unsigned long)0);/* location dimension */
   }

   (*image)->row_size = cols;
   (*image)->col_size = rows;
   (*image)->num_data_bands = 1;
   (*image)->imagedata = (char *)matrix;

   return(1);
} 
  
/***********************************************************************
*
*  Routine Name: readmatrix()
*
*          Date: Fri Oct 12 01:14:11 MDT 1990
*        
*       Purpose: opens the specified input file and calls the matrix
*                parser.  it then rearranges the data and returns.  
*
*         Input: fname - filename to read matrix from. 
*
*        Output: matrix - array of doubles that represents the matrix
*                         an element can be referenced by indexing in
*                         to the array according to row and column sizes.
*
*                rows   - number of rows in matrix.
*
*                cols   - number of columns in matrix.
*
*                type   - type of matrix: 0=real, 1=complex.
*
*                errnum - error code that is nonzero if readmatrix()
*                         returns a 1 (which indicates an error condition):
*                               1 - error during malloc
*                               2 - error during realloc
*                               3 - file not found. 
*                               4 - malloc failure in parser.
*                               5 - syntax error.
*
*    Written By: Jeremy Worley 
*
* Modifications: Sat Oct 27 14:34:02 MDT 1990 p_rows,p_cols initialization
*                       but fixed by adding explicit reset of values in
*                       readmatrix().
*
***********************************************************************/

#define CLEANUP \
    *rows = p_rows; \
    *cols = p_cols; \
    *errnum = 0; \
    kfree((char *)real); \
    real = NULL; \
    kfree((char *)imag); \
    imag = NULL; \
    (void)kfclose(kflptr);

int readmatrix(fname,matrix,rows,cols,type,errnum)
    char *fname;
    double **matrix;
    int *rows, *cols, *type, *errnum;
{
    int i,j;
    int mparse_init();

    kflptr=(kfile *)kfopen(fname,"r");
    if(kflptr==NULL){
       *errnum = 3;
       CLEANUP;
       return(0);
    }

    p_rows = p_cols = 0;
    (void)mparse_init();
   
    j = format_parse();

    if(j==-1){
       *errnum = 4;
       CLEANUP;
       return(0);
    }else if(j==-2){
       *errnum = 5;
       CLEANUP;
       return(0);
    }

    *type = 0;
    for(i=0;i<p_rows*p_cols;i++)
        if(imag[i]!=0.0){
          *type = 1;
          break;
        }

    if(*matrix == NULL){
       *matrix = (double *)kmalloc((unsigned)(p_rows*p_cols*(1+(*type))*
                           sizeof(double)));
       if(*matrix == NULL){
          *errnum = 1;
          CLEANUP;
          return(0);
       }
    }else{
       *matrix = (double *)krealloc((char *)(*matrix),
                          (unsigned)(p_rows*p_cols*(1+(*type))*sizeof(double)));
       if(*matrix ==NULL){
          *errnum = 2;
          CLEANUP;
          return(0);
       }
    }

    for(i=0;i<p_rows*p_cols;i++){
        if(*type){
           j = 2*i;
           (*matrix)[j] = real[i];
           (*matrix)[j+1] = imag[i];
        }else{
           (*matrix)[i] = real[i];
        }
    }

/*
** don't allow zero dimension matrices...
*/

    if(p_rows==0 || p_cols == 0){
       *errnum = 6;
       CLEANUP;
       return(0);
    }

    CLEANUP;
    return(1);
} 
/* -library_code_end */
