#include <stdlib.h>
#include <stdio.h>
#include <math.h>
#include "blas_extended.h"
#include "blas_extended_private.h"
#include "blas_extended_test.h"


double do_test_saxpby(int n, int ntests, int *seed, double thresh, int debug,
		      double *min_ratio, int *num_bad_ratio, int *num_tests)

/*
 * Purpose  
 * =======
 *
 * Runs a series of tests on axpby  
 *
 * Arguments
 * =========
 *
 * n         (input) int
 *           The size of vector being tested
 *
 * ntests    (input) int
 *           The number of tests to run for each set of attributes.
 *
 * seed      (input/output) int         
 *           The seed for the random number generator used in testgen().
 *
 * thresh    (input) double
 *           When the ratio returned from test() exceeds the specified
 *           threshold, the current size, y_true, y_comp, and ratio will be
 *           printed.  (Since ratio is supposed to be O(1), we can set thresh
 *           to ~10.)
 *
 * debug     (input) int
 *           If debug=3, print summary 
 *           If debug=2, print summary only if the number of bad ratios > 0
 *           If debug=1, print complete info if tests fail
 *           If debug=0, return max ratio
 *
 * min_ratio (output) double
 *           The minimum ratio
 * 
 * num_bad_ratio (output) int
 *               The number of tests fail; they are above the threshold.
 *
 * num_tests (output) int
 *           The number of tests is being performed.
 *
 * Return value
 * ============
 *
 * The maximum ratio if run successfully, otherwise return -1 
 *
 * Code structure
 * ==============
 * 
 *  debug loop  -- if debug is one, the first loop computes the max ratio
 *              -- and the last(second) loop outputs debugging information,
 *              -- if the test fail and its ratio > 0.5 * max ratio.
 *              -- if debug is zero, the loop is executed once
 *    alpha loop  -- varying alpha: 0, 1, or random
 *      beta loop   -- varying beta: 0, 1, or random

 *          norm loop   -- varying norm: near undeflow, near one, or 
 *                        -- near overflow
 *            numtest loop  -- how many times the test is perform with 
 *                            -- above set of attributes
 *                incx loop     -- varying incx: -2, -1, 1, 2
 *                  incy loop     -- varying incy: -2, -1, 1, 2
 */
{
  /* function name */
  const char fname[] = "BLAS_saxpby";

  /* max number of debug lines to print */
  const int max_print = 32;

  /* Variables in the "x_val" form are loop vars for corresponding
     variables */
  int i;			/* iterate through the repeating tests */
  int ix, iy;			/* use to index x and y respectively */
  int incx_val, incy_val,	/* for testing different inc values */
    incx, incy, incx_gen, incy_gen, ygen_val, xgen_val, test_val;
  int d_count;			/* counter for debug */
  int find_max_ratio;		/* find_max_ratio = 1 only if debug = 3 */
  int p_count;			/* counter for the number of debug lines printed */
  int tot_tests;		/* total number of tests to be done */
  int norm;			/* input values of near underflow/one/overflow */
  double ratio_max;		/* the current maximum ratio */
  double ratio_min;		/* the current minimum ratio */
  double ratio;			/* the per-use test ratio from test() */
  double new_ratio;
  int bad_ratios;		/* the number of ratios over the threshold */
  double eps_int;		/* the internal epsilon expected--2^(-24) for float */
  double un_int;		/* the internal underflow threshold */
  float alpha;
  float beta;
  float *x;
  float y_fix;
  float *y_ori;
  float *y_comp;		/* the y computed  by BLAS_saxpby */

  int ixmax, iymax;
  int ixmax_max, iymax_max;

  /* x_gen and y_gen are used to store vectors generated by testgen.
     they eventually are copied back to x and y */
  float *x_gen;
  float *y_gen;

  /* the true y calculated by testgen(), in double-double */
  double *head_y_true, *tail_y_true;
  int alpha_val;
  int alpha_flag;		/* input flag for BLAS_sdot_testgen */
  int beta_val;
  int beta_flag;		/* input flag for BLAS_sdot_testgen */

  enum blas_prec_type prec;
  int saved_seed;		/* for saving the original seed */
  int count, old_count;		/* use for counting the number of testgen calls * 2 */

  FPU_FIX_DECL;

  /* test for bad arguments */
  if (n < 0 || ntests < 0)
    BLAS_error(fname, 0, 0, NULL);

  /* if there is nothing to test, return all zero */
  if (n == 0 || ntests == 0) {
    *min_ratio = 0.0;
    *num_bad_ratio = 0;
    *num_tests = 0;
    return 0.0;
  }

  FPU_FIX_START;

  /* get space for calculation */
  x = (float *) blas_malloc(n * 2 * sizeof(float));
  if (n * 2 > 0 && x == NULL) {
    BLAS_error("blas_malloc", 0, 0, "malloc failed.\n");
  }
  y_ori = (float *) blas_malloc(n * 2 * sizeof(float));
  if (n * 2 > 0 && y_ori == NULL) {
    BLAS_error("blas_malloc", 0, 0, "malloc failed.\n");
  }
  y_comp = (float *) blas_malloc(n * 2 * sizeof(float));
  if (n * 2 > 0 && y_comp == NULL) {
    BLAS_error("blas_malloc", 0, 0, "malloc failed.\n");
  }
  head_y_true = (double *) blas_malloc(n * sizeof(double));
  tail_y_true = (double *) blas_malloc(n * sizeof(double));
  if (n > 0 && (head_y_true == NULL || tail_y_true == NULL)) {
    BLAS_error("blas_malloc", 0, 0, "malloc failed.\n");
  }
  x_gen = (float *) blas_malloc(n * sizeof(float));
  if (n > 0 && x_gen == NULL) {
    BLAS_error("blas_malloc", 0, 0, "malloc failed.\n");
  }
  y_gen = (float *) blas_malloc(n * sizeof(float));
  if (n > 0 && y_gen == NULL) {
    BLAS_error("blas_malloc", 0, 0, "malloc failed.\n");
  }

  /* initialization */
  saved_seed = *seed;
  ratio_min = 1e308;
  ratio_max = 0.0;
  tot_tests = 0;
  p_count = 0;
  count = 0;
  bad_ratios = 0;
  ixmax_max = 0;
  iymax_max = 0;
  alpha_flag = 0;
  beta_flag = 0;
  old_count = 0;

  find_max_ratio = 0;
  if (debug == 3)
    find_max_ratio = 1;
  y_fix = 1.0;

  /* initialize incx_gen and incy_gen */
  incx_gen = 1;
  incy_gen = 1;



  /* The debug iteration:
     If debug=1, then will execute the iteration twice. First, compute the
     max ratio. Second, print info if ratio > (50% * ratio_max). */
  for (d_count = 0; d_count <= find_max_ratio; d_count++) {
    bad_ratios = 0;		/* set to zero */

    if ((debug == 3) && (d_count == find_max_ratio))
      *seed = saved_seed;	/* restore the original seed */

    /* varying alpha */
    for (alpha_val = 0; alpha_val < 3; alpha_val++) {
      alpha_flag = 0;
      switch (alpha_val) {
      case 0:
	alpha = 0.0;
	alpha_flag = 1;
	break;
      case 1:
	alpha = 1.0;
	alpha_flag = 1;
	break;
      }

      /* varying beta */
      for (beta_val = 0; beta_val < 3; beta_val++) {
	beta_flag = 0;
	switch (beta_val) {
	case 0:
	  beta = 0.0;
	  beta_flag = 1;
	  break;
	case 1:
	  beta = 1.0;
	  beta_flag = 1;
	  break;
	}


	eps_int = power(2, -BITS_S);
	un_int = pow((double) BLAS_fpinfo_x(blas_base, blas_prec_single),
		     (double) BLAS_fpinfo_x(blas_emin, blas_prec_single));
	prec = blas_prec_single;

	/* values near underflow, 1, or overflow */
	for (norm = -1; norm <= 1; norm++) {

	  /* number of tests */
	  for (i = 0; i < ntests; i++) {

	    /* generate test inputs */
	    BLAS_sdot_testgen(1, 0, 1, norm, blas_no_conj, &alpha, alpha_flag,
			      &beta, beta_flag, &y_fix, x_gen, seed, y_gen,
			      head_y_true, tail_y_true);
	    xgen_val = incx_gen;
	    for (ygen_val = incy_gen; ygen_val < n * incy_gen;
		 ygen_val += incy_gen) {
	      BLAS_sdot_testgen(1, 0, 1, norm, blas_no_conj, &alpha, 1, &beta,
				1, &y_fix, &x_gen[xgen_val], seed,
				&y_gen[ygen_val], &head_y_true[ygen_val],
				&tail_y_true[ygen_val]);
	      xgen_val += incx_gen;
	    }

	    count++;

	    /* varying incx */
	    for (incx_val = -2; incx_val <= 2; incx_val++) {
	      if (incx_val == 0)
		continue;

	      /* setting incx */
	      incx = incx_val;

	      scopy_vector(x_gen, n, 1, x, incx_val);

	      /* varying incy */
	      for (incy_val = -2; incy_val <= 2; incy_val++) {
		if (incy_val == 0)
		  continue;

		/* setting incy */
		incy = incy_val;


		scopy_vector(y_gen, n, 1, y_ori, incy_val);
		scopy_vector(y_gen, n, 1, y_comp, incy_val);

		/* call BLAS_saxpby to get y_comp */
		FPU_FIX_STOP;
		BLAS_saxpby(n, alpha, x, incx_val, beta, y_comp, incy_val);
		FPU_FIX_START;


		/* computing the ratio */
		ix = 0;
		if (incx < 0)
		  ix = -(n - 1) * incx;
		iy = 0;
		if (incy < 0)
		  iy = -(n - 1) * incy;
		ratio = 0.0;

		ixmax = -1;
		iymax = -1;
		for (test_val = 0; test_val < n * incy_gen;
		     test_val += incy_gen) {
		  test_BLAS_sdot(1, blas_no_conj, alpha, beta, y_ori[iy],
				 y_comp[iy], head_y_true[test_val],
				 tail_y_true[test_val], &y_fix, incx, &x[ix],
				 incx, eps_int, un_int, &new_ratio);

		  ix += incx;
		  iy += incy;
		  if (MAX(ratio, new_ratio) == new_ratio) {
		    ixmax = ix;
		    iymax = iy;
		  }
		  ratio = MAX(ratio, new_ratio);
		}

		/* increase the number of bad ratio, if the ratio
		   is bigger than the threshold.
		   The !<= below causes NaN error to be detected.
		   Note that (NaN > thresh) is always false. */
		if (!(ratio <= thresh)) {
		  bad_ratios++;


		  if ((debug == 3) &&	/* print only when debug is on */
		      (count != old_count) &&	/* print if old vector is different */
		      /* from the current one */
		      (d_count == find_max_ratio) &&
		      (p_count <= max_print) && (ratio > 0.5 * ratio_max)) {
		    old_count = count;

		    printf
		      ("FAIL> %s: n = %d, ntests = %d, threshold = %4.2f,\n",
		       fname, n, ntests, thresh);
		    printf("seed = %d\n", *seed);
		    printf("norm = %d\n", norm);


		    /* Print test info */
		    switch (prec) {
		    case blas_prec_single:
		      printf("single ");
		      break;
		    case blas_prec_double:
		      printf("double ");
		      break;
		    case blas_prec_indigenous:
		      printf("indigenous ");
		      break;
		    case blas_prec_extra:
		      printf("extra ");
		      break;
		    }
		    switch (norm) {
		    case -1:
		      printf("near_underflow ");
		      break;
		    case 0:
		      printf("near_one ");
		      break;
		    case 1:
		      printf("near_overflow ");
		      break;
		    }

		    printf("incx=%d, incy=%d:\n", incx, incy);

		    sprint_vector(x, n, incx_val, "x");
		    sprint_vector(y_ori, n, incy_val, "y_ori");
		    sprint_vector(y_comp, n, incy_val, "y_comp");

		    printf("      ");
		    printf("alpha = ");
		    printf("%16.8e", alpha);
		    printf("; ");
		    printf("beta = ");
		    printf("%16.8e", beta);
		    printf("\n");
		    printf("      ratio=%.4e\n", ratio);
		    printf("iymax = %d\n", iymax);
		    printf("ixmax = %d\n", ixmax);
		    p_count++;
		  }
		}
		if (d_count == 0) {
		  if (ratio > ratio_max)
		    ratio_max = ratio;
		  iymax_max = iymax;
		  ixmax_max = ixmax;
		  if (ratio != 0.0 && ratio < ratio_min)
		    ratio_min = ratio;

		  tot_tests++;
		}
	      }			/* incy */
	    }			/* incx */
	  }			/* tests */
	}			/* norm */

      }				/* beta */
    }				/* alpha */
  }				/* debug */

  if ((debug == 2) || ((debug == 1) && (bad_ratios > 0))) {
    printf("      %s:  n = %d, ntests = %d, thresh = %4.2f\n",
	   fname, n, ntests, thresh);
    if (ratio_min == 1.0e+308)
      ratio_min = 0.0;
    printf
      ("      bad/total = %d/%d=%3.2f, min_ratio = %.4e, max_ratio = %.4e\n\n",
       bad_ratios, tot_tests, ((double) bad_ratios) / ((double) tot_tests),
       ratio_min, ratio_max);
    printf("iymax_max = %d, ixmax_max = %d\n", iymax_max, ixmax_max);
  }

  blas_free(x);
  blas_free(y_ori);
  blas_free(y_comp);
  blas_free(head_y_true);
  blas_free(tail_y_true);
  blas_free(x_gen);
  blas_free(y_gen);

  *min_ratio = ratio_min;
  *num_bad_ratio = bad_ratios;
  *num_tests = tot_tests;

  FPU_FIX_STOP;
  return ratio_max;
}				/* end of do_test_saxpby */

double do_test_daxpby(int n, int ntests, int *seed, double thresh, int debug,
		      double *min_ratio, int *num_bad_ratio, int *num_tests)

/*
 * Purpose  
 * =======
 *
 * Runs a series of tests on axpby  
 *
 * Arguments
 * =========
 *
 * n         (input) int
 *           The size of vector being tested
 *
 * ntests    (input) int
 *           The number of tests to run for each set of attributes.
 *
 * seed      (input/output) int         
 *           The seed for the random number generator used in testgen().
 *
 * thresh    (input) double
 *           When the ratio returned from test() exceeds the specified
 *           threshold, the current size, y_true, y_comp, and ratio will be
 *           printed.  (Since ratio is supposed to be O(1), we can set thresh
 *           to ~10.)
 *
 * debug     (input) int
 *           If debug=3, print summary 
 *           If debug=2, print summary only if the number of bad ratios > 0
 *           If debug=1, print complete info if tests fail
 *           If debug=0, return max ratio
 *
 * min_ratio (output) double
 *           The minimum ratio
 * 
 * num_bad_ratio (output) int
 *               The number of tests fail; they are above the threshold.
 *
 * num_tests (output) int
 *           The number of tests is being performed.
 *
 * Return value
 * ============
 *
 * The maximum ratio if run successfully, otherwise return -1 
 *
 * Code structure
 * ==============
 * 
 *  debug loop  -- if debug is one, the first loop computes the max ratio
 *              -- and the last(second) loop outputs debugging information,
 *              -- if the test fail and its ratio > 0.5 * max ratio.
 *              -- if debug is zero, the loop is executed once
 *    alpha loop  -- varying alpha: 0, 1, or random
 *      beta loop   -- varying beta: 0, 1, or random

 *          norm loop   -- varying norm: near undeflow, near one, or 
 *                        -- near overflow
 *            numtest loop  -- how many times the test is perform with 
 *                            -- above set of attributes
 *                incx loop     -- varying incx: -2, -1, 1, 2
 *                  incy loop     -- varying incy: -2, -1, 1, 2
 */
{
  /* function name */
  const char fname[] = "BLAS_daxpby";

  /* max number of debug lines to print */
  const int max_print = 32;

  /* Variables in the "x_val" form are loop vars for corresponding
     variables */
  int i;			/* iterate through the repeating tests */
  int ix, iy;			/* use to index x and y respectively */
  int incx_val, incy_val,	/* for testing different inc values */
    incx, incy, incx_gen, incy_gen, ygen_val, xgen_val, test_val;
  int d_count;			/* counter for debug */
  int find_max_ratio;		/* find_max_ratio = 1 only if debug = 3 */
  int p_count;			/* counter for the number of debug lines printed */
  int tot_tests;		/* total number of tests to be done */
  int norm;			/* input values of near underflow/one/overflow */
  double ratio_max;		/* the current maximum ratio */
  double ratio_min;		/* the current minimum ratio */
  double ratio;			/* the per-use test ratio from test() */
  double new_ratio;
  int bad_ratios;		/* the number of ratios over the threshold */
  double eps_int;		/* the internal epsilon expected--2^(-24) for float */
  double un_int;		/* the internal underflow threshold */
  double alpha;
  double beta;
  double *x;
  double y_fix;
  double *y_ori;
  double *y_comp;		/* the y computed  by BLAS_daxpby */

  int ixmax, iymax;
  int ixmax_max, iymax_max;

  /* x_gen and y_gen are used to store vectors generated by testgen.
     they eventually are copied back to x and y */
  double *x_gen;
  double *y_gen;

  /* the true y calculated by testgen(), in double-double */
  double *head_y_true, *tail_y_true;
  int alpha_val;
  int alpha_flag;		/* input flag for BLAS_ddot_testgen */
  int beta_val;
  int beta_flag;		/* input flag for BLAS_ddot_testgen */

  enum blas_prec_type prec;
  int saved_seed;		/* for saving the original seed */
  int count, old_count;		/* use for counting the number of testgen calls * 2 */

  FPU_FIX_DECL;

  /* test for bad arguments */
  if (n < 0 || ntests < 0)
    BLAS_error(fname, 0, 0, NULL);

  /* if there is nothing to test, return all zero */
  if (n == 0 || ntests == 0) {
    *min_ratio = 0.0;
    *num_bad_ratio = 0;
    *num_tests = 0;
    return 0.0;
  }

  FPU_FIX_START;

  /* get space for calculation */
  x = (double *) blas_malloc(n * 2 * sizeof(double));
  if (n * 2 > 0 && x == NULL) {
    BLAS_error("blas_malloc", 0, 0, "malloc failed.\n");
  }
  y_ori = (double *) blas_malloc(n * 2 * sizeof(double));
  if (n * 2 > 0 && y_ori == NULL) {
    BLAS_error("blas_malloc", 0, 0, "malloc failed.\n");
  }
  y_comp = (double *) blas_malloc(n * 2 * sizeof(double));
  if (n * 2 > 0 && y_comp == NULL) {
    BLAS_error("blas_malloc", 0, 0, "malloc failed.\n");
  }
  head_y_true = (double *) blas_malloc(n * sizeof(double));
  tail_y_true = (double *) blas_malloc(n * sizeof(double));
  if (n > 0 && (head_y_true == NULL || tail_y_true == NULL)) {
    BLAS_error("blas_malloc", 0, 0, "malloc failed.\n");
  }
  x_gen = (double *) blas_malloc(n * sizeof(double));
  if (n > 0 && x_gen == NULL) {
    BLAS_error("blas_malloc", 0, 0, "malloc failed.\n");
  }
  y_gen = (double *) blas_malloc(n * sizeof(double));
  if (n > 0 && y_gen == NULL) {
    BLAS_error("blas_malloc", 0, 0, "malloc failed.\n");
  }

  /* initialization */
  saved_seed = *seed;
  ratio_min = 1e308;
  ratio_max = 0.0;
  tot_tests = 0;
  p_count = 0;
  count = 0;
  bad_ratios = 0;
  ixmax_max = 0;
  iymax_max = 0;
  alpha_flag = 0;
  beta_flag = 0;
  old_count = 0;

  find_max_ratio = 0;
  if (debug == 3)
    find_max_ratio = 1;
  y_fix = 1.0;

  /* initialize incx_gen and incy_gen */
  incx_gen = 1;
  incy_gen = 1;



  /* The debug iteration:
     If debug=1, then will execute the iteration twice. First, compute the
     max ratio. Second, print info if ratio > (50% * ratio_max). */
  for (d_count = 0; d_count <= find_max_ratio; d_count++) {
    bad_ratios = 0;		/* set to zero */

    if ((debug == 3) && (d_count == find_max_ratio))
      *seed = saved_seed;	/* restore the original seed */

    /* varying alpha */
    for (alpha_val = 0; alpha_val < 3; alpha_val++) {
      alpha_flag = 0;
      switch (alpha_val) {
      case 0:
	alpha = 0.0;
	alpha_flag = 1;
	break;
      case 1:
	alpha = 1.0;
	alpha_flag = 1;
	break;
      }

      /* varying beta */
      for (beta_val = 0; beta_val < 3; beta_val++) {
	beta_flag = 0;
	switch (beta_val) {
	case 0:
	  beta = 0.0;
	  beta_flag = 1;
	  break;
	case 1:
	  beta = 1.0;
	  beta_flag = 1;
	  break;
	}


	eps_int = power(2, -BITS_D);
	un_int = pow((double) BLAS_fpinfo_x(blas_base, blas_prec_double),
		     (double) BLAS_fpinfo_x(blas_emin, blas_prec_double));
	prec = blas_prec_double;

	/* values near underflow, 1, or overflow */
	for (norm = -1; norm <= 1; norm++) {

	  /* number of tests */
	  for (i = 0; i < ntests; i++) {

	    /* generate test inputs */
	    BLAS_ddot_testgen(1, 0, 1, norm, blas_no_conj, &alpha, alpha_flag,
			      &beta, beta_flag, &y_fix, x_gen, seed, y_gen,
			      head_y_true, tail_y_true);
	    xgen_val = incx_gen;
	    for (ygen_val = incy_gen; ygen_val < n * incy_gen;
		 ygen_val += incy_gen) {
	      BLAS_ddot_testgen(1, 0, 1, norm, blas_no_conj, &alpha, 1, &beta,
				1, &y_fix, &x_gen[xgen_val], seed,
				&y_gen[ygen_val], &head_y_true[ygen_val],
				&tail_y_true[ygen_val]);
	      xgen_val += incx_gen;
	    }

	    count++;

	    /* varying incx */
	    for (incx_val = -2; incx_val <= 2; incx_val++) {
	      if (incx_val == 0)
		continue;

	      /* setting incx */
	      incx = incx_val;

	      dcopy_vector(x_gen, n, 1, x, incx_val);

	      /* varying incy */
	      for (incy_val = -2; incy_val <= 2; incy_val++) {
		if (incy_val == 0)
		  continue;

		/* setting incy */
		incy = incy_val;


		dcopy_vector(y_gen, n, 1, y_ori, incy_val);
		dcopy_vector(y_gen, n, 1, y_comp, incy_val);

		/* call BLAS_daxpby to get y_comp */
		FPU_FIX_STOP;
		BLAS_daxpby(n, alpha, x, incx_val, beta, y_comp, incy_val);
		FPU_FIX_START;


		/* computing the ratio */
		ix = 0;
		if (incx < 0)
		  ix = -(n - 1) * incx;
		iy = 0;
		if (incy < 0)
		  iy = -(n - 1) * incy;
		ratio = 0.0;

		ixmax = -1;
		iymax = -1;
		for (test_val = 0; test_val < n * incy_gen;
		     test_val += incy_gen) {
		  test_BLAS_ddot(1, blas_no_conj, alpha, beta, y_ori[iy],
				 y_comp[iy], head_y_true[test_val],
				 tail_y_true[test_val], &y_fix, incx, &x[ix],
				 incx, eps_int, un_int, &new_ratio);

		  ix += incx;
		  iy += incy;
		  if (MAX(ratio, new_ratio) == new_ratio) {
		    ixmax = ix;
		    iymax = iy;
		  }
		  ratio = MAX(ratio, new_ratio);
		}

		/* increase the number of bad ratio, if the ratio
		   is bigger than the threshold.
		   The !<= below causes NaN error to be detected.
		   Note that (NaN > thresh) is always false. */
		if (!(ratio <= thresh)) {
		  bad_ratios++;


		  if ((debug == 3) &&	/* print only when debug is on */
		      (count != old_count) &&	/* print if old vector is different */
		      /* from the current one */
		      (d_count == find_max_ratio) &&
		      (p_count <= max_print) && (ratio > 0.5 * ratio_max)) {
		    old_count = count;

		    printf
		      ("FAIL> %s: n = %d, ntests = %d, threshold = %4.2f,\n",
		       fname, n, ntests, thresh);
		    printf("seed = %d\n", *seed);
		    printf("norm = %d\n", norm);


		    /* Print test info */
		    switch (prec) {
		    case blas_prec_single:
		      printf("single ");
		      break;
		    case blas_prec_double:
		      printf("double ");
		      break;
		    case blas_prec_indigenous:
		      printf("indigenous ");
		      break;
		    case blas_prec_extra:
		      printf("extra ");
		      break;
		    }
		    switch (norm) {
		    case -1:
		      printf("near_underflow ");
		      break;
		    case 0:
		      printf("near_one ");
		      break;
		    case 1:
		      printf("near_overflow ");
		      break;
		    }

		    printf("incx=%d, incy=%d:\n", incx, incy);

		    dprint_vector(x, n, incx_val, "x");
		    dprint_vector(y_ori, n, incy_val, "y_ori");
		    dprint_vector(y_comp, n, incy_val, "y_comp");

		    printf("      ");
		    printf("alpha = ");
		    printf("%24.16e", alpha);
		    printf("; ");
		    printf("beta = ");
		    printf("%24.16e", beta);
		    printf("\n");
		    printf("      ratio=%.4e\n", ratio);
		    printf("iymax = %d\n", iymax);
		    printf("ixmax = %d\n", ixmax);
		    p_count++;
		  }
		}
		if (d_count == 0) {
		  if (ratio > ratio_max)
		    ratio_max = ratio;
		  iymax_max = iymax;
		  ixmax_max = ixmax;
		  if (ratio != 0.0 && ratio < ratio_min)
		    ratio_min = ratio;

		  tot_tests++;
		}
	      }			/* incy */
	    }			/* incx */
	  }			/* tests */
	}			/* norm */

      }				/* beta */
    }				/* alpha */
  }				/* debug */

  if ((debug == 2) || ((debug == 1) && (bad_ratios > 0))) {
    printf("      %s:  n = %d, ntests = %d, thresh = %4.2f\n",
	   fname, n, ntests, thresh);
    if (ratio_min == 1.0e+308)
      ratio_min = 0.0;
    printf
      ("      bad/total = %d/%d=%3.2f, min_ratio = %.4e, max_ratio = %.4e\n\n",
       bad_ratios, tot_tests, ((double) bad_ratios) / ((double) tot_tests),
       ratio_min, ratio_max);
    printf("iymax_max = %d, ixmax_max = %d\n", iymax_max, ixmax_max);
  }

  blas_free(x);
  blas_free(y_ori);
  blas_free(y_comp);
  blas_free(head_y_true);
  blas_free(tail_y_true);
  blas_free(x_gen);
  blas_free(y_gen);

  *min_ratio = ratio_min;
  *num_bad_ratio = bad_ratios;
  *num_tests = tot_tests;

  FPU_FIX_STOP;
  return ratio_max;
}				/* end of do_test_daxpby */

double do_test_caxpby(int n, int ntests, int *seed, double thresh, int debug,
		      double *min_ratio, int *num_bad_ratio, int *num_tests)

/*
 * Purpose  
 * =======
 *
 * Runs a series of tests on axpby  
 *
 * Arguments
 * =========
 *
 * n         (input) int
 *           The size of vector being tested
 *
 * ntests    (input) int
 *           The number of tests to run for each set of attributes.
 *
 * seed      (input/output) int         
 *           The seed for the random number generator used in testgen().
 *
 * thresh    (input) double
 *           When the ratio returned from test() exceeds the specified
 *           threshold, the current size, y_true, y_comp, and ratio will be
 *           printed.  (Since ratio is supposed to be O(1), we can set thresh
 *           to ~10.)
 *
 * debug     (input) int
 *           If debug=3, print summary 
 *           If debug=2, print summary only if the number of bad ratios > 0
 *           If debug=1, print complete info if tests fail
 *           If debug=0, return max ratio
 *
 * min_ratio (output) double
 *           The minimum ratio
 * 
 * num_bad_ratio (output) int
 *               The number of tests fail; they are above the threshold.
 *
 * num_tests (output) int
 *           The number of tests is being performed.
 *
 * Return value
 * ============
 *
 * The maximum ratio if run successfully, otherwise return -1 
 *
 * Code structure
 * ==============
 * 
 *  debug loop  -- if debug is one, the first loop computes the max ratio
 *              -- and the last(second) loop outputs debugging information,
 *              -- if the test fail and its ratio > 0.5 * max ratio.
 *              -- if debug is zero, the loop is executed once
 *    alpha loop  -- varying alpha: 0, 1, or random
 *      beta loop   -- varying beta: 0, 1, or random

 *          norm loop   -- varying norm: near undeflow, near one, or 
 *                        -- near overflow
 *            numtest loop  -- how many times the test is perform with 
 *                            -- above set of attributes
 *                incx loop     -- varying incx: -2, -1, 1, 2
 *                  incy loop     -- varying incy: -2, -1, 1, 2
 */
{
  /* function name */
  const char fname[] = "BLAS_caxpby";

  /* max number of debug lines to print */
  const int max_print = 32;

  /* Variables in the "x_val" form are loop vars for corresponding
     variables */
  int i;			/* iterate through the repeating tests */
  int ix, iy;			/* use to index x and y respectively */
  int incx_val, incy_val,	/* for testing different inc values */
    incx, incy, incx_gen, incy_gen, ygen_val, xgen_val, test_val;
  int d_count;			/* counter for debug */
  int find_max_ratio;		/* find_max_ratio = 1 only if debug = 3 */
  int p_count;			/* counter for the number of debug lines printed */
  int tot_tests;		/* total number of tests to be done */
  int norm;			/* input values of near underflow/one/overflow */
  double ratio_max;		/* the current maximum ratio */
  double ratio_min;		/* the current minimum ratio */
  double ratio;			/* the per-use test ratio from test() */
  double new_ratio;
  int bad_ratios;		/* the number of ratios over the threshold */
  double eps_int;		/* the internal epsilon expected--2^(-24) for float */
  double un_int;		/* the internal underflow threshold */
  float alpha[2];
  float beta[2];
  float *x;
  float y_fix[2];
  float *y_ori;
  float *y_comp;		/* the y computed  by BLAS_caxpby */

  int ixmax, iymax;
  int ixmax_max, iymax_max;

  /* x_gen and y_gen are used to store vectors generated by testgen.
     they eventually are copied back to x and y */
  float *x_gen;
  float *y_gen;

  /* the true y calculated by testgen(), in double-double */
  double *head_y_true, *tail_y_true;

  int alpha_val;
  int alpha_flag;		/* input flag for BLAS_cdot_testgen */
  int beta_val;
  int beta_flag;		/* input flag for BLAS_cdot_testgen */

  enum blas_prec_type prec;
  int saved_seed;		/* for saving the original seed */
  int count, old_count;		/* use for counting the number of testgen calls * 2 */

  FPU_FIX_DECL;

  /* test for bad arguments */
  if (n < 0 || ntests < 0)
    BLAS_error(fname, 0, 0, NULL);

  /* if there is nothing to test, return all zero */
  if (n == 0 || ntests == 0) {
    *min_ratio = 0.0;
    *num_bad_ratio = 0;
    *num_tests = 0;
    return 0.0;
  }

  FPU_FIX_START;

  /* get space for calculation */
  x = (float *) blas_malloc(n * 2 * sizeof(float) * 2);
  if (n * 2 > 0 && x == NULL) {
    BLAS_error("blas_malloc", 0, 0, "malloc failed.\n");
  }
  y_ori = (float *) blas_malloc(n * 2 * sizeof(float) * 2);
  if (n * 2 > 0 && y_ori == NULL) {
    BLAS_error("blas_malloc", 0, 0, "malloc failed.\n");
  }
  y_comp = (float *) blas_malloc(n * 2 * sizeof(float) * 2);
  if (n * 2 > 0 && y_comp == NULL) {
    BLAS_error("blas_malloc", 0, 0, "malloc failed.\n");
  }
  head_y_true = (double *) blas_malloc(n * sizeof(double) * 2);
  tail_y_true = (double *) blas_malloc(n * sizeof(double) * 2);
  if (n > 0 && (head_y_true == NULL || tail_y_true == NULL)) {
    BLAS_error("blas_malloc", 0, 0, "malloc failed.\n");
  }
  x_gen = (float *) blas_malloc(n * sizeof(float) * 2);
  if (n > 0 && x_gen == NULL) {
    BLAS_error("blas_malloc", 0, 0, "malloc failed.\n");
  }
  y_gen = (float *) blas_malloc(n * sizeof(float) * 2);
  if (n > 0 && y_gen == NULL) {
    BLAS_error("blas_malloc", 0, 0, "malloc failed.\n");
  }

  /* initialization */
  saved_seed = *seed;
  ratio_min = 1e308;
  ratio_max = 0.0;
  tot_tests = 0;
  p_count = 0;
  count = 0;
  bad_ratios = 0;
  ixmax_max = 0;
  iymax_max = 0;
  alpha_flag = 0;
  beta_flag = 0;
  old_count = 0;

  find_max_ratio = 0;
  if (debug == 3)
    find_max_ratio = 1;
  y_fix[0] = 1.0;
  y_fix[1] = 0.0;

  /* initialize incx_gen and incy_gen */
  incx_gen = 1;
  incy_gen = 1;
  incx_gen *= 2;
  incy_gen *= 2;

  /* The debug iteration:
     If debug=1, then will execute the iteration twice. First, compute the
     max ratio. Second, print info if ratio > (50% * ratio_max). */
  for (d_count = 0; d_count <= find_max_ratio; d_count++) {
    bad_ratios = 0;		/* set to zero */

    if ((debug == 3) && (d_count == find_max_ratio))
      *seed = saved_seed;	/* restore the original seed */

    /* varying alpha */
    for (alpha_val = 0; alpha_val < 3; alpha_val++) {
      alpha_flag = 0;
      switch (alpha_val) {
      case 0:
	alpha[0] = alpha[1] = 0.0;
	alpha_flag = 1;
	break;
      case 1:
	alpha[0] = 1.0;
	alpha[1] = 0.0;
	alpha_flag = 1;
	break;
      }

      /* varying beta */
      for (beta_val = 0; beta_val < 3; beta_val++) {
	beta_flag = 0;
	switch (beta_val) {
	case 0:
	  beta[0] = beta[1] = 0.0;
	  beta_flag = 1;
	  break;
	case 1:
	  beta[0] = 1.0;
	  beta[1] = 0.0;
	  beta_flag = 1;
	  break;
	}


	eps_int = power(2, -BITS_S);
	un_int = pow((double) BLAS_fpinfo_x(blas_base, blas_prec_single),
		     (double) BLAS_fpinfo_x(blas_emin, blas_prec_single));
	prec = blas_prec_single;

	/* values near underflow, 1, or overflow */
	for (norm = -1; norm <= 1; norm++) {

	  /* number of tests */
	  for (i = 0; i < ntests; i++) {

	    /* generate test inputs */
	    BLAS_cdot_testgen(1, 0, 1, norm, blas_no_conj, alpha, alpha_flag,
			      beta, beta_flag, y_fix, x_gen, seed, y_gen,
			      head_y_true, tail_y_true);
	    xgen_val = incx_gen;
	    for (ygen_val = incy_gen; ygen_val < n * incy_gen;
		 ygen_val += incy_gen) {
	      BLAS_cdot_testgen(1, 0, 1, norm, blas_no_conj, alpha, 1, beta,
				1, y_fix, &x_gen[xgen_val], seed,
				&y_gen[ygen_val], &head_y_true[ygen_val],
				&tail_y_true[ygen_val]);
	      xgen_val += incx_gen;
	    }

	    count++;

	    /* varying incx */
	    for (incx_val = -2; incx_val <= 2; incx_val++) {
	      if (incx_val == 0)
		continue;

	      /* setting incx */
	      incx = incx_val;

	      ccopy_vector(x_gen, n, 1, x, incx_val);

	      /* varying incy */
	      for (incy_val = -2; incy_val <= 2; incy_val++) {
		if (incy_val == 0)
		  continue;

		/* setting incy */
		incy = incy_val;
		incy *= 2;

		ccopy_vector(y_gen, n, 1, y_ori, incy_val);
		ccopy_vector(y_gen, n, 1, y_comp, incy_val);

		/* call BLAS_caxpby to get y_comp */
		FPU_FIX_STOP;
		BLAS_caxpby(n, alpha, x, incx_val, beta, y_comp, incy_val);
		FPU_FIX_START;


		/* computing the ratio */
		ix = 0;
		if (incx < 0)
		  ix = -(n - 1) * incx;
		iy = 0;
		if (incy < 0)
		  iy = -(n - 1) * incy;
		ratio = 0.0;

		ixmax = -1;
		iymax = -1;
		for (test_val = 0; test_val < n * incy_gen;
		     test_val += incy_gen) {
		  test_BLAS_cdot(1, blas_no_conj, alpha, beta, &y_ori[iy],
				 &y_comp[iy], &head_y_true[test_val],
				 &tail_y_true[test_val], y_fix, incx, &x[ix],
				 incx, eps_int, un_int, &new_ratio);

		  ix += incx;
		  iy += incy;
		  if (MAX(ratio, new_ratio) == new_ratio) {
		    ixmax = ix;
		    iymax = iy;
		  }
		  ratio = MAX(ratio, new_ratio);
		}

		/* increase the number of bad ratio, if the ratio
		   is bigger than the threshold.
		   The !<= below causes NaN error to be detected.
		   Note that (NaN > thresh) is always false. */
		if (!(ratio <= thresh)) {
		  bad_ratios++;


		  if ((debug == 3) &&	/* print only when debug is on */
		      (count != old_count) &&	/* print if old vector is different */
		      /* from the current one */
		      (d_count == find_max_ratio) &&
		      (p_count <= max_print) && (ratio > 0.5 * ratio_max)) {
		    old_count = count;

		    printf
		      ("FAIL> %s: n = %d, ntests = %d, threshold = %4.2f,\n",
		       fname, n, ntests, thresh);
		    printf("seed = %d\n", *seed);
		    printf("norm = %d\n", norm);


		    /* Print test info */
		    switch (prec) {
		    case blas_prec_single:
		      printf("single ");
		      break;
		    case blas_prec_double:
		      printf("double ");
		      break;
		    case blas_prec_indigenous:
		      printf("indigenous ");
		      break;
		    case blas_prec_extra:
		      printf("extra ");
		      break;
		    }
		    switch (norm) {
		    case -1:
		      printf("near_underflow ");
		      break;
		    case 0:
		      printf("near_one ");
		      break;
		    case 1:
		      printf("near_overflow ");
		      break;
		    }

		    printf("incx=%d, incy=%d:\n", incx, incy);

		    cprint_vector(x, n, incx_val, "x");
		    cprint_vector(y_ori, n, incy_val, "y_ori");
		    cprint_vector(y_comp, n, incy_val, "y_comp");

		    printf("      ");
		    printf("alpha = ");
		    printf("(%16.8e, %16.8e)", alpha[0], alpha[1]);
		    printf("; ");
		    printf("beta = ");
		    printf("(%16.8e, %16.8e)", beta[0], beta[1]);
		    printf("\n");
		    printf("      ratio=%.4e\n", ratio);
		    printf("iymax = %d\n", iymax);
		    printf("ixmax = %d\n", ixmax);
		    p_count++;
		  }
		}
		if (d_count == 0) {
		  if (ratio > ratio_max)
		    ratio_max = ratio;
		  iymax_max = iymax;
		  ixmax_max = ixmax;
		  if (ratio != 0.0 && ratio < ratio_min)
		    ratio_min = ratio;

		  tot_tests++;
		}
	      }			/* incy */
	    }			/* incx */
	  }			/* tests */
	}			/* norm */

      }				/* beta */
    }				/* alpha */
  }				/* debug */

  if ((debug == 2) || ((debug == 1) && (bad_ratios > 0))) {
    printf("      %s:  n = %d, ntests = %d, thresh = %4.2f\n",
	   fname, n, ntests, thresh);
    if (ratio_min == 1.0e+308)
      ratio_min = 0.0;
    printf
      ("      bad/total = %d/%d=%3.2f, min_ratio = %.4e, max_ratio = %.4e\n\n",
       bad_ratios, tot_tests, ((double) bad_ratios) / ((double) tot_tests),
       ratio_min, ratio_max);
    printf("iymax_max = %d, ixmax_max = %d\n", iymax_max, ixmax_max);
  }

  blas_free(x);
  blas_free(y_ori);
  blas_free(y_comp);
  blas_free(head_y_true);
  blas_free(tail_y_true);
  blas_free(x_gen);
  blas_free(y_gen);

  *min_ratio = ratio_min;
  *num_bad_ratio = bad_ratios;
  *num_tests = tot_tests;

  FPU_FIX_STOP;
  return ratio_max;
}				/* end of do_test_caxpby */

double do_test_zaxpby(int n, int ntests, int *seed, double thresh, int debug,
		      double *min_ratio, int *num_bad_ratio, int *num_tests)

/*
 * Purpose  
 * =======
 *
 * Runs a series of tests on axpby  
 *
 * Arguments
 * =========
 *
 * n         (input) int
 *           The size of vector being tested
 *
 * ntests    (input) int
 *           The number of tests to run for each set of attributes.
 *
 * seed      (input/output) int         
 *           The seed for the random number generator used in testgen().
 *
 * thresh    (input) double
 *           When the ratio returned from test() exceeds the specified
 *           threshold, the current size, y_true, y_comp, and ratio will be
 *           printed.  (Since ratio is supposed to be O(1), we can set thresh
 *           to ~10.)
 *
 * debug     (input) int
 *           If debug=3, print summary 
 *           If debug=2, print summary only if the number of bad ratios > 0
 *           If debug=1, print complete info if tests fail
 *           If debug=0, return max ratio
 *
 * min_ratio (output) double
 *           The minimum ratio
 * 
 * num_bad_ratio (output) int
 *               The number of tests fail; they are above the threshold.
 *
 * num_tests (output) int
 *           The number of tests is being performed.
 *
 * Return value
 * ============
 *
 * The maximum ratio if run successfully, otherwise return -1 
 *
 * Code structure
 * ==============
 * 
 *  debug loop  -- if debug is one, the first loop computes the max ratio
 *              -- and the last(second) loop outputs debugging information,
 *              -- if the test fail and its ratio > 0.5 * max ratio.
 *              -- if debug is zero, the loop is executed once
 *    alpha loop  -- varying alpha: 0, 1, or random
 *      beta loop   -- varying beta: 0, 1, or random

 *          norm loop   -- varying norm: near undeflow, near one, or 
 *                        -- near overflow
 *            numtest loop  -- how many times the test is perform with 
 *                            -- above set of attributes
 *                incx loop     -- varying incx: -2, -1, 1, 2
 *                  incy loop     -- varying incy: -2, -1, 1, 2
 */
{
  /* function name */
  const char fname[] = "BLAS_zaxpby";

  /* max number of debug lines to print */
  const int max_print = 32;

  /* Variables in the "x_val" form are loop vars for corresponding
     variables */
  int i;			/* iterate through the repeating tests */
  int ix, iy;			/* use to index x and y respectively */
  int incx_val, incy_val,	/* for testing different inc values */
    incx, incy, incx_gen, incy_gen, ygen_val, xgen_val, test_val;
  int d_count;			/* counter for debug */
  int find_max_ratio;		/* find_max_ratio = 1 only if debug = 3 */
  int p_count;			/* counter for the number of debug lines printed */
  int tot_tests;		/* total number of tests to be done */
  int norm;			/* input values of near underflow/one/overflow */
  double ratio_max;		/* the current maximum ratio */
  double ratio_min;		/* the current minimum ratio */
  double ratio;			/* the per-use test ratio from test() */
  double new_ratio;
  int bad_ratios;		/* the number of ratios over the threshold */
  double eps_int;		/* the internal epsilon expected--2^(-24) for float */
  double un_int;		/* the internal underflow threshold */
  double alpha[2];
  double beta[2];
  double *x;
  double y_fix[2];
  double *y_ori;
  double *y_comp;		/* the y computed  by BLAS_zaxpby */

  int ixmax, iymax;
  int ixmax_max, iymax_max;

  /* x_gen and y_gen are used to store vectors generated by testgen.
     they eventually are copied back to x and y */
  double *x_gen;
  double *y_gen;

  /* the true y calculated by testgen(), in double-double */
  double *head_y_true, *tail_y_true;

  int alpha_val;
  int alpha_flag;		/* input flag for BLAS_zdot_testgen */
  int beta_val;
  int beta_flag;		/* input flag for BLAS_zdot_testgen */

  enum blas_prec_type prec;
  int saved_seed;		/* for saving the original seed */
  int count, old_count;		/* use for counting the number of testgen calls * 2 */

  FPU_FIX_DECL;

  /* test for bad arguments */
  if (n < 0 || ntests < 0)
    BLAS_error(fname, 0, 0, NULL);

  /* if there is nothing to test, return all zero */
  if (n == 0 || ntests == 0) {
    *min_ratio = 0.0;
    *num_bad_ratio = 0;
    *num_tests = 0;
    return 0.0;
  }

  FPU_FIX_START;

  /* get space for calculation */
  x = (double *) blas_malloc(n * 2 * sizeof(double) * 2);
  if (n * 2 > 0 && x == NULL) {
    BLAS_error("blas_malloc", 0, 0, "malloc failed.\n");
  }
  y_ori = (double *) blas_malloc(n * 2 * sizeof(double) * 2);
  if (n * 2 > 0 && y_ori == NULL) {
    BLAS_error("blas_malloc", 0, 0, "malloc failed.\n");
  }
  y_comp = (double *) blas_malloc(n * 2 * sizeof(double) * 2);
  if (n * 2 > 0 && y_comp == NULL) {
    BLAS_error("blas_malloc", 0, 0, "malloc failed.\n");
  }
  head_y_true = (double *) blas_malloc(n * sizeof(double) * 2);
  tail_y_true = (double *) blas_malloc(n * sizeof(double) * 2);
  if (n > 0 && (head_y_true == NULL || tail_y_true == NULL)) {
    BLAS_error("blas_malloc", 0, 0, "malloc failed.\n");
  }
  x_gen = (double *) blas_malloc(n * sizeof(double) * 2);
  if (n > 0 && x_gen == NULL) {
    BLAS_error("blas_malloc", 0, 0, "malloc failed.\n");
  }
  y_gen = (double *) blas_malloc(n * sizeof(double) * 2);
  if (n > 0 && y_gen == NULL) {
    BLAS_error("blas_malloc", 0, 0, "malloc failed.\n");
  }

  /* initialization */
  saved_seed = *seed;
  ratio_min = 1e308;
  ratio_max = 0.0;
  tot_tests = 0;
  p_count = 0;
  count = 0;
  bad_ratios = 0;
  ixmax_max = 0;
  iymax_max = 0;
  alpha_flag = 0;
  beta_flag = 0;
  old_count = 0;

  find_max_ratio = 0;
  if (debug == 3)
    find_max_ratio = 1;
  y_fix[0] = 1.0;
  y_fix[1] = 0.0;

  /* initialize incx_gen and incy_gen */
  incx_gen = 1;
  incy_gen = 1;
  incx_gen *= 2;
  incy_gen *= 2;

  /* The debug iteration:
     If debug=1, then will execute the iteration twice. First, compute the
     max ratio. Second, print info if ratio > (50% * ratio_max). */
  for (d_count = 0; d_count <= find_max_ratio; d_count++) {
    bad_ratios = 0;		/* set to zero */

    if ((debug == 3) && (d_count == find_max_ratio))
      *seed = saved_seed;	/* restore the original seed */

    /* varying alpha */
    for (alpha_val = 0; alpha_val < 3; alpha_val++) {
      alpha_flag = 0;
      switch (alpha_val) {
      case 0:
	alpha[0] = alpha[1] = 0.0;
	alpha_flag = 1;
	break;
      case 1:
	alpha[0] = 1.0;
	alpha[1] = 0.0;
	alpha_flag = 1;
	break;
      }

      /* varying beta */
      for (beta_val = 0; beta_val < 3; beta_val++) {
	beta_flag = 0;
	switch (beta_val) {
	case 0:
	  beta[0] = beta[1] = 0.0;
	  beta_flag = 1;
	  break;
	case 1:
	  beta[0] = 1.0;
	  beta[1] = 0.0;
	  beta_flag = 1;
	  break;
	}


	eps_int = power(2, -BITS_D);
	un_int = pow((double) BLAS_fpinfo_x(blas_base, blas_prec_double),
		     (double) BLAS_fpinfo_x(blas_emin, blas_prec_double));
	prec = blas_prec_double;

	/* values near underflow, 1, or overflow */
	for (norm = -1; norm <= 1; norm++) {

	  /* number of tests */
	  for (i = 0; i < ntests; i++) {

	    /* generate test inputs */
	    BLAS_zdot_testgen(1, 0, 1, norm, blas_no_conj, alpha, alpha_flag,
			      beta, beta_flag, y_fix, x_gen, seed, y_gen,
			      head_y_true, tail_y_true);
	    xgen_val = incx_gen;
	    for (ygen_val = incy_gen; ygen_val < n * incy_gen;
		 ygen_val += incy_gen) {
	      BLAS_zdot_testgen(1, 0, 1, norm, blas_no_conj, alpha, 1, beta,
				1, y_fix, &x_gen[xgen_val], seed,
				&y_gen[ygen_val], &head_y_true[ygen_val],
				&tail_y_true[ygen_val]);
	      xgen_val += incx_gen;
	    }

	    count++;

	    /* varying incx */
	    for (incx_val = -2; incx_val <= 2; incx_val++) {
	      if (incx_val == 0)
		continue;

	      /* setting incx */
	      incx = incx_val;

	      zcopy_vector(x_gen, n, 1, x, incx_val);

	      /* varying incy */
	      for (incy_val = -2; incy_val <= 2; incy_val++) {
		if (incy_val == 0)
		  continue;

		/* setting incy */
		incy = incy_val;
		incy *= 2;

		zcopy_vector(y_gen, n, 1, y_ori, incy_val);
		zcopy_vector(y_gen, n, 1, y_comp, incy_val);

		/* call BLAS_zaxpby to get y_comp */
		FPU_FIX_STOP;
		BLAS_zaxpby(n, alpha, x, incx_val, beta, y_comp, incy_val);
		FPU_FIX_START;


		/* computing the ratio */
		ix = 0;
		if (incx < 0)
		  ix = -(n - 1) * incx;
		iy = 0;
		if (incy < 0)
		  iy = -(n - 1) * incy;
		ratio = 0.0;

		ixmax = -1;
		iymax = -1;
		for (test_val = 0; test_val < n * incy_gen;
		     test_val += incy_gen) {
		  test_BLAS_zdot(1, blas_no_conj, alpha, beta, &y_ori[iy],
				 &y_comp[iy], &head_y_true[test_val],
				 &tail_y_true[test_val], y_fix, incx, &x[ix],
				 incx, eps_int, un_int, &new_ratio);

		  ix += incx;
		  iy += incy;
		  if (MAX(ratio, new_ratio) == new_ratio) {
		    ixmax = ix;
		    iymax = iy;
		  }
		  ratio = MAX(ratio, new_ratio);
		}

		/* increase the number of bad ratio, if the ratio
		   is bigger than the threshold.
		   The !<= below causes NaN error to be detected.
		   Note that (NaN > thresh) is always false. */
		if (!(ratio <= thresh)) {
		  bad_ratios++;


		  if ((debug == 3) &&	/* print only when debug is on */
		      (count != old_count) &&	/* print if old vector is different */
		      /* from the current one */
		      (d_count == find_max_ratio) &&
		      (p_count <= max_print) && (ratio > 0.5 * ratio_max)) {
		    old_count = count;

		    printf
		      ("FAIL> %s: n = %d, ntests = %d, threshold = %4.2f,\n",
		       fname, n, ntests, thresh);
		    printf("seed = %d\n", *seed);
		    printf("norm = %d\n", norm);


		    /* Print test info */
		    switch (prec) {
		    case blas_prec_single:
		      printf("single ");
		      break;
		    case blas_prec_double:
		      printf("double ");
		      break;
		    case blas_prec_indigenous:
		      printf("indigenous ");
		      break;
		    case blas_prec_extra:
		      printf("extra ");
		      break;
		    }
		    switch (norm) {
		    case -1:
		      printf("near_underflow ");
		      break;
		    case 0:
		      printf("near_one ");
		      break;
		    case 1:
		      printf("near_overflow ");
		      break;
		    }

		    printf("incx=%d, incy=%d:\n", incx, incy);

		    zprint_vector(x, n, incx_val, "x");
		    zprint_vector(y_ori, n, incy_val, "y_ori");
		    zprint_vector(y_comp, n, incy_val, "y_comp");

		    printf("      ");
		    printf("alpha = ");
		    printf("(%24.16e, %24.16e)", alpha[0], alpha[1]);
		    printf("; ");
		    printf("beta = ");
		    printf("(%24.16e, %24.16e)", beta[0], beta[1]);
		    printf("\n");
		    printf("      ratio=%.4e\n", ratio);
		    printf("iymax = %d\n", iymax);
		    printf("ixmax = %d\n", ixmax);
		    p_count++;
		  }
		}
		if (d_count == 0) {
		  if (ratio > ratio_max)
		    ratio_max = ratio;
		  iymax_max = iymax;
		  ixmax_max = ixmax;
		  if (ratio != 0.0 && ratio < ratio_min)
		    ratio_min = ratio;

		  tot_tests++;
		}
	      }			/* incy */
	    }			/* incx */
	  }			/* tests */
	}			/* norm */

      }				/* beta */
    }				/* alpha */
  }				/* debug */

  if ((debug == 2) || ((debug == 1) && (bad_ratios > 0))) {
    printf("      %s:  n = %d, ntests = %d, thresh = %4.2f\n",
	   fname, n, ntests, thresh);
    if (ratio_min == 1.0e+308)
      ratio_min = 0.0;
    printf
      ("      bad/total = %d/%d=%3.2f, min_ratio = %.4e, max_ratio = %.4e\n\n",
       bad_ratios, tot_tests, ((double) bad_ratios) / ((double) tot_tests),
       ratio_min, ratio_max);
    printf("iymax_max = %d, ixmax_max = %d\n", iymax_max, ixmax_max);
  }

  blas_free(x);
  blas_free(y_ori);
  blas_free(y_comp);
  blas_free(head_y_true);
  blas_free(tail_y_true);
  blas_free(x_gen);
  blas_free(y_gen);

  *min_ratio = ratio_min;
  *num_bad_ratio = bad_ratios;
  *num_tests = tot_tests;

  FPU_FIX_STOP;
  return ratio_max;
}				/* end of do_test_zaxpby */

double do_test_daxpby_s(int n, int ntests, int *seed, double thresh,
			int debug, double *min_ratio, int *num_bad_ratio,
			int *num_tests)

/*
 * Purpose  
 * =======
 *
 * Runs a series of tests on axpby  
 *
 * Arguments
 * =========
 *
 * n         (input) int
 *           The size of vector being tested
 *
 * ntests    (input) int
 *           The number of tests to run for each set of attributes.
 *
 * seed      (input/output) int         
 *           The seed for the random number generator used in testgen().
 *
 * thresh    (input) double
 *           When the ratio returned from test() exceeds the specified
 *           threshold, the current size, y_true, y_comp, and ratio will be
 *           printed.  (Since ratio is supposed to be O(1), we can set thresh
 *           to ~10.)
 *
 * debug     (input) int
 *           If debug=3, print summary 
 *           If debug=2, print summary only if the number of bad ratios > 0
 *           If debug=1, print complete info if tests fail
 *           If debug=0, return max ratio
 *
 * min_ratio (output) double
 *           The minimum ratio
 * 
 * num_bad_ratio (output) int
 *               The number of tests fail; they are above the threshold.
 *
 * num_tests (output) int
 *           The number of tests is being performed.
 *
 * Return value
 * ============
 *
 * The maximum ratio if run successfully, otherwise return -1 
 *
 * Code structure
 * ==============
 * 
 *  debug loop  -- if debug is one, the first loop computes the max ratio
 *              -- and the last(second) loop outputs debugging information,
 *              -- if the test fail and its ratio > 0.5 * max ratio.
 *              -- if debug is zero, the loop is executed once
 *    alpha loop  -- varying alpha: 0, 1, or random
 *      beta loop   -- varying beta: 0, 1, or random

 *          norm loop   -- varying norm: near undeflow, near one, or 
 *                        -- near overflow
 *            numtest loop  -- how many times the test is perform with 
 *                            -- above set of attributes
 *                incx loop     -- varying incx: -2, -1, 1, 2
 *                  incy loop     -- varying incy: -2, -1, 1, 2
 */
{
  /* function name */
  const char fname[] = "BLAS_daxpby_s";

  /* max number of debug lines to print */
  const int max_print = 32;

  /* Variables in the "x_val" form are loop vars for corresponding
     variables */
  int i;			/* iterate through the repeating tests */
  int ix, iy;			/* use to index x and y respectively */
  int incx_val, incy_val,	/* for testing different inc values */
    incx, incy, incx_gen, incy_gen, ygen_val, xgen_val, test_val;
  int d_count;			/* counter for debug */
  int find_max_ratio;		/* find_max_ratio = 1 only if debug = 3 */
  int p_count;			/* counter for the number of debug lines printed */
  int tot_tests;		/* total number of tests to be done */
  int norm;			/* input values of near underflow/one/overflow */
  double ratio_max;		/* the current maximum ratio */
  double ratio_min;		/* the current minimum ratio */
  double ratio;			/* the per-use test ratio from test() */
  double new_ratio;
  int bad_ratios;		/* the number of ratios over the threshold */
  double eps_int;		/* the internal epsilon expected--2^(-24) for float */
  double un_int;		/* the internal underflow threshold */
  double alpha;
  double beta;
  float *x;
  float y_fix;
  double *y_ori;
  double *y_comp;		/* the y computed  by BLAS_daxpby_s */

  int ixmax, iymax;
  int ixmax_max, iymax_max;

  /* x_gen and y_gen are used to store vectors generated by testgen.
     they eventually are copied back to x and y */
  float *x_gen;
  double *y_gen;

  /* the true y calculated by testgen(), in double-double */
  double *head_y_true, *tail_y_true;
  int alpha_val;
  int alpha_flag;		/* input flag for BLAS_ddot_s_s_testgen */
  int beta_val;
  int beta_flag;		/* input flag for BLAS_ddot_s_s_testgen */

  enum blas_prec_type prec;
  int saved_seed;		/* for saving the original seed */
  int count, old_count;		/* use for counting the number of testgen calls * 2 */

  FPU_FIX_DECL;

  /* test for bad arguments */
  if (n < 0 || ntests < 0)
    BLAS_error(fname, 0, 0, NULL);

  /* if there is nothing to test, return all zero */
  if (n == 0 || ntests == 0) {
    *min_ratio = 0.0;
    *num_bad_ratio = 0;
    *num_tests = 0;
    return 0.0;
  }

  FPU_FIX_START;

  /* get space for calculation */
  x = (float *) blas_malloc(n * 2 * sizeof(float));
  if (n * 2 > 0 && x == NULL) {
    BLAS_error("blas_malloc", 0, 0, "malloc failed.\n");
  }
  y_ori = (double *) blas_malloc(n * 2 * sizeof(double));
  if (n * 2 > 0 && y_ori == NULL) {
    BLAS_error("blas_malloc", 0, 0, "malloc failed.\n");
  }
  y_comp = (double *) blas_malloc(n * 2 * sizeof(double));
  if (n * 2 > 0 && y_comp == NULL) {
    BLAS_error("blas_malloc", 0, 0, "malloc failed.\n");
  }
  head_y_true = (double *) blas_malloc(n * sizeof(double));
  tail_y_true = (double *) blas_malloc(n * sizeof(double));
  if (n > 0 && (head_y_true == NULL || tail_y_true == NULL)) {
    BLAS_error("blas_malloc", 0, 0, "malloc failed.\n");
  }
  x_gen = (float *) blas_malloc(n * sizeof(float));
  if (n > 0 && x_gen == NULL) {
    BLAS_error("blas_malloc", 0, 0, "malloc failed.\n");
  }
  y_gen = (double *) blas_malloc(n * sizeof(double));
  if (n > 0 && y_gen == NULL) {
    BLAS_error("blas_malloc", 0, 0, "malloc failed.\n");
  }

  /* initialization */
  saved_seed = *seed;
  ratio_min = 1e308;
  ratio_max = 0.0;
  tot_tests = 0;
  p_count = 0;
  count = 0;
  bad_ratios = 0;
  ixmax_max = 0;
  iymax_max = 0;
  alpha_flag = 0;
  beta_flag = 0;
  old_count = 0;

  find_max_ratio = 0;
  if (debug == 3)
    find_max_ratio = 1;
  y_fix = 1.0;

  /* initialize incx_gen and incy_gen */
  incx_gen = 1;
  incy_gen = 1;



  /* The debug iteration:
     If debug=1, then will execute the iteration twice. First, compute the
     max ratio. Second, print info if ratio > (50% * ratio_max). */
  for (d_count = 0; d_count <= find_max_ratio; d_count++) {
    bad_ratios = 0;		/* set to zero */

    if ((debug == 3) && (d_count == find_max_ratio))
      *seed = saved_seed;	/* restore the original seed */

    /* varying alpha */
    for (alpha_val = 0; alpha_val < 3; alpha_val++) {
      alpha_flag = 0;
      switch (alpha_val) {
      case 0:
	alpha = 0.0;
	alpha_flag = 1;
	break;
      case 1:
	alpha = 1.0;
	alpha_flag = 1;
	break;
      }

      /* varying beta */
      for (beta_val = 0; beta_val < 3; beta_val++) {
	beta_flag = 0;
	switch (beta_val) {
	case 0:
	  beta = 0.0;
	  beta_flag = 1;
	  break;
	case 1:
	  beta = 1.0;
	  beta_flag = 1;
	  break;
	}


	eps_int = power(2, -BITS_D);
	un_int = pow((double) BLAS_fpinfo_x(blas_base, blas_prec_double),
		     (double) BLAS_fpinfo_x(blas_emin, blas_prec_double));
	prec = blas_prec_double;

	/* values near underflow, 1, or overflow */
	for (norm = -1; norm <= 1; norm++) {

	  /* number of tests */
	  for (i = 0; i < ntests; i++) {

	    /* generate test inputs */
	    BLAS_ddot_s_s_testgen(1, 0, 1, norm, blas_no_conj, &alpha,
				  alpha_flag, &beta, beta_flag, &y_fix, x_gen,
				  seed, y_gen, head_y_true, tail_y_true);
	    xgen_val = incx_gen;
	    for (ygen_val = incy_gen; ygen_val < n * incy_gen;
		 ygen_val += incy_gen) {
	      BLAS_ddot_s_s_testgen(1, 0, 1, norm, blas_no_conj, &alpha, 1,
				    &beta, 1, &y_fix, &x_gen[xgen_val], seed,
				    &y_gen[ygen_val], &head_y_true[ygen_val],
				    &tail_y_true[ygen_val]);
	      xgen_val += incx_gen;
	    }

	    count++;

	    /* varying incx */
	    for (incx_val = -2; incx_val <= 2; incx_val++) {
	      if (incx_val == 0)
		continue;

	      /* setting incx */
	      incx = incx_val;

	      scopy_vector(x_gen, n, 1, x, incx_val);

	      /* varying incy */
	      for (incy_val = -2; incy_val <= 2; incy_val++) {
		if (incy_val == 0)
		  continue;

		/* setting incy */
		incy = incy_val;


		dcopy_vector(y_gen, n, 1, y_ori, incy_val);
		dcopy_vector(y_gen, n, 1, y_comp, incy_val);

		/* call BLAS_daxpby_s to get y_comp */
		FPU_FIX_STOP;
		BLAS_daxpby_s(n, alpha, x, incx_val, beta, y_comp, incy_val);
		FPU_FIX_START;


		/* computing the ratio */
		ix = 0;
		if (incx < 0)
		  ix = -(n - 1) * incx;
		iy = 0;
		if (incy < 0)
		  iy = -(n - 1) * incy;
		ratio = 0.0;

		ixmax = -1;
		iymax = -1;
		for (test_val = 0; test_val < n * incy_gen;
		     test_val += incy_gen) {
		  test_BLAS_ddot_s_s(1, blas_no_conj, alpha, beta, y_ori[iy],
				     y_comp[iy], head_y_true[test_val],
				     tail_y_true[test_val], &y_fix, incx,
				     &x[ix], incx, eps_int, un_int,
				     &new_ratio);

		  ix += incx;
		  iy += incy;
		  if (MAX(ratio, new_ratio) == new_ratio) {
		    ixmax = ix;
		    iymax = iy;
		  }
		  ratio = MAX(ratio, new_ratio);
		}

		/* increase the number of bad ratio, if the ratio
		   is bigger than the threshold.
		   The !<= below causes NaN error to be detected.
		   Note that (NaN > thresh) is always false. */
		if (!(ratio <= thresh)) {
		  bad_ratios++;


		  if ((debug == 3) &&	/* print only when debug is on */
		      (count != old_count) &&	/* print if old vector is different */
		      /* from the current one */
		      (d_count == find_max_ratio) &&
		      (p_count <= max_print) && (ratio > 0.5 * ratio_max)) {
		    old_count = count;

		    printf
		      ("FAIL> %s: n = %d, ntests = %d, threshold = %4.2f,\n",
		       fname, n, ntests, thresh);
		    printf("seed = %d\n", *seed);
		    printf("norm = %d\n", norm);


		    /* Print test info */
		    switch (prec) {
		    case blas_prec_single:
		      printf("single ");
		      break;
		    case blas_prec_double:
		      printf("double ");
		      break;
		    case blas_prec_indigenous:
		      printf("indigenous ");
		      break;
		    case blas_prec_extra:
		      printf("extra ");
		      break;
		    }
		    switch (norm) {
		    case -1:
		      printf("near_underflow ");
		      break;
		    case 0:
		      printf("near_one ");
		      break;
		    case 1:
		      printf("near_overflow ");
		      break;
		    }

		    printf("incx=%d, incy=%d:\n", incx, incy);

		    sprint_vector(x, n, incx_val, "x");
		    dprint_vector(y_ori, n, incy_val, "y_ori");
		    dprint_vector(y_comp, n, incy_val, "y_comp");

		    printf("      ");
		    printf("alpha = ");
		    printf("%24.16e", alpha);
		    printf("; ");
		    printf("beta = ");
		    printf("%24.16e", beta);
		    printf("\n");
		    printf("      ratio=%.4e\n", ratio);
		    printf("iymax = %d\n", iymax);
		    printf("ixmax = %d\n", ixmax);
		    p_count++;
		  }
		}
		if (d_count == 0) {
		  if (ratio > ratio_max)
		    ratio_max = ratio;
		  iymax_max = iymax;
		  ixmax_max = ixmax;
		  if (ratio != 0.0 && ratio < ratio_min)
		    ratio_min = ratio;

		  tot_tests++;
		}
	      }			/* incy */
	    }			/* incx */
	  }			/* tests */
	}			/* norm */

      }				/* beta */
    }				/* alpha */
  }				/* debug */

  if ((debug == 2) || ((debug == 1) && (bad_ratios > 0))) {
    printf("      %s:  n = %d, ntests = %d, thresh = %4.2f\n",
	   fname, n, ntests, thresh);
    if (ratio_min == 1.0e+308)
      ratio_min = 0.0;
    printf
      ("      bad/total = %d/%d=%3.2f, min_ratio = %.4e, max_ratio = %.4e\n\n",
       bad_ratios, tot_tests, ((double) bad_ratios) / ((double) tot_tests),
       ratio_min, ratio_max);
    printf("iymax_max = %d, ixmax_max = %d\n", iymax_max, ixmax_max);
  }

  blas_free(x);
  blas_free(y_ori);
  blas_free(y_comp);
  blas_free(head_y_true);
  blas_free(tail_y_true);
  blas_free(x_gen);
  blas_free(y_gen);

  *min_ratio = ratio_min;
  *num_bad_ratio = bad_ratios;
  *num_tests = tot_tests;

  FPU_FIX_STOP;
  return ratio_max;
}				/* end of do_test_daxpby_s */

double do_test_caxpby_s(int n, int ntests, int *seed, double thresh,
			int debug, double *min_ratio, int *num_bad_ratio,
			int *num_tests)

/*
 * Purpose  
 * =======
 *
 * Runs a series of tests on axpby  
 *
 * Arguments
 * =========
 *
 * n         (input) int
 *           The size of vector being tested
 *
 * ntests    (input) int
 *           The number of tests to run for each set of attributes.
 *
 * seed      (input/output) int         
 *           The seed for the random number generator used in testgen().
 *
 * thresh    (input) double
 *           When the ratio returned from test() exceeds the specified
 *           threshold, the current size, y_true, y_comp, and ratio will be
 *           printed.  (Since ratio is supposed to be O(1), we can set thresh
 *           to ~10.)
 *
 * debug     (input) int
 *           If debug=3, print summary 
 *           If debug=2, print summary only if the number of bad ratios > 0
 *           If debug=1, print complete info if tests fail
 *           If debug=0, return max ratio
 *
 * min_ratio (output) double
 *           The minimum ratio
 * 
 * num_bad_ratio (output) int
 *               The number of tests fail; they are above the threshold.
 *
 * num_tests (output) int
 *           The number of tests is being performed.
 *
 * Return value
 * ============
 *
 * The maximum ratio if run successfully, otherwise return -1 
 *
 * Code structure
 * ==============
 * 
 *  debug loop  -- if debug is one, the first loop computes the max ratio
 *              -- and the last(second) loop outputs debugging information,
 *              -- if the test fail and its ratio > 0.5 * max ratio.
 *              -- if debug is zero, the loop is executed once
 *    alpha loop  -- varying alpha: 0, 1, or random
 *      beta loop   -- varying beta: 0, 1, or random

 *          norm loop   -- varying norm: near undeflow, near one, or 
 *                        -- near overflow
 *            numtest loop  -- how many times the test is perform with 
 *                            -- above set of attributes
 *                incx loop     -- varying incx: -2, -1, 1, 2
 *                  incy loop     -- varying incy: -2, -1, 1, 2
 */
{
  /* function name */
  const char fname[] = "BLAS_caxpby_s";

  /* max number of debug lines to print */
  const int max_print = 32;

  /* Variables in the "x_val" form are loop vars for corresponding
     variables */
  int i;			/* iterate through the repeating tests */
  int ix, iy;			/* use to index x and y respectively */
  int incx_val, incy_val,	/* for testing different inc values */
    incx, incy, incx_gen, incy_gen, ygen_val, xgen_val, test_val;
  int d_count;			/* counter for debug */
  int find_max_ratio;		/* find_max_ratio = 1 only if debug = 3 */
  int p_count;			/* counter for the number of debug lines printed */
  int tot_tests;		/* total number of tests to be done */
  int norm;			/* input values of near underflow/one/overflow */
  double ratio_max;		/* the current maximum ratio */
  double ratio_min;		/* the current minimum ratio */
  double ratio;			/* the per-use test ratio from test() */
  double new_ratio;
  int bad_ratios;		/* the number of ratios over the threshold */
  double eps_int;		/* the internal epsilon expected--2^(-24) for float */
  double un_int;		/* the internal underflow threshold */
  float alpha[2];
  float beta[2];
  float *x;
  float y_fix;
  float *y_ori;
  float *y_comp;		/* the y computed  by BLAS_caxpby_s */

  int ixmax, iymax;
  int ixmax_max, iymax_max;

  /* x_gen and y_gen are used to store vectors generated by testgen.
     they eventually are copied back to x and y */
  float *x_gen;
  float *y_gen;

  /* the true y calculated by testgen(), in double-double */
  double *head_y_true, *tail_y_true;

  int alpha_val;
  int alpha_flag;		/* input flag for BLAS_cdot_s_s_testgen */
  int beta_val;
  int beta_flag;		/* input flag for BLAS_cdot_s_s_testgen */

  enum blas_prec_type prec;
  int saved_seed;		/* for saving the original seed */
  int count, old_count;		/* use for counting the number of testgen calls * 2 */

  FPU_FIX_DECL;

  /* test for bad arguments */
  if (n < 0 || ntests < 0)
    BLAS_error(fname, 0, 0, NULL);

  /* if there is nothing to test, return all zero */
  if (n == 0 || ntests == 0) {
    *min_ratio = 0.0;
    *num_bad_ratio = 0;
    *num_tests = 0;
    return 0.0;
  }

  FPU_FIX_START;

  /* get space for calculation */
  x = (float *) blas_malloc(n * 2 * sizeof(float));
  if (n * 2 > 0 && x == NULL) {
    BLAS_error("blas_malloc", 0, 0, "malloc failed.\n");
  }
  y_ori = (float *) blas_malloc(n * 2 * sizeof(float) * 2);
  if (n * 2 > 0 && y_ori == NULL) {
    BLAS_error("blas_malloc", 0, 0, "malloc failed.\n");
  }
  y_comp = (float *) blas_malloc(n * 2 * sizeof(float) * 2);
  if (n * 2 > 0 && y_comp == NULL) {
    BLAS_error("blas_malloc", 0, 0, "malloc failed.\n");
  }
  head_y_true = (double *) blas_malloc(n * sizeof(double) * 2);
  tail_y_true = (double *) blas_malloc(n * sizeof(double) * 2);
  if (n > 0 && (head_y_true == NULL || tail_y_true == NULL)) {
    BLAS_error("blas_malloc", 0, 0, "malloc failed.\n");
  }
  x_gen = (float *) blas_malloc(n * sizeof(float));
  if (n > 0 && x_gen == NULL) {
    BLAS_error("blas_malloc", 0, 0, "malloc failed.\n");
  }
  y_gen = (float *) blas_malloc(n * sizeof(float) * 2);
  if (n > 0 && y_gen == NULL) {
    BLAS_error("blas_malloc", 0, 0, "malloc failed.\n");
  }

  /* initialization */
  saved_seed = *seed;
  ratio_min = 1e308;
  ratio_max = 0.0;
  tot_tests = 0;
  p_count = 0;
  count = 0;
  bad_ratios = 0;
  ixmax_max = 0;
  iymax_max = 0;
  alpha_flag = 0;
  beta_flag = 0;
  old_count = 0;

  find_max_ratio = 0;
  if (debug == 3)
    find_max_ratio = 1;
  y_fix = 1.0;

  /* initialize incx_gen and incy_gen */
  incx_gen = 1;
  incy_gen = 1;

  incy_gen *= 2;

  /* The debug iteration:
     If debug=1, then will execute the iteration twice. First, compute the
     max ratio. Second, print info if ratio > (50% * ratio_max). */
  for (d_count = 0; d_count <= find_max_ratio; d_count++) {
    bad_ratios = 0;		/* set to zero */

    if ((debug == 3) && (d_count == find_max_ratio))
      *seed = saved_seed;	/* restore the original seed */

    /* varying alpha */
    for (alpha_val = 0; alpha_val < 3; alpha_val++) {
      alpha_flag = 0;
      switch (alpha_val) {
      case 0:
	alpha[0] = alpha[1] = 0.0;
	alpha_flag = 1;
	break;
      case 1:
	alpha[0] = 1.0;
	alpha[1] = 0.0;
	alpha_flag = 1;
	break;
      }

      /* varying beta */
      for (beta_val = 0; beta_val < 3; beta_val++) {
	beta_flag = 0;
	switch (beta_val) {
	case 0:
	  beta[0] = beta[1] = 0.0;
	  beta_flag = 1;
	  break;
	case 1:
	  beta[0] = 1.0;
	  beta[1] = 0.0;
	  beta_flag = 1;
	  break;
	}


	eps_int = power(2, -BITS_S);
	un_int = pow((double) BLAS_fpinfo_x(blas_base, blas_prec_single),
		     (double) BLAS_fpinfo_x(blas_emin, blas_prec_single));
	prec = blas_prec_single;

	/* values near underflow, 1, or overflow */
	for (norm = -1; norm <= 1; norm++) {

	  /* number of tests */
	  for (i = 0; i < ntests; i++) {

	    /* generate test inputs */
	    BLAS_cdot_s_s_testgen(1, 0, 1, norm, blas_no_conj, alpha,
				  alpha_flag, beta, beta_flag, &y_fix, x_gen,
				  seed, y_gen, head_y_true, tail_y_true);
	    xgen_val = incx_gen;
	    for (ygen_val = incy_gen; ygen_val < n * incy_gen;
		 ygen_val += incy_gen) {
	      BLAS_cdot_s_s_testgen(1, 0, 1, norm, blas_no_conj, alpha, 1,
				    beta, 1, &y_fix, &x_gen[xgen_val], seed,
				    &y_gen[ygen_val], &head_y_true[ygen_val],
				    &tail_y_true[ygen_val]);
	      xgen_val += incx_gen;
	    }

	    count++;

	    /* varying incx */
	    for (incx_val = -2; incx_val <= 2; incx_val++) {
	      if (incx_val == 0)
		continue;

	      /* setting incx */
	      incx = incx_val;

	      scopy_vector(x_gen, n, 1, x, incx_val);

	      /* varying incy */
	      for (incy_val = -2; incy_val <= 2; incy_val++) {
		if (incy_val == 0)
		  continue;

		/* setting incy */
		incy = incy_val;
		incy *= 2;

		ccopy_vector(y_gen, n, 1, y_ori, incy_val);
		ccopy_vector(y_gen, n, 1, y_comp, incy_val);

		/* call BLAS_caxpby_s to get y_comp */
		FPU_FIX_STOP;
		BLAS_caxpby_s(n, alpha, x, incx_val, beta, y_comp, incy_val);
		FPU_FIX_START;


		/* computing the ratio */
		ix = 0;
		if (incx < 0)
		  ix = -(n - 1) * incx;
		iy = 0;
		if (incy < 0)
		  iy = -(n - 1) * incy;
		ratio = 0.0;

		ixmax = -1;
		iymax = -1;
		for (test_val = 0; test_val < n * incy_gen;
		     test_val += incy_gen) {
		  test_BLAS_cdot_s_s(1, blas_no_conj, alpha, beta, &y_ori[iy],
				     &y_comp[iy], &head_y_true[test_val],
				     &tail_y_true[test_val], &y_fix, incx,
				     &x[ix], incx, eps_int, un_int,
				     &new_ratio);

		  ix += incx;
		  iy += incy;
		  if (MAX(ratio, new_ratio) == new_ratio) {
		    ixmax = ix;
		    iymax = iy;
		  }
		  ratio = MAX(ratio, new_ratio);
		}

		/* increase the number of bad ratio, if the ratio
		   is bigger than the threshold.
		   The !<= below causes NaN error to be detected.
		   Note that (NaN > thresh) is always false. */
		if (!(ratio <= thresh)) {
		  bad_ratios++;


		  if ((debug == 3) &&	/* print only when debug is on */
		      (count != old_count) &&	/* print if old vector is different */
		      /* from the current one */
		      (d_count == find_max_ratio) &&
		      (p_count <= max_print) && (ratio > 0.5 * ratio_max)) {
		    old_count = count;

		    printf
		      ("FAIL> %s: n = %d, ntests = %d, threshold = %4.2f,\n",
		       fname, n, ntests, thresh);
		    printf("seed = %d\n", *seed);
		    printf("norm = %d\n", norm);


		    /* Print test info */
		    switch (prec) {
		    case blas_prec_single:
		      printf("single ");
		      break;
		    case blas_prec_double:
		      printf("double ");
		      break;
		    case blas_prec_indigenous:
		      printf("indigenous ");
		      break;
		    case blas_prec_extra:
		      printf("extra ");
		      break;
		    }
		    switch (norm) {
		    case -1:
		      printf("near_underflow ");
		      break;
		    case 0:
		      printf("near_one ");
		      break;
		    case 1:
		      printf("near_overflow ");
		      break;
		    }

		    printf("incx=%d, incy=%d:\n", incx, incy);

		    sprint_vector(x, n, incx_val, "x");
		    cprint_vector(y_ori, n, incy_val, "y_ori");
		    cprint_vector(y_comp, n, incy_val, "y_comp");

		    printf("      ");
		    printf("alpha = ");
		    printf("(%16.8e, %16.8e)", alpha[0], alpha[1]);
		    printf("; ");
		    printf("beta = ");
		    printf("(%16.8e, %16.8e)", beta[0], beta[1]);
		    printf("\n");
		    printf("      ratio=%.4e\n", ratio);
		    printf("iymax = %d\n", iymax);
		    printf("ixmax = %d\n", ixmax);
		    p_count++;
		  }
		}
		if (d_count == 0) {
		  if (ratio > ratio_max)
		    ratio_max = ratio;
		  iymax_max = iymax;
		  ixmax_max = ixmax;
		  if (ratio != 0.0 && ratio < ratio_min)
		    ratio_min = ratio;

		  tot_tests++;
		}
	      }			/* incy */
	    }			/* incx */
	  }			/* tests */
	}			/* norm */

      }				/* beta */
    }				/* alpha */
  }				/* debug */

  if ((debug == 2) || ((debug == 1) && (bad_ratios > 0))) {
    printf("      %s:  n = %d, ntests = %d, thresh = %4.2f\n",
	   fname, n, ntests, thresh);
    if (ratio_min == 1.0e+308)
      ratio_min = 0.0;
    printf
      ("      bad/total = %d/%d=%3.2f, min_ratio = %.4e, max_ratio = %.4e\n\n",
       bad_ratios, tot_tests, ((double) bad_ratios) / ((double) tot_tests),
       ratio_min, ratio_max);
    printf("iymax_max = %d, ixmax_max = %d\n", iymax_max, ixmax_max);
  }

  blas_free(x);
  blas_free(y_ori);
  blas_free(y_comp);
  blas_free(head_y_true);
  blas_free(tail_y_true);
  blas_free(x_gen);
  blas_free(y_gen);

  *min_ratio = ratio_min;
  *num_bad_ratio = bad_ratios;
  *num_tests = tot_tests;

  FPU_FIX_STOP;
  return ratio_max;
}				/* end of do_test_caxpby_s */

double do_test_zaxpby_c(int n, int ntests, int *seed, double thresh,
			int debug, double *min_ratio, int *num_bad_ratio,
			int *num_tests)

/*
 * Purpose  
 * =======
 *
 * Runs a series of tests on axpby  
 *
 * Arguments
 * =========
 *
 * n         (input) int
 *           The size of vector being tested
 *
 * ntests    (input) int
 *           The number of tests to run for each set of attributes.
 *
 * seed      (input/output) int         
 *           The seed for the random number generator used in testgen().
 *
 * thresh    (input) double
 *           When the ratio returned from test() exceeds the specified
 *           threshold, the current size, y_true, y_comp, and ratio will be
 *           printed.  (Since ratio is supposed to be O(1), we can set thresh
 *           to ~10.)
 *
 * debug     (input) int
 *           If debug=3, print summary 
 *           If debug=2, print summary only if the number of bad ratios > 0
 *           If debug=1, print complete info if tests fail
 *           If debug=0, return max ratio
 *
 * min_ratio (output) double
 *           The minimum ratio
 * 
 * num_bad_ratio (output) int
 *               The number of tests fail; they are above the threshold.
 *
 * num_tests (output) int
 *           The number of tests is being performed.
 *
 * Return value
 * ============
 *
 * The maximum ratio if run successfully, otherwise return -1 
 *
 * Code structure
 * ==============
 * 
 *  debug loop  -- if debug is one, the first loop computes the max ratio
 *              -- and the last(second) loop outputs debugging information,
 *              -- if the test fail and its ratio > 0.5 * max ratio.
 *              -- if debug is zero, the loop is executed once
 *    alpha loop  -- varying alpha: 0, 1, or random
 *      beta loop   -- varying beta: 0, 1, or random

 *          norm loop   -- varying norm: near undeflow, near one, or 
 *                        -- near overflow
 *            numtest loop  -- how many times the test is perform with 
 *                            -- above set of attributes
 *                incx loop     -- varying incx: -2, -1, 1, 2
 *                  incy loop     -- varying incy: -2, -1, 1, 2
 */
{
  /* function name */
  const char fname[] = "BLAS_zaxpby_c";

  /* max number of debug lines to print */
  const int max_print = 32;

  /* Variables in the "x_val" form are loop vars for corresponding
     variables */
  int i;			/* iterate through the repeating tests */
  int ix, iy;			/* use to index x and y respectively */
  int incx_val, incy_val,	/* for testing different inc values */
    incx, incy, incx_gen, incy_gen, ygen_val, xgen_val, test_val;
  int d_count;			/* counter for debug */
  int find_max_ratio;		/* find_max_ratio = 1 only if debug = 3 */
  int p_count;			/* counter for the number of debug lines printed */
  int tot_tests;		/* total number of tests to be done */
  int norm;			/* input values of near underflow/one/overflow */
  double ratio_max;		/* the current maximum ratio */
  double ratio_min;		/* the current minimum ratio */
  double ratio;			/* the per-use test ratio from test() */
  double new_ratio;
  int bad_ratios;		/* the number of ratios over the threshold */
  double eps_int;		/* the internal epsilon expected--2^(-24) for float */
  double un_int;		/* the internal underflow threshold */
  double alpha[2];
  double beta[2];
  float *x;
  float y_fix[2];
  double *y_ori;
  double *y_comp;		/* the y computed  by BLAS_zaxpby_c */

  int ixmax, iymax;
  int ixmax_max, iymax_max;

  /* x_gen and y_gen are used to store vectors generated by testgen.
     they eventually are copied back to x and y */
  float *x_gen;
  double *y_gen;

  /* the true y calculated by testgen(), in double-double */
  double *head_y_true, *tail_y_true;

  int alpha_val;
  int alpha_flag;		/* input flag for BLAS_zdot_c_c_testgen */
  int beta_val;
  int beta_flag;		/* input flag for BLAS_zdot_c_c_testgen */

  enum blas_prec_type prec;
  int saved_seed;		/* for saving the original seed */
  int count, old_count;		/* use for counting the number of testgen calls * 2 */

  FPU_FIX_DECL;

  /* test for bad arguments */
  if (n < 0 || ntests < 0)
    BLAS_error(fname, 0, 0, NULL);

  /* if there is nothing to test, return all zero */
  if (n == 0 || ntests == 0) {
    *min_ratio = 0.0;
    *num_bad_ratio = 0;
    *num_tests = 0;
    return 0.0;
  }

  FPU_FIX_START;

  /* get space for calculation */
  x = (float *) blas_malloc(n * 2 * sizeof(float) * 2);
  if (n * 2 > 0 && x == NULL) {
    BLAS_error("blas_malloc", 0, 0, "malloc failed.\n");
  }
  y_ori = (double *) blas_malloc(n * 2 * sizeof(double) * 2);
  if (n * 2 > 0 && y_ori == NULL) {
    BLAS_error("blas_malloc", 0, 0, "malloc failed.\n");
  }
  y_comp = (double *) blas_malloc(n * 2 * sizeof(double) * 2);
  if (n * 2 > 0 && y_comp == NULL) {
    BLAS_error("blas_malloc", 0, 0, "malloc failed.\n");
  }
  head_y_true = (double *) blas_malloc(n * sizeof(double) * 2);
  tail_y_true = (double *) blas_malloc(n * sizeof(double) * 2);
  if (n > 0 && (head_y_true == NULL || tail_y_true == NULL)) {
    BLAS_error("blas_malloc", 0, 0, "malloc failed.\n");
  }
  x_gen = (float *) blas_malloc(n * sizeof(float) * 2);
  if (n > 0 && x_gen == NULL) {
    BLAS_error("blas_malloc", 0, 0, "malloc failed.\n");
  }
  y_gen = (double *) blas_malloc(n * sizeof(double) * 2);
  if (n > 0 && y_gen == NULL) {
    BLAS_error("blas_malloc", 0, 0, "malloc failed.\n");
  }

  /* initialization */
  saved_seed = *seed;
  ratio_min = 1e308;
  ratio_max = 0.0;
  tot_tests = 0;
  p_count = 0;
  count = 0;
  bad_ratios = 0;
  ixmax_max = 0;
  iymax_max = 0;
  alpha_flag = 0;
  beta_flag = 0;
  old_count = 0;

  find_max_ratio = 0;
  if (debug == 3)
    find_max_ratio = 1;
  y_fix[0] = 1.0;
  y_fix[1] = 0.0;

  /* initialize incx_gen and incy_gen */
  incx_gen = 1;
  incy_gen = 1;
  incx_gen *= 2;
  incy_gen *= 2;

  /* The debug iteration:
     If debug=1, then will execute the iteration twice. First, compute the
     max ratio. Second, print info if ratio > (50% * ratio_max). */
  for (d_count = 0; d_count <= find_max_ratio; d_count++) {
    bad_ratios = 0;		/* set to zero */

    if ((debug == 3) && (d_count == find_max_ratio))
      *seed = saved_seed;	/* restore the original seed */

    /* varying alpha */
    for (alpha_val = 0; alpha_val < 3; alpha_val++) {
      alpha_flag = 0;
      switch (alpha_val) {
      case 0:
	alpha[0] = alpha[1] = 0.0;
	alpha_flag = 1;
	break;
      case 1:
	alpha[0] = 1.0;
	alpha[1] = 0.0;
	alpha_flag = 1;
	break;
      }

      /* varying beta */
      for (beta_val = 0; beta_val < 3; beta_val++) {
	beta_flag = 0;
	switch (beta_val) {
	case 0:
	  beta[0] = beta[1] = 0.0;
	  beta_flag = 1;
	  break;
	case 1:
	  beta[0] = 1.0;
	  beta[1] = 0.0;
	  beta_flag = 1;
	  break;
	}


	eps_int = power(2, -BITS_D);
	un_int = pow((double) BLAS_fpinfo_x(blas_base, blas_prec_double),
		     (double) BLAS_fpinfo_x(blas_emin, blas_prec_double));
	prec = blas_prec_double;

	/* values near underflow, 1, or overflow */
	for (norm = -1; norm <= 1; norm++) {

	  /* number of tests */
	  for (i = 0; i < ntests; i++) {

	    /* generate test inputs */
	    BLAS_zdot_c_c_testgen(1, 0, 1, norm, blas_no_conj, alpha,
				  alpha_flag, beta, beta_flag, y_fix, x_gen,
				  seed, y_gen, head_y_true, tail_y_true);
	    xgen_val = incx_gen;
	    for (ygen_val = incy_gen; ygen_val < n * incy_gen;
		 ygen_val += incy_gen) {
	      BLAS_zdot_c_c_testgen(1, 0, 1, norm, blas_no_conj, alpha, 1,
				    beta, 1, y_fix, &x_gen[xgen_val], seed,
				    &y_gen[ygen_val], &head_y_true[ygen_val],
				    &tail_y_true[ygen_val]);
	      xgen_val += incx_gen;
	    }

	    count++;

	    /* varying incx */
	    for (incx_val = -2; incx_val <= 2; incx_val++) {
	      if (incx_val == 0)
		continue;

	      /* setting incx */
	      incx = incx_val;

	      ccopy_vector(x_gen, n, 1, x, incx_val);

	      /* varying incy */
	      for (incy_val = -2; incy_val <= 2; incy_val++) {
		if (incy_val == 0)
		  continue;

		/* setting incy */
		incy = incy_val;
		incy *= 2;

		zcopy_vector(y_gen, n, 1, y_ori, incy_val);
		zcopy_vector(y_gen, n, 1, y_comp, incy_val);

		/* call BLAS_zaxpby_c to get y_comp */
		FPU_FIX_STOP;
		BLAS_zaxpby_c(n, alpha, x, incx_val, beta, y_comp, incy_val);
		FPU_FIX_START;


		/* computing the ratio */
		ix = 0;
		if (incx < 0)
		  ix = -(n - 1) * incx;
		iy = 0;
		if (incy < 0)
		  iy = -(n - 1) * incy;
		ratio = 0.0;

		ixmax = -1;
		iymax = -1;
		for (test_val = 0; test_val < n * incy_gen;
		     test_val += incy_gen) {
		  test_BLAS_zdot_c_c(1, blas_no_conj, alpha, beta, &y_ori[iy],
				     &y_comp[iy], &head_y_true[test_val],
				     &tail_y_true[test_val], y_fix, incx,
				     &x[ix], incx, eps_int, un_int,
				     &new_ratio);

		  ix += incx;
		  iy += incy;
		  if (MAX(ratio, new_ratio) == new_ratio) {
		    ixmax = ix;
		    iymax = iy;
		  }
		  ratio = MAX(ratio, new_ratio);
		}

		/* increase the number of bad ratio, if the ratio
		   is bigger than the threshold.
		   The !<= below causes NaN error to be detected.
		   Note that (NaN > thresh) is always false. */
		if (!(ratio <= thresh)) {
		  bad_ratios++;


		  if ((debug == 3) &&	/* print only when debug is on */
		      (count != old_count) &&	/* print if old vector is different */
		      /* from the current one */
		      (d_count == find_max_ratio) &&
		      (p_count <= max_print) && (ratio > 0.5 * ratio_max)) {
		    old_count = count;

		    printf
		      ("FAIL> %s: n = %d, ntests = %d, threshold = %4.2f,\n",
		       fname, n, ntests, thresh);
		    printf("seed = %d\n", *seed);
		    printf("norm = %d\n", norm);


		    /* Print test info */
		    switch (prec) {
		    case blas_prec_single:
		      printf("single ");
		      break;
		    case blas_prec_double:
		      printf("double ");
		      break;
		    case blas_prec_indigenous:
		      printf("indigenous ");
		      break;
		    case blas_prec_extra:
		      printf("extra ");
		      break;
		    }
		    switch (norm) {
		    case -1:
		      printf("near_underflow ");
		      break;
		    case 0:
		      printf("near_one ");
		      break;
		    case 1:
		      printf("near_overflow ");
		      break;
		    }

		    printf("incx=%d, incy=%d:\n", incx, incy);

		    cprint_vector(x, n, incx_val, "x");
		    zprint_vector(y_ori, n, incy_val, "y_ori");
		    zprint_vector(y_comp, n, incy_val, "y_comp");

		    printf("      ");
		    printf("alpha = ");
		    printf("(%24.16e, %24.16e)", alpha[0], alpha[1]);
		    printf("; ");
		    printf("beta = ");
		    printf("(%24.16e, %24.16e)", beta[0], beta[1]);
		    printf("\n");
		    printf("      ratio=%.4e\n", ratio);
		    printf("iymax = %d\n", iymax);
		    printf("ixmax = %d\n", ixmax);
		    p_count++;
		  }
		}
		if (d_count == 0) {
		  if (ratio > ratio_max)
		    ratio_max = ratio;
		  iymax_max = iymax;
		  ixmax_max = ixmax;
		  if (ratio != 0.0 && ratio < ratio_min)
		    ratio_min = ratio;

		  tot_tests++;
		}
	      }			/* incy */
	    }			/* incx */
	  }			/* tests */
	}			/* norm */

      }				/* beta */
    }				/* alpha */
  }				/* debug */

  if ((debug == 2) || ((debug == 1) && (bad_ratios > 0))) {
    printf("      %s:  n = %d, ntests = %d, thresh = %4.2f\n",
	   fname, n, ntests, thresh);
    if (ratio_min == 1.0e+308)
      ratio_min = 0.0;
    printf
      ("      bad/total = %d/%d=%3.2f, min_ratio = %.4e, max_ratio = %.4e\n\n",
       bad_ratios, tot_tests, ((double) bad_ratios) / ((double) tot_tests),
       ratio_min, ratio_max);
    printf("iymax_max = %d, ixmax_max = %d\n", iymax_max, ixmax_max);
  }

  blas_free(x);
  blas_free(y_ori);
  blas_free(y_comp);
  blas_free(head_y_true);
  blas_free(tail_y_true);
  blas_free(x_gen);
  blas_free(y_gen);

  *min_ratio = ratio_min;
  *num_bad_ratio = bad_ratios;
  *num_tests = tot_tests;

  FPU_FIX_STOP;
  return ratio_max;
}				/* end of do_test_zaxpby_c */

double do_test_zaxpby_d(int n, int ntests, int *seed, double thresh,
			int debug, double *min_ratio, int *num_bad_ratio,
			int *num_tests)

/*
 * Purpose  
 * =======
 *
 * Runs a series of tests on axpby  
 *
 * Arguments
 * =========
 *
 * n         (input) int
 *           The size of vector being tested
 *
 * ntests    (input) int
 *           The number of tests to run for each set of attributes.
 *
 * seed      (input/output) int         
 *           The seed for the random number generator used in testgen().
 *
 * thresh    (input) double
 *           When the ratio returned from test() exceeds the specified
 *           threshold, the current size, y_true, y_comp, and ratio will be
 *           printed.  (Since ratio is supposed to be O(1), we can set thresh
 *           to ~10.)
 *
 * debug     (input) int
 *           If debug=3, print summary 
 *           If debug=2, print summary only if the number of bad ratios > 0
 *           If debug=1, print complete info if tests fail
 *           If debug=0, return max ratio
 *
 * min_ratio (output) double
 *           The minimum ratio
 * 
 * num_bad_ratio (output) int
 *               The number of tests fail; they are above the threshold.
 *
 * num_tests (output) int
 *           The number of tests is being performed.
 *
 * Return value
 * ============
 *
 * The maximum ratio if run successfully, otherwise return -1 
 *
 * Code structure
 * ==============
 * 
 *  debug loop  -- if debug is one, the first loop computes the max ratio
 *              -- and the last(second) loop outputs debugging information,
 *              -- if the test fail and its ratio > 0.5 * max ratio.
 *              -- if debug is zero, the loop is executed once
 *    alpha loop  -- varying alpha: 0, 1, or random
 *      beta loop   -- varying beta: 0, 1, or random

 *          norm loop   -- varying norm: near undeflow, near one, or 
 *                        -- near overflow
 *            numtest loop  -- how many times the test is perform with 
 *                            -- above set of attributes
 *                incx loop     -- varying incx: -2, -1, 1, 2
 *                  incy loop     -- varying incy: -2, -1, 1, 2
 */
{
  /* function name */
  const char fname[] = "BLAS_zaxpby_d";

  /* max number of debug lines to print */
  const int max_print = 32;

  /* Variables in the "x_val" form are loop vars for corresponding
     variables */
  int i;			/* iterate through the repeating tests */
  int ix, iy;			/* use to index x and y respectively */
  int incx_val, incy_val,	/* for testing different inc values */
    incx, incy, incx_gen, incy_gen, ygen_val, xgen_val, test_val;
  int d_count;			/* counter for debug */
  int find_max_ratio;		/* find_max_ratio = 1 only if debug = 3 */
  int p_count;			/* counter for the number of debug lines printed */
  int tot_tests;		/* total number of tests to be done */
  int norm;			/* input values of near underflow/one/overflow */
  double ratio_max;		/* the current maximum ratio */
  double ratio_min;		/* the current minimum ratio */
  double ratio;			/* the per-use test ratio from test() */
  double new_ratio;
  int bad_ratios;		/* the number of ratios over the threshold */
  double eps_int;		/* the internal epsilon expected--2^(-24) for float */
  double un_int;		/* the internal underflow threshold */
  double alpha[2];
  double beta[2];
  double *x;
  double y_fix;
  double *y_ori;
  double *y_comp;		/* the y computed  by BLAS_zaxpby_d */

  int ixmax, iymax;
  int ixmax_max, iymax_max;

  /* x_gen and y_gen are used to store vectors generated by testgen.
     they eventually are copied back to x and y */
  double *x_gen;
  double *y_gen;

  /* the true y calculated by testgen(), in double-double */
  double *head_y_true, *tail_y_true;

  int alpha_val;
  int alpha_flag;		/* input flag for BLAS_zdot_d_d_testgen */
  int beta_val;
  int beta_flag;		/* input flag for BLAS_zdot_d_d_testgen */

  enum blas_prec_type prec;
  int saved_seed;		/* for saving the original seed */
  int count, old_count;		/* use for counting the number of testgen calls * 2 */

  FPU_FIX_DECL;

  /* test for bad arguments */
  if (n < 0 || ntests < 0)
    BLAS_error(fname, 0, 0, NULL);

  /* if there is nothing to test, return all zero */
  if (n == 0 || ntests == 0) {
    *min_ratio = 0.0;
    *num_bad_ratio = 0;
    *num_tests = 0;
    return 0.0;
  }

  FPU_FIX_START;

  /* get space for calculation */
  x = (double *) blas_malloc(n * 2 * sizeof(double));
  if (n * 2 > 0 && x == NULL) {
    BLAS_error("blas_malloc", 0, 0, "malloc failed.\n");
  }
  y_ori = (double *) blas_malloc(n * 2 * sizeof(double) * 2);
  if (n * 2 > 0 && y_ori == NULL) {
    BLAS_error("blas_malloc", 0, 0, "malloc failed.\n");
  }
  y_comp = (double *) blas_malloc(n * 2 * sizeof(double) * 2);
  if (n * 2 > 0 && y_comp == NULL) {
    BLAS_error("blas_malloc", 0, 0, "malloc failed.\n");
  }
  head_y_true = (double *) blas_malloc(n * sizeof(double) * 2);
  tail_y_true = (double *) blas_malloc(n * sizeof(double) * 2);
  if (n > 0 && (head_y_true == NULL || tail_y_true == NULL)) {
    BLAS_error("blas_malloc", 0, 0, "malloc failed.\n");
  }
  x_gen = (double *) blas_malloc(n * sizeof(double));
  if (n > 0 && x_gen == NULL) {
    BLAS_error("blas_malloc", 0, 0, "malloc failed.\n");
  }
  y_gen = (double *) blas_malloc(n * sizeof(double) * 2);
  if (n > 0 && y_gen == NULL) {
    BLAS_error("blas_malloc", 0, 0, "malloc failed.\n");
  }

  /* initialization */
  saved_seed = *seed;
  ratio_min = 1e308;
  ratio_max = 0.0;
  tot_tests = 0;
  p_count = 0;
  count = 0;
  bad_ratios = 0;
  ixmax_max = 0;
  iymax_max = 0;
  alpha_flag = 0;
  beta_flag = 0;
  old_count = 0;

  find_max_ratio = 0;
  if (debug == 3)
    find_max_ratio = 1;
  y_fix = 1.0;

  /* initialize incx_gen and incy_gen */
  incx_gen = 1;
  incy_gen = 1;

  incy_gen *= 2;

  /* The debug iteration:
     If debug=1, then will execute the iteration twice. First, compute the
     max ratio. Second, print info if ratio > (50% * ratio_max). */
  for (d_count = 0; d_count <= find_max_ratio; d_count++) {
    bad_ratios = 0;		/* set to zero */

    if ((debug == 3) && (d_count == find_max_ratio))
      *seed = saved_seed;	/* restore the original seed */

    /* varying alpha */
    for (alpha_val = 0; alpha_val < 3; alpha_val++) {
      alpha_flag = 0;
      switch (alpha_val) {
      case 0:
	alpha[0] = alpha[1] = 0.0;
	alpha_flag = 1;
	break;
      case 1:
	alpha[0] = 1.0;
	alpha[1] = 0.0;
	alpha_flag = 1;
	break;
      }

      /* varying beta */
      for (beta_val = 0; beta_val < 3; beta_val++) {
	beta_flag = 0;
	switch (beta_val) {
	case 0:
	  beta[0] = beta[1] = 0.0;
	  beta_flag = 1;
	  break;
	case 1:
	  beta[0] = 1.0;
	  beta[1] = 0.0;
	  beta_flag = 1;
	  break;
	}


	eps_int = power(2, -BITS_D);
	un_int = pow((double) BLAS_fpinfo_x(blas_base, blas_prec_double),
		     (double) BLAS_fpinfo_x(blas_emin, blas_prec_double));
	prec = blas_prec_double;

	/* values near underflow, 1, or overflow */
	for (norm = -1; norm <= 1; norm++) {

	  /* number of tests */
	  for (i = 0; i < ntests; i++) {

	    /* generate test inputs */
	    BLAS_zdot_d_d_testgen(1, 0, 1, norm, blas_no_conj, alpha,
				  alpha_flag, beta, beta_flag, &y_fix, x_gen,
				  seed, y_gen, head_y_true, tail_y_true);
	    xgen_val = incx_gen;
	    for (ygen_val = incy_gen; ygen_val < n * incy_gen;
		 ygen_val += incy_gen) {
	      BLAS_zdot_d_d_testgen(1, 0, 1, norm, blas_no_conj, alpha, 1,
				    beta, 1, &y_fix, &x_gen[xgen_val], seed,
				    &y_gen[ygen_val], &head_y_true[ygen_val],
				    &tail_y_true[ygen_val]);
	      xgen_val += incx_gen;
	    }

	    count++;

	    /* varying incx */
	    for (incx_val = -2; incx_val <= 2; incx_val++) {
	      if (incx_val == 0)
		continue;

	      /* setting incx */
	      incx = incx_val;

	      dcopy_vector(x_gen, n, 1, x, incx_val);

	      /* varying incy */
	      for (incy_val = -2; incy_val <= 2; incy_val++) {
		if (incy_val == 0)
		  continue;

		/* setting incy */
		incy = incy_val;
		incy *= 2;

		zcopy_vector(y_gen, n, 1, y_ori, incy_val);
		zcopy_vector(y_gen, n, 1, y_comp, incy_val);

		/* call BLAS_zaxpby_d to get y_comp */
		FPU_FIX_STOP;
		BLAS_zaxpby_d(n, alpha, x, incx_val, beta, y_comp, incy_val);
		FPU_FIX_START;


		/* computing the ratio */
		ix = 0;
		if (incx < 0)
		  ix = -(n - 1) * incx;
		iy = 0;
		if (incy < 0)
		  iy = -(n - 1) * incy;
		ratio = 0.0;

		ixmax = -1;
		iymax = -1;
		for (test_val = 0; test_val < n * incy_gen;
		     test_val += incy_gen) {
		  test_BLAS_zdot_d_d(1, blas_no_conj, alpha, beta, &y_ori[iy],
				     &y_comp[iy], &head_y_true[test_val],
				     &tail_y_true[test_val], &y_fix, incx,
				     &x[ix], incx, eps_int, un_int,
				     &new_ratio);

		  ix += incx;
		  iy += incy;
		  if (MAX(ratio, new_ratio) == new_ratio) {
		    ixmax = ix;
		    iymax = iy;
		  }
		  ratio = MAX(ratio, new_ratio);
		}

		/* increase the number of bad ratio, if the ratio
		   is bigger than the threshold.
		   The !<= below causes NaN error to be detected.
		   Note that (NaN > thresh) is always false. */
		if (!(ratio <= thresh)) {
		  bad_ratios++;


		  if ((debug == 3) &&	/* print only when debug is on */
		      (count != old_count) &&	/* print if old vector is different */
		      /* from the current one */
		      (d_count == find_max_ratio) &&
		      (p_count <= max_print) && (ratio > 0.5 * ratio_max)) {
		    old_count = count;

		    printf
		      ("FAIL> %s: n = %d, ntests = %d, threshold = %4.2f,\n",
		       fname, n, ntests, thresh);
		    printf("seed = %d\n", *seed);
		    printf("norm = %d\n", norm);


		    /* Print test info */
		    switch (prec) {
		    case blas_prec_single:
		      printf("single ");
		      break;
		    case blas_prec_double:
		      printf("double ");
		      break;
		    case blas_prec_indigenous:
		      printf("indigenous ");
		      break;
		    case blas_prec_extra:
		      printf("extra ");
		      break;
		    }
		    switch (norm) {
		    case -1:
		      printf("near_underflow ");
		      break;
		    case 0:
		      printf("near_one ");
		      break;
		    case 1:
		      printf("near_overflow ");
		      break;
		    }

		    printf("incx=%d, incy=%d:\n", incx, incy);

		    dprint_vector(x, n, incx_val, "x");
		    zprint_vector(y_ori, n, incy_val, "y_ori");
		    zprint_vector(y_comp, n, incy_val, "y_comp");

		    printf("      ");
		    printf("alpha = ");
		    printf("(%24.16e, %24.16e)", alpha[0], alpha[1]);
		    printf("; ");
		    printf("beta = ");
		    printf("(%24.16e, %24.16e)", beta[0], beta[1]);
		    printf("\n");
		    printf("      ratio=%.4e\n", ratio);
		    printf("iymax = %d\n", iymax);
		    printf("ixmax = %d\n", ixmax);
		    p_count++;
		  }
		}
		if (d_count == 0) {
		  if (ratio > ratio_max)
		    ratio_max = ratio;
		  iymax_max = iymax;
		  ixmax_max = ixmax;
		  if (ratio != 0.0 && ratio < ratio_min)
		    ratio_min = ratio;

		  tot_tests++;
		}
	      }			/* incy */
	    }			/* incx */
	  }			/* tests */
	}			/* norm */

      }				/* beta */
    }				/* alpha */
  }				/* debug */

  if ((debug == 2) || ((debug == 1) && (bad_ratios > 0))) {
    printf("      %s:  n = %d, ntests = %d, thresh = %4.2f\n",
	   fname, n, ntests, thresh);
    if (ratio_min == 1.0e+308)
      ratio_min = 0.0;
    printf
      ("      bad/total = %d/%d=%3.2f, min_ratio = %.4e, max_ratio = %.4e\n\n",
       bad_ratios, tot_tests, ((double) bad_ratios) / ((double) tot_tests),
       ratio_min, ratio_max);
    printf("iymax_max = %d, ixmax_max = %d\n", iymax_max, ixmax_max);
  }

  blas_free(x);
  blas_free(y_ori);
  blas_free(y_comp);
  blas_free(head_y_true);
  blas_free(tail_y_true);
  blas_free(x_gen);
  blas_free(y_gen);

  *min_ratio = ratio_min;
  *num_bad_ratio = bad_ratios;
  *num_tests = tot_tests;

  FPU_FIX_STOP;
  return ratio_max;
}				/* end of do_test_zaxpby_d */

double do_test_saxpby_x(int n, int ntests, int *seed, double thresh,
			int debug, double *min_ratio, int *num_bad_ratio,
			int *num_tests)

/*
 * Purpose  
 * =======
 *
 * Runs a series of tests on axpby  
 *
 * Arguments
 * =========
 *
 * n         (input) int
 *           The size of vector being tested
 *
 * ntests    (input) int
 *           The number of tests to run for each set of attributes.
 *
 * seed      (input/output) int         
 *           The seed for the random number generator used in testgen().
 *
 * thresh    (input) double
 *           When the ratio returned from test() exceeds the specified
 *           threshold, the current size, y_true, y_comp, and ratio will be
 *           printed.  (Since ratio is supposed to be O(1), we can set thresh
 *           to ~10.)
 *
 * debug     (input) int
 *           If debug=3, print summary 
 *           If debug=2, print summary only if the number of bad ratios > 0
 *           If debug=1, print complete info if tests fail
 *           If debug=0, return max ratio
 *
 * min_ratio (output) double
 *           The minimum ratio
 * 
 * num_bad_ratio (output) int
 *               The number of tests fail; they are above the threshold.
 *
 * num_tests (output) int
 *           The number of tests is being performed.
 *
 * Return value
 * ============
 *
 * The maximum ratio if run successfully, otherwise return -1 
 *
 * Code structure
 * ==============
 * 
 *  debug loop  -- if debug is one, the first loop computes the max ratio
 *              -- and the last(second) loop outputs debugging information,
 *              -- if the test fail and its ratio > 0.5 * max ratio.
 *              -- if debug is zero, the loop is executed once
 *    alpha loop  -- varying alpha: 0, 1, or random
 *      beta loop   -- varying beta: 0, 1, or random
 *        prec loop   -- varying internal prec: single, double, or extra
 *          norm loop   -- varying norm: near undeflow, near one, or 
 *                        -- near overflow
 *            numtest loop  -- how many times the test is perform with 
 *                            -- above set of attributes
 *                incx loop     -- varying incx: -2, -1, 1, 2
 *                  incy loop     -- varying incy: -2, -1, 1, 2
 */
{
  /* function name */
  const char fname[] = "BLAS_saxpby_x";

  /* max number of debug lines to print */
  const int max_print = 32;

  /* Variables in the "x_val" form are loop vars for corresponding
     variables */
  int i;			/* iterate through the repeating tests */
  int ix, iy;			/* use to index x and y respectively */
  int incx_val, incy_val,	/* for testing different inc values */
    incx, incy, incx_gen, incy_gen, ygen_val, xgen_val, test_val;
  int d_count;			/* counter for debug */
  int find_max_ratio;		/* find_max_ratio = 1 only if debug = 3 */
  int p_count;			/* counter for the number of debug lines printed */
  int tot_tests;		/* total number of tests to be done */
  int norm;			/* input values of near underflow/one/overflow */
  double ratio_max;		/* the current maximum ratio */
  double ratio_min;		/* the current minimum ratio */
  double ratio;			/* the per-use test ratio from test() */
  double new_ratio;
  int bad_ratios;		/* the number of ratios over the threshold */
  double eps_int;		/* the internal epsilon expected--2^(-24) for float */
  double un_int;		/* the internal underflow threshold */
  float alpha;
  float beta;
  float *x;
  float y_fix;
  float *y_ori;
  float *y_comp;		/* the y computed  by BLAS_saxpby_x */

  int ixmax, iymax;
  int ixmax_max, iymax_max;

  /* x_gen and y_gen are used to store vectors generated by testgen.
     they eventually are copied back to x and y */
  float *x_gen;
  float *y_gen;

  /* the true y calculated by testgen(), in double-double */
  double *head_y_true, *tail_y_true;
  int alpha_val;
  int alpha_flag;		/* input flag for BLAS_sdot_testgen */
  int beta_val;
  int beta_flag;		/* input flag for BLAS_sdot_testgen */
  int prec_val;
  enum blas_prec_type prec;
  int saved_seed;		/* for saving the original seed */
  int count, old_count;		/* use for counting the number of testgen calls * 2 */

  FPU_FIX_DECL;

  /* test for bad arguments */
  if (n < 0 || ntests < 0)
    BLAS_error(fname, 0, 0, NULL);

  /* if there is nothing to test, return all zero */
  if (n == 0 || ntests == 0) {
    *min_ratio = 0.0;
    *num_bad_ratio = 0;
    *num_tests = 0;
    return 0.0;
  }

  FPU_FIX_START;

  /* get space for calculation */
  x = (float *) blas_malloc(n * 2 * sizeof(float));
  if (n * 2 > 0 && x == NULL) {
    BLAS_error("blas_malloc", 0, 0, "malloc failed.\n");
  }
  y_ori = (float *) blas_malloc(n * 2 * sizeof(float));
  if (n * 2 > 0 && y_ori == NULL) {
    BLAS_error("blas_malloc", 0, 0, "malloc failed.\n");
  }
  y_comp = (float *) blas_malloc(n * 2 * sizeof(float));
  if (n * 2 > 0 && y_comp == NULL) {
    BLAS_error("blas_malloc", 0, 0, "malloc failed.\n");
  }
  head_y_true = (double *) blas_malloc(n * sizeof(double));
  tail_y_true = (double *) blas_malloc(n * sizeof(double));
  if (n > 0 && (head_y_true == NULL || tail_y_true == NULL)) {
    BLAS_error("blas_malloc", 0, 0, "malloc failed.\n");
  }
  x_gen = (float *) blas_malloc(n * sizeof(float));
  if (n > 0 && x_gen == NULL) {
    BLAS_error("blas_malloc", 0, 0, "malloc failed.\n");
  }
  y_gen = (float *) blas_malloc(n * sizeof(float));
  if (n > 0 && y_gen == NULL) {
    BLAS_error("blas_malloc", 0, 0, "malloc failed.\n");
  }

  /* initialization */
  saved_seed = *seed;
  ratio_min = 1e308;
  ratio_max = 0.0;
  tot_tests = 0;
  p_count = 0;
  count = 0;
  bad_ratios = 0;
  ixmax_max = 0;
  iymax_max = 0;
  alpha_flag = 0;
  beta_flag = 0;
  old_count = 0;

  find_max_ratio = 0;
  if (debug == 3)
    find_max_ratio = 1;
  y_fix = 1.0;

  /* initialize incx_gen and incy_gen */
  incx_gen = 1;
  incy_gen = 1;



  /* The debug iteration:
     If debug=1, then will execute the iteration twice. First, compute the
     max ratio. Second, print info if ratio > (50% * ratio_max). */
  for (d_count = 0; d_count <= find_max_ratio; d_count++) {
    bad_ratios = 0;		/* set to zero */

    if ((debug == 3) && (d_count == find_max_ratio))
      *seed = saved_seed;	/* restore the original seed */

    /* varying alpha */
    for (alpha_val = 0; alpha_val < 3; alpha_val++) {
      alpha_flag = 0;
      switch (alpha_val) {
      case 0:
	alpha = 0.0;
	alpha_flag = 1;
	break;
      case 1:
	alpha = 1.0;
	alpha_flag = 1;
	break;
      }

      /* varying beta */
      for (beta_val = 0; beta_val < 3; beta_val++) {
	beta_flag = 0;
	switch (beta_val) {
	case 0:
	  beta = 0.0;
	  beta_flag = 1;
	  break;
	case 1:
	  beta = 1.0;
	  beta_flag = 1;
	  break;
	}


	/* varying extra precs */
	for (prec_val = 0; prec_val <= 2; prec_val++) {
	  switch (prec_val) {
	  case 0:
	    eps_int = power(2, -BITS_S);
	    un_int = pow((double) BLAS_fpinfo_x(blas_base, blas_prec_single),
			 (double) BLAS_fpinfo_x(blas_emin, blas_prec_single));
	    prec = blas_prec_single;
	    break;
	  case 1:
	    eps_int = power(2, -BITS_D);
	    un_int = pow((double) BLAS_fpinfo_x(blas_base, blas_prec_double),
			 (double) BLAS_fpinfo_x(blas_emin, blas_prec_double));
	    prec = blas_prec_double;
	    break;
	  case 2:
	  default:
	    eps_int = power(2, -BITS_E);
	    un_int = pow((double) BLAS_fpinfo_x(blas_base, blas_prec_extra),
			 (double) BLAS_fpinfo_x(blas_emin, blas_prec_extra));
	    prec = blas_prec_extra;
	    break;
	  }

	  /* values near underflow, 1, or overflow */
	  for (norm = -1; norm <= 1; norm++) {

	    /* number of tests */
	    for (i = 0; i < ntests; i++) {

	      /* generate test inputs */
	      BLAS_sdot_testgen(1, 0, 1, norm, blas_no_conj, &alpha,
				alpha_flag, &beta, beta_flag, &y_fix, x_gen,
				seed, y_gen, head_y_true, tail_y_true);
	      xgen_val = incx_gen;
	      for (ygen_val = incy_gen; ygen_val < n * incy_gen;
		   ygen_val += incy_gen) {
		BLAS_sdot_testgen(1, 0, 1, norm, blas_no_conj, &alpha, 1,
				  &beta, 1, &y_fix, &x_gen[xgen_val], seed,
				  &y_gen[ygen_val], &head_y_true[ygen_val],
				  &tail_y_true[ygen_val]);
		xgen_val += incx_gen;
	      }

	      count++;

	      /* varying incx */
	      for (incx_val = -2; incx_val <= 2; incx_val++) {
		if (incx_val == 0)
		  continue;

		/* setting incx */
		incx = incx_val;

		scopy_vector(x_gen, n, 1, x, incx_val);

		/* varying incy */
		for (incy_val = -2; incy_val <= 2; incy_val++) {
		  if (incy_val == 0)
		    continue;

		  /* setting incy */
		  incy = incy_val;


		  scopy_vector(y_gen, n, 1, y_ori, incy_val);
		  scopy_vector(y_gen, n, 1, y_comp, incy_val);

		  /* call BLAS_saxpby_x to get y_comp */
		  FPU_FIX_STOP;
		  BLAS_saxpby_x(n, alpha, x, incx_val, beta,
				y_comp, incy_val, prec);
		  FPU_FIX_START;


		  /* computing the ratio */
		  ix = 0;
		  if (incx < 0)
		    ix = -(n - 1) * incx;
		  iy = 0;
		  if (incy < 0)
		    iy = -(n - 1) * incy;
		  ratio = 0.0;

		  ixmax = -1;
		  iymax = -1;
		  for (test_val = 0; test_val < n * incy_gen;
		       test_val += incy_gen) {
		    test_BLAS_sdot(1, blas_no_conj, alpha, beta, y_ori[iy],
				   y_comp[iy], head_y_true[test_val],
				   tail_y_true[test_val], &y_fix, incx,
				   &x[ix], incx, eps_int, un_int, &new_ratio);

		    ix += incx;
		    iy += incy;
		    if (MAX(ratio, new_ratio) == new_ratio) {
		      ixmax = ix;
		      iymax = iy;
		    }
		    ratio = MAX(ratio, new_ratio);
		  }

		  /* increase the number of bad ratio, if the ratio
		     is bigger than the threshold.
		     The !<= below causes NaN error to be detected.
		     Note that (NaN > thresh) is always false. */
		  if (!(ratio <= thresh)) {
		    bad_ratios++;


		    if ((debug == 3) &&	/* print only when debug is on */
			(count != old_count) &&	/* print if old vector is different */
			/* from the current one */
			(d_count == find_max_ratio) &&
			(p_count <= max_print) && (ratio > 0.5 * ratio_max)) {
		      old_count = count;

		      printf
			("FAIL> %s: n = %d, ntests = %d, threshold = %4.2f,\n",
			 fname, n, ntests, thresh);
		      printf("seed = %d\n", *seed);
		      printf("norm = %d\n", norm);


		      /* Print test info */
		      switch (prec) {
		      case blas_prec_single:
			printf("single ");
			break;
		      case blas_prec_double:
			printf("double ");
			break;
		      case blas_prec_indigenous:
			printf("indigenous ");
			break;
		      case blas_prec_extra:
			printf("extra ");
			break;
		      }
		      switch (norm) {
		      case -1:
			printf("near_underflow ");
			break;
		      case 0:
			printf("near_one ");
			break;
		      case 1:
			printf("near_overflow ");
			break;
		      }

		      printf("incx=%d, incy=%d:\n", incx, incy);

		      sprint_vector(x, n, incx_val, "x");
		      sprint_vector(y_ori, n, incy_val, "y_ori");
		      sprint_vector(y_comp, n, incy_val, "y_comp");

		      printf("      ");
		      printf("alpha = ");
		      printf("%16.8e", alpha);
		      printf("; ");
		      printf("beta = ");
		      printf("%16.8e", beta);
		      printf("\n");
		      printf("      ratio=%.4e\n", ratio);
		      printf("iymax = %d\n", iymax);
		      printf("ixmax = %d\n", ixmax);
		      p_count++;
		    }
		  }
		  if (d_count == 0) {
		    if (ratio > ratio_max)
		      ratio_max = ratio;
		    iymax_max = iymax;
		    ixmax_max = ixmax;
		    if (ratio != 0.0 && ratio < ratio_min)
		      ratio_min = ratio;

		    tot_tests++;
		  }
		}		/* incy */
	      }			/* incx */
	    }			/* tests */
	  }			/* norm */
	}			/* prec */
      }				/* beta */
    }				/* alpha */
  }				/* debug */

  if ((debug == 2) || ((debug == 1) && (bad_ratios > 0))) {
    printf("      %s:  n = %d, ntests = %d, thresh = %4.2f\n",
	   fname, n, ntests, thresh);
    if (ratio_min == 1.0e+308)
      ratio_min = 0.0;
    printf
      ("      bad/total = %d/%d=%3.2f, min_ratio = %.4e, max_ratio = %.4e\n\n",
       bad_ratios, tot_tests, ((double) bad_ratios) / ((double) tot_tests),
       ratio_min, ratio_max);
    printf("iymax_max = %d, ixmax_max = %d\n", iymax_max, ixmax_max);
  }

  blas_free(x);
  blas_free(y_ori);
  blas_free(y_comp);
  blas_free(head_y_true);
  blas_free(tail_y_true);
  blas_free(x_gen);
  blas_free(y_gen);

  *min_ratio = ratio_min;
  *num_bad_ratio = bad_ratios;
  *num_tests = tot_tests;

  FPU_FIX_STOP;
  return ratio_max;
}				/* end of do_test_saxpby_x */

double do_test_daxpby_x(int n, int ntests, int *seed, double thresh,
			int debug, double *min_ratio, int *num_bad_ratio,
			int *num_tests)

/*
 * Purpose  
 * =======
 *
 * Runs a series of tests on axpby  
 *
 * Arguments
 * =========
 *
 * n         (input) int
 *           The size of vector being tested
 *
 * ntests    (input) int
 *           The number of tests to run for each set of attributes.
 *
 * seed      (input/output) int         
 *           The seed for the random number generator used in testgen().
 *
 * thresh    (input) double
 *           When the ratio returned from test() exceeds the specified
 *           threshold, the current size, y_true, y_comp, and ratio will be
 *           printed.  (Since ratio is supposed to be O(1), we can set thresh
 *           to ~10.)
 *
 * debug     (input) int
 *           If debug=3, print summary 
 *           If debug=2, print summary only if the number of bad ratios > 0
 *           If debug=1, print complete info if tests fail
 *           If debug=0, return max ratio
 *
 * min_ratio (output) double
 *           The minimum ratio
 * 
 * num_bad_ratio (output) int
 *               The number of tests fail; they are above the threshold.
 *
 * num_tests (output) int
 *           The number of tests is being performed.
 *
 * Return value
 * ============
 *
 * The maximum ratio if run successfully, otherwise return -1 
 *
 * Code structure
 * ==============
 * 
 *  debug loop  -- if debug is one, the first loop computes the max ratio
 *              -- and the last(second) loop outputs debugging information,
 *              -- if the test fail and its ratio > 0.5 * max ratio.
 *              -- if debug is zero, the loop is executed once
 *    alpha loop  -- varying alpha: 0, 1, or random
 *      beta loop   -- varying beta: 0, 1, or random
 *        prec loop   -- varying internal prec: single, double, or extra
 *          norm loop   -- varying norm: near undeflow, near one, or 
 *                        -- near overflow
 *            numtest loop  -- how many times the test is perform with 
 *                            -- above set of attributes
 *                incx loop     -- varying incx: -2, -1, 1, 2
 *                  incy loop     -- varying incy: -2, -1, 1, 2
 */
{
  /* function name */
  const char fname[] = "BLAS_daxpby_x";

  /* max number of debug lines to print */
  const int max_print = 32;

  /* Variables in the "x_val" form are loop vars for corresponding
     variables */
  int i;			/* iterate through the repeating tests */
  int ix, iy;			/* use to index x and y respectively */
  int incx_val, incy_val,	/* for testing different inc values */
    incx, incy, incx_gen, incy_gen, ygen_val, xgen_val, test_val;
  int d_count;			/* counter for debug */
  int find_max_ratio;		/* find_max_ratio = 1 only if debug = 3 */
  int p_count;			/* counter for the number of debug lines printed */
  int tot_tests;		/* total number of tests to be done */
  int norm;			/* input values of near underflow/one/overflow */
  double ratio_max;		/* the current maximum ratio */
  double ratio_min;		/* the current minimum ratio */
  double ratio;			/* the per-use test ratio from test() */
  double new_ratio;
  int bad_ratios;		/* the number of ratios over the threshold */
  double eps_int;		/* the internal epsilon expected--2^(-24) for float */
  double un_int;		/* the internal underflow threshold */
  double alpha;
  double beta;
  double *x;
  double y_fix;
  double *y_ori;
  double *y_comp;		/* the y computed  by BLAS_daxpby_x */

  int ixmax, iymax;
  int ixmax_max, iymax_max;

  /* x_gen and y_gen are used to store vectors generated by testgen.
     they eventually are copied back to x and y */
  double *x_gen;
  double *y_gen;

  /* the true y calculated by testgen(), in double-double */
  double *head_y_true, *tail_y_true;
  int alpha_val;
  int alpha_flag;		/* input flag for BLAS_ddot_testgen */
  int beta_val;
  int beta_flag;		/* input flag for BLAS_ddot_testgen */
  int prec_val;
  enum blas_prec_type prec;
  int saved_seed;		/* for saving the original seed */
  int count, old_count;		/* use for counting the number of testgen calls * 2 */

  FPU_FIX_DECL;

  /* test for bad arguments */
  if (n < 0 || ntests < 0)
    BLAS_error(fname, 0, 0, NULL);

  /* if there is nothing to test, return all zero */
  if (n == 0 || ntests == 0) {
    *min_ratio = 0.0;
    *num_bad_ratio = 0;
    *num_tests = 0;
    return 0.0;
  }

  FPU_FIX_START;

  /* get space for calculation */
  x = (double *) blas_malloc(n * 2 * sizeof(double));
  if (n * 2 > 0 && x == NULL) {
    BLAS_error("blas_malloc", 0, 0, "malloc failed.\n");
  }
  y_ori = (double *) blas_malloc(n * 2 * sizeof(double));
  if (n * 2 > 0 && y_ori == NULL) {
    BLAS_error("blas_malloc", 0, 0, "malloc failed.\n");
  }
  y_comp = (double *) blas_malloc(n * 2 * sizeof(double));
  if (n * 2 > 0 && y_comp == NULL) {
    BLAS_error("blas_malloc", 0, 0, "malloc failed.\n");
  }
  head_y_true = (double *) blas_malloc(n * sizeof(double));
  tail_y_true = (double *) blas_malloc(n * sizeof(double));
  if (n > 0 && (head_y_true == NULL || tail_y_true == NULL)) {
    BLAS_error("blas_malloc", 0, 0, "malloc failed.\n");
  }
  x_gen = (double *) blas_malloc(n * sizeof(double));
  if (n > 0 && x_gen == NULL) {
    BLAS_error("blas_malloc", 0, 0, "malloc failed.\n");
  }
  y_gen = (double *) blas_malloc(n * sizeof(double));
  if (n > 0 && y_gen == NULL) {
    BLAS_error("blas_malloc", 0, 0, "malloc failed.\n");
  }

  /* initialization */
  saved_seed = *seed;
  ratio_min = 1e308;
  ratio_max = 0.0;
  tot_tests = 0;
  p_count = 0;
  count = 0;
  bad_ratios = 0;
  ixmax_max = 0;
  iymax_max = 0;
  alpha_flag = 0;
  beta_flag = 0;
  old_count = 0;

  find_max_ratio = 0;
  if (debug == 3)
    find_max_ratio = 1;
  y_fix = 1.0;

  /* initialize incx_gen and incy_gen */
  incx_gen = 1;
  incy_gen = 1;



  /* The debug iteration:
     If debug=1, then will execute the iteration twice. First, compute the
     max ratio. Second, print info if ratio > (50% * ratio_max). */
  for (d_count = 0; d_count <= find_max_ratio; d_count++) {
    bad_ratios = 0;		/* set to zero */

    if ((debug == 3) && (d_count == find_max_ratio))
      *seed = saved_seed;	/* restore the original seed */

    /* varying alpha */
    for (alpha_val = 0; alpha_val < 3; alpha_val++) {
      alpha_flag = 0;
      switch (alpha_val) {
      case 0:
	alpha = 0.0;
	alpha_flag = 1;
	break;
      case 1:
	alpha = 1.0;
	alpha_flag = 1;
	break;
      }

      /* varying beta */
      for (beta_val = 0; beta_val < 3; beta_val++) {
	beta_flag = 0;
	switch (beta_val) {
	case 0:
	  beta = 0.0;
	  beta_flag = 1;
	  break;
	case 1:
	  beta = 1.0;
	  beta_flag = 1;
	  break;
	}


	/* varying extra precs */
	for (prec_val = 0; prec_val <= 2; prec_val++) {
	  switch (prec_val) {
	  case 0:
	    eps_int = power(2, -BITS_D);
	    un_int = pow((double) BLAS_fpinfo_x(blas_base, blas_prec_double),
			 (double) BLAS_fpinfo_x(blas_emin, blas_prec_double));
	    prec = blas_prec_double;
	    break;
	  case 1:
	    eps_int = power(2, -BITS_D);
	    un_int = pow((double) BLAS_fpinfo_x(blas_base, blas_prec_double),
			 (double) BLAS_fpinfo_x(blas_emin, blas_prec_double));
	    prec = blas_prec_double;
	    break;
	  case 2:
	  default:
	    eps_int = power(2, -BITS_E);
	    un_int = pow((double) BLAS_fpinfo_x(blas_base, blas_prec_extra),
			 (double) BLAS_fpinfo_x(blas_emin, blas_prec_extra));
	    prec = blas_prec_extra;
	    break;
	  }

	  /* values near underflow, 1, or overflow */
	  for (norm = -1; norm <= 1; norm++) {

	    /* number of tests */
	    for (i = 0; i < ntests; i++) {

	      /* generate test inputs */
	      BLAS_ddot_testgen(1, 0, 1, norm, blas_no_conj, &alpha,
				alpha_flag, &beta, beta_flag, &y_fix, x_gen,
				seed, y_gen, head_y_true, tail_y_true);
	      xgen_val = incx_gen;
	      for (ygen_val = incy_gen; ygen_val < n * incy_gen;
		   ygen_val += incy_gen) {
		BLAS_ddot_testgen(1, 0, 1, norm, blas_no_conj, &alpha, 1,
				  &beta, 1, &y_fix, &x_gen[xgen_val], seed,
				  &y_gen[ygen_val], &head_y_true[ygen_val],
				  &tail_y_true[ygen_val]);
		xgen_val += incx_gen;
	      }

	      count++;

	      /* varying incx */
	      for (incx_val = -2; incx_val <= 2; incx_val++) {
		if (incx_val == 0)
		  continue;

		/* setting incx */
		incx = incx_val;

		dcopy_vector(x_gen, n, 1, x, incx_val);

		/* varying incy */
		for (incy_val = -2; incy_val <= 2; incy_val++) {
		  if (incy_val == 0)
		    continue;

		  /* setting incy */
		  incy = incy_val;


		  dcopy_vector(y_gen, n, 1, y_ori, incy_val);
		  dcopy_vector(y_gen, n, 1, y_comp, incy_val);

		  /* call BLAS_daxpby_x to get y_comp */
		  FPU_FIX_STOP;
		  BLAS_daxpby_x(n, alpha, x, incx_val, beta,
				y_comp, incy_val, prec);
		  FPU_FIX_START;


		  /* computing the ratio */
		  ix = 0;
		  if (incx < 0)
		    ix = -(n - 1) * incx;
		  iy = 0;
		  if (incy < 0)
		    iy = -(n - 1) * incy;
		  ratio = 0.0;

		  ixmax = -1;
		  iymax = -1;
		  for (test_val = 0; test_val < n * incy_gen;
		       test_val += incy_gen) {
		    test_BLAS_ddot(1, blas_no_conj, alpha, beta, y_ori[iy],
				   y_comp[iy], head_y_true[test_val],
				   tail_y_true[test_val], &y_fix, incx,
				   &x[ix], incx, eps_int, un_int, &new_ratio);

		    ix += incx;
		    iy += incy;
		    if (MAX(ratio, new_ratio) == new_ratio) {
		      ixmax = ix;
		      iymax = iy;
		    }
		    ratio = MAX(ratio, new_ratio);
		  }

		  /* increase the number of bad ratio, if the ratio
		     is bigger than the threshold.
		     The !<= below causes NaN error to be detected.
		     Note that (NaN > thresh) is always false. */
		  if (!(ratio <= thresh)) {
		    bad_ratios++;


		    if ((debug == 3) &&	/* print only when debug is on */
			(count != old_count) &&	/* print if old vector is different */
			/* from the current one */
			(d_count == find_max_ratio) &&
			(p_count <= max_print) && (ratio > 0.5 * ratio_max)) {
		      old_count = count;

		      printf
			("FAIL> %s: n = %d, ntests = %d, threshold = %4.2f,\n",
			 fname, n, ntests, thresh);
		      printf("seed = %d\n", *seed);
		      printf("norm = %d\n", norm);


		      /* Print test info */
		      switch (prec) {
		      case blas_prec_single:
			printf("single ");
			break;
		      case blas_prec_double:
			printf("double ");
			break;
		      case blas_prec_indigenous:
			printf("indigenous ");
			break;
		      case blas_prec_extra:
			printf("extra ");
			break;
		      }
		      switch (norm) {
		      case -1:
			printf("near_underflow ");
			break;
		      case 0:
			printf("near_one ");
			break;
		      case 1:
			printf("near_overflow ");
			break;
		      }

		      printf("incx=%d, incy=%d:\n", incx, incy);

		      dprint_vector(x, n, incx_val, "x");
		      dprint_vector(y_ori, n, incy_val, "y_ori");
		      dprint_vector(y_comp, n, incy_val, "y_comp");

		      printf("      ");
		      printf("alpha = ");
		      printf("%24.16e", alpha);
		      printf("; ");
		      printf("beta = ");
		      printf("%24.16e", beta);
		      printf("\n");
		      printf("      ratio=%.4e\n", ratio);
		      printf("iymax = %d\n", iymax);
		      printf("ixmax = %d\n", ixmax);
		      p_count++;
		    }
		  }
		  if (d_count == 0) {
		    if (ratio > ratio_max)
		      ratio_max = ratio;
		    iymax_max = iymax;
		    ixmax_max = ixmax;
		    if (ratio != 0.0 && ratio < ratio_min)
		      ratio_min = ratio;

		    tot_tests++;
		  }
		}		/* incy */
	      }			/* incx */
	    }			/* tests */
	  }			/* norm */
	}			/* prec */
      }				/* beta */
    }				/* alpha */
  }				/* debug */

  if ((debug == 2) || ((debug == 1) && (bad_ratios > 0))) {
    printf("      %s:  n = %d, ntests = %d, thresh = %4.2f\n",
	   fname, n, ntests, thresh);
    if (ratio_min == 1.0e+308)
      ratio_min = 0.0;
    printf
      ("      bad/total = %d/%d=%3.2f, min_ratio = %.4e, max_ratio = %.4e\n\n",
       bad_ratios, tot_tests, ((double) bad_ratios) / ((double) tot_tests),
       ratio_min, ratio_max);
    printf("iymax_max = %d, ixmax_max = %d\n", iymax_max, ixmax_max);
  }

  blas_free(x);
  blas_free(y_ori);
  blas_free(y_comp);
  blas_free(head_y_true);
  blas_free(tail_y_true);
  blas_free(x_gen);
  blas_free(y_gen);

  *min_ratio = ratio_min;
  *num_bad_ratio = bad_ratios;
  *num_tests = tot_tests;

  FPU_FIX_STOP;
  return ratio_max;
}				/* end of do_test_daxpby_x */

double do_test_caxpby_x(int n, int ntests, int *seed, double thresh,
			int debug, double *min_ratio, int *num_bad_ratio,
			int *num_tests)

/*
 * Purpose  
 * =======
 *
 * Runs a series of tests on axpby  
 *
 * Arguments
 * =========
 *
 * n         (input) int
 *           The size of vector being tested
 *
 * ntests    (input) int
 *           The number of tests to run for each set of attributes.
 *
 * seed      (input/output) int         
 *           The seed for the random number generator used in testgen().
 *
 * thresh    (input) double
 *           When the ratio returned from test() exceeds the specified
 *           threshold, the current size, y_true, y_comp, and ratio will be
 *           printed.  (Since ratio is supposed to be O(1), we can set thresh
 *           to ~10.)
 *
 * debug     (input) int
 *           If debug=3, print summary 
 *           If debug=2, print summary only if the number of bad ratios > 0
 *           If debug=1, print complete info if tests fail
 *           If debug=0, return max ratio
 *
 * min_ratio (output) double
 *           The minimum ratio
 * 
 * num_bad_ratio (output) int
 *               The number of tests fail; they are above the threshold.
 *
 * num_tests (output) int
 *           The number of tests is being performed.
 *
 * Return value
 * ============
 *
 * The maximum ratio if run successfully, otherwise return -1 
 *
 * Code structure
 * ==============
 * 
 *  debug loop  -- if debug is one, the first loop computes the max ratio
 *              -- and the last(second) loop outputs debugging information,
 *              -- if the test fail and its ratio > 0.5 * max ratio.
 *              -- if debug is zero, the loop is executed once
 *    alpha loop  -- varying alpha: 0, 1, or random
 *      beta loop   -- varying beta: 0, 1, or random
 *        prec loop   -- varying internal prec: single, double, or extra
 *          norm loop   -- varying norm: near undeflow, near one, or 
 *                        -- near overflow
 *            numtest loop  -- how many times the test is perform with 
 *                            -- above set of attributes
 *                incx loop     -- varying incx: -2, -1, 1, 2
 *                  incy loop     -- varying incy: -2, -1, 1, 2
 */
{
  /* function name */
  const char fname[] = "BLAS_caxpby_x";

  /* max number of debug lines to print */
  const int max_print = 32;

  /* Variables in the "x_val" form are loop vars for corresponding
     variables */
  int i;			/* iterate through the repeating tests */
  int ix, iy;			/* use to index x and y respectively */
  int incx_val, incy_val,	/* for testing different inc values */
    incx, incy, incx_gen, incy_gen, ygen_val, xgen_val, test_val;
  int d_count;			/* counter for debug */
  int find_max_ratio;		/* find_max_ratio = 1 only if debug = 3 */
  int p_count;			/* counter for the number of debug lines printed */
  int tot_tests;		/* total number of tests to be done */
  int norm;			/* input values of near underflow/one/overflow */
  double ratio_max;		/* the current maximum ratio */
  double ratio_min;		/* the current minimum ratio */
  double ratio;			/* the per-use test ratio from test() */
  double new_ratio;
  int bad_ratios;		/* the number of ratios over the threshold */
  double eps_int;		/* the internal epsilon expected--2^(-24) for float */
  double un_int;		/* the internal underflow threshold */
  float alpha[2];
  float beta[2];
  float *x;
  float y_fix[2];
  float *y_ori;
  float *y_comp;		/* the y computed  by BLAS_caxpby_x */

  int ixmax, iymax;
  int ixmax_max, iymax_max;

  /* x_gen and y_gen are used to store vectors generated by testgen.
     they eventually are copied back to x and y */
  float *x_gen;
  float *y_gen;

  /* the true y calculated by testgen(), in double-double */
  double *head_y_true, *tail_y_true;

  int alpha_val;
  int alpha_flag;		/* input flag for BLAS_cdot_testgen */
  int beta_val;
  int beta_flag;		/* input flag for BLAS_cdot_testgen */
  int prec_val;
  enum blas_prec_type prec;
  int saved_seed;		/* for saving the original seed */
  int count, old_count;		/* use for counting the number of testgen calls * 2 */

  FPU_FIX_DECL;

  /* test for bad arguments */
  if (n < 0 || ntests < 0)
    BLAS_error(fname, 0, 0, NULL);

  /* if there is nothing to test, return all zero */
  if (n == 0 || ntests == 0) {
    *min_ratio = 0.0;
    *num_bad_ratio = 0;
    *num_tests = 0;
    return 0.0;
  }

  FPU_FIX_START;

  /* get space for calculation */
  x = (float *) blas_malloc(n * 2 * sizeof(float) * 2);
  if (n * 2 > 0 && x == NULL) {
    BLAS_error("blas_malloc", 0, 0, "malloc failed.\n");
  }
  y_ori = (float *) blas_malloc(n * 2 * sizeof(float) * 2);
  if (n * 2 > 0 && y_ori == NULL) {
    BLAS_error("blas_malloc", 0, 0, "malloc failed.\n");
  }
  y_comp = (float *) blas_malloc(n * 2 * sizeof(float) * 2);
  if (n * 2 > 0 && y_comp == NULL) {
    BLAS_error("blas_malloc", 0, 0, "malloc failed.\n");
  }
  head_y_true = (double *) blas_malloc(n * sizeof(double) * 2);
  tail_y_true = (double *) blas_malloc(n * sizeof(double) * 2);
  if (n > 0 && (head_y_true == NULL || tail_y_true == NULL)) {
    BLAS_error("blas_malloc", 0, 0, "malloc failed.\n");
  }
  x_gen = (float *) blas_malloc(n * sizeof(float) * 2);
  if (n > 0 && x_gen == NULL) {
    BLAS_error("blas_malloc", 0, 0, "malloc failed.\n");
  }
  y_gen = (float *) blas_malloc(n * sizeof(float) * 2);
  if (n > 0 && y_gen == NULL) {
    BLAS_error("blas_malloc", 0, 0, "malloc failed.\n");
  }

  /* initialization */
  saved_seed = *seed;
  ratio_min = 1e308;
  ratio_max = 0.0;
  tot_tests = 0;
  p_count = 0;
  count = 0;
  bad_ratios = 0;
  ixmax_max = 0;
  iymax_max = 0;
  alpha_flag = 0;
  beta_flag = 0;
  old_count = 0;

  find_max_ratio = 0;
  if (debug == 3)
    find_max_ratio = 1;
  y_fix[0] = 1.0;
  y_fix[1] = 0.0;

  /* initialize incx_gen and incy_gen */
  incx_gen = 1;
  incy_gen = 1;
  incx_gen *= 2;
  incy_gen *= 2;

  /* The debug iteration:
     If debug=1, then will execute the iteration twice. First, compute the
     max ratio. Second, print info if ratio > (50% * ratio_max). */
  for (d_count = 0; d_count <= find_max_ratio; d_count++) {
    bad_ratios = 0;		/* set to zero */

    if ((debug == 3) && (d_count == find_max_ratio))
      *seed = saved_seed;	/* restore the original seed */

    /* varying alpha */
    for (alpha_val = 0; alpha_val < 3; alpha_val++) {
      alpha_flag = 0;
      switch (alpha_val) {
      case 0:
	alpha[0] = alpha[1] = 0.0;
	alpha_flag = 1;
	break;
      case 1:
	alpha[0] = 1.0;
	alpha[1] = 0.0;
	alpha_flag = 1;
	break;
      }

      /* varying beta */
      for (beta_val = 0; beta_val < 3; beta_val++) {
	beta_flag = 0;
	switch (beta_val) {
	case 0:
	  beta[0] = beta[1] = 0.0;
	  beta_flag = 1;
	  break;
	case 1:
	  beta[0] = 1.0;
	  beta[1] = 0.0;
	  beta_flag = 1;
	  break;
	}


	/* varying extra precs */
	for (prec_val = 0; prec_val <= 2; prec_val++) {
	  switch (prec_val) {
	  case 0:
	    eps_int = power(2, -BITS_S);
	    un_int = pow((double) BLAS_fpinfo_x(blas_base, blas_prec_single),
			 (double) BLAS_fpinfo_x(blas_emin, blas_prec_single));
	    prec = blas_prec_single;
	    break;
	  case 1:
	    eps_int = power(2, -BITS_D);
	    un_int = pow((double) BLAS_fpinfo_x(blas_base, blas_prec_double),
			 (double) BLAS_fpinfo_x(blas_emin, blas_prec_double));
	    prec = blas_prec_double;
	    break;
	  case 2:
	  default:
	    eps_int = power(2, -BITS_E);
	    un_int = pow((double) BLAS_fpinfo_x(blas_base, blas_prec_extra),
			 (double) BLAS_fpinfo_x(blas_emin, blas_prec_extra));
	    prec = blas_prec_extra;
	    break;
	  }

	  /* values near underflow, 1, or overflow */
	  for (norm = -1; norm <= 1; norm++) {

	    /* number of tests */
	    for (i = 0; i < ntests; i++) {

	      /* generate test inputs */
	      BLAS_cdot_testgen(1, 0, 1, norm, blas_no_conj, alpha,
				alpha_flag, beta, beta_flag, y_fix, x_gen,
				seed, y_gen, head_y_true, tail_y_true);
	      xgen_val = incx_gen;
	      for (ygen_val = incy_gen; ygen_val < n * incy_gen;
		   ygen_val += incy_gen) {
		BLAS_cdot_testgen(1, 0, 1, norm, blas_no_conj, alpha, 1, beta,
				  1, y_fix, &x_gen[xgen_val], seed,
				  &y_gen[ygen_val], &head_y_true[ygen_val],
				  &tail_y_true[ygen_val]);
		xgen_val += incx_gen;
	      }

	      count++;

	      /* varying incx */
	      for (incx_val = -2; incx_val <= 2; incx_val++) {
		if (incx_val == 0)
		  continue;

		/* setting incx */
		incx = incx_val;

		ccopy_vector(x_gen, n, 1, x, incx_val);

		/* varying incy */
		for (incy_val = -2; incy_val <= 2; incy_val++) {
		  if (incy_val == 0)
		    continue;

		  /* setting incy */
		  incy = incy_val;
		  incy *= 2;

		  ccopy_vector(y_gen, n, 1, y_ori, incy_val);
		  ccopy_vector(y_gen, n, 1, y_comp, incy_val);

		  /* call BLAS_caxpby_x to get y_comp */
		  FPU_FIX_STOP;
		  BLAS_caxpby_x(n, alpha, x, incx_val, beta,
				y_comp, incy_val, prec);
		  FPU_FIX_START;


		  /* computing the ratio */
		  ix = 0;
		  if (incx < 0)
		    ix = -(n - 1) * incx;
		  iy = 0;
		  if (incy < 0)
		    iy = -(n - 1) * incy;
		  ratio = 0.0;

		  ixmax = -1;
		  iymax = -1;
		  for (test_val = 0; test_val < n * incy_gen;
		       test_val += incy_gen) {
		    test_BLAS_cdot(1, blas_no_conj, alpha, beta, &y_ori[iy],
				   &y_comp[iy], &head_y_true[test_val],
				   &tail_y_true[test_val], y_fix, incx,
				   &x[ix], incx, eps_int, un_int, &new_ratio);

		    ix += incx;
		    iy += incy;
		    if (MAX(ratio, new_ratio) == new_ratio) {
		      ixmax = ix;
		      iymax = iy;
		    }
		    ratio = MAX(ratio, new_ratio);
		  }

		  /* increase the number of bad ratio, if the ratio
		     is bigger than the threshold.
		     The !<= below causes NaN error to be detected.
		     Note that (NaN > thresh) is always false. */
		  if (!(ratio <= thresh)) {
		    bad_ratios++;


		    if ((debug == 3) &&	/* print only when debug is on */
			(count != old_count) &&	/* print if old vector is different */
			/* from the current one */
			(d_count == find_max_ratio) &&
			(p_count <= max_print) && (ratio > 0.5 * ratio_max)) {
		      old_count = count;

		      printf
			("FAIL> %s: n = %d, ntests = %d, threshold = %4.2f,\n",
			 fname, n, ntests, thresh);
		      printf("seed = %d\n", *seed);
		      printf("norm = %d\n", norm);


		      /* Print test info */
		      switch (prec) {
		      case blas_prec_single:
			printf("single ");
			break;
		      case blas_prec_double:
			printf("double ");
			break;
		      case blas_prec_indigenous:
			printf("indigenous ");
			break;
		      case blas_prec_extra:
			printf("extra ");
			break;
		      }
		      switch (norm) {
		      case -1:
			printf("near_underflow ");
			break;
		      case 0:
			printf("near_one ");
			break;
		      case 1:
			printf("near_overflow ");
			break;
		      }

		      printf("incx=%d, incy=%d:\n", incx, incy);

		      cprint_vector(x, n, incx_val, "x");
		      cprint_vector(y_ori, n, incy_val, "y_ori");
		      cprint_vector(y_comp, n, incy_val, "y_comp");

		      printf("      ");
		      printf("alpha = ");
		      printf("(%16.8e, %16.8e)", alpha[0], alpha[1]);
		      printf("; ");
		      printf("beta = ");
		      printf("(%16.8e, %16.8e)", beta[0], beta[1]);
		      printf("\n");
		      printf("      ratio=%.4e\n", ratio);
		      printf("iymax = %d\n", iymax);
		      printf("ixmax = %d\n", ixmax);
		      p_count++;
		    }
		  }
		  if (d_count == 0) {
		    if (ratio > ratio_max)
		      ratio_max = ratio;
		    iymax_max = iymax;
		    ixmax_max = ixmax;
		    if (ratio != 0.0 && ratio < ratio_min)
		      ratio_min = ratio;

		    tot_tests++;
		  }
		}		/* incy */
	      }			/* incx */
	    }			/* tests */
	  }			/* norm */
	}			/* prec */
      }				/* beta */
    }				/* alpha */
  }				/* debug */

  if ((debug == 2) || ((debug == 1) && (bad_ratios > 0))) {
    printf("      %s:  n = %d, ntests = %d, thresh = %4.2f\n",
	   fname, n, ntests, thresh);
    if (ratio_min == 1.0e+308)
      ratio_min = 0.0;
    printf
      ("      bad/total = %d/%d=%3.2f, min_ratio = %.4e, max_ratio = %.4e\n\n",
       bad_ratios, tot_tests, ((double) bad_ratios) / ((double) tot_tests),
       ratio_min, ratio_max);
    printf("iymax_max = %d, ixmax_max = %d\n", iymax_max, ixmax_max);
  }

  blas_free(x);
  blas_free(y_ori);
  blas_free(y_comp);
  blas_free(head_y_true);
  blas_free(tail_y_true);
  blas_free(x_gen);
  blas_free(y_gen);

  *min_ratio = ratio_min;
  *num_bad_ratio = bad_ratios;
  *num_tests = tot_tests;

  FPU_FIX_STOP;
  return ratio_max;
}				/* end of do_test_caxpby_x */

double do_test_zaxpby_x(int n, int ntests, int *seed, double thresh,
			int debug, double *min_ratio, int *num_bad_ratio,
			int *num_tests)

/*
 * Purpose  
 * =======
 *
 * Runs a series of tests on axpby  
 *
 * Arguments
 * =========
 *
 * n         (input) int
 *           The size of vector being tested
 *
 * ntests    (input) int
 *           The number of tests to run for each set of attributes.
 *
 * seed      (input/output) int         
 *           The seed for the random number generator used in testgen().
 *
 * thresh    (input) double
 *           When the ratio returned from test() exceeds the specified
 *           threshold, the current size, y_true, y_comp, and ratio will be
 *           printed.  (Since ratio is supposed to be O(1), we can set thresh
 *           to ~10.)
 *
 * debug     (input) int
 *           If debug=3, print summary 
 *           If debug=2, print summary only if the number of bad ratios > 0
 *           If debug=1, print complete info if tests fail
 *           If debug=0, return max ratio
 *
 * min_ratio (output) double
 *           The minimum ratio
 * 
 * num_bad_ratio (output) int
 *               The number of tests fail; they are above the threshold.
 *
 * num_tests (output) int
 *           The number of tests is being performed.
 *
 * Return value
 * ============
 *
 * The maximum ratio if run successfully, otherwise return -1 
 *
 * Code structure
 * ==============
 * 
 *  debug loop  -- if debug is one, the first loop computes the max ratio
 *              -- and the last(second) loop outputs debugging information,
 *              -- if the test fail and its ratio > 0.5 * max ratio.
 *              -- if debug is zero, the loop is executed once
 *    alpha loop  -- varying alpha: 0, 1, or random
 *      beta loop   -- varying beta: 0, 1, or random
 *        prec loop   -- varying internal prec: single, double, or extra
 *          norm loop   -- varying norm: near undeflow, near one, or 
 *                        -- near overflow
 *            numtest loop  -- how many times the test is perform with 
 *                            -- above set of attributes
 *                incx loop     -- varying incx: -2, -1, 1, 2
 *                  incy loop     -- varying incy: -2, -1, 1, 2
 */
{
  /* function name */
  const char fname[] = "BLAS_zaxpby_x";

  /* max number of debug lines to print */
  const int max_print = 32;

  /* Variables in the "x_val" form are loop vars for corresponding
     variables */
  int i;			/* iterate through the repeating tests */
  int ix, iy;			/* use to index x and y respectively */
  int incx_val, incy_val,	/* for testing different inc values */
    incx, incy, incx_gen, incy_gen, ygen_val, xgen_val, test_val;
  int d_count;			/* counter for debug */
  int find_max_ratio;		/* find_max_ratio = 1 only if debug = 3 */
  int p_count;			/* counter for the number of debug lines printed */
  int tot_tests;		/* total number of tests to be done */
  int norm;			/* input values of near underflow/one/overflow */
  double ratio_max;		/* the current maximum ratio */
  double ratio_min;		/* the current minimum ratio */
  double ratio;			/* the per-use test ratio from test() */
  double new_ratio;
  int bad_ratios;		/* the number of ratios over the threshold */
  double eps_int;		/* the internal epsilon expected--2^(-24) for float */
  double un_int;		/* the internal underflow threshold */
  double alpha[2];
  double beta[2];
  double *x;
  double y_fix[2];
  double *y_ori;
  double *y_comp;		/* the y computed  by BLAS_zaxpby_x */

  int ixmax, iymax;
  int ixmax_max, iymax_max;

  /* x_gen and y_gen are used to store vectors generated by testgen.
     they eventually are copied back to x and y */
  double *x_gen;
  double *y_gen;

  /* the true y calculated by testgen(), in double-double */
  double *head_y_true, *tail_y_true;

  int alpha_val;
  int alpha_flag;		/* input flag for BLAS_zdot_testgen */
  int beta_val;
  int beta_flag;		/* input flag for BLAS_zdot_testgen */
  int prec_val;
  enum blas_prec_type prec;
  int saved_seed;		/* for saving the original seed */
  int count, old_count;		/* use for counting the number of testgen calls * 2 */

  FPU_FIX_DECL;

  /* test for bad arguments */
  if (n < 0 || ntests < 0)
    BLAS_error(fname, 0, 0, NULL);

  /* if there is nothing to test, return all zero */
  if (n == 0 || ntests == 0) {
    *min_ratio = 0.0;
    *num_bad_ratio = 0;
    *num_tests = 0;
    return 0.0;
  }

  FPU_FIX_START;

  /* get space for calculation */
  x = (double *) blas_malloc(n * 2 * sizeof(double) * 2);
  if (n * 2 > 0 && x == NULL) {
    BLAS_error("blas_malloc", 0, 0, "malloc failed.\n");
  }
  y_ori = (double *) blas_malloc(n * 2 * sizeof(double) * 2);
  if (n * 2 > 0 && y_ori == NULL) {
    BLAS_error("blas_malloc", 0, 0, "malloc failed.\n");
  }
  y_comp = (double *) blas_malloc(n * 2 * sizeof(double) * 2);
  if (n * 2 > 0 && y_comp == NULL) {
    BLAS_error("blas_malloc", 0, 0, "malloc failed.\n");
  }
  head_y_true = (double *) blas_malloc(n * sizeof(double) * 2);
  tail_y_true = (double *) blas_malloc(n * sizeof(double) * 2);
  if (n > 0 && (head_y_true == NULL || tail_y_true == NULL)) {
    BLAS_error("blas_malloc", 0, 0, "malloc failed.\n");
  }
  x_gen = (double *) blas_malloc(n * sizeof(double) * 2);
  if (n > 0 && x_gen == NULL) {
    BLAS_error("blas_malloc", 0, 0, "malloc failed.\n");
  }
  y_gen = (double *) blas_malloc(n * sizeof(double) * 2);
  if (n > 0 && y_gen == NULL) {
    BLAS_error("blas_malloc", 0, 0, "malloc failed.\n");
  }

  /* initialization */
  saved_seed = *seed;
  ratio_min = 1e308;
  ratio_max = 0.0;
  tot_tests = 0;
  p_count = 0;
  count = 0;
  bad_ratios = 0;
  ixmax_max = 0;
  iymax_max = 0;
  alpha_flag = 0;
  beta_flag = 0;
  old_count = 0;

  find_max_ratio = 0;
  if (debug == 3)
    find_max_ratio = 1;
  y_fix[0] = 1.0;
  y_fix[1] = 0.0;

  /* initialize incx_gen and incy_gen */
  incx_gen = 1;
  incy_gen = 1;
  incx_gen *= 2;
  incy_gen *= 2;

  /* The debug iteration:
     If debug=1, then will execute the iteration twice. First, compute the
     max ratio. Second, print info if ratio > (50% * ratio_max). */
  for (d_count = 0; d_count <= find_max_ratio; d_count++) {
    bad_ratios = 0;		/* set to zero */

    if ((debug == 3) && (d_count == find_max_ratio))
      *seed = saved_seed;	/* restore the original seed */

    /* varying alpha */
    for (alpha_val = 0; alpha_val < 3; alpha_val++) {
      alpha_flag = 0;
      switch (alpha_val) {
      case 0:
	alpha[0] = alpha[1] = 0.0;
	alpha_flag = 1;
	break;
      case 1:
	alpha[0] = 1.0;
	alpha[1] = 0.0;
	alpha_flag = 1;
	break;
      }

      /* varying beta */
      for (beta_val = 0; beta_val < 3; beta_val++) {
	beta_flag = 0;
	switch (beta_val) {
	case 0:
	  beta[0] = beta[1] = 0.0;
	  beta_flag = 1;
	  break;
	case 1:
	  beta[0] = 1.0;
	  beta[1] = 0.0;
	  beta_flag = 1;
	  break;
	}


	/* varying extra precs */
	for (prec_val = 0; prec_val <= 2; prec_val++) {
	  switch (prec_val) {
	  case 0:
	    eps_int = power(2, -BITS_D);
	    un_int = pow((double) BLAS_fpinfo_x(blas_base, blas_prec_double),
			 (double) BLAS_fpinfo_x(blas_emin, blas_prec_double));
	    prec = blas_prec_double;
	    break;
	  case 1:
	    eps_int = power(2, -BITS_D);
	    un_int = pow((double) BLAS_fpinfo_x(blas_base, blas_prec_double),
			 (double) BLAS_fpinfo_x(blas_emin, blas_prec_double));
	    prec = blas_prec_double;
	    break;
	  case 2:
	  default:
	    eps_int = power(2, -BITS_E);
	    un_int = pow((double) BLAS_fpinfo_x(blas_base, blas_prec_extra),
			 (double) BLAS_fpinfo_x(blas_emin, blas_prec_extra));
	    prec = blas_prec_extra;
	    break;
	  }

	  /* values near underflow, 1, or overflow */
	  for (norm = -1; norm <= 1; norm++) {

	    /* number of tests */
	    for (i = 0; i < ntests; i++) {

	      /* generate test inputs */
	      BLAS_zdot_testgen(1, 0, 1, norm, blas_no_conj, alpha,
				alpha_flag, beta, beta_flag, y_fix, x_gen,
				seed, y_gen, head_y_true, tail_y_true);
	      xgen_val = incx_gen;
	      for (ygen_val = incy_gen; ygen_val < n * incy_gen;
		   ygen_val += incy_gen) {
		BLAS_zdot_testgen(1, 0, 1, norm, blas_no_conj, alpha, 1, beta,
				  1, y_fix, &x_gen[xgen_val], seed,
				  &y_gen[ygen_val], &head_y_true[ygen_val],
				  &tail_y_true[ygen_val]);
		xgen_val += incx_gen;
	      }

	      count++;

	      /* varying incx */
	      for (incx_val = -2; incx_val <= 2; incx_val++) {
		if (incx_val == 0)
		  continue;

		/* setting incx */
		incx = incx_val;

		zcopy_vector(x_gen, n, 1, x, incx_val);

		/* varying incy */
		for (incy_val = -2; incy_val <= 2; incy_val++) {
		  if (incy_val == 0)
		    continue;

		  /* setting incy */
		  incy = incy_val;
		  incy *= 2;

		  zcopy_vector(y_gen, n, 1, y_ori, incy_val);
		  zcopy_vector(y_gen, n, 1, y_comp, incy_val);

		  /* call BLAS_zaxpby_x to get y_comp */
		  FPU_FIX_STOP;
		  BLAS_zaxpby_x(n, alpha, x, incx_val, beta,
				y_comp, incy_val, prec);
		  FPU_FIX_START;


		  /* computing the ratio */
		  ix = 0;
		  if (incx < 0)
		    ix = -(n - 1) * incx;
		  iy = 0;
		  if (incy < 0)
		    iy = -(n - 1) * incy;
		  ratio = 0.0;

		  ixmax = -1;
		  iymax = -1;
		  for (test_val = 0; test_val < n * incy_gen;
		       test_val += incy_gen) {
		    test_BLAS_zdot(1, blas_no_conj, alpha, beta, &y_ori[iy],
				   &y_comp[iy], &head_y_true[test_val],
				   &tail_y_true[test_val], y_fix, incx,
				   &x[ix], incx, eps_int, un_int, &new_ratio);

		    ix += incx;
		    iy += incy;
		    if (MAX(ratio, new_ratio) == new_ratio) {
		      ixmax = ix;
		      iymax = iy;
		    }
		    ratio = MAX(ratio, new_ratio);
		  }

		  /* increase the number of bad ratio, if the ratio
		     is bigger than the threshold.
		     The !<= below causes NaN error to be detected.
		     Note that (NaN > thresh) is always false. */
		  if (!(ratio <= thresh)) {
		    bad_ratios++;


		    if ((debug == 3) &&	/* print only when debug is on */
			(count != old_count) &&	/* print if old vector is different */
			/* from the current one */
			(d_count == find_max_ratio) &&
			(p_count <= max_print) && (ratio > 0.5 * ratio_max)) {
		      old_count = count;

		      printf
			("FAIL> %s: n = %d, ntests = %d, threshold = %4.2f,\n",
			 fname, n, ntests, thresh);
		      printf("seed = %d\n", *seed);
		      printf("norm = %d\n", norm);


		      /* Print test info */
		      switch (prec) {
		      case blas_prec_single:
			printf("single ");
			break;
		      case blas_prec_double:
			printf("double ");
			break;
		      case blas_prec_indigenous:
			printf("indigenous ");
			break;
		      case blas_prec_extra:
			printf("extra ");
			break;
		      }
		      switch (norm) {
		      case -1:
			printf("near_underflow ");
			break;
		      case 0:
			printf("near_one ");
			break;
		      case 1:
			printf("near_overflow ");
			break;
		      }

		      printf("incx=%d, incy=%d:\n", incx, incy);

		      zprint_vector(x, n, incx_val, "x");
		      zprint_vector(y_ori, n, incy_val, "y_ori");
		      zprint_vector(y_comp, n, incy_val, "y_comp");

		      printf("      ");
		      printf("alpha = ");
		      printf("(%24.16e, %24.16e)", alpha[0], alpha[1]);
		      printf("; ");
		      printf("beta = ");
		      printf("(%24.16e, %24.16e)", beta[0], beta[1]);
		      printf("\n");
		      printf("      ratio=%.4e\n", ratio);
		      printf("iymax = %d\n", iymax);
		      printf("ixmax = %d\n", ixmax);
		      p_count++;
		    }
		  }
		  if (d_count == 0) {
		    if (ratio > ratio_max)
		      ratio_max = ratio;
		    iymax_max = iymax;
		    ixmax_max = ixmax;
		    if (ratio != 0.0 && ratio < ratio_min)
		      ratio_min = ratio;

		    tot_tests++;
		  }
		}		/* incy */
	      }			/* incx */
	    }			/* tests */
	  }			/* norm */
	}			/* prec */
      }				/* beta */
    }				/* alpha */
  }				/* debug */

  if ((debug == 2) || ((debug == 1) && (bad_ratios > 0))) {
    printf("      %s:  n = %d, ntests = %d, thresh = %4.2f\n",
	   fname, n, ntests, thresh);
    if (ratio_min == 1.0e+308)
      ratio_min = 0.0;
    printf
      ("      bad/total = %d/%d=%3.2f, min_ratio = %.4e, max_ratio = %.4e\n\n",
       bad_ratios, tot_tests, ((double) bad_ratios) / ((double) tot_tests),
       ratio_min, ratio_max);
    printf("iymax_max = %d, ixmax_max = %d\n", iymax_max, ixmax_max);
  }

  blas_free(x);
  blas_free(y_ori);
  blas_free(y_comp);
  blas_free(head_y_true);
  blas_free(tail_y_true);
  blas_free(x_gen);
  blas_free(y_gen);

  *min_ratio = ratio_min;
  *num_bad_ratio = bad_ratios;
  *num_tests = tot_tests;

  FPU_FIX_STOP;
  return ratio_max;
}				/* end of do_test_zaxpby_x */

double do_test_daxpby_s_x(int n, int ntests, int *seed, double thresh,
			  int debug, double *min_ratio, int *num_bad_ratio,
			  int *num_tests)

/*
 * Purpose  
 * =======
 *
 * Runs a series of tests on axpby  
 *
 * Arguments
 * =========
 *
 * n         (input) int
 *           The size of vector being tested
 *
 * ntests    (input) int
 *           The number of tests to run for each set of attributes.
 *
 * seed      (input/output) int         
 *           The seed for the random number generator used in testgen().
 *
 * thresh    (input) double
 *           When the ratio returned from test() exceeds the specified
 *           threshold, the current size, y_true, y_comp, and ratio will be
 *           printed.  (Since ratio is supposed to be O(1), we can set thresh
 *           to ~10.)
 *
 * debug     (input) int
 *           If debug=3, print summary 
 *           If debug=2, print summary only if the number of bad ratios > 0
 *           If debug=1, print complete info if tests fail
 *           If debug=0, return max ratio
 *
 * min_ratio (output) double
 *           The minimum ratio
 * 
 * num_bad_ratio (output) int
 *               The number of tests fail; they are above the threshold.
 *
 * num_tests (output) int
 *           The number of tests is being performed.
 *
 * Return value
 * ============
 *
 * The maximum ratio if run successfully, otherwise return -1 
 *
 * Code structure
 * ==============
 * 
 *  debug loop  -- if debug is one, the first loop computes the max ratio
 *              -- and the last(second) loop outputs debugging information,
 *              -- if the test fail and its ratio > 0.5 * max ratio.
 *              -- if debug is zero, the loop is executed once
 *    alpha loop  -- varying alpha: 0, 1, or random
 *      beta loop   -- varying beta: 0, 1, or random
 *        prec loop   -- varying internal prec: single, double, or extra
 *          norm loop   -- varying norm: near undeflow, near one, or 
 *                        -- near overflow
 *            numtest loop  -- how many times the test is perform with 
 *                            -- above set of attributes
 *                incx loop     -- varying incx: -2, -1, 1, 2
 *                  incy loop     -- varying incy: -2, -1, 1, 2
 */
{
  /* function name */
  const char fname[] = "BLAS_daxpby_s_x";

  /* max number of debug lines to print */
  const int max_print = 32;

  /* Variables in the "x_val" form are loop vars for corresponding
     variables */
  int i;			/* iterate through the repeating tests */
  int ix, iy;			/* use to index x and y respectively */
  int incx_val, incy_val,	/* for testing different inc values */
    incx, incy, incx_gen, incy_gen, ygen_val, xgen_val, test_val;
  int d_count;			/* counter for debug */
  int find_max_ratio;		/* find_max_ratio = 1 only if debug = 3 */
  int p_count;			/* counter for the number of debug lines printed */
  int tot_tests;		/* total number of tests to be done */
  int norm;			/* input values of near underflow/one/overflow */
  double ratio_max;		/* the current maximum ratio */
  double ratio_min;		/* the current minimum ratio */
  double ratio;			/* the per-use test ratio from test() */
  double new_ratio;
  int bad_ratios;		/* the number of ratios over the threshold */
  double eps_int;		/* the internal epsilon expected--2^(-24) for float */
  double un_int;		/* the internal underflow threshold */
  double alpha;
  double beta;
  float *x;
  float y_fix;
  double *y_ori;
  double *y_comp;		/* the y computed  by BLAS_daxpby_s_x */

  int ixmax, iymax;
  int ixmax_max, iymax_max;

  /* x_gen and y_gen are used to store vectors generated by testgen.
     they eventually are copied back to x and y */
  float *x_gen;
  double *y_gen;

  /* the true y calculated by testgen(), in double-double */
  double *head_y_true, *tail_y_true;
  int alpha_val;
  int alpha_flag;		/* input flag for BLAS_ddot_s_s_testgen */
  int beta_val;
  int beta_flag;		/* input flag for BLAS_ddot_s_s_testgen */
  int prec_val;
  enum blas_prec_type prec;
  int saved_seed;		/* for saving the original seed */
  int count, old_count;		/* use for counting the number of testgen calls * 2 */

  FPU_FIX_DECL;

  /* test for bad arguments */
  if (n < 0 || ntests < 0)
    BLAS_error(fname, 0, 0, NULL);

  /* if there is nothing to test, return all zero */
  if (n == 0 || ntests == 0) {
    *min_ratio = 0.0;
    *num_bad_ratio = 0;
    *num_tests = 0;
    return 0.0;
  }

  FPU_FIX_START;

  /* get space for calculation */
  x = (float *) blas_malloc(n * 2 * sizeof(float));
  if (n * 2 > 0 && x == NULL) {
    BLAS_error("blas_malloc", 0, 0, "malloc failed.\n");
  }
  y_ori = (double *) blas_malloc(n * 2 * sizeof(double));
  if (n * 2 > 0 && y_ori == NULL) {
    BLAS_error("blas_malloc", 0, 0, "malloc failed.\n");
  }
  y_comp = (double *) blas_malloc(n * 2 * sizeof(double));
  if (n * 2 > 0 && y_comp == NULL) {
    BLAS_error("blas_malloc", 0, 0, "malloc failed.\n");
  }
  head_y_true = (double *) blas_malloc(n * sizeof(double));
  tail_y_true = (double *) blas_malloc(n * sizeof(double));
  if (n > 0 && (head_y_true == NULL || tail_y_true == NULL)) {
    BLAS_error("blas_malloc", 0, 0, "malloc failed.\n");
  }
  x_gen = (float *) blas_malloc(n * sizeof(float));
  if (n > 0 && x_gen == NULL) {
    BLAS_error("blas_malloc", 0, 0, "malloc failed.\n");
  }
  y_gen = (double *) blas_malloc(n * sizeof(double));
  if (n > 0 && y_gen == NULL) {
    BLAS_error("blas_malloc", 0, 0, "malloc failed.\n");
  }

  /* initialization */
  saved_seed = *seed;
  ratio_min = 1e308;
  ratio_max = 0.0;
  tot_tests = 0;
  p_count = 0;
  count = 0;
  bad_ratios = 0;
  ixmax_max = 0;
  iymax_max = 0;
  alpha_flag = 0;
  beta_flag = 0;
  old_count = 0;

  find_max_ratio = 0;
  if (debug == 3)
    find_max_ratio = 1;
  y_fix = 1.0;

  /* initialize incx_gen and incy_gen */
  incx_gen = 1;
  incy_gen = 1;



  /* The debug iteration:
     If debug=1, then will execute the iteration twice. First, compute the
     max ratio. Second, print info if ratio > (50% * ratio_max). */
  for (d_count = 0; d_count <= find_max_ratio; d_count++) {
    bad_ratios = 0;		/* set to zero */

    if ((debug == 3) && (d_count == find_max_ratio))
      *seed = saved_seed;	/* restore the original seed */

    /* varying alpha */
    for (alpha_val = 0; alpha_val < 3; alpha_val++) {
      alpha_flag = 0;
      switch (alpha_val) {
      case 0:
	alpha = 0.0;
	alpha_flag = 1;
	break;
      case 1:
	alpha = 1.0;
	alpha_flag = 1;
	break;
      }

      /* varying beta */
      for (beta_val = 0; beta_val < 3; beta_val++) {
	beta_flag = 0;
	switch (beta_val) {
	case 0:
	  beta = 0.0;
	  beta_flag = 1;
	  break;
	case 1:
	  beta = 1.0;
	  beta_flag = 1;
	  break;
	}


	/* varying extra precs */
	for (prec_val = 0; prec_val <= 2; prec_val++) {
	  switch (prec_val) {
	  case 0:
	    eps_int = power(2, -BITS_D);
	    un_int = pow((double) BLAS_fpinfo_x(blas_base, blas_prec_double),
			 (double) BLAS_fpinfo_x(blas_emin, blas_prec_double));
	    prec = blas_prec_double;
	    break;
	  case 1:
	    eps_int = power(2, -BITS_D);
	    un_int = pow((double) BLAS_fpinfo_x(blas_base, blas_prec_double),
			 (double) BLAS_fpinfo_x(blas_emin, blas_prec_double));
	    prec = blas_prec_double;
	    break;
	  case 2:
	  default:
	    eps_int = power(2, -BITS_E);
	    un_int = pow((double) BLAS_fpinfo_x(blas_base, blas_prec_extra),
			 (double) BLAS_fpinfo_x(blas_emin, blas_prec_extra));
	    prec = blas_prec_extra;
	    break;
	  }

	  /* values near underflow, 1, or overflow */
	  for (norm = -1; norm <= 1; norm++) {

	    /* number of tests */
	    for (i = 0; i < ntests; i++) {

	      /* generate test inputs */
	      BLAS_ddot_s_s_testgen(1, 0, 1, norm, blas_no_conj, &alpha,
				    alpha_flag, &beta, beta_flag, &y_fix,
				    x_gen, seed, y_gen, head_y_true,
				    tail_y_true);
	      xgen_val = incx_gen;
	      for (ygen_val = incy_gen; ygen_val < n * incy_gen;
		   ygen_val += incy_gen) {
		BLAS_ddot_s_s_testgen(1, 0, 1, norm, blas_no_conj, &alpha, 1,
				      &beta, 1, &y_fix, &x_gen[xgen_val],
				      seed, &y_gen[ygen_val],
				      &head_y_true[ygen_val],
				      &tail_y_true[ygen_val]);
		xgen_val += incx_gen;
	      }

	      count++;

	      /* varying incx */
	      for (incx_val = -2; incx_val <= 2; incx_val++) {
		if (incx_val == 0)
		  continue;

		/* setting incx */
		incx = incx_val;

		scopy_vector(x_gen, n, 1, x, incx_val);

		/* varying incy */
		for (incy_val = -2; incy_val <= 2; incy_val++) {
		  if (incy_val == 0)
		    continue;

		  /* setting incy */
		  incy = incy_val;


		  dcopy_vector(y_gen, n, 1, y_ori, incy_val);
		  dcopy_vector(y_gen, n, 1, y_comp, incy_val);

		  /* call BLAS_daxpby_s_x to get y_comp */
		  FPU_FIX_STOP;
		  BLAS_daxpby_s_x(n, alpha, x, incx_val, beta,
				  y_comp, incy_val, prec);
		  FPU_FIX_START;


		  /* computing the ratio */
		  ix = 0;
		  if (incx < 0)
		    ix = -(n - 1) * incx;
		  iy = 0;
		  if (incy < 0)
		    iy = -(n - 1) * incy;
		  ratio = 0.0;

		  ixmax = -1;
		  iymax = -1;
		  for (test_val = 0; test_val < n * incy_gen;
		       test_val += incy_gen) {
		    test_BLAS_ddot_s_s(1, blas_no_conj, alpha, beta,
				       y_ori[iy], y_comp[iy],
				       head_y_true[test_val],
				       tail_y_true[test_val], &y_fix, incx,
				       &x[ix], incx, eps_int, un_int,
				       &new_ratio);

		    ix += incx;
		    iy += incy;
		    if (MAX(ratio, new_ratio) == new_ratio) {
		      ixmax = ix;
		      iymax = iy;
		    }
		    ratio = MAX(ratio, new_ratio);
		  }

		  /* increase the number of bad ratio, if the ratio
		     is bigger than the threshold.
		     The !<= below causes NaN error to be detected.
		     Note that (NaN > thresh) is always false. */
		  if (!(ratio <= thresh)) {
		    bad_ratios++;


		    if ((debug == 3) &&	/* print only when debug is on */
			(count != old_count) &&	/* print if old vector is different */
			/* from the current one */
			(d_count == find_max_ratio) &&
			(p_count <= max_print) && (ratio > 0.5 * ratio_max)) {
		      old_count = count;

		      printf
			("FAIL> %s: n = %d, ntests = %d, threshold = %4.2f,\n",
			 fname, n, ntests, thresh);
		      printf("seed = %d\n", *seed);
		      printf("norm = %d\n", norm);


		      /* Print test info */
		      switch (prec) {
		      case blas_prec_single:
			printf("single ");
			break;
		      case blas_prec_double:
			printf("double ");
			break;
		      case blas_prec_indigenous:
			printf("indigenous ");
			break;
		      case blas_prec_extra:
			printf("extra ");
			break;
		      }
		      switch (norm) {
		      case -1:
			printf("near_underflow ");
			break;
		      case 0:
			printf("near_one ");
			break;
		      case 1:
			printf("near_overflow ");
			break;
		      }

		      printf("incx=%d, incy=%d:\n", incx, incy);

		      sprint_vector(x, n, incx_val, "x");
		      dprint_vector(y_ori, n, incy_val, "y_ori");
		      dprint_vector(y_comp, n, incy_val, "y_comp");

		      printf("      ");
		      printf("alpha = ");
		      printf("%24.16e", alpha);
		      printf("; ");
		      printf("beta = ");
		      printf("%24.16e", beta);
		      printf("\n");
		      printf("      ratio=%.4e\n", ratio);
		      printf("iymax = %d\n", iymax);
		      printf("ixmax = %d\n", ixmax);
		      p_count++;
		    }
		  }
		  if (d_count == 0) {
		    if (ratio > ratio_max)
		      ratio_max = ratio;
		    iymax_max = iymax;
		    ixmax_max = ixmax;
		    if (ratio != 0.0 && ratio < ratio_min)
		      ratio_min = ratio;

		    tot_tests++;
		  }
		}		/* incy */
	      }			/* incx */
	    }			/* tests */
	  }			/* norm */
	}			/* prec */
      }				/* beta */
    }				/* alpha */
  }				/* debug */

  if ((debug == 2) || ((debug == 1) && (bad_ratios > 0))) {
    printf("      %s:  n = %d, ntests = %d, thresh = %4.2f\n",
	   fname, n, ntests, thresh);
    if (ratio_min == 1.0e+308)
      ratio_min = 0.0;
    printf
      ("      bad/total = %d/%d=%3.2f, min_ratio = %.4e, max_ratio = %.4e\n\n",
       bad_ratios, tot_tests, ((double) bad_ratios) / ((double) tot_tests),
       ratio_min, ratio_max);
    printf("iymax_max = %d, ixmax_max = %d\n", iymax_max, ixmax_max);
  }

  blas_free(x);
  blas_free(y_ori);
  blas_free(y_comp);
  blas_free(head_y_true);
  blas_free(tail_y_true);
  blas_free(x_gen);
  blas_free(y_gen);

  *min_ratio = ratio_min;
  *num_bad_ratio = bad_ratios;
  *num_tests = tot_tests;

  FPU_FIX_STOP;
  return ratio_max;
}				/* end of do_test_daxpby_s_x */

double do_test_zaxpby_c_x(int n, int ntests, int *seed, double thresh,
			  int debug, double *min_ratio, int *num_bad_ratio,
			  int *num_tests)

/*
 * Purpose  
 * =======
 *
 * Runs a series of tests on axpby  
 *
 * Arguments
 * =========
 *
 * n         (input) int
 *           The size of vector being tested
 *
 * ntests    (input) int
 *           The number of tests to run for each set of attributes.
 *
 * seed      (input/output) int         
 *           The seed for the random number generator used in testgen().
 *
 * thresh    (input) double
 *           When the ratio returned from test() exceeds the specified
 *           threshold, the current size, y_true, y_comp, and ratio will be
 *           printed.  (Since ratio is supposed to be O(1), we can set thresh
 *           to ~10.)
 *
 * debug     (input) int
 *           If debug=3, print summary 
 *           If debug=2, print summary only if the number of bad ratios > 0
 *           If debug=1, print complete info if tests fail
 *           If debug=0, return max ratio
 *
 * min_ratio (output) double
 *           The minimum ratio
 * 
 * num_bad_ratio (output) int
 *               The number of tests fail; they are above the threshold.
 *
 * num_tests (output) int
 *           The number of tests is being performed.
 *
 * Return value
 * ============
 *
 * The maximum ratio if run successfully, otherwise return -1 
 *
 * Code structure
 * ==============
 * 
 *  debug loop  -- if debug is one, the first loop computes the max ratio
 *              -- and the last(second) loop outputs debugging information,
 *              -- if the test fail and its ratio > 0.5 * max ratio.
 *              -- if debug is zero, the loop is executed once
 *    alpha loop  -- varying alpha: 0, 1, or random
 *      beta loop   -- varying beta: 0, 1, or random
 *        prec loop   -- varying internal prec: single, double, or extra
 *          norm loop   -- varying norm: near undeflow, near one, or 
 *                        -- near overflow
 *            numtest loop  -- how many times the test is perform with 
 *                            -- above set of attributes
 *                incx loop     -- varying incx: -2, -1, 1, 2
 *                  incy loop     -- varying incy: -2, -1, 1, 2
 */
{
  /* function name */
  const char fname[] = "BLAS_zaxpby_c_x";

  /* max number of debug lines to print */
  const int max_print = 32;

  /* Variables in the "x_val" form are loop vars for corresponding
     variables */
  int i;			/* iterate through the repeating tests */
  int ix, iy;			/* use to index x and y respectively */
  int incx_val, incy_val,	/* for testing different inc values */
    incx, incy, incx_gen, incy_gen, ygen_val, xgen_val, test_val;
  int d_count;			/* counter for debug */
  int find_max_ratio;		/* find_max_ratio = 1 only if debug = 3 */
  int p_count;			/* counter for the number of debug lines printed */
  int tot_tests;		/* total number of tests to be done */
  int norm;			/* input values of near underflow/one/overflow */
  double ratio_max;		/* the current maximum ratio */
  double ratio_min;		/* the current minimum ratio */
  double ratio;			/* the per-use test ratio from test() */
  double new_ratio;
  int bad_ratios;		/* the number of ratios over the threshold */
  double eps_int;		/* the internal epsilon expected--2^(-24) for float */
  double un_int;		/* the internal underflow threshold */
  double alpha[2];
  double beta[2];
  float *x;
  float y_fix[2];
  double *y_ori;
  double *y_comp;		/* the y computed  by BLAS_zaxpby_c_x */

  int ixmax, iymax;
  int ixmax_max, iymax_max;

  /* x_gen and y_gen are used to store vectors generated by testgen.
     they eventually are copied back to x and y */
  float *x_gen;
  double *y_gen;

  /* the true y calculated by testgen(), in double-double */
  double *head_y_true, *tail_y_true;

  int alpha_val;
  int alpha_flag;		/* input flag for BLAS_zdot_c_c_testgen */
  int beta_val;
  int beta_flag;		/* input flag for BLAS_zdot_c_c_testgen */
  int prec_val;
  enum blas_prec_type prec;
  int saved_seed;		/* for saving the original seed */
  int count, old_count;		/* use for counting the number of testgen calls * 2 */

  FPU_FIX_DECL;

  /* test for bad arguments */
  if (n < 0 || ntests < 0)
    BLAS_error(fname, 0, 0, NULL);

  /* if there is nothing to test, return all zero */
  if (n == 0 || ntests == 0) {
    *min_ratio = 0.0;
    *num_bad_ratio = 0;
    *num_tests = 0;
    return 0.0;
  }

  FPU_FIX_START;

  /* get space for calculation */
  x = (float *) blas_malloc(n * 2 * sizeof(float) * 2);
  if (n * 2 > 0 && x == NULL) {
    BLAS_error("blas_malloc", 0, 0, "malloc failed.\n");
  }
  y_ori = (double *) blas_malloc(n * 2 * sizeof(double) * 2);
  if (n * 2 > 0 && y_ori == NULL) {
    BLAS_error("blas_malloc", 0, 0, "malloc failed.\n");
  }
  y_comp = (double *) blas_malloc(n * 2 * sizeof(double) * 2);
  if (n * 2 > 0 && y_comp == NULL) {
    BLAS_error("blas_malloc", 0, 0, "malloc failed.\n");
  }
  head_y_true = (double *) blas_malloc(n * sizeof(double) * 2);
  tail_y_true = (double *) blas_malloc(n * sizeof(double) * 2);
  if (n > 0 && (head_y_true == NULL || tail_y_true == NULL)) {
    BLAS_error("blas_malloc", 0, 0, "malloc failed.\n");
  }
  x_gen = (float *) blas_malloc(n * sizeof(float) * 2);
  if (n > 0 && x_gen == NULL) {
    BLAS_error("blas_malloc", 0, 0, "malloc failed.\n");
  }
  y_gen = (double *) blas_malloc(n * sizeof(double) * 2);
  if (n > 0 && y_gen == NULL) {
    BLAS_error("blas_malloc", 0, 0, "malloc failed.\n");
  }

  /* initialization */
  saved_seed = *seed;
  ratio_min = 1e308;
  ratio_max = 0.0;
  tot_tests = 0;
  p_count = 0;
  count = 0;
  bad_ratios = 0;
  ixmax_max = 0;
  iymax_max = 0;
  alpha_flag = 0;
  beta_flag = 0;
  old_count = 0;

  find_max_ratio = 0;
  if (debug == 3)
    find_max_ratio = 1;
  y_fix[0] = 1.0;
  y_fix[1] = 0.0;

  /* initialize incx_gen and incy_gen */
  incx_gen = 1;
  incy_gen = 1;
  incx_gen *= 2;
  incy_gen *= 2;

  /* The debug iteration:
     If debug=1, then will execute the iteration twice. First, compute the
     max ratio. Second, print info if ratio > (50% * ratio_max). */
  for (d_count = 0; d_count <= find_max_ratio; d_count++) {
    bad_ratios = 0;		/* set to zero */

    if ((debug == 3) && (d_count == find_max_ratio))
      *seed = saved_seed;	/* restore the original seed */

    /* varying alpha */
    for (alpha_val = 0; alpha_val < 3; alpha_val++) {
      alpha_flag = 0;
      switch (alpha_val) {
      case 0:
	alpha[0] = alpha[1] = 0.0;
	alpha_flag = 1;
	break;
      case 1:
	alpha[0] = 1.0;
	alpha[1] = 0.0;
	alpha_flag = 1;
	break;
      }

      /* varying beta */
      for (beta_val = 0; beta_val < 3; beta_val++) {
	beta_flag = 0;
	switch (beta_val) {
	case 0:
	  beta[0] = beta[1] = 0.0;
	  beta_flag = 1;
	  break;
	case 1:
	  beta[0] = 1.0;
	  beta[1] = 0.0;
	  beta_flag = 1;
	  break;
	}


	/* varying extra precs */
	for (prec_val = 0; prec_val <= 2; prec_val++) {
	  switch (prec_val) {
	  case 0:
	    eps_int = power(2, -BITS_D);
	    un_int = pow((double) BLAS_fpinfo_x(blas_base, blas_prec_double),
			 (double) BLAS_fpinfo_x(blas_emin, blas_prec_double));
	    prec = blas_prec_double;
	    break;
	  case 1:
	    eps_int = power(2, -BITS_D);
	    un_int = pow((double) BLAS_fpinfo_x(blas_base, blas_prec_double),
			 (double) BLAS_fpinfo_x(blas_emin, blas_prec_double));
	    prec = blas_prec_double;
	    break;
	  case 2:
	  default:
	    eps_int = power(2, -BITS_E);
	    un_int = pow((double) BLAS_fpinfo_x(blas_base, blas_prec_extra),
			 (double) BLAS_fpinfo_x(blas_emin, blas_prec_extra));
	    prec = blas_prec_extra;
	    break;
	  }

	  /* values near underflow, 1, or overflow */
	  for (norm = -1; norm <= 1; norm++) {

	    /* number of tests */
	    for (i = 0; i < ntests; i++) {

	      /* generate test inputs */
	      BLAS_zdot_c_c_testgen(1, 0, 1, norm, blas_no_conj, alpha,
				    alpha_flag, beta, beta_flag, y_fix, x_gen,
				    seed, y_gen, head_y_true, tail_y_true);
	      xgen_val = incx_gen;
	      for (ygen_val = incy_gen; ygen_val < n * incy_gen;
		   ygen_val += incy_gen) {
		BLAS_zdot_c_c_testgen(1, 0, 1, norm, blas_no_conj, alpha, 1,
				      beta, 1, y_fix, &x_gen[xgen_val], seed,
				      &y_gen[ygen_val],
				      &head_y_true[ygen_val],
				      &tail_y_true[ygen_val]);
		xgen_val += incx_gen;
	      }

	      count++;

	      /* varying incx */
	      for (incx_val = -2; incx_val <= 2; incx_val++) {
		if (incx_val == 0)
		  continue;

		/* setting incx */
		incx = incx_val;

		ccopy_vector(x_gen, n, 1, x, incx_val);

		/* varying incy */
		for (incy_val = -2; incy_val <= 2; incy_val++) {
		  if (incy_val == 0)
		    continue;

		  /* setting incy */
		  incy = incy_val;
		  incy *= 2;

		  zcopy_vector(y_gen, n, 1, y_ori, incy_val);
		  zcopy_vector(y_gen, n, 1, y_comp, incy_val);

		  /* call BLAS_zaxpby_c_x to get y_comp */
		  FPU_FIX_STOP;
		  BLAS_zaxpby_c_x(n, alpha, x, incx_val, beta,
				  y_comp, incy_val, prec);
		  FPU_FIX_START;


		  /* computing the ratio */
		  ix = 0;
		  if (incx < 0)
		    ix = -(n - 1) * incx;
		  iy = 0;
		  if (incy < 0)
		    iy = -(n - 1) * incy;
		  ratio = 0.0;

		  ixmax = -1;
		  iymax = -1;
		  for (test_val = 0; test_val < n * incy_gen;
		       test_val += incy_gen) {
		    test_BLAS_zdot_c_c(1, blas_no_conj, alpha, beta,
				       &y_ori[iy], &y_comp[iy],
				       &head_y_true[test_val],
				       &tail_y_true[test_val], y_fix, incx,
				       &x[ix], incx, eps_int, un_int,
				       &new_ratio);

		    ix += incx;
		    iy += incy;
		    if (MAX(ratio, new_ratio) == new_ratio) {
		      ixmax = ix;
		      iymax = iy;
		    }
		    ratio = MAX(ratio, new_ratio);
		  }

		  /* increase the number of bad ratio, if the ratio
		     is bigger than the threshold.
		     The !<= below causes NaN error to be detected.
		     Note that (NaN > thresh) is always false. */
		  if (!(ratio <= thresh)) {
		    bad_ratios++;


		    if ((debug == 3) &&	/* print only when debug is on */
			(count != old_count) &&	/* print if old vector is different */
			/* from the current one */
			(d_count == find_max_ratio) &&
			(p_count <= max_print) && (ratio > 0.5 * ratio_max)) {
		      old_count = count;

		      printf
			("FAIL> %s: n = %d, ntests = %d, threshold = %4.2f,\n",
			 fname, n, ntests, thresh);
		      printf("seed = %d\n", *seed);
		      printf("norm = %d\n", norm);


		      /* Print test info */
		      switch (prec) {
		      case blas_prec_single:
			printf("single ");
			break;
		      case blas_prec_double:
			printf("double ");
			break;
		      case blas_prec_indigenous:
			printf("indigenous ");
			break;
		      case blas_prec_extra:
			printf("extra ");
			break;
		      }
		      switch (norm) {
		      case -1:
			printf("near_underflow ");
			break;
		      case 0:
			printf("near_one ");
			break;
		      case 1:
			printf("near_overflow ");
			break;
		      }

		      printf("incx=%d, incy=%d:\n", incx, incy);

		      cprint_vector(x, n, incx_val, "x");
		      zprint_vector(y_ori, n, incy_val, "y_ori");
		      zprint_vector(y_comp, n, incy_val, "y_comp");

		      printf("      ");
		      printf("alpha = ");
		      printf("(%24.16e, %24.16e)", alpha[0], alpha[1]);
		      printf("; ");
		      printf("beta = ");
		      printf("(%24.16e, %24.16e)", beta[0], beta[1]);
		      printf("\n");
		      printf("      ratio=%.4e\n", ratio);
		      printf("iymax = %d\n", iymax);
		      printf("ixmax = %d\n", ixmax);
		      p_count++;
		    }
		  }
		  if (d_count == 0) {
		    if (ratio > ratio_max)
		      ratio_max = ratio;
		    iymax_max = iymax;
		    ixmax_max = ixmax;
		    if (ratio != 0.0 && ratio < ratio_min)
		      ratio_min = ratio;

		    tot_tests++;
		  }
		}		/* incy */
	      }			/* incx */
	    }			/* tests */
	  }			/* norm */
	}			/* prec */
      }				/* beta */
    }				/* alpha */
  }				/* debug */

  if ((debug == 2) || ((debug == 1) && (bad_ratios > 0))) {
    printf("      %s:  n = %d, ntests = %d, thresh = %4.2f\n",
	   fname, n, ntests, thresh);
    if (ratio_min == 1.0e+308)
      ratio_min = 0.0;
    printf
      ("      bad/total = %d/%d=%3.2f, min_ratio = %.4e, max_ratio = %.4e\n\n",
       bad_ratios, tot_tests, ((double) bad_ratios) / ((double) tot_tests),
       ratio_min, ratio_max);
    printf("iymax_max = %d, ixmax_max = %d\n", iymax_max, ixmax_max);
  }

  blas_free(x);
  blas_free(y_ori);
  blas_free(y_comp);
  blas_free(head_y_true);
  blas_free(tail_y_true);
  blas_free(x_gen);
  blas_free(y_gen);

  *min_ratio = ratio_min;
  *num_bad_ratio = bad_ratios;
  *num_tests = tot_tests;

  FPU_FIX_STOP;
  return ratio_max;
}				/* end of do_test_zaxpby_c_x */

double do_test_caxpby_s_x(int n, int ntests, int *seed, double thresh,
			  int debug, double *min_ratio, int *num_bad_ratio,
			  int *num_tests)

/*
 * Purpose  
 * =======
 *
 * Runs a series of tests on axpby  
 *
 * Arguments
 * =========
 *
 * n         (input) int
 *           The size of vector being tested
 *
 * ntests    (input) int
 *           The number of tests to run for each set of attributes.
 *
 * seed      (input/output) int         
 *           The seed for the random number generator used in testgen().
 *
 * thresh    (input) double
 *           When the ratio returned from test() exceeds the specified
 *           threshold, the current size, y_true, y_comp, and ratio will be
 *           printed.  (Since ratio is supposed to be O(1), we can set thresh
 *           to ~10.)
 *
 * debug     (input) int
 *           If debug=3, print summary 
 *           If debug=2, print summary only if the number of bad ratios > 0
 *           If debug=1, print complete info if tests fail
 *           If debug=0, return max ratio
 *
 * min_ratio (output) double
 *           The minimum ratio
 * 
 * num_bad_ratio (output) int
 *               The number of tests fail; they are above the threshold.
 *
 * num_tests (output) int
 *           The number of tests is being performed.
 *
 * Return value
 * ============
 *
 * The maximum ratio if run successfully, otherwise return -1 
 *
 * Code structure
 * ==============
 * 
 *  debug loop  -- if debug is one, the first loop computes the max ratio
 *              -- and the last(second) loop outputs debugging information,
 *              -- if the test fail and its ratio > 0.5 * max ratio.
 *              -- if debug is zero, the loop is executed once
 *    alpha loop  -- varying alpha: 0, 1, or random
 *      beta loop   -- varying beta: 0, 1, or random
 *        prec loop   -- varying internal prec: single, double, or extra
 *          norm loop   -- varying norm: near undeflow, near one, or 
 *                        -- near overflow
 *            numtest loop  -- how many times the test is perform with 
 *                            -- above set of attributes
 *                incx loop     -- varying incx: -2, -1, 1, 2
 *                  incy loop     -- varying incy: -2, -1, 1, 2
 */
{
  /* function name */
  const char fname[] = "BLAS_caxpby_s_x";

  /* max number of debug lines to print */
  const int max_print = 32;

  /* Variables in the "x_val" form are loop vars for corresponding
     variables */
  int i;			/* iterate through the repeating tests */
  int ix, iy;			/* use to index x and y respectively */
  int incx_val, incy_val,	/* for testing different inc values */
    incx, incy, incx_gen, incy_gen, ygen_val, xgen_val, test_val;
  int d_count;			/* counter for debug */
  int find_max_ratio;		/* find_max_ratio = 1 only if debug = 3 */
  int p_count;			/* counter for the number of debug lines printed */
  int tot_tests;		/* total number of tests to be done */
  int norm;			/* input values of near underflow/one/overflow */
  double ratio_max;		/* the current maximum ratio */
  double ratio_min;		/* the current minimum ratio */
  double ratio;			/* the per-use test ratio from test() */
  double new_ratio;
  int bad_ratios;		/* the number of ratios over the threshold */
  double eps_int;		/* the internal epsilon expected--2^(-24) for float */
  double un_int;		/* the internal underflow threshold */
  float alpha[2];
  float beta[2];
  float *x;
  float y_fix;
  float *y_ori;
  float *y_comp;		/* the y computed  by BLAS_caxpby_s_x */

  int ixmax, iymax;
  int ixmax_max, iymax_max;

  /* x_gen and y_gen are used to store vectors generated by testgen.
     they eventually are copied back to x and y */
  float *x_gen;
  float *y_gen;

  /* the true y calculated by testgen(), in double-double */
  double *head_y_true, *tail_y_true;

  int alpha_val;
  int alpha_flag;		/* input flag for BLAS_cdot_s_s_testgen */
  int beta_val;
  int beta_flag;		/* input flag for BLAS_cdot_s_s_testgen */
  int prec_val;
  enum blas_prec_type prec;
  int saved_seed;		/* for saving the original seed */
  int count, old_count;		/* use for counting the number of testgen calls * 2 */

  FPU_FIX_DECL;

  /* test for bad arguments */
  if (n < 0 || ntests < 0)
    BLAS_error(fname, 0, 0, NULL);

  /* if there is nothing to test, return all zero */
  if (n == 0 || ntests == 0) {
    *min_ratio = 0.0;
    *num_bad_ratio = 0;
    *num_tests = 0;
    return 0.0;
  }

  FPU_FIX_START;

  /* get space for calculation */
  x = (float *) blas_malloc(n * 2 * sizeof(float));
  if (n * 2 > 0 && x == NULL) {
    BLAS_error("blas_malloc", 0, 0, "malloc failed.\n");
  }
  y_ori = (float *) blas_malloc(n * 2 * sizeof(float) * 2);
  if (n * 2 > 0 && y_ori == NULL) {
    BLAS_error("blas_malloc", 0, 0, "malloc failed.\n");
  }
  y_comp = (float *) blas_malloc(n * 2 * sizeof(float) * 2);
  if (n * 2 > 0 && y_comp == NULL) {
    BLAS_error("blas_malloc", 0, 0, "malloc failed.\n");
  }
  head_y_true = (double *) blas_malloc(n * sizeof(double) * 2);
  tail_y_true = (double *) blas_malloc(n * sizeof(double) * 2);
  if (n > 0 && (head_y_true == NULL || tail_y_true == NULL)) {
    BLAS_error("blas_malloc", 0, 0, "malloc failed.\n");
  }
  x_gen = (float *) blas_malloc(n * sizeof(float));
  if (n > 0 && x_gen == NULL) {
    BLAS_error("blas_malloc", 0, 0, "malloc failed.\n");
  }
  y_gen = (float *) blas_malloc(n * sizeof(float) * 2);
  if (n > 0 && y_gen == NULL) {
    BLAS_error("blas_malloc", 0, 0, "malloc failed.\n");
  }

  /* initialization */
  saved_seed = *seed;
  ratio_min = 1e308;
  ratio_max = 0.0;
  tot_tests = 0;
  p_count = 0;
  count = 0;
  bad_ratios = 0;
  ixmax_max = 0;
  iymax_max = 0;
  alpha_flag = 0;
  beta_flag = 0;
  old_count = 0;

  find_max_ratio = 0;
  if (debug == 3)
    find_max_ratio = 1;
  y_fix = 1.0;

  /* initialize incx_gen and incy_gen */
  incx_gen = 1;
  incy_gen = 1;

  incy_gen *= 2;

  /* The debug iteration:
     If debug=1, then will execute the iteration twice. First, compute the
     max ratio. Second, print info if ratio > (50% * ratio_max). */
  for (d_count = 0; d_count <= find_max_ratio; d_count++) {
    bad_ratios = 0;		/* set to zero */

    if ((debug == 3) && (d_count == find_max_ratio))
      *seed = saved_seed;	/* restore the original seed */

    /* varying alpha */
    for (alpha_val = 0; alpha_val < 3; alpha_val++) {
      alpha_flag = 0;
      switch (alpha_val) {
      case 0:
	alpha[0] = alpha[1] = 0.0;
	alpha_flag = 1;
	break;
      case 1:
	alpha[0] = 1.0;
	alpha[1] = 0.0;
	alpha_flag = 1;
	break;
      }

      /* varying beta */
      for (beta_val = 0; beta_val < 3; beta_val++) {
	beta_flag = 0;
	switch (beta_val) {
	case 0:
	  beta[0] = beta[1] = 0.0;
	  beta_flag = 1;
	  break;
	case 1:
	  beta[0] = 1.0;
	  beta[1] = 0.0;
	  beta_flag = 1;
	  break;
	}


	/* varying extra precs */
	for (prec_val = 0; prec_val <= 2; prec_val++) {
	  switch (prec_val) {
	  case 0:
	    eps_int = power(2, -BITS_S);
	    un_int = pow((double) BLAS_fpinfo_x(blas_base, blas_prec_single),
			 (double) BLAS_fpinfo_x(blas_emin, blas_prec_single));
	    prec = blas_prec_single;
	    break;
	  case 1:
	    eps_int = power(2, -BITS_D);
	    un_int = pow((double) BLAS_fpinfo_x(blas_base, blas_prec_double),
			 (double) BLAS_fpinfo_x(blas_emin, blas_prec_double));
	    prec = blas_prec_double;
	    break;
	  case 2:
	  default:
	    eps_int = power(2, -BITS_E);
	    un_int = pow((double) BLAS_fpinfo_x(blas_base, blas_prec_extra),
			 (double) BLAS_fpinfo_x(blas_emin, blas_prec_extra));
	    prec = blas_prec_extra;
	    break;
	  }

	  /* values near underflow, 1, or overflow */
	  for (norm = -1; norm <= 1; norm++) {

	    /* number of tests */
	    for (i = 0; i < ntests; i++) {

	      /* generate test inputs */
	      BLAS_cdot_s_s_testgen(1, 0, 1, norm, blas_no_conj, alpha,
				    alpha_flag, beta, beta_flag, &y_fix,
				    x_gen, seed, y_gen, head_y_true,
				    tail_y_true);
	      xgen_val = incx_gen;
	      for (ygen_val = incy_gen; ygen_val < n * incy_gen;
		   ygen_val += incy_gen) {
		BLAS_cdot_s_s_testgen(1, 0, 1, norm, blas_no_conj, alpha, 1,
				      beta, 1, &y_fix, &x_gen[xgen_val], seed,
				      &y_gen[ygen_val],
				      &head_y_true[ygen_val],
				      &tail_y_true[ygen_val]);
		xgen_val += incx_gen;
	      }

	      count++;

	      /* varying incx */
	      for (incx_val = -2; incx_val <= 2; incx_val++) {
		if (incx_val == 0)
		  continue;

		/* setting incx */
		incx = incx_val;

		scopy_vector(x_gen, n, 1, x, incx_val);

		/* varying incy */
		for (incy_val = -2; incy_val <= 2; incy_val++) {
		  if (incy_val == 0)
		    continue;

		  /* setting incy */
		  incy = incy_val;
		  incy *= 2;

		  ccopy_vector(y_gen, n, 1, y_ori, incy_val);
		  ccopy_vector(y_gen, n, 1, y_comp, incy_val);

		  /* call BLAS_caxpby_s_x to get y_comp */
		  FPU_FIX_STOP;
		  BLAS_caxpby_s_x(n, alpha, x, incx_val, beta,
				  y_comp, incy_val, prec);
		  FPU_FIX_START;


		  /* computing the ratio */
		  ix = 0;
		  if (incx < 0)
		    ix = -(n - 1) * incx;
		  iy = 0;
		  if (incy < 0)
		    iy = -(n - 1) * incy;
		  ratio = 0.0;

		  ixmax = -1;
		  iymax = -1;
		  for (test_val = 0; test_val < n * incy_gen;
		       test_val += incy_gen) {
		    test_BLAS_cdot_s_s(1, blas_no_conj, alpha, beta,
				       &y_ori[iy], &y_comp[iy],
				       &head_y_true[test_val],
				       &tail_y_true[test_val], &y_fix, incx,
				       &x[ix], incx, eps_int, un_int,
				       &new_ratio);

		    ix += incx;
		    iy += incy;
		    if (MAX(ratio, new_ratio) == new_ratio) {
		      ixmax = ix;
		      iymax = iy;
		    }
		    ratio = MAX(ratio, new_ratio);
		  }

		  /* increase the number of bad ratio, if the ratio
		     is bigger than the threshold.
		     The !<= below causes NaN error to be detected.
		     Note that (NaN > thresh) is always false. */
		  if (!(ratio <= thresh)) {
		    bad_ratios++;


		    if ((debug == 3) &&	/* print only when debug is on */
			(count != old_count) &&	/* print if old vector is different */
			/* from the current one */
			(d_count == find_max_ratio) &&
			(p_count <= max_print) && (ratio > 0.5 * ratio_max)) {
		      old_count = count;

		      printf
			("FAIL> %s: n = %d, ntests = %d, threshold = %4.2f,\n",
			 fname, n, ntests, thresh);
		      printf("seed = %d\n", *seed);
		      printf("norm = %d\n", norm);


		      /* Print test info */
		      switch (prec) {
		      case blas_prec_single:
			printf("single ");
			break;
		      case blas_prec_double:
			printf("double ");
			break;
		      case blas_prec_indigenous:
			printf("indigenous ");
			break;
		      case blas_prec_extra:
			printf("extra ");
			break;
		      }
		      switch (norm) {
		      case -1:
			printf("near_underflow ");
			break;
		      case 0:
			printf("near_one ");
			break;
		      case 1:
			printf("near_overflow ");
			break;
		      }

		      printf("incx=%d, incy=%d:\n", incx, incy);

		      sprint_vector(x, n, incx_val, "x");
		      cprint_vector(y_ori, n, incy_val, "y_ori");
		      cprint_vector(y_comp, n, incy_val, "y_comp");

		      printf("      ");
		      printf("alpha = ");
		      printf("(%16.8e, %16.8e)", alpha[0], alpha[1]);
		      printf("; ");
		      printf("beta = ");
		      printf("(%16.8e, %16.8e)", beta[0], beta[1]);
		      printf("\n");
		      printf("      ratio=%.4e\n", ratio);
		      printf("iymax = %d\n", iymax);
		      printf("ixmax = %d\n", ixmax);
		      p_count++;
		    }
		  }
		  if (d_count == 0) {
		    if (ratio > ratio_max)
		      ratio_max = ratio;
		    iymax_max = iymax;
		    ixmax_max = ixmax;
		    if (ratio != 0.0 && ratio < ratio_min)
		      ratio_min = ratio;

		    tot_tests++;
		  }
		}		/* incy */
	      }			/* incx */
	    }			/* tests */
	  }			/* norm */
	}			/* prec */
      }				/* beta */
    }				/* alpha */
  }				/* debug */

  if ((debug == 2) || ((debug == 1) && (bad_ratios > 0))) {
    printf("      %s:  n = %d, ntests = %d, thresh = %4.2f\n",
	   fname, n, ntests, thresh);
    if (ratio_min == 1.0e+308)
      ratio_min = 0.0;
    printf
      ("      bad/total = %d/%d=%3.2f, min_ratio = %.4e, max_ratio = %.4e\n\n",
       bad_ratios, tot_tests, ((double) bad_ratios) / ((double) tot_tests),
       ratio_min, ratio_max);
    printf("iymax_max = %d, ixmax_max = %d\n", iymax_max, ixmax_max);
  }

  blas_free(x);
  blas_free(y_ori);
  blas_free(y_comp);
  blas_free(head_y_true);
  blas_free(tail_y_true);
  blas_free(x_gen);
  blas_free(y_gen);

  *min_ratio = ratio_min;
  *num_bad_ratio = bad_ratios;
  *num_tests = tot_tests;

  FPU_FIX_STOP;
  return ratio_max;
}				/* end of do_test_caxpby_s_x */

double do_test_zaxpby_d_x(int n, int ntests, int *seed, double thresh,
			  int debug, double *min_ratio, int *num_bad_ratio,
			  int *num_tests)

/*
 * Purpose  
 * =======
 *
 * Runs a series of tests on axpby  
 *
 * Arguments
 * =========
 *
 * n         (input) int
 *           The size of vector being tested
 *
 * ntests    (input) int
 *           The number of tests to run for each set of attributes.
 *
 * seed      (input/output) int         
 *           The seed for the random number generator used in testgen().
 *
 * thresh    (input) double
 *           When the ratio returned from test() exceeds the specified
 *           threshold, the current size, y_true, y_comp, and ratio will be
 *           printed.  (Since ratio is supposed to be O(1), we can set thresh
 *           to ~10.)
 *
 * debug     (input) int
 *           If debug=3, print summary 
 *           If debug=2, print summary only if the number of bad ratios > 0
 *           If debug=1, print complete info if tests fail
 *           If debug=0, return max ratio
 *
 * min_ratio (output) double
 *           The minimum ratio
 * 
 * num_bad_ratio (output) int
 *               The number of tests fail; they are above the threshold.
 *
 * num_tests (output) int
 *           The number of tests is being performed.
 *
 * Return value
 * ============
 *
 * The maximum ratio if run successfully, otherwise return -1 
 *
 * Code structure
 * ==============
 * 
 *  debug loop  -- if debug is one, the first loop computes the max ratio
 *              -- and the last(second) loop outputs debugging information,
 *              -- if the test fail and its ratio > 0.5 * max ratio.
 *              -- if debug is zero, the loop is executed once
 *    alpha loop  -- varying alpha: 0, 1, or random
 *      beta loop   -- varying beta: 0, 1, or random
 *        prec loop   -- varying internal prec: single, double, or extra
 *          norm loop   -- varying norm: near undeflow, near one, or 
 *                        -- near overflow
 *            numtest loop  -- how many times the test is perform with 
 *                            -- above set of attributes
 *                incx loop     -- varying incx: -2, -1, 1, 2
 *                  incy loop     -- varying incy: -2, -1, 1, 2
 */
{
  /* function name */
  const char fname[] = "BLAS_zaxpby_d_x";

  /* max number of debug lines to print */
  const int max_print = 32;

  /* Variables in the "x_val" form are loop vars for corresponding
     variables */
  int i;			/* iterate through the repeating tests */
  int ix, iy;			/* use to index x and y respectively */
  int incx_val, incy_val,	/* for testing different inc values */
    incx, incy, incx_gen, incy_gen, ygen_val, xgen_val, test_val;
  int d_count;			/* counter for debug */
  int find_max_ratio;		/* find_max_ratio = 1 only if debug = 3 */
  int p_count;			/* counter for the number of debug lines printed */
  int tot_tests;		/* total number of tests to be done */
  int norm;			/* input values of near underflow/one/overflow */
  double ratio_max;		/* the current maximum ratio */
  double ratio_min;		/* the current minimum ratio */
  double ratio;			/* the per-use test ratio from test() */
  double new_ratio;
  int bad_ratios;		/* the number of ratios over the threshold */
  double eps_int;		/* the internal epsilon expected--2^(-24) for float */
  double un_int;		/* the internal underflow threshold */
  double alpha[2];
  double beta[2];
  double *x;
  double y_fix;
  double *y_ori;
  double *y_comp;		/* the y computed  by BLAS_zaxpby_d_x */

  int ixmax, iymax;
  int ixmax_max, iymax_max;

  /* x_gen and y_gen are used to store vectors generated by testgen.
     they eventually are copied back to x and y */
  double *x_gen;
  double *y_gen;

  /* the true y calculated by testgen(), in double-double */
  double *head_y_true, *tail_y_true;

  int alpha_val;
  int alpha_flag;		/* input flag for BLAS_zdot_d_d_testgen */
  int beta_val;
  int beta_flag;		/* input flag for BLAS_zdot_d_d_testgen */
  int prec_val;
  enum blas_prec_type prec;
  int saved_seed;		/* for saving the original seed */
  int count, old_count;		/* use for counting the number of testgen calls * 2 */

  FPU_FIX_DECL;

  /* test for bad arguments */
  if (n < 0 || ntests < 0)
    BLAS_error(fname, 0, 0, NULL);

  /* if there is nothing to test, return all zero */
  if (n == 0 || ntests == 0) {
    *min_ratio = 0.0;
    *num_bad_ratio = 0;
    *num_tests = 0;
    return 0.0;
  }

  FPU_FIX_START;

  /* get space for calculation */
  x = (double *) blas_malloc(n * 2 * sizeof(double));
  if (n * 2 > 0 && x == NULL) {
    BLAS_error("blas_malloc", 0, 0, "malloc failed.\n");
  }
  y_ori = (double *) blas_malloc(n * 2 * sizeof(double) * 2);
  if (n * 2 > 0 && y_ori == NULL) {
    BLAS_error("blas_malloc", 0, 0, "malloc failed.\n");
  }
  y_comp = (double *) blas_malloc(n * 2 * sizeof(double) * 2);
  if (n * 2 > 0 && y_comp == NULL) {
    BLAS_error("blas_malloc", 0, 0, "malloc failed.\n");
  }
  head_y_true = (double *) blas_malloc(n * sizeof(double) * 2);
  tail_y_true = (double *) blas_malloc(n * sizeof(double) * 2);
  if (n > 0 && (head_y_true == NULL || tail_y_true == NULL)) {
    BLAS_error("blas_malloc", 0, 0, "malloc failed.\n");
  }
  x_gen = (double *) blas_malloc(n * sizeof(double));
  if (n > 0 && x_gen == NULL) {
    BLAS_error("blas_malloc", 0, 0, "malloc failed.\n");
  }
  y_gen = (double *) blas_malloc(n * sizeof(double) * 2);
  if (n > 0 && y_gen == NULL) {
    BLAS_error("blas_malloc", 0, 0, "malloc failed.\n");
  }

  /* initialization */
  saved_seed = *seed;
  ratio_min = 1e308;
  ratio_max = 0.0;
  tot_tests = 0;
  p_count = 0;
  count = 0;
  bad_ratios = 0;
  ixmax_max = 0;
  iymax_max = 0;
  alpha_flag = 0;
  beta_flag = 0;
  old_count = 0;

  find_max_ratio = 0;
  if (debug == 3)
    find_max_ratio = 1;
  y_fix = 1.0;

  /* initialize incx_gen and incy_gen */
  incx_gen = 1;
  incy_gen = 1;

  incy_gen *= 2;

  /* The debug iteration:
     If debug=1, then will execute the iteration twice. First, compute the
     max ratio. Second, print info if ratio > (50% * ratio_max). */
  for (d_count = 0; d_count <= find_max_ratio; d_count++) {
    bad_ratios = 0;		/* set to zero */

    if ((debug == 3) && (d_count == find_max_ratio))
      *seed = saved_seed;	/* restore the original seed */

    /* varying alpha */
    for (alpha_val = 0; alpha_val < 3; alpha_val++) {
      alpha_flag = 0;
      switch (alpha_val) {
      case 0:
	alpha[0] = alpha[1] = 0.0;
	alpha_flag = 1;
	break;
      case 1:
	alpha[0] = 1.0;
	alpha[1] = 0.0;
	alpha_flag = 1;
	break;
      }

      /* varying beta */
      for (beta_val = 0; beta_val < 3; beta_val++) {
	beta_flag = 0;
	switch (beta_val) {
	case 0:
	  beta[0] = beta[1] = 0.0;
	  beta_flag = 1;
	  break;
	case 1:
	  beta[0] = 1.0;
	  beta[1] = 0.0;
	  beta_flag = 1;
	  break;
	}


	/* varying extra precs */
	for (prec_val = 0; prec_val <= 2; prec_val++) {
	  switch (prec_val) {
	  case 0:
	    eps_int = power(2, -BITS_D);
	    un_int = pow((double) BLAS_fpinfo_x(blas_base, blas_prec_double),
			 (double) BLAS_fpinfo_x(blas_emin, blas_prec_double));
	    prec = blas_prec_double;
	    break;
	  case 1:
	    eps_int = power(2, -BITS_D);
	    un_int = pow((double) BLAS_fpinfo_x(blas_base, blas_prec_double),
			 (double) BLAS_fpinfo_x(blas_emin, blas_prec_double));
	    prec = blas_prec_double;
	    break;
	  case 2:
	  default:
	    eps_int = power(2, -BITS_E);
	    un_int = pow((double) BLAS_fpinfo_x(blas_base, blas_prec_extra),
			 (double) BLAS_fpinfo_x(blas_emin, blas_prec_extra));
	    prec = blas_prec_extra;
	    break;
	  }

	  /* values near underflow, 1, or overflow */
	  for (norm = -1; norm <= 1; norm++) {

	    /* number of tests */
	    for (i = 0; i < ntests; i++) {

	      /* generate test inputs */
	      BLAS_zdot_d_d_testgen(1, 0, 1, norm, blas_no_conj, alpha,
				    alpha_flag, beta, beta_flag, &y_fix,
				    x_gen, seed, y_gen, head_y_true,
				    tail_y_true);
	      xgen_val = incx_gen;
	      for (ygen_val = incy_gen; ygen_val < n * incy_gen;
		   ygen_val += incy_gen) {
		BLAS_zdot_d_d_testgen(1, 0, 1, norm, blas_no_conj, alpha, 1,
				      beta, 1, &y_fix, &x_gen[xgen_val], seed,
				      &y_gen[ygen_val],
				      &head_y_true[ygen_val],
				      &tail_y_true[ygen_val]);
		xgen_val += incx_gen;
	      }

	      count++;

	      /* varying incx */
	      for (incx_val = -2; incx_val <= 2; incx_val++) {
		if (incx_val == 0)
		  continue;

		/* setting incx */
		incx = incx_val;

		dcopy_vector(x_gen, n, 1, x, incx_val);

		/* varying incy */
		for (incy_val = -2; incy_val <= 2; incy_val++) {
		  if (incy_val == 0)
		    continue;

		  /* setting incy */
		  incy = incy_val;
		  incy *= 2;

		  zcopy_vector(y_gen, n, 1, y_ori, incy_val);
		  zcopy_vector(y_gen, n, 1, y_comp, incy_val);

		  /* call BLAS_zaxpby_d_x to get y_comp */
		  FPU_FIX_STOP;
		  BLAS_zaxpby_d_x(n, alpha, x, incx_val, beta,
				  y_comp, incy_val, prec);
		  FPU_FIX_START;


		  /* computing the ratio */
		  ix = 0;
		  if (incx < 0)
		    ix = -(n - 1) * incx;
		  iy = 0;
		  if (incy < 0)
		    iy = -(n - 1) * incy;
		  ratio = 0.0;

		  ixmax = -1;
		  iymax = -1;
		  for (test_val = 0; test_val < n * incy_gen;
		       test_val += incy_gen) {
		    test_BLAS_zdot_d_d(1, blas_no_conj, alpha, beta,
				       &y_ori[iy], &y_comp[iy],
				       &head_y_true[test_val],
				       &tail_y_true[test_val], &y_fix, incx,
				       &x[ix], incx, eps_int, un_int,
				       &new_ratio);

		    ix += incx;
		    iy += incy;
		    if (MAX(ratio, new_ratio) == new_ratio) {
		      ixmax = ix;
		      iymax = iy;
		    }
		    ratio = MAX(ratio, new_ratio);
		  }

		  /* increase the number of bad ratio, if the ratio
		     is bigger than the threshold.
		     The !<= below causes NaN error to be detected.
		     Note that (NaN > thresh) is always false. */
		  if (!(ratio <= thresh)) {
		    bad_ratios++;


		    if ((debug == 3) &&	/* print only when debug is on */
			(count != old_count) &&	/* print if old vector is different */
			/* from the current one */
			(d_count == find_max_ratio) &&
			(p_count <= max_print) && (ratio > 0.5 * ratio_max)) {
		      old_count = count;

		      printf
			("FAIL> %s: n = %d, ntests = %d, threshold = %4.2f,\n",
			 fname, n, ntests, thresh);
		      printf("seed = %d\n", *seed);
		      printf("norm = %d\n", norm);


		      /* Print test info */
		      switch (prec) {
		      case blas_prec_single:
			printf("single ");
			break;
		      case blas_prec_double:
			printf("double ");
			break;
		      case blas_prec_indigenous:
			printf("indigenous ");
			break;
		      case blas_prec_extra:
			printf("extra ");
			break;
		      }
		      switch (norm) {
		      case -1:
			printf("near_underflow ");
			break;
		      case 0:
			printf("near_one ");
			break;
		      case 1:
			printf("near_overflow ");
			break;
		      }

		      printf("incx=%d, incy=%d:\n", incx, incy);

		      dprint_vector(x, n, incx_val, "x");
		      zprint_vector(y_ori, n, incy_val, "y_ori");
		      zprint_vector(y_comp, n, incy_val, "y_comp");

		      printf("      ");
		      printf("alpha = ");
		      printf("(%24.16e, %24.16e)", alpha[0], alpha[1]);
		      printf("; ");
		      printf("beta = ");
		      printf("(%24.16e, %24.16e)", beta[0], beta[1]);
		      printf("\n");
		      printf("      ratio=%.4e\n", ratio);
		      printf("iymax = %d\n", iymax);
		      printf("ixmax = %d\n", ixmax);
		      p_count++;
		    }
		  }
		  if (d_count == 0) {
		    if (ratio > ratio_max)
		      ratio_max = ratio;
		    iymax_max = iymax;
		    ixmax_max = ixmax;
		    if (ratio != 0.0 && ratio < ratio_min)
		      ratio_min = ratio;

		    tot_tests++;
		  }
		}		/* incy */
	      }			/* incx */
	    }			/* tests */
	  }			/* norm */
	}			/* prec */
      }				/* beta */
    }				/* alpha */
  }				/* debug */

  if ((debug == 2) || ((debug == 1) && (bad_ratios > 0))) {
    printf("      %s:  n = %d, ntests = %d, thresh = %4.2f\n",
	   fname, n, ntests, thresh);
    if (ratio_min == 1.0e+308)
      ratio_min = 0.0;
    printf
      ("      bad/total = %d/%d=%3.2f, min_ratio = %.4e, max_ratio = %.4e\n\n",
       bad_ratios, tot_tests, ((double) bad_ratios) / ((double) tot_tests),
       ratio_min, ratio_max);
    printf("iymax_max = %d, ixmax_max = %d\n", iymax_max, ixmax_max);
  }

  blas_free(x);
  blas_free(y_ori);
  blas_free(y_comp);
  blas_free(head_y_true);
  blas_free(tail_y_true);
  blas_free(x_gen);
  blas_free(y_gen);

  *min_ratio = ratio_min;
  *num_bad_ratio = bad_ratios;
  *num_tests = tot_tests;

  FPU_FIX_STOP;
  return ratio_max;
}				/* end of do_test_zaxpby_d_x */


int main(int argc, char **argv)
{
  int nsizes, ntests, debug;
  double thresh, test_prob;
  double total_min_ratio, total_max_ratio;
  int total_bad_ratios;
  int seed, num_bad_ratio, num_tests;
  int total_tests, nr_failed_routines = 0, nr_routines = 0;
  double min_ratio, max_ratio;
  const char *base_routine = "axpby";
  char *fname;
  int n;


  if (argc != 6) {
    printf("Usage:\n");
    printf("do_test_axpby <nsizes> <ntests> <thresh> <debug> <test_prob>\n");
    printf("   <nsizes>: number of sizes to be run.\n");
    printf
      ("   <ntests>: the number of tests performed for each set of attributes\n");
    printf
      ("   <thresh>: to catch bad ratios if it is greater than <thresh>\n");
    printf("    <debug>: 0, 1, 2, or 3; \n");
    printf("        if 0, no printing \n");
    printf("        if 1, print error summary only if tests fail\n");
    printf("        if 2, print error summary for each n\n");
    printf("        if 3, print complete info each test fails \n");
    printf("<test_prob>: probability of preforming a given \n");
    printf("           test case: 0.0 does no tests, 1.0 does all tests\n");
    return -1;
  } else {
    nsizes = atoi(argv[1]);
    ntests = atoi(argv[2]);
    thresh = atof(argv[3]);
    debug = atoi(argv[4]);
    test_prob = atof(argv[5]);
  }

  seed = 1999;

  if (nsizes < 0 || ntests < 0 || debug < 0 || debug > 3)
    BLAS_error("Testing axpby", 0, 0, NULL);

  printf("Testing %s...\n", base_routine);
  printf("INPUT: nsizes = %d, ntests = %d, thresh = %4.2f, debug = %d\n\n",
	 nsizes, ntests, thresh, debug);



  min_ratio = 1e308;
  max_ratio = 0.0;
  total_bad_ratios = 0;
  total_tests = 0;
  fname = "BLAS_saxpby";
  printf("Testing %s...\n", fname);
  for (n = 0; n <= nsizes; n++) {
    total_max_ratio =
      do_test_saxpby(n, ntests, &seed, thresh, debug, &total_min_ratio,
		     &num_bad_ratio, &num_tests);
    if (total_max_ratio > max_ratio)
      max_ratio = total_max_ratio;

    if (total_min_ratio < min_ratio)
      min_ratio = total_min_ratio;

    total_bad_ratios += num_bad_ratio;
    total_tests += num_tests;
  }

  if (total_bad_ratios == 0)
    printf("PASS> ");
  else {
    printf("FAIL> ");
    nr_failed_routines++;
  }
  nr_routines++;

  printf("%-24s: bad/total = %d/%d, max_ratio = %.2e\n\n", fname,
	 total_bad_ratios, total_tests, max_ratio);

  min_ratio = 1e308;
  max_ratio = 0.0;
  total_bad_ratios = 0;
  total_tests = 0;
  fname = "BLAS_daxpby";
  printf("Testing %s...\n", fname);
  for (n = 0; n <= nsizes; n++) {
    total_max_ratio =
      do_test_daxpby(n, ntests, &seed, thresh, debug, &total_min_ratio,
		     &num_bad_ratio, &num_tests);
    if (total_max_ratio > max_ratio)
      max_ratio = total_max_ratio;

    if (total_min_ratio < min_ratio)
      min_ratio = total_min_ratio;

    total_bad_ratios += num_bad_ratio;
    total_tests += num_tests;
  }

  if (total_bad_ratios == 0)
    printf("PASS> ");
  else {
    printf("FAIL> ");
    nr_failed_routines++;
  }
  nr_routines++;

  printf("%-24s: bad/total = %d/%d, max_ratio = %.2e\n\n", fname,
	 total_bad_ratios, total_tests, max_ratio);

  min_ratio = 1e308;
  max_ratio = 0.0;
  total_bad_ratios = 0;
  total_tests = 0;
  fname = "BLAS_caxpby";
  printf("Testing %s...\n", fname);
  for (n = 0; n <= nsizes; n++) {
    total_max_ratio =
      do_test_caxpby(n, ntests, &seed, thresh, debug, &total_min_ratio,
		     &num_bad_ratio, &num_tests);
    if (total_max_ratio > max_ratio)
      max_ratio = total_max_ratio;

    if (total_min_ratio < min_ratio)
      min_ratio = total_min_ratio;

    total_bad_ratios += num_bad_ratio;
    total_tests += num_tests;
  }

  if (total_bad_ratios == 0)
    printf("PASS> ");
  else {
    printf("FAIL> ");
    nr_failed_routines++;
  }
  nr_routines++;

  printf("%-24s: bad/total = %d/%d, max_ratio = %.2e\n\n", fname,
	 total_bad_ratios, total_tests, max_ratio);

  min_ratio = 1e308;
  max_ratio = 0.0;
  total_bad_ratios = 0;
  total_tests = 0;
  fname = "BLAS_zaxpby";
  printf("Testing %s...\n", fname);
  for (n = 0; n <= nsizes; n++) {
    total_max_ratio =
      do_test_zaxpby(n, ntests, &seed, thresh, debug, &total_min_ratio,
		     &num_bad_ratio, &num_tests);
    if (total_max_ratio > max_ratio)
      max_ratio = total_max_ratio;

    if (total_min_ratio < min_ratio)
      min_ratio = total_min_ratio;

    total_bad_ratios += num_bad_ratio;
    total_tests += num_tests;
  }

  if (total_bad_ratios == 0)
    printf("PASS> ");
  else {
    printf("FAIL> ");
    nr_failed_routines++;
  }
  nr_routines++;

  printf("%-24s: bad/total = %d/%d, max_ratio = %.2e\n\n", fname,
	 total_bad_ratios, total_tests, max_ratio);

  min_ratio = 1e308;
  max_ratio = 0.0;
  total_bad_ratios = 0;
  total_tests = 0;
  fname = "BLAS_daxpby_s";
  printf("Testing %s...\n", fname);
  for (n = 0; n <= nsizes; n++) {
    total_max_ratio =
      do_test_daxpby_s(n, ntests, &seed, thresh, debug, &total_min_ratio,
		       &num_bad_ratio, &num_tests);
    if (total_max_ratio > max_ratio)
      max_ratio = total_max_ratio;

    if (total_min_ratio < min_ratio)
      min_ratio = total_min_ratio;

    total_bad_ratios += num_bad_ratio;
    total_tests += num_tests;
  }

  if (total_bad_ratios == 0)
    printf("PASS> ");
  else {
    printf("FAIL> ");
    nr_failed_routines++;
  }
  nr_routines++;

  printf("%-24s: bad/total = %d/%d, max_ratio = %.2e\n\n", fname,
	 total_bad_ratios, total_tests, max_ratio);

  min_ratio = 1e308;
  max_ratio = 0.0;
  total_bad_ratios = 0;
  total_tests = 0;
  fname = "BLAS_caxpby_s";
  printf("Testing %s...\n", fname);
  for (n = 0; n <= nsizes; n++) {
    total_max_ratio =
      do_test_caxpby_s(n, ntests, &seed, thresh, debug, &total_min_ratio,
		       &num_bad_ratio, &num_tests);
    if (total_max_ratio > max_ratio)
      max_ratio = total_max_ratio;

    if (total_min_ratio < min_ratio)
      min_ratio = total_min_ratio;

    total_bad_ratios += num_bad_ratio;
    total_tests += num_tests;
  }

  if (total_bad_ratios == 0)
    printf("PASS> ");
  else {
    printf("FAIL> ");
    nr_failed_routines++;
  }
  nr_routines++;

  printf("%-24s: bad/total = %d/%d, max_ratio = %.2e\n\n", fname,
	 total_bad_ratios, total_tests, max_ratio);

  min_ratio = 1e308;
  max_ratio = 0.0;
  total_bad_ratios = 0;
  total_tests = 0;
  fname = "BLAS_zaxpby_c";
  printf("Testing %s...\n", fname);
  for (n = 0; n <= nsizes; n++) {
    total_max_ratio =
      do_test_zaxpby_c(n, ntests, &seed, thresh, debug, &total_min_ratio,
		       &num_bad_ratio, &num_tests);
    if (total_max_ratio > max_ratio)
      max_ratio = total_max_ratio;

    if (total_min_ratio < min_ratio)
      min_ratio = total_min_ratio;

    total_bad_ratios += num_bad_ratio;
    total_tests += num_tests;
  }

  if (total_bad_ratios == 0)
    printf("PASS> ");
  else {
    printf("FAIL> ");
    nr_failed_routines++;
  }
  nr_routines++;

  printf("%-24s: bad/total = %d/%d, max_ratio = %.2e\n\n", fname,
	 total_bad_ratios, total_tests, max_ratio);

  min_ratio = 1e308;
  max_ratio = 0.0;
  total_bad_ratios = 0;
  total_tests = 0;
  fname = "BLAS_zaxpby_d";
  printf("Testing %s...\n", fname);
  for (n = 0; n <= nsizes; n++) {
    total_max_ratio =
      do_test_zaxpby_d(n, ntests, &seed, thresh, debug, &total_min_ratio,
		       &num_bad_ratio, &num_tests);
    if (total_max_ratio > max_ratio)
      max_ratio = total_max_ratio;

    if (total_min_ratio < min_ratio)
      min_ratio = total_min_ratio;

    total_bad_ratios += num_bad_ratio;
    total_tests += num_tests;
  }

  if (total_bad_ratios == 0)
    printf("PASS> ");
  else {
    printf("FAIL> ");
    nr_failed_routines++;
  }
  nr_routines++;

  printf("%-24s: bad/total = %d/%d, max_ratio = %.2e\n\n", fname,
	 total_bad_ratios, total_tests, max_ratio);

  min_ratio = 1e308;
  max_ratio = 0.0;
  total_bad_ratios = 0;
  total_tests = 0;
  fname = "BLAS_saxpby_x";
  printf("Testing %s...\n", fname);
  for (n = 0; n <= nsizes; n++) {
    total_max_ratio =
      do_test_saxpby_x(n, ntests, &seed, thresh, debug, &total_min_ratio,
		       &num_bad_ratio, &num_tests);
    if (total_max_ratio > max_ratio)
      max_ratio = total_max_ratio;

    if (total_min_ratio < min_ratio)
      min_ratio = total_min_ratio;

    total_bad_ratios += num_bad_ratio;
    total_tests += num_tests;
  }

  if (total_bad_ratios == 0)
    printf("PASS> ");
  else {
    printf("FAIL> ");
    nr_failed_routines++;
  }
  nr_routines++;

  printf("%-24s: bad/total = %d/%d, max_ratio = %.2e\n\n", fname,
	 total_bad_ratios, total_tests, max_ratio);

  min_ratio = 1e308;
  max_ratio = 0.0;
  total_bad_ratios = 0;
  total_tests = 0;
  fname = "BLAS_daxpby_x";
  printf("Testing %s...\n", fname);
  for (n = 0; n <= nsizes; n++) {
    total_max_ratio =
      do_test_daxpby_x(n, ntests, &seed, thresh, debug, &total_min_ratio,
		       &num_bad_ratio, &num_tests);
    if (total_max_ratio > max_ratio)
      max_ratio = total_max_ratio;

    if (total_min_ratio < min_ratio)
      min_ratio = total_min_ratio;

    total_bad_ratios += num_bad_ratio;
    total_tests += num_tests;
  }

  if (total_bad_ratios == 0)
    printf("PASS> ");
  else {
    printf("FAIL> ");
    nr_failed_routines++;
  }
  nr_routines++;

  printf("%-24s: bad/total = %d/%d, max_ratio = %.2e\n\n", fname,
	 total_bad_ratios, total_tests, max_ratio);

  min_ratio = 1e308;
  max_ratio = 0.0;
  total_bad_ratios = 0;
  total_tests = 0;
  fname = "BLAS_caxpby_x";
  printf("Testing %s...\n", fname);
  for (n = 0; n <= nsizes; n++) {
    total_max_ratio =
      do_test_caxpby_x(n, ntests, &seed, thresh, debug, &total_min_ratio,
		       &num_bad_ratio, &num_tests);
    if (total_max_ratio > max_ratio)
      max_ratio = total_max_ratio;

    if (total_min_ratio < min_ratio)
      min_ratio = total_min_ratio;

    total_bad_ratios += num_bad_ratio;
    total_tests += num_tests;
  }

  if (total_bad_ratios == 0)
    printf("PASS> ");
  else {
    printf("FAIL> ");
    nr_failed_routines++;
  }
  nr_routines++;

  printf("%-24s: bad/total = %d/%d, max_ratio = %.2e\n\n", fname,
	 total_bad_ratios, total_tests, max_ratio);

  min_ratio = 1e308;
  max_ratio = 0.0;
  total_bad_ratios = 0;
  total_tests = 0;
  fname = "BLAS_zaxpby_x";
  printf("Testing %s...\n", fname);
  for (n = 0; n <= nsizes; n++) {
    total_max_ratio =
      do_test_zaxpby_x(n, ntests, &seed, thresh, debug, &total_min_ratio,
		       &num_bad_ratio, &num_tests);
    if (total_max_ratio > max_ratio)
      max_ratio = total_max_ratio;

    if (total_min_ratio < min_ratio)
      min_ratio = total_min_ratio;

    total_bad_ratios += num_bad_ratio;
    total_tests += num_tests;
  }

  if (total_bad_ratios == 0)
    printf("PASS> ");
  else {
    printf("FAIL> ");
    nr_failed_routines++;
  }
  nr_routines++;

  printf("%-24s: bad/total = %d/%d, max_ratio = %.2e\n\n", fname,
	 total_bad_ratios, total_tests, max_ratio);

  min_ratio = 1e308;
  max_ratio = 0.0;
  total_bad_ratios = 0;
  total_tests = 0;
  fname = "BLAS_daxpby_s_x";
  printf("Testing %s...\n", fname);
  for (n = 0; n <= nsizes; n++) {
    total_max_ratio =
      do_test_daxpby_s_x(n, ntests, &seed, thresh, debug, &total_min_ratio,
			 &num_bad_ratio, &num_tests);
    if (total_max_ratio > max_ratio)
      max_ratio = total_max_ratio;

    if (total_min_ratio < min_ratio)
      min_ratio = total_min_ratio;

    total_bad_ratios += num_bad_ratio;
    total_tests += num_tests;
  }

  if (total_bad_ratios == 0)
    printf("PASS> ");
  else {
    printf("FAIL> ");
    nr_failed_routines++;
  }
  nr_routines++;

  printf("%-24s: bad/total = %d/%d, max_ratio = %.2e\n\n", fname,
	 total_bad_ratios, total_tests, max_ratio);

  min_ratio = 1e308;
  max_ratio = 0.0;
  total_bad_ratios = 0;
  total_tests = 0;
  fname = "BLAS_zaxpby_c_x";
  printf("Testing %s...\n", fname);
  for (n = 0; n <= nsizes; n++) {
    total_max_ratio =
      do_test_zaxpby_c_x(n, ntests, &seed, thresh, debug, &total_min_ratio,
			 &num_bad_ratio, &num_tests);
    if (total_max_ratio > max_ratio)
      max_ratio = total_max_ratio;

    if (total_min_ratio < min_ratio)
      min_ratio = total_min_ratio;

    total_bad_ratios += num_bad_ratio;
    total_tests += num_tests;
  }

  if (total_bad_ratios == 0)
    printf("PASS> ");
  else {
    printf("FAIL> ");
    nr_failed_routines++;
  }
  nr_routines++;

  printf("%-24s: bad/total = %d/%d, max_ratio = %.2e\n\n", fname,
	 total_bad_ratios, total_tests, max_ratio);

  min_ratio = 1e308;
  max_ratio = 0.0;
  total_bad_ratios = 0;
  total_tests = 0;
  fname = "BLAS_caxpby_s_x";
  printf("Testing %s...\n", fname);
  for (n = 0; n <= nsizes; n++) {
    total_max_ratio =
      do_test_caxpby_s_x(n, ntests, &seed, thresh, debug, &total_min_ratio,
			 &num_bad_ratio, &num_tests);
    if (total_max_ratio > max_ratio)
      max_ratio = total_max_ratio;

    if (total_min_ratio < min_ratio)
      min_ratio = total_min_ratio;

    total_bad_ratios += num_bad_ratio;
    total_tests += num_tests;
  }

  if (total_bad_ratios == 0)
    printf("PASS> ");
  else {
    printf("FAIL> ");
    nr_failed_routines++;
  }
  nr_routines++;

  printf("%-24s: bad/total = %d/%d, max_ratio = %.2e\n\n", fname,
	 total_bad_ratios, total_tests, max_ratio);

  min_ratio = 1e308;
  max_ratio = 0.0;
  total_bad_ratios = 0;
  total_tests = 0;
  fname = "BLAS_zaxpby_d_x";
  printf("Testing %s...\n", fname);
  for (n = 0; n <= nsizes; n++) {
    total_max_ratio =
      do_test_zaxpby_d_x(n, ntests, &seed, thresh, debug, &total_min_ratio,
			 &num_bad_ratio, &num_tests);
    if (total_max_ratio > max_ratio)
      max_ratio = total_max_ratio;

    if (total_min_ratio < min_ratio)
      min_ratio = total_min_ratio;

    total_bad_ratios += num_bad_ratio;
    total_tests += num_tests;
  }

  if (total_bad_ratios == 0)
    printf("PASS> ");
  else {
    printf("FAIL> ");
    nr_failed_routines++;
  }
  nr_routines++;

  printf("%-24s: bad/total = %d/%d, max_ratio = %.2e\n\n", fname,
	 total_bad_ratios, total_tests, max_ratio);



  printf("\n");
  if (nr_failed_routines)
    printf("FAILED ");
  else
    printf("PASSED ");
  printf("%-10s: FAIL/TOTAL = %d/%d\n",
	 base_routine, nr_failed_routines, nr_routines);

  return 0;
}

