
#line 1 "/opt/local/var/macports/build/rb31-numo-linalg-003c080d/work/destroot/opt/local/lib/ruby3.1/gems/3.1.0/gems/numo-linalg-0.1.7/ext/numo/linalg/blas/gen/../tmpl/lib.c"
/*
  BLAS wrapper for Ruby/Numo
    (C) Copyright 2017 by Masahiro TANAKA

  This program is free software.
  NO WARRANTY.
*/

#include <assert.h>
#include <ruby.h>
#include "numo/narray.h"
#include "numo/template.h"
#include "numo_blas.h"

static ID id_alpha;
static ID id_axis;
static ID id_beta;
static ID id_diag;
static ID id_imag;
static ID id_keepdims;
static ID id_order;
static ID id_real;
static ID id_sb;
static ID id_side;
static ID id_trans;
static ID id_transa;
static ID id_transb;
static ID id_uplo;



#line 1 "/opt/local/var/macports/build/rb31-numo-linalg-003c080d/work/destroot/opt/local/lib/ruby3.1/gems/3.1.0/gems/numo-linalg-0.1.7/ext/numo/linalg/blas/gen/../tmpl/module.c"
/*
  module definition: Numo::Linalg
*/

#line 6 "/opt/local/var/macports/build/rb31-numo-linalg-003c080d/work/destroot/opt/local/lib/ruby3.1/gems/3.1.0/gems/numo-linalg-0.1.7/ext/numo/linalg/blas/gen/../tmpl/module.c"
static VALUE mLinalg;




#line 1 "/opt/local/var/macports/build/rb31-numo-linalg-003c080d/work/destroot/opt/local/lib/ruby3.1/gems/3.1.0/gems/numo-linalg-0.1.7/ext/numo/linalg/blas/gen/../tmpl/module.c"
/*
  module definition: Numo::Linalg::Blas
*/

#line 6 "/opt/local/var/macports/build/rb31-numo-linalg-003c080d/work/destroot/opt/local/lib/ruby3.1/gems/3.1.0/gems/numo-linalg-0.1.7/ext/numo/linalg/blas/gen/../tmpl/module.c"
static VALUE mBlas;


#line 1 "/opt/local/var/macports/build/rb31-numo-linalg-003c080d/work/destroot/opt/local/lib/ruby3.1/gems/3.1.0/gems/numo-linalg-0.1.7/ext/numo/linalg/blas/gen/../tmpl/def_c.c"
#include "numo/types/scomplex.h"

#define DP(a) (&(a))


#line 1 "/opt/local/var/macports/build/rb31-numo-linalg-003c080d/work/destroot/opt/local/lib/ruby3.1/gems/3.1.0/gems/numo-linalg-0.1.7/ext/numo/linalg/blas/gen/../tmpl/dot.c"
#define func_p cdotc_sub_p

static cdotc_sub_t func_p = 0;

#undef result_dtype
#define result_dtype scomplex

static void
iter_blas_s_cdotc(na_loop_t *const lp)
{
    char *p1, *p2, *p3;
    size_t n;
    ssize_t s1, s2;

    INIT_PTR(lp,0,p1,s1);
    INIT_PTR(lp,1,p2,s2);
    p3 = NDL_PTR(lp,2);
    n  = NDL_SHAPE(lp,0)[0];

  
    (*func_p)(n, (dtype*)p1, s1/sizeof(dtype),
                 (dtype*)p2, s2/sizeof(dtype), (result_dtype*)p3);
  
#line 27 "/opt/local/var/macports/build/rb31-numo-linalg-003c080d/work/destroot/opt/local/lib/ruby3.1/gems/3.1.0/gems/numo-linalg-0.1.7/ext/numo/linalg/blas/gen/../tmpl/dot.c"
}

/*
  @overload cdotc( x, y )
  @param x [Numo::SComplex]  vector (>=1-dimentional NArray).
  @param y [Numo::SComplex]  vector (>=1-dimentional NArray).
  @return [Numo::SComplex] op(x) dot y

CDOTC forms the dot product of two complex vectors

        CDOTC = X^H * Y

*/
static VALUE
blas_s_cdotc(VALUE mod, VALUE x, VALUE y)
{
    VALUE     ans;
    narray_t *na1, *na2;
    size_t    nx, ny, shape[1]={1};
    ndfunc_arg_in_t ain[2] = {{cT,1},{cT,1}};
    ndfunc_arg_out_t aout[1] = {{numo_cSComplex,0,shape}};
    ndfunc_t ndf = {iter_blas_s_cdotc, NDF_EXTRACT, 2,1, ain,aout};

    CHECK_FUNC(func_p,"cdotc_sub");

    GetNArray(x,na1);
    GetNArray(y,na2);
    CHECK_DIM_GE(na1,1);
    CHECK_DIM_GE(na2,1);
    CHECK_NON_EMPTY(na1);
    CHECK_NON_EMPTY(na2);
    nx = COL_SIZE(na1);
    ny = COL_SIZE(na2);
    CHECK_SIZE_EQ(nx,ny);

    ans = na_ndloop(&ndf, 2, x, y);

    return ans;
}
#undef func_p


#line 1 "/opt/local/var/macports/build/rb31-numo-linalg-003c080d/work/destroot/opt/local/lib/ruby3.1/gems/3.1.0/gems/numo-linalg-0.1.7/ext/numo/linalg/blas/gen/../tmpl/dot.c"
#define func_p cdotu_sub_p

static cdotu_sub_t func_p = 0;

#undef result_dtype
#define result_dtype scomplex

static void
iter_blas_s_cdotu(na_loop_t *const lp)
{
    char *p1, *p2, *p3;
    size_t n;
    ssize_t s1, s2;

    INIT_PTR(lp,0,p1,s1);
    INIT_PTR(lp,1,p2,s2);
    p3 = NDL_PTR(lp,2);
    n  = NDL_SHAPE(lp,0)[0];

  
    (*func_p)(n, (dtype*)p1, s1/sizeof(dtype),
                 (dtype*)p2, s2/sizeof(dtype), (result_dtype*)p3);
  
#line 27 "/opt/local/var/macports/build/rb31-numo-linalg-003c080d/work/destroot/opt/local/lib/ruby3.1/gems/3.1.0/gems/numo-linalg-0.1.7/ext/numo/linalg/blas/gen/../tmpl/dot.c"
}

/*
  @overload cdotu( x, y )
  @param x [Numo::SComplex]  vector (>=1-dimentional NArray).
  @param y [Numo::SComplex]  vector (>=1-dimentional NArray).
  @return [Numo::SComplex] op(x) dot y

CDOTU forms the dot product of two complex vectors

        CDOTU = X^T * Y

*/
static VALUE
blas_s_cdotu(VALUE mod, VALUE x, VALUE y)
{
    VALUE     ans;
    narray_t *na1, *na2;
    size_t    nx, ny, shape[1]={1};
    ndfunc_arg_in_t ain[2] = {{cT,1},{cT,1}};
    ndfunc_arg_out_t aout[1] = {{numo_cSComplex,0,shape}};
    ndfunc_t ndf = {iter_blas_s_cdotu, NDF_EXTRACT, 2,1, ain,aout};

    CHECK_FUNC(func_p,"cdotu_sub");

    GetNArray(x,na1);
    GetNArray(y,na2);
    CHECK_DIM_GE(na1,1);
    CHECK_DIM_GE(na2,1);
    CHECK_NON_EMPTY(na1);
    CHECK_NON_EMPTY(na2);
    nx = COL_SIZE(na1);
    ny = COL_SIZE(na2);
    CHECK_SIZE_EQ(nx,ny);

    ans = na_ndloop(&ndf, 2, x, y);

    return ans;
}
#undef func_p


#line 1 "/opt/local/var/macports/build/rb31-numo-linalg-003c080d/work/destroot/opt/local/lib/ruby3.1/gems/3.1.0/gems/numo-linalg-0.1.7/ext/numo/linalg/blas/gen/../tmpl/nrm2.c"
#define func_p scnrm2_p

static scnrm2_t func_p = 0;

#undef result_dtype
#define result_dtype float

static void
iter_blas_s_scnrm2(na_loop_t *const lp)
{
    char *p1, *p2;
    size_t n;
    ssize_t s1;

    INIT_PTR(lp,0,p1,s1);
    p2 = NDL_PTR(lp,1);
    n  = NDL_SHAPE(lp,0)[0];

    *(result_dtype*)p2 = (*func_p)(n, (dtype*)p1, s1/sizeof(dtype));
}

/*

  @overload scnrm2( x )
  @param x [Numo::SComplex]  vector (>=1-dimentional NArray).
  @param keepdims [String or Symbol]  
  @return [Numo::SFloat] euclidean norm of x

SCNRM2 returns the euclidean norm of a vector via the function
name, so that

        SCNRM2 := sqrt( x**H*x )

*/
static VALUE
blas_s_scnrm2(int argc, VALUE const argv[], VALUE UNUSED(mod))
{
    VALUE     x, keepdims, ans;
    narray_t *na1;
    ndfunc_arg_in_t ain[1] = {{cT,1}};
    ndfunc_arg_out_t aout[1] = {{cRT,0}};
    ndfunc_t ndf = {iter_blas_s_scnrm2, NDF_EXTRACT, 1,1, ain,aout};

    VALUE opts[1] = {Qundef};
    ID    kw_table[1] = {id_keepdims};
    VALUE kw_hash = Qnil;

    CHECK_FUNC(func_p,"scnrm2");

    rb_scan_args(argc, argv, "1:", &x, &kw_hash);
    rb_get_kwargs(kw_hash, kw_table, 0, 1, opts);
    keepdims = option_value(opts[0],Qfalse);

    if (RTEST(keepdims)) {
        ndf.flag |= NDF_KEEP_DIM;
    }

    GetNArray(x,na1);
    CHECK_DIM_GE(na1,1);
    CHECK_NON_EMPTY(na1);

    ans = na_ndloop(&ndf, 1, x);

    return ans;
}

#undef func_p


#line 1 "/opt/local/var/macports/build/rb31-numo-linalg-003c080d/work/destroot/opt/local/lib/ruby3.1/gems/3.1.0/gems/numo-linalg-0.1.7/ext/numo/linalg/blas/gen/../tmpl/nrm2.c"
#define func_p scasum_p

static scasum_t func_p = 0;

#undef result_dtype
#define result_dtype float

static void
iter_blas_s_scasum(na_loop_t *const lp)
{
    char *p1, *p2;
    size_t n;
    ssize_t s1;

    INIT_PTR(lp,0,p1,s1);
    p2 = NDL_PTR(lp,1);
    n  = NDL_SHAPE(lp,0)[0];

    *(result_dtype*)p2 = (*func_p)(n, (dtype*)p1, s1/sizeof(dtype));
}

/*

  @overload scasum( x )
  @param x [Numo::SComplex]  vector (>=1-dimentional NArray).
  @param keepdims [String or Symbol]  
  @return [Numo::SFloat] euclidean norm of x

SCASUM takes the sum of the (|Re(.)| + |Im(.)|)'s of a complex vector and
returns a single precision result.

*/
static VALUE
blas_s_scasum(int argc, VALUE const argv[], VALUE UNUSED(mod))
{
    VALUE     x, keepdims, ans;
    narray_t *na1;
    ndfunc_arg_in_t ain[1] = {{cT,1}};
    ndfunc_arg_out_t aout[1] = {{cRT,0}};
    ndfunc_t ndf = {iter_blas_s_scasum, NDF_EXTRACT, 1,1, ain,aout};

    VALUE opts[1] = {Qundef};
    ID    kw_table[1] = {id_keepdims};
    VALUE kw_hash = Qnil;

    CHECK_FUNC(func_p,"scasum");

    rb_scan_args(argc, argv, "1:", &x, &kw_hash);
    rb_get_kwargs(kw_hash, kw_table, 0, 1, opts);
    keepdims = option_value(opts[0],Qfalse);

    if (RTEST(keepdims)) {
        ndf.flag |= NDF_KEEP_DIM;
    }

    GetNArray(x,na1);
    CHECK_DIM_GE(na1,1);
    CHECK_NON_EMPTY(na1);

    ans = na_ndloop(&ndf, 1, x);

    return ans;
}

#undef func_p


#line 1 "/opt/local/var/macports/build/rb31-numo-linalg-003c080d/work/destroot/opt/local/lib/ruby3.1/gems/3.1.0/gems/numo-linalg-0.1.7/ext/numo/linalg/blas/gen/../tmpl/swap.c"
#define func_p cswap_p

static cswap_t func_p = 0;

static void
iter_blas_s_cswap(na_loop_t *const lp)
{
    char *p1, *p2;
    size_t n;
    ssize_t s1, s2;

    INIT_COUNTER(lp,n);
    INIT_PTR(lp,0,p1,s1);
    INIT_PTR(lp,1,p2,s2);

    (*func_p)(n, (dtype*)p1, s1/sizeof(dtype),
                 (dtype*)p2, s2/sizeof(dtype));
}

/*
  @overload cswap( x, y )
  @param x [Numo::SComplex]  vector (>=1-dimentional NArray).
  @param y [Numo::SComplex]  vector (>=1-dimentional NArray).
  @return [nil]

CSWAP interchanges two vectors.

*/
static VALUE
blas_s_cswap(VALUE UNUSED(mod), VALUE x, VALUE y)
{
    narray_t *na1, *na2;
    ndfunc_arg_in_t ain[2] = {{OVERWRITE,0},{OVERWRITE,0}};
    ndfunc_t ndf = {iter_blas_s_cswap, STRIDE_LOOP, 2,0, ain,0};

    CHECK_FUNC(func_p,"cswap");

    CHECK_NARRAY_TYPE(x,cT);
    CHECK_NARRAY_TYPE(y,cT);
    GetNArray(x,na1);
    GetNArray(y,na2);
    CHECK_DIM_GE(na1,1);
    CHECK_DIM_GE(na2,1);
    CHECK_NON_EMPTY(na1);
    CHECK_NON_EMPTY(na2);
    CHECK_SAME_SHAPE(na1,na2);

    na_ndloop(&ndf, 2, x, y);

    return Qnil;
}

#undef func_p


#line 1 "/opt/local/var/macports/build/rb31-numo-linalg-003c080d/work/destroot/opt/local/lib/ruby3.1/gems/3.1.0/gems/numo-linalg-0.1.7/ext/numo/linalg/blas/gen/../tmpl/copy.c"
#define func_p ccopy_p

static ccopy_t func_p = 0;

static void
iter_blas_s_ccopy(na_loop_t *const lp)
{
    char *p1, *p2;
    size_t n;
    ssize_t s1, s2;

    INIT_COUNTER(lp,n);
    INIT_PTR(lp,0,p1,s1);
    INIT_PTR(lp,1,p2,s2);

    (*func_p)(n, (dtype*)p1, s1/sizeof(dtype),
                 (dtype*)p2, s2/sizeof(dtype));
}

/*
  @overload ccopy( x, y )
  @param x [Numo::SComplex]  vector (>=1-dimentional NArray).
  @param y [Numo::SComplex]  vector (>=1-dimentional NArray).
  @return [nil]

CCOPY copies a vector x to a vector y.

*/
static VALUE
blas_s_ccopy(VALUE UNUSED(mod), VALUE x, VALUE y)
{
    narray_t *na1, *na2;
    ndfunc_arg_in_t ain[2] = {{cT,0},{OVERWRITE,0}};
    ndfunc_t ndf = {iter_blas_s_ccopy, STRIDE_LOOP, 2,0, ain,0};

    CHECK_FUNC(func_p,"ccopy");

    CHECK_NARRAY_TYPE(x,cT);
    CHECK_NARRAY_TYPE(y,cT);
    GetNArray(x,na1);
    GetNArray(y,na2);
    CHECK_DIM_GE(na1,1);
    CHECK_DIM_GE(na2,1);
    CHECK_NON_EMPTY(na1);
    CHECK_NON_EMPTY(na2);
    CHECK_SAME_SHAPE(na1,na2);

    na_ndloop(&ndf, 2, x, y);

    return Qnil;
}

#undef func_p


#line 1 "/opt/local/var/macports/build/rb31-numo-linalg-003c080d/work/destroot/opt/local/lib/ruby3.1/gems/3.1.0/gems/numo-linalg-0.1.7/ext/numo/linalg/blas/gen/../tmpl/axpy.c"
#define args_t caxpy_args_t

typedef struct {
    dtype alpha;
} args_t;

#define func_p caxpy_p
static caxpy_t func_p = 0;

static void
iter_blas_s_caxpy(na_loop_t *const lp)
{
    char   *p1, *p2;
    size_t  n;
    ssize_t s1, s2;
    dtype  *g;

    INIT_COUNTER(lp,n);
    INIT_PTR(lp,0,p1,s1);
    INIT_PTR(lp,1,p2,s2);
    g = (dtype*)(lp->opt_ptr);

    (*func_p)(n, DP(*g), (dtype*)p1, s1/sizeof(dtype),
                         (dtype*)p2, s2/sizeof(dtype));
}

/*
  @overload caxpy( x, y, [alpha:1] )
  @param x [Numo::SComplex]  vector (>=1-dimentional NArray).
  @param y [Numo::SComplex]  vector (>=1-dimentional NArray, inplace allowed).
  @param alpha [Float]  (default=1.0)
  @return [Numo::SComplex] y = alpha * x + y

CAXPY constant times a vector plus a vector.

*/
static VALUE
blas_s_caxpy(int argc, VALUE const argv[], VALUE UNUSED(mod))
{
    VALUE x, y, alpha;
    narray_t *na1, *na2;
    ndfunc_arg_in_t ain[2] = {{cT,0},{OVERWRITE,0}};
    ndfunc_t ndf = {iter_blas_s_caxpy, STRIDE_LOOP, 2, 0, ain, 0};

    dtype g;
    VALUE kw_hash = Qnil;
    ID kw_table[1] = {id_alpha};
    VALUE opts[1] = {Qundef};

    CHECK_FUNC(func_p,"caxpy");

    rb_scan_args(argc, argv, "2:", &x, &y, &kw_hash);
    rb_get_kwargs(kw_hash, kw_table, 0, 1, opts);
    alpha = option_value(opts[0],Qnil);
    g     = RTEST(alpha) ? m_num_to_data(alpha) : m_one;

    COPY_OR_CAST_TO(y,cT);
    GetNArray(x,na1);
    GetNArray(y,na2);
    CHECK_DIM_GE(na1,1);
    CHECK_DIM_GE(na2,1);
    CHECK_NON_EMPTY(na1);
    CHECK_NON_EMPTY(na2);
    CHECK_SAME_SHAPE(na1,na2);

    na_ndloop3(&ndf, &g, 2, x, y);
    return y;
}

#undef func_p
#undef args_t


#line 1 "/opt/local/var/macports/build/rb31-numo-linalg-003c080d/work/destroot/opt/local/lib/ruby3.1/gems/3.1.0/gems/numo-linalg-0.1.7/ext/numo/linalg/blas/gen/../tmpl/scal.c"
#define func_p cscal_p

static cscal_t func_p = 0;

#line 8 "/opt/local/var/macports/build/rb31-numo-linalg-003c080d/work/destroot/opt/local/lib/ruby3.1/gems/3.1.0/gems/numo-linalg-0.1.7/ext/numo/linalg/blas/gen/../tmpl/scal.c"
#define scal_t dtype

#line 11 "/opt/local/var/macports/build/rb31-numo-linalg-003c080d/work/destroot/opt/local/lib/ruby3.1/gems/3.1.0/gems/numo-linalg-0.1.7/ext/numo/linalg/blas/gen/../tmpl/scal.c"
static void
iter_blas_s_cscal(na_loop_t *const lp)
{
    char *p1;
    size_t n;
    ssize_t s1;
    scal_t *g;

    INIT_COUNTER(lp,n);
    INIT_PTR(lp,0,p1,s1);
    g = (scal_t*)(lp->opt_ptr);

  
    (*func_p)(n, g, (dtype*)p1, s1/sizeof(dtype));
  
#line 28 "/opt/local/var/macports/build/rb31-numo-linalg-003c080d/work/destroot/opt/local/lib/ruby3.1/gems/3.1.0/gems/numo-linalg-0.1.7/ext/numo/linalg/blas/gen/../tmpl/scal.c"
}

/*
  @overload cscal( a, x )
  @param [Float]        a  scale factor
  @param x [Numo::SComplex]  vector (>=1-dimentional NArray).
  @return [Numo::SComplex] returns a*x.

CSCAL scales a vector by a constant.

 */
static VALUE
blas_s_cscal(VALUE mod, VALUE a, VALUE x)
{
    scal_t g[1];
    narray_t *na1;
    ndfunc_arg_in_t ain[1] = {{OVERWRITE,0}};
    ndfunc_t ndf = {iter_blas_s_cscal, STRIDE_LOOP, 1,0, ain,0};

    CHECK_FUNC(func_p,"cscal");

  
#line 56 "/opt/local/var/macports/build/rb31-numo-linalg-003c080d/work/destroot/opt/local/lib/ruby3.1/gems/3.1.0/gems/numo-linalg-0.1.7/ext/numo/linalg/blas/gen/../tmpl/scal.c"
    if (RTEST(a)) {g[0] = m_num_to_data(a);} else {g[0]=m_one;}
  
    COPY_OR_CAST_TO(x,cT);
    GetNArray(x,na1);
    CHECK_DIM_GE(na1,1);
    CHECK_NON_EMPTY(na1);

    na_ndloop3(&ndf, g, 1, x);

    return x;
}

#undef func_p
#undef scal_t


#line 1 "/opt/local/var/macports/build/rb31-numo-linalg-003c080d/work/destroot/opt/local/lib/ruby3.1/gems/3.1.0/gems/numo-linalg-0.1.7/ext/numo/linalg/blas/gen/../tmpl/scal.c"
#define func_p csscal_p

static csscal_t func_p = 0;

#line 6 "/opt/local/var/macports/build/rb31-numo-linalg-003c080d/work/destroot/opt/local/lib/ruby3.1/gems/3.1.0/gems/numo-linalg-0.1.7/ext/numo/linalg/blas/gen/../tmpl/scal.c"
#define scal_t rtype

#line 11 "/opt/local/var/macports/build/rb31-numo-linalg-003c080d/work/destroot/opt/local/lib/ruby3.1/gems/3.1.0/gems/numo-linalg-0.1.7/ext/numo/linalg/blas/gen/../tmpl/scal.c"
static void
iter_blas_s_csscal(na_loop_t *const lp)
{
    char *p1;
    size_t n;
    ssize_t s1;
    scal_t *g;

    INIT_COUNTER(lp,n);
    INIT_PTR(lp,0,p1,s1);
    g = (scal_t*)(lp->opt_ptr);

  
#line 26 "/opt/local/var/macports/build/rb31-numo-linalg-003c080d/work/destroot/opt/local/lib/ruby3.1/gems/3.1.0/gems/numo-linalg-0.1.7/ext/numo/linalg/blas/gen/../tmpl/scal.c"
    (*func_p)(n, *g, (dtype*)p1, s1/sizeof(dtype));
  
}

/*
  @overload csscal( a, x )
  @param [Float]        a  scale factor
  @param x [Numo::SComplex]  vector (>=1-dimentional NArray).
  @return [Numo::SComplex] returns a*x.

CSSCAL scales a complex vector by a real constant.

 */
static VALUE
blas_s_csscal(VALUE mod, VALUE a, VALUE x)
{
    scal_t g[1];
    narray_t *na1;
    ndfunc_arg_in_t ain[1] = {{OVERWRITE,0}};
    ndfunc_t ndf = {iter_blas_s_csscal, STRIDE_LOOP, 1,0, ain,0};

    CHECK_FUNC(func_p,"csscal");

  
    if (RTEST(a)) {g[0] = NUM2DBL(a);} else {g[0]=1;}
  
#line 58 "/opt/local/var/macports/build/rb31-numo-linalg-003c080d/work/destroot/opt/local/lib/ruby3.1/gems/3.1.0/gems/numo-linalg-0.1.7/ext/numo/linalg/blas/gen/../tmpl/scal.c"
    COPY_OR_CAST_TO(x,cT);
    GetNArray(x,na1);
    CHECK_DIM_GE(na1,1);
    CHECK_NON_EMPTY(na1);

    na_ndloop3(&ndf, g, 1, x);

    return x;
}

#undef func_p
#undef scal_t


#line 1 "/opt/local/var/macports/build/rb31-numo-linalg-003c080d/work/destroot/opt/local/lib/ruby3.1/gems/3.1.0/gems/numo-linalg-0.1.7/ext/numo/linalg/blas/gen/../tmpl/mv.c"
/**/
#line 6 "/opt/local/var/macports/build/rb31-numo-linalg-003c080d/work/destroot/opt/local/lib/ruby3.1/gems/3.1.0/gems/numo-linalg-0.1.7/ext/numo/linalg/blas/gen/../tmpl/mv.c"
#define GE 1
#define TR 0
#define args_t cgemv_args_t

typedef struct {
  enum CBLAS_ORDER order;
  enum CBLAS_TRANSPOSE trans;
  enum CBLAS_UPLO uplo;
  enum CBLAS_DIAG diag;
  dtype alpha, beta;
  blasint m, n;
} args_t;

#define func_p cgemv_p

static cgemv_t func_p = 0;

static void
iter_blas_s_cgemv(na_loop_t *const lp)
{
    dtype *a;
    char *p1;
    ssize_t s1;
#if !TR
    char *p2;
    ssize_t s2;
#endif
#if !GE
    int n;
#endif
    int lda;
    args_t *g;

    a = (dtype*)NDL_PTR(lp,0);
    INIT_PTR(lp,1,p1,s1);
#if !TR
    INIT_PTR(lp,2,p2,s2);
#endif
    g = (args_t*)(lp->opt_ptr);

#if !GE
    n = NDL_SHAPE(lp,0)[1];
#endif
    lda = NDL_STEP(lp,0) / sizeof(dtype);

#if GE
    (*func_p)( g->order, g->trans, g->m, g->n,
        DP(g->alpha), a, lda, (dtype*)p1, s1/sizeof(dtype),
        DP(g->beta), (dtype*)p2, s2/sizeof(dtype) );
#elif TR
    (*func_p)( g->order, g->uplo, g->trans, g->diag, n, a, lda,
        (dtype*)p1, s1/sizeof(dtype) );
#else // SY,HE
    (*func_p)( g->order, g->uplo, n,
        DP(g->alpha), a, lda, (dtype*)p1, s1/sizeof(dtype),
        DP(g->beta), (dtype*)p2, s2/sizeof(dtype) );
#endif
}

/*
  @overload cgemv(a, x, [y, alpha:1, beta:0, trans:'N', order:'R'])
  @param a [Numo::SComplex]  matrix (>=2-dimentional NArray).
  @param x [Numo::SComplex]  vector (>=1-dimentional NArray).
  @param y [Numo::SComplex]  vector (>=1-dimentional NArray, optional, inplace allowed).
  @param alpha [Float]  (default=1.0)
  @param beta [Float]  (default=0.0)
  @param trans [String or Symbol]  if 'N': Not transpose , if 'T': Transpose . (default='N')
  @param order [String or Symbol]  if 'R': Row-major, if 'C': Column-major. (default='R')
  @return [Numo::SComplex] returns y = alpha*op(A)\*x + beta\*y.

CGEMV performs one of the matrix-vector operations

        y := alpha*A*x + beta*y,   or   y := alpha*A**T*x + beta*y,   or
        y := alpha*A**H*x + beta*y,

where alpha and beta are scalars, x and y are vectors and A is an
m by n matrix.

*/
static VALUE
blas_s_cgemv(int argc, VALUE const argv[], VALUE UNUSED(mod))
{
    VALUE     a, x, y=Qnil, alpha, beta;
    narray_t *na1, *na2;
    blasint   ma, na, nx;
#if GE
    blasint   tmp;
#endif
    size_t    shape[1];
    ndfunc_arg_in_t ain[4] = {{cT,2},{cT,1},{OVERWRITE,1},{sym_init,0}};
    ndfunc_arg_out_t aout[1] = {{cT,1,shape}};
    ndfunc_t ndf = {iter_blas_s_cgemv, NO_LOOP, 3, 0, ain, aout};

    args_t g;
    VALUE kw_hash = Qnil;
#if GE
    ID kw_table[4] = {id_alpha,id_beta,id_order,id_trans};
#elif TR
    ID kw_table[6] = {id_alpha,id_beta,id_order,id_uplo,id_trans,id_diag};
#else
    ID kw_table[4] = {id_alpha,id_beta,id_order,id_uplo};
#endif
    VALUE opts[6] = {Qundef,Qundef,Qundef,Qundef,Qundef,Qundef};

    CHECK_FUNC(func_p,"cgemv");

    rb_scan_args(argc, argv, "21:", &a, &x, &y, &kw_hash);
    rb_get_kwargs(kw_hash, kw_table, 0, 4+2*TR, opts);
    alpha   = option_value(opts[0],Qnil);
    g.alpha = RTEST(alpha) ? m_num_to_data(alpha) : m_one;
    beta    = option_value(opts[1],Qnil);
    g.beta  = RTEST(beta)  ? m_num_to_data(beta)  : m_zero;
    g.order = option_order(opts[2]);
#if GE
    g.trans = option_trans(opts[3]);
#else
    g.uplo  = option_uplo(opts[3]);
#endif
#if TR
    g.trans = option_trans(opts[4]);
    g.diag  = option_diag(opts[5]);
#endif

    GetNArray(a,na1);
    CHECK_DIM_GE(na1,2);
    ma = ROW_SIZE(na1);
    na = COL_SIZE(na1);

    GetNArray(x,na2);
    CHECK_DIM_GE(na2,1);
    nx = COL_SIZE(na2);
#if GE
    SWAP_IFCOL(g.order, ma, na, tmp);
    g.m = ma;
    g.n = na;
    SWAP_IFTRANS(g.trans, ma, na, tmp);
#else
    CHECK_SQUARE("a",na1);
#endif
    CHECK_INT_EQ("na",na,"nx",nx);
    shape[0] = ma;

#if TR
    if (y != Qnil) {
        rb_raise(rb_eArgError,"wrong number of arguments (3 for 2)");
    }
    COPY_OR_CAST_TO(x,cT);
    ndf.nin = 2;
    na_ndloop3(&ndf, &g, 2, a, x);
    return x;

#else // GE,SY,HE

    if (y == Qnil) { // c is not given.
        ndf.nout = 1;
        ain[2] = ain[3];
        y = INT2FIX(0);
        shape[0] = ma;
    } else {
        narray_t *na3;
        COPY_OR_CAST_TO(y,cT);
        GetNArray(y,na3);
        CHECK_DIM_GE(na3,1);
        CHECK_SIZE_GE(na3,nx);
    }
    {
        VALUE ans;
        ans = na_ndloop3(&ndf, &g, 3, a, x, y);

        if (ndf.nout == 1) { // c is not given.
            return ans;
        } else {
            return y;
        }
    }
#endif
}

#undef func_p
#undef args_t
#undef GE
#undef TR


#line 1 "/opt/local/var/macports/build/rb31-numo-linalg-003c080d/work/destroot/opt/local/lib/ruby3.1/gems/3.1.0/gems/numo-linalg-0.1.7/ext/numo/linalg/blas/gen/../tmpl/mv.c"
/**/
#line 6 "/opt/local/var/macports/build/rb31-numo-linalg-003c080d/work/destroot/opt/local/lib/ruby3.1/gems/3.1.0/gems/numo-linalg-0.1.7/ext/numo/linalg/blas/gen/../tmpl/mv.c"
#define GE 0
#define TR 1
#define args_t ctrmv_args_t

typedef struct {
  enum CBLAS_ORDER order;
  enum CBLAS_TRANSPOSE trans;
  enum CBLAS_UPLO uplo;
  enum CBLAS_DIAG diag;
  dtype alpha, beta;
  blasint m, n;
} args_t;

#define func_p ctrmv_p

static ctrmv_t func_p = 0;

static void
iter_blas_s_ctrmv(na_loop_t *const lp)
{
    dtype *a;
    char *p1;
    ssize_t s1;
#if !TR
    char *p2;
    ssize_t s2;
#endif
#if !GE
    int n;
#endif
    int lda;
    args_t *g;

    a = (dtype*)NDL_PTR(lp,0);
    INIT_PTR(lp,1,p1,s1);
#if !TR
    INIT_PTR(lp,2,p2,s2);
#endif
    g = (args_t*)(lp->opt_ptr);

#if !GE
    n = NDL_SHAPE(lp,0)[1];
#endif
    lda = NDL_STEP(lp,0) / sizeof(dtype);

#if GE
    (*func_p)( g->order, g->trans, g->m, g->n,
        DP(g->alpha), a, lda, (dtype*)p1, s1/sizeof(dtype),
        DP(g->beta), (dtype*)p2, s2/sizeof(dtype) );
#elif TR
    (*func_p)( g->order, g->uplo, g->trans, g->diag, n, a, lda,
        (dtype*)p1, s1/sizeof(dtype) );
#else // SY,HE
    (*func_p)( g->order, g->uplo, n,
        DP(g->alpha), a, lda, (dtype*)p1, s1/sizeof(dtype),
        DP(g->beta), (dtype*)p2, s2/sizeof(dtype) );
#endif
}

/*
  @overload ctrmv(a, x, [uplo:'U', trans:'N', diag:'U', order:'R'])
  @param a [Numo::SComplex]  matrix (>=2-dimentional NArray).
  @param x [Numo::SComplex]  vector (>=1-dimentional NArray).
  @param alpha [Float]  (default=1.0)
  @param beta [Float]  (default=0.0)
  @param side [String or Symbol]  if 'L': op(A)\*B (left-side op), if 'R': B\*op(A) (right-side op). (default='L')
  @param uplo [String or Symbol]  if 'U': Upper triangle, if 'L': Lower triangle. (default='U')
  @param trans [String or Symbol]  if 'N': Not transpose , if 'T': Transpose . (default='N')
  @param order [String or Symbol]  if 'R': Row-major, if 'C': Column-major. (default='R')
  @return [Numo::SComplex] returns y = alpha*op(A)\*x + beta\*y.

CTRMV  performs one of the matrix-vector operations

        x := A*x,   or   x := A**T*x,   or   x := A**H*x,

where x is an n element vector and  A is an n by n unit, or non-unit,
upper or lower triangular matrix.

*/
static VALUE
blas_s_ctrmv(int argc, VALUE const argv[], VALUE UNUSED(mod))
{
    VALUE     a, x, y=Qnil, alpha, beta;
    narray_t *na1, *na2;
    blasint   ma, na, nx;
#if GE
    blasint   tmp;
#endif
    size_t    shape[1];
    ndfunc_arg_in_t ain[4] = {{cT,2},{cT,1},{OVERWRITE,1},{sym_init,0}};
    ndfunc_arg_out_t aout[1] = {{cT,1,shape}};
    ndfunc_t ndf = {iter_blas_s_ctrmv, NO_LOOP, 3, 0, ain, aout};

    args_t g;
    VALUE kw_hash = Qnil;
#if GE
    ID kw_table[4] = {id_alpha,id_beta,id_order,id_trans};
#elif TR
    ID kw_table[6] = {id_alpha,id_beta,id_order,id_uplo,id_trans,id_diag};
#else
    ID kw_table[4] = {id_alpha,id_beta,id_order,id_uplo};
#endif
    VALUE opts[6] = {Qundef,Qundef,Qundef,Qundef,Qundef,Qundef};

    CHECK_FUNC(func_p,"ctrmv");

    rb_scan_args(argc, argv, "21:", &a, &x, &y, &kw_hash);
    rb_get_kwargs(kw_hash, kw_table, 0, 4+2*TR, opts);
    alpha   = option_value(opts[0],Qnil);
    g.alpha = RTEST(alpha) ? m_num_to_data(alpha) : m_one;
    beta    = option_value(opts[1],Qnil);
    g.beta  = RTEST(beta)  ? m_num_to_data(beta)  : m_zero;
    g.order = option_order(opts[2]);
#if GE
    g.trans = option_trans(opts[3]);
#else
    g.uplo  = option_uplo(opts[3]);
#endif
#if TR
    g.trans = option_trans(opts[4]);
    g.diag  = option_diag(opts[5]);
#endif

    GetNArray(a,na1);
    CHECK_DIM_GE(na1,2);
    ma = ROW_SIZE(na1);
    na = COL_SIZE(na1);

    GetNArray(x,na2);
    CHECK_DIM_GE(na2,1);
    nx = COL_SIZE(na2);
#if GE
    SWAP_IFCOL(g.order, ma, na, tmp);
    g.m = ma;
    g.n = na;
    SWAP_IFTRANS(g.trans, ma, na, tmp);
#else
    CHECK_SQUARE("a",na1);
#endif
    CHECK_INT_EQ("na",na,"nx",nx);
    shape[0] = ma;

#if TR
    if (y != Qnil) {
        rb_raise(rb_eArgError,"wrong number of arguments (3 for 2)");
    }
    COPY_OR_CAST_TO(x,cT);
    ndf.nin = 2;
    na_ndloop3(&ndf, &g, 2, a, x);
    return x;

#else // GE,SY,HE

    if (y == Qnil) { // c is not given.
        ndf.nout = 1;
        ain[2] = ain[3];
        y = INT2FIX(0);
        shape[0] = ma;
    } else {
        narray_t *na3;
        COPY_OR_CAST_TO(y,cT);
        GetNArray(y,na3);
        CHECK_DIM_GE(na3,1);
        CHECK_SIZE_GE(na3,nx);
    }
    {
        VALUE ans;
        ans = na_ndloop3(&ndf, &g, 3, a, x, y);

        if (ndf.nout == 1) { // c is not given.
            return ans;
        } else {
            return y;
        }
    }
#endif
}

#undef func_p
#undef args_t
#undef GE
#undef TR


#line 1 "/opt/local/var/macports/build/rb31-numo-linalg-003c080d/work/destroot/opt/local/lib/ruby3.1/gems/3.1.0/gems/numo-linalg-0.1.7/ext/numo/linalg/blas/gen/../tmpl/mv.c"
/**/
#line 6 "/opt/local/var/macports/build/rb31-numo-linalg-003c080d/work/destroot/opt/local/lib/ruby3.1/gems/3.1.0/gems/numo-linalg-0.1.7/ext/numo/linalg/blas/gen/../tmpl/mv.c"
#define GE 0
#define TR 0
#define args_t chemv_args_t

typedef struct {
  enum CBLAS_ORDER order;
  enum CBLAS_TRANSPOSE trans;
  enum CBLAS_UPLO uplo;
  enum CBLAS_DIAG diag;
  dtype alpha, beta;
  blasint m, n;
} args_t;

#define func_p chemv_p

static chemv_t func_p = 0;

static void
iter_blas_s_chemv(na_loop_t *const lp)
{
    dtype *a;
    char *p1;
    ssize_t s1;
#if !TR
    char *p2;
    ssize_t s2;
#endif
#if !GE
    int n;
#endif
    int lda;
    args_t *g;

    a = (dtype*)NDL_PTR(lp,0);
    INIT_PTR(lp,1,p1,s1);
#if !TR
    INIT_PTR(lp,2,p2,s2);
#endif
    g = (args_t*)(lp->opt_ptr);

#if !GE
    n = NDL_SHAPE(lp,0)[1];
#endif
    lda = NDL_STEP(lp,0) / sizeof(dtype);

#if GE
    (*func_p)( g->order, g->trans, g->m, g->n,
        DP(g->alpha), a, lda, (dtype*)p1, s1/sizeof(dtype),
        DP(g->beta), (dtype*)p2, s2/sizeof(dtype) );
#elif TR
    (*func_p)( g->order, g->uplo, g->trans, g->diag, n, a, lda,
        (dtype*)p1, s1/sizeof(dtype) );
#else // SY,HE
    (*func_p)( g->order, g->uplo, n,
        DP(g->alpha), a, lda, (dtype*)p1, s1/sizeof(dtype),
        DP(g->beta), (dtype*)p2, s2/sizeof(dtype) );
#endif
}

/*
  @overload chemv(a, x, [y, alpha:1, beta:0, uplo:'U', order:'R'])
  @param a [Numo::SComplex]  matrix (>=2-dimentional NArray).
  @param x [Numo::SComplex]  vector (>=1-dimentional NArray).
  @param y [Numo::SComplex]  vector (>=1-dimentional NArray, optional, inplace allowed).
  @param alpha [Float]  (default=1.0)
  @param beta [Float]  (default=0.0)
  @param side [String or Symbol]  if 'L': op(A)\*B (left-side op), if 'R': B\*op(A) (right-side op). (default='L')
  @param uplo [String or Symbol]  if 'U': Upper triangle, if 'L': Lower triangle. (default='U')
  @param order [String or Symbol]  if 'R': Row-major, if 'C': Column-major. (default='R')
  @return [Numo::SComplex] returns y = alpha*op(A)\*x + beta\*y.

CHEMV  performs the matrix-vector  operation

        y := alpha*A*x + beta*y,

where alpha and beta are scalars, x and y are n element vectors and
A is an n by n hermitian matrix.

*/
static VALUE
blas_s_chemv(int argc, VALUE const argv[], VALUE UNUSED(mod))
{
    VALUE     a, x, y=Qnil, alpha, beta;
    narray_t *na1, *na2;
    blasint   ma, na, nx;
#if GE
    blasint   tmp;
#endif
    size_t    shape[1];
    ndfunc_arg_in_t ain[4] = {{cT,2},{cT,1},{OVERWRITE,1},{sym_init,0}};
    ndfunc_arg_out_t aout[1] = {{cT,1,shape}};
    ndfunc_t ndf = {iter_blas_s_chemv, NO_LOOP, 3, 0, ain, aout};

    args_t g;
    VALUE kw_hash = Qnil;
#if GE
    ID kw_table[4] = {id_alpha,id_beta,id_order,id_trans};
#elif TR
    ID kw_table[6] = {id_alpha,id_beta,id_order,id_uplo,id_trans,id_diag};
#else
    ID kw_table[4] = {id_alpha,id_beta,id_order,id_uplo};
#endif
    VALUE opts[6] = {Qundef,Qundef,Qundef,Qundef,Qundef,Qundef};

    CHECK_FUNC(func_p,"chemv");

    rb_scan_args(argc, argv, "21:", &a, &x, &y, &kw_hash);
    rb_get_kwargs(kw_hash, kw_table, 0, 4+2*TR, opts);
    alpha   = option_value(opts[0],Qnil);
    g.alpha = RTEST(alpha) ? m_num_to_data(alpha) : m_one;
    beta    = option_value(opts[1],Qnil);
    g.beta  = RTEST(beta)  ? m_num_to_data(beta)  : m_zero;
    g.order = option_order(opts[2]);
#if GE
    g.trans = option_trans(opts[3]);
#else
    g.uplo  = option_uplo(opts[3]);
#endif
#if TR
    g.trans = option_trans(opts[4]);
    g.diag  = option_diag(opts[5]);
#endif

    GetNArray(a,na1);
    CHECK_DIM_GE(na1,2);
    ma = ROW_SIZE(na1);
    na = COL_SIZE(na1);

    GetNArray(x,na2);
    CHECK_DIM_GE(na2,1);
    nx = COL_SIZE(na2);
#if GE
    SWAP_IFCOL(g.order, ma, na, tmp);
    g.m = ma;
    g.n = na;
    SWAP_IFTRANS(g.trans, ma, na, tmp);
#else
    CHECK_SQUARE("a",na1);
#endif
    CHECK_INT_EQ("na",na,"nx",nx);
    shape[0] = ma;

#if TR
    if (y != Qnil) {
        rb_raise(rb_eArgError,"wrong number of arguments (3 for 2)");
    }
    COPY_OR_CAST_TO(x,cT);
    ndf.nin = 2;
    na_ndloop3(&ndf, &g, 2, a, x);
    return x;

#else // GE,SY,HE

    if (y == Qnil) { // c is not given.
        ndf.nout = 1;
        ain[2] = ain[3];
        y = INT2FIX(0);
        shape[0] = ma;
    } else {
        narray_t *na3;
        COPY_OR_CAST_TO(y,cT);
        GetNArray(y,na3);
        CHECK_DIM_GE(na3,1);
        CHECK_SIZE_GE(na3,nx);
    }
    {
        VALUE ans;
        ans = na_ndloop3(&ndf, &g, 3, a, x, y);

        if (ndf.nout == 1) { // c is not given.
            return ans;
        } else {
            return y;
        }
    }
#endif
}

#undef func_p
#undef args_t
#undef GE
#undef TR


#line 1 "/opt/local/var/macports/build/rb31-numo-linalg-003c080d/work/destroot/opt/local/lib/ruby3.1/gems/3.1.0/gems/numo-linalg-0.1.7/ext/numo/linalg/blas/gen/../tmpl/ger.c"
#define args_t cgerc_args_t

typedef struct {
    enum CBLAS_ORDER order;
    dtype alpha;
    blasint m, n;
} args_t;

#define func_p cgerc_p

static cgerc_t func_p = 0;

static void
iter_blas_s_cgerc(na_loop_t *const lp)
{
    dtype *a;
    char *p1, *p2;
    ssize_t s1, s2;
    args_t *g;
    int lda;

    INIT_PTR(lp,0,p1,s1);
    INIT_PTR(lp,1,p2,s2);
    a = (dtype*)NDL_PTR(lp,2);
    g = (args_t*)(lp->opt_ptr);

    lda = NDL_STEP(lp,2) / sizeof(dtype);

    (*func_p)(g->order, g->m, g->n,
              DP(g->alpha), (dtype*)p1, s1/sizeof(dtype),
              (dtype*)p2, s2/sizeof(dtype), a, lda);
}

/*
  @overload cgerc( x, y, [a, alpha:1, order:'R'] )
  @param x [Numo::SComplex]  vector (>=1-dimentional NArray).
  @param y [Numo::SComplex]  vector (>=1-dimentional NArray).
  @param a [Numo::SComplex]  matrix (>=2-dimentional NArray, m-by-n symmetric matrix, optional, inplace allowed).
  @param alpha [Float]  (default=1.0)
  @param order [String or Symbol]  if 'R': Row-major, if 'C': Column-major. (default='R')
  @return [Numo::SComplex] returns a.

  CGERC  performs the rank 1 operation

        A := alpha*x*y**H + A,

where alpha is a scalar, x is an m element vector, y is an n element
vector and A is an m by n matrix.


 */
static VALUE
blas_s_cgerc(int argc, VALUE const argv[], VALUE UNUSED(mod))
{
    VALUE     ans;
    VALUE     x, y, a=Qnil, alpha;
    narray_t *na1, *na2;
    blasint   mx, ny, tmp;
    size_t    shape[2];
    ndfunc_arg_in_t ain[4] = {{cT,1},{cT,1},{OVERWRITE,2},{sym_init,0}};
    ndfunc_arg_out_t aout[1] = {{cT,2,shape}};
    ndfunc_t ndf = {iter_blas_s_cgerc, NO_LOOP, 3, 0, ain, aout};

    args_t g;
    VALUE kw_hash = Qnil;
    ID kw_table[2] = {id_alpha,id_order};
    VALUE opts[2] = {Qundef};

    CHECK_FUNC(func_p,"cgerc");

    rb_scan_args(argc, argv, "21:", &x, &y, &a, &kw_hash);
    rb_get_kwargs(kw_hash, kw_table, 0, 2, opts);
    alpha   = option_value(opts[0],Qnil);
    g.alpha = RTEST(alpha) ? m_num_to_data(alpha) : m_one;
    g.order = option_order(opts[1]);

    GetNArray(x,na1);
    GetNArray(y,na2);
    CHECK_DIM_GE(na1,1);
    CHECK_DIM_GE(na2,1);
    mx = COL_SIZE(na1); // m
    ny = COL_SIZE(na2); // n
    g.m = mx;
    g.n = ny;

    SWAP_IFCOL(g.order, mx,ny, tmp);

    if (a == Qnil) { // c is not given.
        ndf.nout = 1;
        ain[2] = ain[3];
        a = INT2FIX(0);
        shape[0] = mx;
        shape[1] = ny;
    } else {
        narray_t  *na3;
        blasint    ma, na;
        COPY_OR_CAST_TO(a,cT);
        GetNArray(a,na3);
        CHECK_DIM_GE(na3,2);
        ma = ROW_SIZE(na3); // m
        na = COL_SIZE(na3); // n (lda)
        CHECK_SIZE_EQ(ma,mx);
        CHECK_SIZE_EQ(na,ny);
    }

    ans = na_ndloop3(&ndf, &g, 3, x, y, a);

    if (ndf.nout = 1) { // a is not given.
        return ans;
    } else {
        return a;
    }
}

#undef func_p
#undef args_t


#line 1 "/opt/local/var/macports/build/rb31-numo-linalg-003c080d/work/destroot/opt/local/lib/ruby3.1/gems/3.1.0/gems/numo-linalg-0.1.7/ext/numo/linalg/blas/gen/../tmpl/ger.c"
#define args_t cgeru_args_t

typedef struct {
    enum CBLAS_ORDER order;
    dtype alpha;
    blasint m, n;
} args_t;

#define func_p cgeru_p

static cgeru_t func_p = 0;

static void
iter_blas_s_cgeru(na_loop_t *const lp)
{
    dtype *a;
    char *p1, *p2;
    ssize_t s1, s2;
    args_t *g;
    int lda;

    INIT_PTR(lp,0,p1,s1);
    INIT_PTR(lp,1,p2,s2);
    a = (dtype*)NDL_PTR(lp,2);
    g = (args_t*)(lp->opt_ptr);

    lda = NDL_STEP(lp,2) / sizeof(dtype);

    (*func_p)(g->order, g->m, g->n,
              DP(g->alpha), (dtype*)p1, s1/sizeof(dtype),
              (dtype*)p2, s2/sizeof(dtype), a, lda);
}

/*
  @overload cgeru( x, y, [a, alpha:1, order:'R'] )
  @param x [Numo::SComplex]  vector (>=1-dimentional NArray).
  @param y [Numo::SComplex]  vector (>=1-dimentional NArray).
  @param a [Numo::SComplex]  matrix (>=2-dimentional NArray, m-by-n symmetric matrix, optional, inplace allowed).
  @param alpha [Float]  (default=1.0)
  @param order [String or Symbol]  if 'R': Row-major, if 'C': Column-major. (default='R')
  @return [Numo::SComplex] returns a.

  CGERU  performs the rank 1 operation

        A := alpha*x*y**T + A,

where alpha is a scalar, x is an m element vector, y is an n element
vector and A is an m by n matrix.


 */
static VALUE
blas_s_cgeru(int argc, VALUE const argv[], VALUE UNUSED(mod))
{
    VALUE     ans;
    VALUE     x, y, a=Qnil, alpha;
    narray_t *na1, *na2;
    blasint   mx, ny, tmp;
    size_t    shape[2];
    ndfunc_arg_in_t ain[4] = {{cT,1},{cT,1},{OVERWRITE,2},{sym_init,0}};
    ndfunc_arg_out_t aout[1] = {{cT,2,shape}};
    ndfunc_t ndf = {iter_blas_s_cgeru, NO_LOOP, 3, 0, ain, aout};

    args_t g;
    VALUE kw_hash = Qnil;
    ID kw_table[2] = {id_alpha,id_order};
    VALUE opts[2] = {Qundef};

    CHECK_FUNC(func_p,"cgeru");

    rb_scan_args(argc, argv, "21:", &x, &y, &a, &kw_hash);
    rb_get_kwargs(kw_hash, kw_table, 0, 2, opts);
    alpha   = option_value(opts[0],Qnil);
    g.alpha = RTEST(alpha) ? m_num_to_data(alpha) : m_one;
    g.order = option_order(opts[1]);

    GetNArray(x,na1);
    GetNArray(y,na2);
    CHECK_DIM_GE(na1,1);
    CHECK_DIM_GE(na2,1);
    mx = COL_SIZE(na1); // m
    ny = COL_SIZE(na2); // n
    g.m = mx;
    g.n = ny;

    SWAP_IFCOL(g.order, mx,ny, tmp);

    if (a == Qnil) { // c is not given.
        ndf.nout = 1;
        ain[2] = ain[3];
        a = INT2FIX(0);
        shape[0] = mx;
        shape[1] = ny;
    } else {
        narray_t  *na3;
        blasint    ma, na;
        COPY_OR_CAST_TO(a,cT);
        GetNArray(a,na3);
        CHECK_DIM_GE(na3,2);
        ma = ROW_SIZE(na3); // m
        na = COL_SIZE(na3); // n (lda)
        CHECK_SIZE_EQ(ma,mx);
        CHECK_SIZE_EQ(na,ny);
    }

    ans = na_ndloop3(&ndf, &g, 3, x, y, a);

    if (ndf.nout = 1) { // a is not given.
        return ans;
    } else {
        return a;
    }
}

#undef func_p
#undef args_t


#line 1 "/opt/local/var/macports/build/rb31-numo-linalg-003c080d/work/destroot/opt/local/lib/ruby3.1/gems/3.1.0/gems/numo-linalg-0.1.7/ext/numo/linalg/blas/gen/../tmpl/syr.c"
#define args_t cher_args_t

typedef struct {
    enum CBLAS_ORDER order;
    enum CBLAS_UPLO uplo;
    rtype alpha;
} args_t;

#define func_p cher_p

static cher_t func_p = 0;

static void
iter_blas_s_cher(na_loop_t *const lp)
{
    dtype *a;
    char *p1;
    ssize_t s1;
    args_t *g;
    blasint n, lda;

    INIT_PTR(lp,0,p1,s1);
    a = (dtype*)NDL_PTR(lp,1);
    g = (args_t*)(lp->opt_ptr);

    n = NDL_SHAPE(lp,0)[0];
    lda = NDL_STEP(lp,1) / sizeof(dtype);

    (*func_p)(g->order, g->uplo, n, g->alpha,
              (dtype*)p1, s1/sizeof(dtype), a, lda);
}

/*
  @overload cher( x, [a, alpha:1, uplo:'U', order:'R'] )
  @param x [Numo::SComplex]  vector (>=1-dimentional NArray).
  @param a [Numo::SComplex]  matrix (>=2-dimentional NArray, inplace allowed).
  @param alpha [Float]  (default=1.0)
  @param uplo [String or Symbol]  if 'U': Upper triangle, if 'L': Lower triangle. (default='U')
  @param order [String or Symbol]  if 'R': Row-major, if 'C': Column-major. (default='R')
  @return [Numo::SComplex] return a
CHER   performs the hermitian rank 1 operation

        A := alpha*x*x**H + A,

where alpha is a real scalar, x is an n element vector and A is an
n by n hermitian matrix.

 */
static VALUE
blas_s_cher(int argc, VALUE const argv[], VALUE UNUSED(mod))
{
    VALUE     ans;
    VALUE     x, a, alpha;
    narray_t *na1, *na3;
    blasint   nx, na;
    size_t    shape[2];
    ndfunc_arg_in_t ain[3] = {{cT,1},{OVERWRITE,2},{sym_init,0}};
    ndfunc_arg_out_t aout[1] = {{cT,2,shape}};
    ndfunc_t ndf = {iter_blas_s_cher, NO_LOOP, 2, 0, ain, aout};

    args_t g;
    VALUE kw_hash = Qnil;
    ID kw_table[3] = {id_alpha,id_order,id_uplo};
    VALUE opts[3] = {Qundef,Qundef,Qundef};

    CHECK_FUNC(func_p,"cher");

    rb_scan_args(argc, argv, "11:", &x, &a, &kw_hash);
    rb_get_kwargs(kw_hash, kw_table, 0, 3, opts);
    alpha   = option_value(opts[0],Qnil);
    g.alpha = RTEST(alpha) ? NUM2DBL(alpha) : 1;
    g.order = option_order(opts[1]);
    g.uplo  = option_uplo(opts[2]);

    GetNArray(x,na1);
    CHECK_DIM_GE(na1,1);
    nx = COL_SIZE(na1); // n

    if (a == Qnil) { // c is not given.
        ndf.nout = 1;
        ain[1] = ain[2];
        a = INT2FIX(0);
        shape[0] = shape[1] = nx;
    } else {
        COPY_OR_CAST_TO(a,cT);
        GetNArray(a,na3);
        CHECK_DIM_GE(na3,2);
        CHECK_SQUARE("a",na3);
        na = COL_SIZE(na3); // n (lda)
        CHECK_SIZE_EQ(na,nx);
    }

    ans = na_ndloop3(&ndf, &g, 2, x, a);

    if (ndf.nout == 1) { // a is not given.
        return ans;
    } else {
        return a;
    }
}

#undef func_p
#undef args_t


#line 1 "/opt/local/var/macports/build/rb31-numo-linalg-003c080d/work/destroot/opt/local/lib/ruby3.1/gems/3.1.0/gems/numo-linalg-0.1.7/ext/numo/linalg/blas/gen/../tmpl/syr2.c"
#define args_t cher2_args_t

typedef struct {
    enum CBLAS_ORDER order;
    enum CBLAS_UPLO uplo;
    dtype alpha;
} args_t;

#define func_p cher2_p

static cher2_t func_p = 0;

static void
iter_blas_s_cher2(na_loop_t *const lp)
{
    dtype *a;
    char *p1, *p2;
    ssize_t s1, s2;
    args_t *g;
    blasint n, lda;

    INIT_PTR(lp,0,p1,s1);
    INIT_PTR(lp,1,p2,s2);
    a = (dtype*)NDL_PTR(lp,2);
    g = (args_t*)(lp->opt_ptr);

    n = NDL_SHAPE(lp,0)[0];
    lda = NDL_STEP(lp,2) / sizeof(dtype);

    (*func_p)(g->order, g->uplo, n,
              DP(g->alpha), (dtype*)p1, s1/sizeof(dtype),
              (dtype*)p2, s2/sizeof(dtype), a, lda);
}

/*
  @overload cher2( x, y, [a, alpha:1, uplo:'U', order:'R'] )
  @param x [Numo::SComplex]  vector (>=1-dimentional NArray).
  @param y [Numo::SComplex]  vector (>=1-dimentional NArray).
  @param a [Numo::SComplex]  matrix (>=2-dimentional NArray, inplace allowed).
  @param alpha [Float]  (default=1.0)
  @param uplo [String or Symbol]  if 'U': Upper triangle, if 'L': Lower triangle. (default='U')
  @param order [String or Symbol]  if 'R': Row-major, if 'C': Column-major. (default='R')
  @return [Numo::SComplex] returns a.

CHER2  performs the hermitian rank 2 operation

        A := alpha*x*y**H + conjg( alpha )*y*x**H + A,

where alpha is a scalar, x and y are n element vectors and A is an n
by n hermitian matrix.

*/
static VALUE
blas_s_cher2(int argc, VALUE const argv[], VALUE UNUSED(mod))
{
    VALUE     ans;
    VALUE     x, y, a, alpha;
    narray_t *na1, *na2, *na3;
    blasint   nx, ny, na;
    size_t    shape[2];
    ndfunc_arg_in_t ain[4] = {{cT,1},{cT,1},{OVERWRITE,2},{sym_init,0}};
    ndfunc_arg_out_t aout[1] = {{cT,2,shape}};
    ndfunc_t ndf = {iter_blas_s_cher2, NO_LOOP, 3, 0, ain, aout};

    args_t g;
    VALUE kw_hash = Qnil;
    ID kw_table[3] = {id_alpha,id_order,id_uplo};
    VALUE opts[3] = {Qundef,Qundef,Qundef};

    CHECK_FUNC(func_p,"cher2");

    rb_scan_args(argc, argv, "21:", &x, &y, &a, &kw_hash);
    rb_get_kwargs(kw_hash, kw_table, 0, 3, opts);
    alpha   = option_value(opts[0],Qnil);
    g.alpha = RTEST(alpha) ? m_num_to_data(alpha) : m_one;
    g.order = option_order(opts[1]);
    g.uplo  = option_uplo(opts[2]);

    GetNArray(x,na1);
    GetNArray(y,na2);
    CHECK_DIM_GE(na1,1);
    CHECK_DIM_GE(na2,1);
    nx = COL_SIZE(na1); // n
    ny = COL_SIZE(na2); // n
    CHECK_INT_EQ("nx",nx,"ny",ny);

    if (a == Qnil) { // c is not given.
        ndf.nout = 1;
        ain[2] = ain[3];
        a = INT2FIX(0);
        shape[0] = shape[1] = nx;
    } else {
        COPY_OR_CAST_TO(a,cT);
        GetNArray(a,na3);
        CHECK_DIM_GE(na3,2);
        CHECK_SQUARE("a",na3);
        na = COL_SIZE(na3); // n (lda)
        CHECK_SIZE_EQ(na,nx);
    }

    ans = na_ndloop3(&ndf, &g, 3, x, y, a);

    if (ndf.nout == 1) { // a is not given.
        return ans;
    } else {
        return a;
    }
}

#undef func_p
#undef args_t


#line 1 "/opt/local/var/macports/build/rb31-numo-linalg-003c080d/work/destroot/opt/local/lib/ruby3.1/gems/3.1.0/gems/numo-linalg-0.1.7/ext/numo/linalg/blas/gen/../tmpl/syrk.c"
/**/
#line 6 "/opt/local/var/macports/build/rb31-numo-linalg-003c080d/work/destroot/opt/local/lib/ruby3.1/gems/3.1.0/gems/numo-linalg-0.1.7/ext/numo/linalg/blas/gen/../tmpl/syrk.c"
#define P(a) (a)

#line 11 "/opt/local/var/macports/build/rb31-numo-linalg-003c080d/work/destroot/opt/local/lib/ruby3.1/gems/3.1.0/gems/numo-linalg-0.1.7/ext/numo/linalg/blas/gen/../tmpl/syrk.c"
#define args_t cherk_args_t

typedef struct {
    enum CBLAS_ORDER order;
    enum CBLAS_UPLO uplo;
    enum CBLAS_TRANSPOSE trans;
    rtype alpha, beta;
    blasint n, k;
} args_t;

#define func_p cherk_p

static cherk_t func_p = 0;

static void
iter_blas_s_cherk(na_loop_t *const lp)
{
    dtype *a, *c;
    args_t *g;
    blasint lda, ldc;

    a = (dtype*)NDL_PTR(lp,0);
    c = (dtype*)NDL_PTR(lp,1);
    g = (args_t*)(lp->opt_ptr);

    lda = NDL_STEP(lp,0) / sizeof(dtype);
    ldc = NDL_STEP(lp,1) / sizeof(dtype);

    (*func_p)(g->order, g->uplo, g->trans, g->n, g->k,
              P(g->alpha), a, lda, P(g->beta), c, ldc);
}

/*
  @overload cherk( a, [c, alpha:1, beta:0, uplo:'U', trans:'N', order:'R'] )
  @param a [Numo::SComplex]  matrix (>=2-dimentional NArray, n-by-k, inpace).
  @param c [Numo::SComplex]  matrix (>=2-dimentional NArray, n-by-n, optional, inpace).
  @param alpha [Float]  (default=1.0)
  @param beta [Float]  (default=0.0)
  @param uplo [String or Symbol]  if 'U': Upper triangle, if 'L': Lower triangle. (default='U')
  @param trans [String or Symbol]  if 'N': Not transpose , if 'T': Transpose . (default='N')
  @param order [String or Symbol]  if 'R': Row-major, if 'C': Column-major. (default='R')
  @return [Numo::SComplex] returns c.

CHERK  performs one of the hermitian rank k operations

        C := alpha*A*A**H + beta*C,

or

        C := alpha*A**H*A + beta*C,

where  alpha and beta  are  real scalars,  C is an  n by n  hermitian
matrix and  A  is an  n by k  matrix in the  first case and a  k by n
matrix in the second case.

 */
static VALUE
blas_s_cherk(int argc, VALUE const argv[], VALUE UNUSED(mod))
{
    VALUE     ans;
    VALUE     a, c, alpha, beta;
    narray_t *na1, *na3;
    blasint   na, ka, nc, tmp;
    size_t    shape[2];
    ndfunc_arg_in_t ain[3] = {{cT,2},{OVERWRITE,2},{sym_init,0}};
    ndfunc_arg_out_t aout[1] = {{cT,2,shape}};
    ndfunc_t ndf = {iter_blas_s_cherk, NO_LOOP, 2, 0, ain, aout};

    args_t g;
    VALUE kw_hash = Qnil;
    ID kw_table[5] = {id_alpha,id_beta,id_order,id_uplo,id_trans};
    VALUE opts[5] = {Qundef,Qundef,Qundef,Qundef,Qundef};

    CHECK_FUNC(func_p,"cherk");

    rb_scan_args(argc, argv, "11:", &a, &c, &kw_hash);
    rb_get_kwargs(kw_hash, kw_table, 0, 5, opts);
    alpha   = option_value(opts[0],Qnil);
    beta    = option_value(opts[1],Qnil);
#line 85 "/opt/local/var/macports/build/rb31-numo-linalg-003c080d/work/destroot/opt/local/lib/ruby3.1/gems/3.1.0/gems/numo-linalg-0.1.7/ext/numo/linalg/blas/gen/../tmpl/syrk.c"
    g.alpha = RTEST(alpha) ? DBL2NUM(alpha) : 1;
    g.beta  = RTEST(beta)  ? DBL2NUM(beta)  : 0;
#line 91 "/opt/local/var/macports/build/rb31-numo-linalg-003c080d/work/destroot/opt/local/lib/ruby3.1/gems/3.1.0/gems/numo-linalg-0.1.7/ext/numo/linalg/blas/gen/../tmpl/syrk.c"
    g.order = option_order(opts[2]);
    g.uplo  = option_uplo(opts[3]);
    g.trans = option_trans(opts[4]);

    GetNArray(a,na1);
    CHECK_DIM_GE(na1,2);

    na = ROW_SIZE(na1); // n
    ka = COL_SIZE(na1); // k (lda)
    SWAP_IFCOLTR(g.order,g.trans, na,ka, tmp);
    g.n = na;
    g.k = ka;

    if (c == Qnil) { // c is not given.
        ndf.nout = 1;
        ain[1] = ain[2];
        c = INT2FIX(0);
        shape[0] = na;
        shape[1] = na;
    } else {
        COPY_OR_CAST_TO(c,cT);
        GetNArray(c,na3);
        CHECK_DIM_GE(na3,2);
        nc = ROW_SIZE(na3);
        if (nc < na) {
            rb_raise(nary_eShapeError,"nc=%d must be >= na=%d",nc,na);
        }
        //CHECK_LEADING_GE("ldc",g.ldc,"n",na);
    }

    ans = na_ndloop3(&ndf, &g, 2, a, c);

    if (ndf.nout == 1) { // c is not given.
        return ans;
    } else {
        return c;
    }
}

#undef func_p
#undef args_t
#undef P


#line 1 "/opt/local/var/macports/build/rb31-numo-linalg-003c080d/work/destroot/opt/local/lib/ruby3.1/gems/3.1.0/gems/numo-linalg-0.1.7/ext/numo/linalg/blas/gen/../tmpl/mm.c"
/**/
#line 7 "/opt/local/var/macports/build/rb31-numo-linalg-003c080d/work/destroot/opt/local/lib/ruby3.1/gems/3.1.0/gems/numo-linalg-0.1.7/ext/numo/linalg/blas/gen/../tmpl/mm.c"
#define GE 1
#define TR 0
#define args_t cgemm_args_t

typedef struct {
  enum CBLAS_ORDER order;
  enum CBLAS_TRANSPOSE transa, transb;
  enum CBLAS_SIDE side;
  enum CBLAS_UPLO uplo;
  enum CBLAS_DIAG diag;
  dtype alpha, beta;
  blasint m, n, k;
} args_t;

#define func_p cgemm_p

static cgemm_t func_p = 0;

static void
iter_blas_s_cgemm(na_loop_t *const lp)
{
    dtype *a, *b;
    int    lda, ldb;
#if !TR
    dtype *c;
    int    ldc;
#endif
    args_t *g;

    a = (dtype*)NDL_PTR(lp,0);
    b = (dtype*)NDL_PTR(lp,1);
#if !TR
    c = (dtype*)NDL_PTR(lp,2);
#endif
    g = (args_t*)(lp->opt_ptr);

    lda = NDL_STEP(lp,0) / sizeof(dtype);
    ldb = NDL_STEP(lp,1) / sizeof(dtype);
#if !TR
    ldc = NDL_STEP(lp,2) / sizeof(dtype);
#endif

    //printf("m=%d n=%d k=%d\n",g->m,g->n,g->k);

#if GE
    (*func_p)( g->order, g->transa, g->transb, g->m, g->n, g->k,
              DP(g->alpha), a, lda, b, ldb, DP(g->beta), c, ldc);
#elif TR
    (*func_p)( g->order, g->side, g->uplo, g->transa, g->diag, g->m, g->n,
               DP(g->alpha), a, lda, b, ldb);
#else // SY,HE
    (*func_p)( g->order, g->side, g->uplo, g->m, g->n,
               DP(g->alpha), a, lda, b, ldb, DP(g->beta), c, ldc);
#endif
}

/*

  @overload cgemm(a, b, [c, alpha:1, beta:0, transa:'N', transb:'N', order:'R'])
  @param a [Numo::SComplex]  matrix (>=2-dimentional NArray).
  @param b [Numo::SComplex]  matrix (>=2-dimentional NArray).
  @param c [Numo::SComplex]  matrix (>=2-dimentional NArray, optional, inplace allowed).
  @param alpha [Float]  (default=1.0)
  @param beta [Float]  (default=0.0)
  @param transa [String or Symbol]  if 'N': Not transpose a, if 'T': Transpose a. (default='N')
  @param transb [String or Symbol]  if 'N': Not transpose b, if 'T': Transpose b. (default='N')
  @param order [String or Symbol]  if 'R': Row-major, if 'C': Column-major. (default='R')
  @return [Numo::SComplex] returns c = alpha\*op( A )\*op( B ) + beta\*C.
CGEMM  performs one of the matrix-matrix operations

        C := alpha*op( A )*op( B ) + beta*C,

where  op( X ) is one of

        op( X ) = X   or   op( X ) = X**T   or   op( X ) = X**H,

alpha and beta are scalars, and A, B and C are matrices, with op( A )
an m by k matrix,  op( B )  a  k by n matrix and  C an m by n matrix.

*/
static VALUE
blas_s_cgemm(int argc, VALUE const argv[], VALUE UNUSED(mod))
{
    VALUE     a, b, c=Qnil, alpha, beta;
    narray_t *na1, *na2;
    blasint   ma, ka, kb, nb, tmp;
    size_t    shape[2];
    ndfunc_arg_in_t ain[3] = {{cT,2},{cT,2},{OVERWRITE,2}};
    ndfunc_arg_out_t aout[1] = {{cT,2,shape}};
    ndfunc_t ndf = {iter_blas_s_cgemm, NO_LOOP, 3, 0, ain, aout};

    args_t g;
    VALUE kw_hash = Qnil;
#if GE
    ID kw_table[5] = {id_alpha,id_beta,id_order,id_transa,id_transb};
#elif TR
    ID kw_table[7] = {id_alpha,id_beta,id_order,id_side,id_uplo,id_transa,id_diag};
#else
    ID kw_table[5] = {id_alpha,id_beta,id_order,id_side,id_uplo};
#endif
    VALUE opts[7] = {Qundef,Qundef,Qundef,Qundef,Qundef,Qundef,Qundef};

    CHECK_FUNC(func_p,"cgemm");

    rb_scan_args(argc, argv, "21:", &a, &b, &c, &kw_hash);
    rb_get_kwargs(kw_hash, kw_table, 0, 5+TR*2, opts);
    alpha    = option_value(opts[0],Qnil);
    g.alpha  = RTEST(alpha) ? m_num_to_data(alpha) : m_one;
    beta     = option_value(opts[1],Qnil);
    g.beta   = RTEST(beta)  ? m_num_to_data(beta)  : m_zero;
    g.order  = option_order(opts[2]);
#if GE
    g.transa = option_trans(opts[3]);
    g.transb = option_trans(opts[4]);
#else
    g.side   = option_side(opts[3]);
    g.uplo   = option_uplo(opts[4]);
#endif
#if TR
    g.transa = option_trans(opts[5]);
    g.diag   = option_diag(opts[6]);
#endif

    GetNArray(a,na1);
    GetNArray(b,na2);
    CHECK_DIM_GE(na1,2);
    CHECK_DIM_GE(na2,2);
    ma = ROW_SIZE(na1); // m
    ka = COL_SIZE(na1); // k (lda)
    kb = ROW_SIZE(na2); // k
    nb = COL_SIZE(na2); // n (ldb)

#if GE
    SWAP_IFCOLTR(g.order,g.transa, ma,ka, tmp);
    SWAP_IFCOLTR(g.order,g.transb, kb,nb, tmp);
    CHECK_INT_EQ("ka",ka,"kb",kb);
    g.m = ma;
    g.n = nb;
    g.k = ka;
#else
    CHECK_SQUARE("a",na1); // ma == ka
    SWAP_IFCOL(g.order, kb,nb, tmp);
    // row major             L    R
    //ma = ROW_SIZE(na1); // m or n
    //ka = COL_SIZE(na1); // m or n (lda)
    g.m = kb; // m
    g.n = nb; // n (ldb)
    if (g.side == CblasLeft) {
        CHECK_SIZE_EQ(ka, g.m);
    } else {
        CHECK_SIZE_EQ(ka, g.n);
    }
#endif

    SWAP_IFROW(g.order, ma,nb, tmp);

#if TR
    if (c != Qnil) {
        rb_raise(rb_eArgError,"wrong number of arguments (3 for 2)");
    }
    COPY_OR_CAST_TO(b,cT);
    ndf.nin = 2;

    na_ndloop3(&ndf, &g, 2, a, b);
    return b;
#else

    if (c == Qnil) { // c is not given.
        ndfunc_arg_in_t ain_init = {sym_init,0};
        ain[2] = ain_init;
        ndf.nout = 1;
        c = INT2FIX(0);
        shape[0] = nb;
        shape[1] = ma;
    } else {
        narray_t *na3;
        int nc;
        COPY_OR_CAST_TO(c,cT);
        GetNArray(c,na3);
        CHECK_DIM_GE(na3,2);
        nc = ROW_SIZE(na3);
        if (nc < nb) {
            rb_raise(nary_eShapeError,"nc=%d must be >= nb=%d",nc,nb);
        }
        //CHECK_LEADING_GE("ldc",g.ldc,"m",ma);
    }
    {
        VALUE ans = na_ndloop3(&ndf, &g, 3, a, b, c);

        if (ndf.nout == 1) { // c is not given.
            return ans;
        } else {
            return c;
        }
    }
#endif
}

#undef func_p
#undef args_t
#undef GE
#undef TR


#line 1 "/opt/local/var/macports/build/rb31-numo-linalg-003c080d/work/destroot/opt/local/lib/ruby3.1/gems/3.1.0/gems/numo-linalg-0.1.7/ext/numo/linalg/blas/gen/../tmpl/mm.c"
/**/
#line 7 "/opt/local/var/macports/build/rb31-numo-linalg-003c080d/work/destroot/opt/local/lib/ruby3.1/gems/3.1.0/gems/numo-linalg-0.1.7/ext/numo/linalg/blas/gen/../tmpl/mm.c"
#define GE 0
#define TR 0
#define args_t csymm_args_t

typedef struct {
  enum CBLAS_ORDER order;
  enum CBLAS_TRANSPOSE transa, transb;
  enum CBLAS_SIDE side;
  enum CBLAS_UPLO uplo;
  enum CBLAS_DIAG diag;
  dtype alpha, beta;
  blasint m, n, k;
} args_t;

#define func_p csymm_p

static csymm_t func_p = 0;

static void
iter_blas_s_csymm(na_loop_t *const lp)
{
    dtype *a, *b;
    int    lda, ldb;
#if !TR
    dtype *c;
    int    ldc;
#endif
    args_t *g;

    a = (dtype*)NDL_PTR(lp,0);
    b = (dtype*)NDL_PTR(lp,1);
#if !TR
    c = (dtype*)NDL_PTR(lp,2);
#endif
    g = (args_t*)(lp->opt_ptr);

    lda = NDL_STEP(lp,0) / sizeof(dtype);
    ldb = NDL_STEP(lp,1) / sizeof(dtype);
#if !TR
    ldc = NDL_STEP(lp,2) / sizeof(dtype);
#endif

    //printf("m=%d n=%d k=%d\n",g->m,g->n,g->k);

#if GE
    (*func_p)( g->order, g->transa, g->transb, g->m, g->n, g->k,
              DP(g->alpha), a, lda, b, ldb, DP(g->beta), c, ldc);
#elif TR
    (*func_p)( g->order, g->side, g->uplo, g->transa, g->diag, g->m, g->n,
               DP(g->alpha), a, lda, b, ldb);
#else // SY,HE
    (*func_p)( g->order, g->side, g->uplo, g->m, g->n,
               DP(g->alpha), a, lda, b, ldb, DP(g->beta), c, ldc);
#endif
}

/*

  @overload csymm(a, b, [c, alpha:1, beta:0, side:'L', uplo:'U', order:'R'])
  @param a [Numo::SComplex]  matrix (>=2-dimentional NArray).
  @param b [Numo::SComplex]  matrix (>=2-dimentional NArray).
  @param c [Numo::SComplex]  matrix (>=2-dimentional NArray, optional, inplace allowed).
  @param alpha [Float]  (default=1.0)
  @param beta [Float]  (default=0.0)
  @param side [String or Symbol]  if 'L': op(A)\*B (left-side op), if 'R': B\*op(A) (right-side op). (default='L')
  @param uplo [String or Symbol]  if 'U': Upper triangle, if 'L': Lower triangle. (default='U')
  @param order [String or Symbol]  if 'R': Row-major, if 'C': Column-major. (default='R')
  @return [Numo::SComplex] returns c = alpha\*op( A )\*op( B ) + beta\*C.
CSYMM  performs one of the matrix-matrix operations

        C := alpha*A*B + beta*C,

or

        C := alpha*B*A + beta*C,

where  alpha and beta are scalars, A is a symmetric matrix and  B and
C are m by n matrices.

*/
static VALUE
blas_s_csymm(int argc, VALUE const argv[], VALUE UNUSED(mod))
{
    VALUE     a, b, c=Qnil, alpha, beta;
    narray_t *na1, *na2;
    blasint   ma, ka, kb, nb, tmp;
    size_t    shape[2];
    ndfunc_arg_in_t ain[3] = {{cT,2},{cT,2},{OVERWRITE,2}};
    ndfunc_arg_out_t aout[1] = {{cT,2,shape}};
    ndfunc_t ndf = {iter_blas_s_csymm, NO_LOOP, 3, 0, ain, aout};

    args_t g;
    VALUE kw_hash = Qnil;
#if GE
    ID kw_table[5] = {id_alpha,id_beta,id_order,id_transa,id_transb};
#elif TR
    ID kw_table[7] = {id_alpha,id_beta,id_order,id_side,id_uplo,id_transa,id_diag};
#else
    ID kw_table[5] = {id_alpha,id_beta,id_order,id_side,id_uplo};
#endif
    VALUE opts[7] = {Qundef,Qundef,Qundef,Qundef,Qundef,Qundef,Qundef};

    CHECK_FUNC(func_p,"csymm");

    rb_scan_args(argc, argv, "21:", &a, &b, &c, &kw_hash);
    rb_get_kwargs(kw_hash, kw_table, 0, 5+TR*2, opts);
    alpha    = option_value(opts[0],Qnil);
    g.alpha  = RTEST(alpha) ? m_num_to_data(alpha) : m_one;
    beta     = option_value(opts[1],Qnil);
    g.beta   = RTEST(beta)  ? m_num_to_data(beta)  : m_zero;
    g.order  = option_order(opts[2]);
#if GE
    g.transa = option_trans(opts[3]);
    g.transb = option_trans(opts[4]);
#else
    g.side   = option_side(opts[3]);
    g.uplo   = option_uplo(opts[4]);
#endif
#if TR
    g.transa = option_trans(opts[5]);
    g.diag   = option_diag(opts[6]);
#endif

    GetNArray(a,na1);
    GetNArray(b,na2);
    CHECK_DIM_GE(na1,2);
    CHECK_DIM_GE(na2,2);
    ma = ROW_SIZE(na1); // m
    ka = COL_SIZE(na1); // k (lda)
    kb = ROW_SIZE(na2); // k
    nb = COL_SIZE(na2); // n (ldb)

#if GE
    SWAP_IFCOLTR(g.order,g.transa, ma,ka, tmp);
    SWAP_IFCOLTR(g.order,g.transb, kb,nb, tmp);
    CHECK_INT_EQ("ka",ka,"kb",kb);
    g.m = ma;
    g.n = nb;
    g.k = ka;
#else
    CHECK_SQUARE("a",na1); // ma == ka
    SWAP_IFCOL(g.order, kb,nb, tmp);
    // row major             L    R
    //ma = ROW_SIZE(na1); // m or n
    //ka = COL_SIZE(na1); // m or n (lda)
    g.m = kb; // m
    g.n = nb; // n (ldb)
    if (g.side == CblasLeft) {
        CHECK_SIZE_EQ(ka, g.m);
    } else {
        CHECK_SIZE_EQ(ka, g.n);
    }
#endif

    SWAP_IFROW(g.order, ma,nb, tmp);

#if TR
    if (c != Qnil) {
        rb_raise(rb_eArgError,"wrong number of arguments (3 for 2)");
    }
    COPY_OR_CAST_TO(b,cT);
    ndf.nin = 2;

    na_ndloop3(&ndf, &g, 2, a, b);
    return b;
#else

    if (c == Qnil) { // c is not given.
        ndfunc_arg_in_t ain_init = {sym_init,0};
        ain[2] = ain_init;
        ndf.nout = 1;
        c = INT2FIX(0);
        shape[0] = nb;
        shape[1] = ma;
    } else {
        narray_t *na3;
        int nc;
        COPY_OR_CAST_TO(c,cT);
        GetNArray(c,na3);
        CHECK_DIM_GE(na3,2);
        nc = ROW_SIZE(na3);
        if (nc < nb) {
            rb_raise(nary_eShapeError,"nc=%d must be >= nb=%d",nc,nb);
        }
        //CHECK_LEADING_GE("ldc",g.ldc,"m",ma);
    }
    {
        VALUE ans = na_ndloop3(&ndf, &g, 3, a, b, c);

        if (ndf.nout == 1) { // c is not given.
            return ans;
        } else {
            return c;
        }
    }
#endif
}

#undef func_p
#undef args_t
#undef GE
#undef TR


#line 1 "/opt/local/var/macports/build/rb31-numo-linalg-003c080d/work/destroot/opt/local/lib/ruby3.1/gems/3.1.0/gems/numo-linalg-0.1.7/ext/numo/linalg/blas/gen/../tmpl/mm.c"
/**/
#line 7 "/opt/local/var/macports/build/rb31-numo-linalg-003c080d/work/destroot/opt/local/lib/ruby3.1/gems/3.1.0/gems/numo-linalg-0.1.7/ext/numo/linalg/blas/gen/../tmpl/mm.c"
#define GE 0
#define TR 1
#define args_t ctrmm_args_t

typedef struct {
  enum CBLAS_ORDER order;
  enum CBLAS_TRANSPOSE transa, transb;
  enum CBLAS_SIDE side;
  enum CBLAS_UPLO uplo;
  enum CBLAS_DIAG diag;
  dtype alpha, beta;
  blasint m, n, k;
} args_t;

#define func_p ctrmm_p

static ctrmm_t func_p = 0;

static void
iter_blas_s_ctrmm(na_loop_t *const lp)
{
    dtype *a, *b;
    int    lda, ldb;
#if !TR
    dtype *c;
    int    ldc;
#endif
    args_t *g;

    a = (dtype*)NDL_PTR(lp,0);
    b = (dtype*)NDL_PTR(lp,1);
#if !TR
    c = (dtype*)NDL_PTR(lp,2);
#endif
    g = (args_t*)(lp->opt_ptr);

    lda = NDL_STEP(lp,0) / sizeof(dtype);
    ldb = NDL_STEP(lp,1) / sizeof(dtype);
#if !TR
    ldc = NDL_STEP(lp,2) / sizeof(dtype);
#endif

    //printf("m=%d n=%d k=%d\n",g->m,g->n,g->k);

#if GE
    (*func_p)( g->order, g->transa, g->transb, g->m, g->n, g->k,
              DP(g->alpha), a, lda, b, ldb, DP(g->beta), c, ldc);
#elif TR
    (*func_p)( g->order, g->side, g->uplo, g->transa, g->diag, g->m, g->n,
               DP(g->alpha), a, lda, b, ldb);
#else // SY,HE
    (*func_p)( g->order, g->side, g->uplo, g->m, g->n,
               DP(g->alpha), a, lda, b, ldb, DP(g->beta), c, ldc);
#endif
}

/*

  @overload ctrmm(a, b, [alpha:1, side:'L', uplo:'U', transa:'N', diag:'U', order:'R'])
  @param a [Numo::SComplex]  matrix (>=2-dimentional NArray).
  @param b [Numo::SComplex]  matrix (>=2-dimentional NArray).
  @param alpha [Float]  (default=1.0)
  @param beta [Float]  (default=0.0)
  @param side [String or Symbol]  if 'L': op(A)\*B (left-side op), if 'R': B\*op(A) (right-side op). (default='L')
  @param uplo [String or Symbol]  if 'U': Upper triangle, if 'L': Lower triangle. (default='U')
  @param transa [String or Symbol]  if 'N': Not transpose a, if 'T': Transpose a. (default='N')
  @param order [String or Symbol]  if 'R': Row-major, if 'C': Column-major. (default='R')
  @return [Numo::SComplex] returns c = alpha\*op( A )\*op( B ) + beta\*C.
CTRMM  performs one of the matrix-matrix operations

        B := alpha*op( A )*B,   or   B := alpha*B*op( A )

where  alpha  is a scalar,  B  is an m by n matrix,  A  is a unit, or
non-unit,  upper or lower triangular matrix  and  op( A )  is one  of

        op( A ) = A   or   op( A ) = A**T   or   op( A ) = A**H.

*/
static VALUE
blas_s_ctrmm(int argc, VALUE const argv[], VALUE UNUSED(mod))
{
    VALUE     a, b, c=Qnil, alpha, beta;
    narray_t *na1, *na2;
    blasint   ma, ka, kb, nb, tmp;
    size_t    shape[2];
    ndfunc_arg_in_t ain[3] = {{cT,2},{cT,2},{OVERWRITE,2}};
    ndfunc_arg_out_t aout[1] = {{cT,2,shape}};
    ndfunc_t ndf = {iter_blas_s_ctrmm, NO_LOOP, 3, 0, ain, aout};

    args_t g;
    VALUE kw_hash = Qnil;
#if GE
    ID kw_table[5] = {id_alpha,id_beta,id_order,id_transa,id_transb};
#elif TR
    ID kw_table[7] = {id_alpha,id_beta,id_order,id_side,id_uplo,id_transa,id_diag};
#else
    ID kw_table[5] = {id_alpha,id_beta,id_order,id_side,id_uplo};
#endif
    VALUE opts[7] = {Qundef,Qundef,Qundef,Qundef,Qundef,Qundef,Qundef};

    CHECK_FUNC(func_p,"ctrmm");

    rb_scan_args(argc, argv, "21:", &a, &b, &c, &kw_hash);
    rb_get_kwargs(kw_hash, kw_table, 0, 5+TR*2, opts);
    alpha    = option_value(opts[0],Qnil);
    g.alpha  = RTEST(alpha) ? m_num_to_data(alpha) : m_one;
    beta     = option_value(opts[1],Qnil);
    g.beta   = RTEST(beta)  ? m_num_to_data(beta)  : m_zero;
    g.order  = option_order(opts[2]);
#if GE
    g.transa = option_trans(opts[3]);
    g.transb = option_trans(opts[4]);
#else
    g.side   = option_side(opts[3]);
    g.uplo   = option_uplo(opts[4]);
#endif
#if TR
    g.transa = option_trans(opts[5]);
    g.diag   = option_diag(opts[6]);
#endif

    GetNArray(a,na1);
    GetNArray(b,na2);
    CHECK_DIM_GE(na1,2);
    CHECK_DIM_GE(na2,2);
    ma = ROW_SIZE(na1); // m
    ka = COL_SIZE(na1); // k (lda)
    kb = ROW_SIZE(na2); // k
    nb = COL_SIZE(na2); // n (ldb)

#if GE
    SWAP_IFCOLTR(g.order,g.transa, ma,ka, tmp);
    SWAP_IFCOLTR(g.order,g.transb, kb,nb, tmp);
    CHECK_INT_EQ("ka",ka,"kb",kb);
    g.m = ma;
    g.n = nb;
    g.k = ka;
#else
    CHECK_SQUARE("a",na1); // ma == ka
    SWAP_IFCOL(g.order, kb,nb, tmp);
    // row major             L    R
    //ma = ROW_SIZE(na1); // m or n
    //ka = COL_SIZE(na1); // m or n (lda)
    g.m = kb; // m
    g.n = nb; // n (ldb)
    if (g.side == CblasLeft) {
        CHECK_SIZE_EQ(ka, g.m);
    } else {
        CHECK_SIZE_EQ(ka, g.n);
    }
#endif

    SWAP_IFROW(g.order, ma,nb, tmp);

#if TR
    if (c != Qnil) {
        rb_raise(rb_eArgError,"wrong number of arguments (3 for 2)");
    }
    COPY_OR_CAST_TO(b,cT);
    ndf.nin = 2;

    na_ndloop3(&ndf, &g, 2, a, b);
    return b;
#else

    if (c == Qnil) { // c is not given.
        ndfunc_arg_in_t ain_init = {sym_init,0};
        ain[2] = ain_init;
        ndf.nout = 1;
        c = INT2FIX(0);
        shape[0] = nb;
        shape[1] = ma;
    } else {
        narray_t *na3;
        int nc;
        COPY_OR_CAST_TO(c,cT);
        GetNArray(c,na3);
        CHECK_DIM_GE(na3,2);
        nc = ROW_SIZE(na3);
        if (nc < nb) {
            rb_raise(nary_eShapeError,"nc=%d must be >= nb=%d",nc,nb);
        }
        //CHECK_LEADING_GE("ldc",g.ldc,"m",ma);
    }
    {
        VALUE ans = na_ndloop3(&ndf, &g, 3, a, b, c);

        if (ndf.nout == 1) { // c is not given.
            return ans;
        } else {
            return c;
        }
    }
#endif
}

#undef func_p
#undef args_t
#undef GE
#undef TR


#line 1 "/opt/local/var/macports/build/rb31-numo-linalg-003c080d/work/destroot/opt/local/lib/ruby3.1/gems/3.1.0/gems/numo-linalg-0.1.7/ext/numo/linalg/blas/gen/../tmpl/mm.c"
/**/
#line 7 "/opt/local/var/macports/build/rb31-numo-linalg-003c080d/work/destroot/opt/local/lib/ruby3.1/gems/3.1.0/gems/numo-linalg-0.1.7/ext/numo/linalg/blas/gen/../tmpl/mm.c"
#define GE 0
#define TR 0
#define args_t chemm_args_t

typedef struct {
  enum CBLAS_ORDER order;
  enum CBLAS_TRANSPOSE transa, transb;
  enum CBLAS_SIDE side;
  enum CBLAS_UPLO uplo;
  enum CBLAS_DIAG diag;
  dtype alpha, beta;
  blasint m, n, k;
} args_t;

#define func_p chemm_p

static chemm_t func_p = 0;

static void
iter_blas_s_chemm(na_loop_t *const lp)
{
    dtype *a, *b;
    int    lda, ldb;
#if !TR
    dtype *c;
    int    ldc;
#endif
    args_t *g;

    a = (dtype*)NDL_PTR(lp,0);
    b = (dtype*)NDL_PTR(lp,1);
#if !TR
    c = (dtype*)NDL_PTR(lp,2);
#endif
    g = (args_t*)(lp->opt_ptr);

    lda = NDL_STEP(lp,0) / sizeof(dtype);
    ldb = NDL_STEP(lp,1) / sizeof(dtype);
#if !TR
    ldc = NDL_STEP(lp,2) / sizeof(dtype);
#endif

    //printf("m=%d n=%d k=%d\n",g->m,g->n,g->k);

#if GE
    (*func_p)( g->order, g->transa, g->transb, g->m, g->n, g->k,
              DP(g->alpha), a, lda, b, ldb, DP(g->beta), c, ldc);
#elif TR
    (*func_p)( g->order, g->side, g->uplo, g->transa, g->diag, g->m, g->n,
               DP(g->alpha), a, lda, b, ldb);
#else // SY,HE
    (*func_p)( g->order, g->side, g->uplo, g->m, g->n,
               DP(g->alpha), a, lda, b, ldb, DP(g->beta), c, ldc);
#endif
}

/*

  @overload chemm(a, b, [c, alpha:1, beta:0, side:'L', uplo:'U', order:'R'])
  @param a [Numo::SComplex]  matrix (>=2-dimentional NArray).
  @param b [Numo::SComplex]  matrix (>=2-dimentional NArray).
  @param c [Numo::SComplex]  matrix (>=2-dimentional NArray, optional, inplace allowed).
  @param alpha [Float]  (default=1.0)
  @param beta [Float]  (default=0.0)
  @param side [String or Symbol]  if 'L': op(A)\*B (left-side op), if 'R': B\*op(A) (right-side op). (default='L')
  @param uplo [String or Symbol]  if 'U': Upper triangle, if 'L': Lower triangle. (default='U')
  @param order [String or Symbol]  if 'R': Row-major, if 'C': Column-major. (default='R')
  @return [Numo::SComplex] returns c = alpha\*op( A )\*op( B ) + beta\*C.
CHEMM  performs one of the matrix-matrix operations

        C := alpha*A*B + beta*C,

or

        C := alpha*B*A + beta*C,

where alpha and beta are scalars, A is an hermitian matrix and  B and
C are m by n matrices.

*/
static VALUE
blas_s_chemm(int argc, VALUE const argv[], VALUE UNUSED(mod))
{
    VALUE     a, b, c=Qnil, alpha, beta;
    narray_t *na1, *na2;
    blasint   ma, ka, kb, nb, tmp;
    size_t    shape[2];
    ndfunc_arg_in_t ain[3] = {{cT,2},{cT,2},{OVERWRITE,2}};
    ndfunc_arg_out_t aout[1] = {{cT,2,shape}};
    ndfunc_t ndf = {iter_blas_s_chemm, NO_LOOP, 3, 0, ain, aout};

    args_t g;
    VALUE kw_hash = Qnil;
#if GE
    ID kw_table[5] = {id_alpha,id_beta,id_order,id_transa,id_transb};
#elif TR
    ID kw_table[7] = {id_alpha,id_beta,id_order,id_side,id_uplo,id_transa,id_diag};
#else
    ID kw_table[5] = {id_alpha,id_beta,id_order,id_side,id_uplo};
#endif
    VALUE opts[7] = {Qundef,Qundef,Qundef,Qundef,Qundef,Qundef,Qundef};

    CHECK_FUNC(func_p,"chemm");

    rb_scan_args(argc, argv, "21:", &a, &b, &c, &kw_hash);
    rb_get_kwargs(kw_hash, kw_table, 0, 5+TR*2, opts);
    alpha    = option_value(opts[0],Qnil);
    g.alpha  = RTEST(alpha) ? m_num_to_data(alpha) : m_one;
    beta     = option_value(opts[1],Qnil);
    g.beta   = RTEST(beta)  ? m_num_to_data(beta)  : m_zero;
    g.order  = option_order(opts[2]);
#if GE
    g.transa = option_trans(opts[3]);
    g.transb = option_trans(opts[4]);
#else
    g.side   = option_side(opts[3]);
    g.uplo   = option_uplo(opts[4]);
#endif
#if TR
    g.transa = option_trans(opts[5]);
    g.diag   = option_diag(opts[6]);
#endif

    GetNArray(a,na1);
    GetNArray(b,na2);
    CHECK_DIM_GE(na1,2);
    CHECK_DIM_GE(na2,2);
    ma = ROW_SIZE(na1); // m
    ka = COL_SIZE(na1); // k (lda)
    kb = ROW_SIZE(na2); // k
    nb = COL_SIZE(na2); // n (ldb)

#if GE
    SWAP_IFCOLTR(g.order,g.transa, ma,ka, tmp);
    SWAP_IFCOLTR(g.order,g.transb, kb,nb, tmp);
    CHECK_INT_EQ("ka",ka,"kb",kb);
    g.m = ma;
    g.n = nb;
    g.k = ka;
#else
    CHECK_SQUARE("a",na1); // ma == ka
    SWAP_IFCOL(g.order, kb,nb, tmp);
    // row major             L    R
    //ma = ROW_SIZE(na1); // m or n
    //ka = COL_SIZE(na1); // m or n (lda)
    g.m = kb; // m
    g.n = nb; // n (ldb)
    if (g.side == CblasLeft) {
        CHECK_SIZE_EQ(ka, g.m);
    } else {
        CHECK_SIZE_EQ(ka, g.n);
    }
#endif

    SWAP_IFROW(g.order, ma,nb, tmp);

#if TR
    if (c != Qnil) {
        rb_raise(rb_eArgError,"wrong number of arguments (3 for 2)");
    }
    COPY_OR_CAST_TO(b,cT);
    ndf.nin = 2;

    na_ndloop3(&ndf, &g, 2, a, b);
    return b;
#else

    if (c == Qnil) { // c is not given.
        ndfunc_arg_in_t ain_init = {sym_init,0};
        ain[2] = ain_init;
        ndf.nout = 1;
        c = INT2FIX(0);
        shape[0] = nb;
        shape[1] = ma;
    } else {
        narray_t *na3;
        int nc;
        COPY_OR_CAST_TO(c,cT);
        GetNArray(c,na3);
        CHECK_DIM_GE(na3,2);
        nc = ROW_SIZE(na3);
        if (nc < nb) {
            rb_raise(nary_eShapeError,"nc=%d must be >= nb=%d",nc,nb);
        }
        //CHECK_LEADING_GE("ldc",g.ldc,"m",ma);
    }
    {
        VALUE ans = na_ndloop3(&ndf, &g, 3, a, b, c);

        if (ndf.nout == 1) { // c is not given.
            return ans;
        } else {
            return c;
        }
    }
#endif
}

#undef func_p
#undef args_t
#undef GE
#undef TR


#line 1 "/opt/local/var/macports/build/rb31-numo-linalg-003c080d/work/destroot/opt/local/lib/ruby3.1/gems/3.1.0/gems/numo-linalg-0.1.7/ext/numo/linalg/blas/gen/../tmpl/syrk.c"
/**/
#line 8 "/opt/local/var/macports/build/rb31-numo-linalg-003c080d/work/destroot/opt/local/lib/ruby3.1/gems/3.1.0/gems/numo-linalg-0.1.7/ext/numo/linalg/blas/gen/../tmpl/syrk.c"
#define P(a) DP(a)

#line 11 "/opt/local/var/macports/build/rb31-numo-linalg-003c080d/work/destroot/opt/local/lib/ruby3.1/gems/3.1.0/gems/numo-linalg-0.1.7/ext/numo/linalg/blas/gen/../tmpl/syrk.c"
#define args_t csyrk_args_t

typedef struct {
    enum CBLAS_ORDER order;
    enum CBLAS_UPLO uplo;
    enum CBLAS_TRANSPOSE trans;
    dtype alpha, beta;
    blasint n, k;
} args_t;

#define func_p csyrk_p

static csyrk_t func_p = 0;

static void
iter_blas_s_csyrk(na_loop_t *const lp)
{
    dtype *a, *c;
    args_t *g;
    blasint lda, ldc;

    a = (dtype*)NDL_PTR(lp,0);
    c = (dtype*)NDL_PTR(lp,1);
    g = (args_t*)(lp->opt_ptr);

    lda = NDL_STEP(lp,0) / sizeof(dtype);
    ldc = NDL_STEP(lp,1) / sizeof(dtype);

    (*func_p)(g->order, g->uplo, g->trans, g->n, g->k,
              P(g->alpha), a, lda, P(g->beta), c, ldc);
}

/*
  @overload csyrk( a, [c, alpha:1, beta:0, uplo:'U', trans:'N', order:'R'] )
  @param a [Numo::SComplex]  matrix (>=2-dimentional NArray, n-by-k, inpace).
  @param c [Numo::SComplex]  matrix (>=2-dimentional NArray, n-by-n, optional, inpace).
  @param alpha [Float]  (default=1.0)
  @param beta [Float]  (default=0.0)
  @param uplo [String or Symbol]  if 'U': Upper triangle, if 'L': Lower triangle. (default='U')
  @param trans [String or Symbol]  if 'N': Not transpose , if 'T': Transpose . (default='N')
  @param order [String or Symbol]  if 'R': Row-major, if 'C': Column-major. (default='R')
  @return [Numo::SComplex] returns c.

CSYRK  performs one of the symmetric rank k operations

        C := alpha*A*A**T + beta*C,

or

        C := alpha*A**T*A + beta*C,

where  alpha and beta  are scalars,  C is an  n by n symmetric matrix
and  A  is an  n by k  matrix in the first case and a  k by n  matrix
in the second case.

 */
static VALUE
blas_s_csyrk(int argc, VALUE const argv[], VALUE UNUSED(mod))
{
    VALUE     ans;
    VALUE     a, c, alpha, beta;
    narray_t *na1, *na3;
    blasint   na, ka, nc, tmp;
    size_t    shape[2];
    ndfunc_arg_in_t ain[3] = {{cT,2},{OVERWRITE,2},{sym_init,0}};
    ndfunc_arg_out_t aout[1] = {{cT,2,shape}};
    ndfunc_t ndf = {iter_blas_s_csyrk, NO_LOOP, 2, 0, ain, aout};

    args_t g;
    VALUE kw_hash = Qnil;
    ID kw_table[5] = {id_alpha,id_beta,id_order,id_uplo,id_trans};
    VALUE opts[5] = {Qundef,Qundef,Qundef,Qundef,Qundef};

    CHECK_FUNC(func_p,"csyrk");

    rb_scan_args(argc, argv, "11:", &a, &c, &kw_hash);
    rb_get_kwargs(kw_hash, kw_table, 0, 5, opts);
    alpha   = option_value(opts[0],Qnil);
    beta    = option_value(opts[1],Qnil);
#line 88 "/opt/local/var/macports/build/rb31-numo-linalg-003c080d/work/destroot/opt/local/lib/ruby3.1/gems/3.1.0/gems/numo-linalg-0.1.7/ext/numo/linalg/blas/gen/../tmpl/syrk.c"
    g.alpha = RTEST(alpha) ? m_num_to_data(alpha) : m_one;
    g.beta  = RTEST(beta)  ? m_num_to_data(beta)  : m_zero;
#line 91 "/opt/local/var/macports/build/rb31-numo-linalg-003c080d/work/destroot/opt/local/lib/ruby3.1/gems/3.1.0/gems/numo-linalg-0.1.7/ext/numo/linalg/blas/gen/../tmpl/syrk.c"
    g.order = option_order(opts[2]);
    g.uplo  = option_uplo(opts[3]);
    g.trans = option_trans(opts[4]);

    GetNArray(a,na1);
    CHECK_DIM_GE(na1,2);

    na = ROW_SIZE(na1); // n
    ka = COL_SIZE(na1); // k (lda)
    SWAP_IFCOLTR(g.order,g.trans, na,ka, tmp);
    g.n = na;
    g.k = ka;

    if (c == Qnil) { // c is not given.
        ndf.nout = 1;
        ain[1] = ain[2];
        c = INT2FIX(0);
        shape[0] = na;
        shape[1] = na;
    } else {
        COPY_OR_CAST_TO(c,cT);
        GetNArray(c,na3);
        CHECK_DIM_GE(na3,2);
        nc = ROW_SIZE(na3);
        if (nc < na) {
            rb_raise(nary_eShapeError,"nc=%d must be >= na=%d",nc,na);
        }
        //CHECK_LEADING_GE("ldc",g.ldc,"n",na);
    }

    ans = na_ndloop3(&ndf, &g, 2, a, c);

    if (ndf.nout == 1) { // c is not given.
        return ans;
    } else {
        return c;
    }
}

#undef func_p
#undef args_t
#undef P


#line 1 "/opt/local/var/macports/build/rb31-numo-linalg-003c080d/work/destroot/opt/local/lib/ruby3.1/gems/3.1.0/gems/numo-linalg-0.1.7/ext/numo/linalg/blas/gen/../tmpl/syr2k.c"
#define args_t csyr2k_args_t

typedef struct {
    enum CBLAS_ORDER order;
    enum CBLAS_UPLO uplo;
    enum CBLAS_TRANSPOSE trans;
    dtype alpha, beta;
    blasint n, k;
} args_t;

#define func_p csyr2k_p

static csyr2k_t func_p = 0;

static void
iter_blas_s_csyr2k(na_loop_t *const lp)
{
    dtype *a, *b, *c;
    blasint lda, ldb, ldc;
    args_t *g;

    a = (dtype*)NDL_PTR(lp,0);
    b = (dtype*)NDL_PTR(lp,1);
    c = (dtype*)NDL_PTR(lp,2);
    g = (args_t*)(lp->opt_ptr);

    lda = NDL_STEP(lp,0) / sizeof(dtype);
    ldb = NDL_STEP(lp,1) / sizeof(dtype);
    ldc = NDL_STEP(lp,2) / sizeof(dtype);

    (*func_p)(g->order, g->uplo, g->trans, g->n, g->k,
              DP(g->alpha), a, lda, b, ldb, DP(g->beta), c, ldc);
}

/*
  @overload csyr2k( a, b, [c, alpha:1, beta:0, uplo:'U', trans:'N', order:'R'] )
  @param a [Numo::SComplex]  matrix (>=2-dimentional NArray, n-by-k).
  @param b [Numo::SComplex]  matrix (>=2-dimentional NArray, n-by-k).
  @param c [Numo::SComplex]  matrix (>=2-dimentional NArray, n-by-n, optional, inpace).
  @param alpha [Float]  (default=1.0)
  @param beta [Float]  (default=0.0)
  @param uplo [String or Symbol]  if 'U': Upper triangle, if 'L': Lower triangle. (default='U')
  @param trans [String or Symbol]  if 'N': Not transpose , if 'T': Transpose . (default='N')
  @param order [String or Symbol]  if 'R': Row-major, if 'C': Column-major. (default='R')
  @return [Numo::SComplex] returns c.

CSYR2K  performs one of the symmetric rank 2k operations

        C := alpha*A*B**T + alpha*B*A**T + beta*C,

or

        C := alpha*A**T*B + alpha*B**T*A + beta*C,

where  alpha and beta  are scalars,  C is an  n by n symmetric matrix
and  A and B  are  n by k  matrices  in the  first  case  and  k by n
matrices in the second case.

 */
static VALUE
blas_s_csyr2k(int argc, VALUE const argv[], VALUE UNUSED(mod))
{
    VALUE     ans;
    VALUE     a, b, c=Qnil, alpha, beta;
    narray_t *na1, *na2, *na3;
    blasint   na, ka, kb, nb, nc, tmp;
    size_t    shape[2];
    ndfunc_arg_in_t ain[4] = {{cT,2},{cT,2},{OVERWRITE,2},{sym_init,0}};
    ndfunc_arg_out_t aout[1] = {{cT,2,shape}};
    ndfunc_t ndf = {iter_blas_s_csyr2k, NO_LOOP, 3, 0, ain, aout};

    args_t g;
    VALUE kw_hash = Qnil;
    ID kw_table[5] = {id_alpha,id_beta,id_order,id_uplo,id_trans};
    VALUE opts[5] = {Qundef,Qundef,Qundef,Qundef,Qundef};

    CHECK_FUNC(func_p,"csyr2k");

    rb_scan_args(argc, argv, "21:", &a, &b, &c, &kw_hash);
    rb_get_kwargs(kw_hash, kw_table, 0, 5, opts);
    alpha    = option_value(opts[0],Qnil);
    g.alpha  = RTEST(alpha) ? m_num_to_data(alpha) : m_one;
    beta     = option_value(opts[1],Qnil);
    g.beta   = RTEST(beta)  ? m_num_to_data(beta)  : m_zero;
    g.order  = option_order(opts[2]);
    g.uplo   = option_uplo(opts[3]);
    g.trans  = option_trans(opts[4]);

    GetNArray(a,na1);
    GetNArray(b,na2);
    CHECK_DIM_GE(na1,2);
    CHECK_DIM_GE(na2,2);

    na = ROW_SIZE(na1); // n
    ka = COL_SIZE(na1); // k (lda)
    SWAP_IFCOLTR(g.order, g.trans, na, ka, tmp);

    nb = ROW_SIZE(na2); // n
    kb = COL_SIZE(na2); // k (ldb)
    SWAP_IFCOLTR(g.order, g.trans, kb, nb, tmp);
    CHECK_INT_EQ("na",na,"nb",nb);
    CHECK_INT_EQ("ka",ka,"kb",kb);
    g.n = nb;
    g.k = kb;

    SWAP_IFROW(g.order, na, nb, tmp);

    if (c == Qnil) { // c is not given.
        ndf.nout = 1;
        ain[2] = ain[3];
        c = INT2FIX(0);
        shape[0] = nb;
        shape[1] = na;
    } else {
        COPY_OR_CAST_TO(c,cT);
        GetNArray(c,na3);
        CHECK_DIM_GE(na3,2);
        nc = ROW_SIZE(na3); // n
        if (nc < nb) {
            rb_raise(nary_eShapeError,"nc=%d must be >= nb=%d",nc,nb);
        }
        //CHECK_LEADING_GE("ldc",g.ldc,"n",na);
    }

    ans = na_ndloop3(&ndf, &g, 3, a, b, c);

    if (ndf.nout = 1) { // c is not given.
        return ans;
    } else {
        return c;
    }
}

#undef func_p
#undef args_t



#line 27 "/opt/local/var/macports/build/rb31-numo-linalg-003c080d/work/destroot/opt/local/lib/ruby3.1/gems/3.1.0/gems/numo-linalg-0.1.7/ext/numo/linalg/blas/gen/../tmpl/lib.c"
void
Init_numo_linalg_blas_c(void)
{
    VALUE mN;

    mN = rb_define_module("Numo");

    
    id_alpha = rb_intern("alpha");
    id_axis = rb_intern("axis");
    id_beta = rb_intern("beta");
    id_diag = rb_intern("diag");
    id_imag = rb_intern("imag");
    id_keepdims = rb_intern("keepdims");
    id_order = rb_intern("order");
    id_real = rb_intern("real");
    id_sb = rb_intern("sb");
    id_side = rb_intern("side");
    id_trans = rb_intern("trans");
    id_transa = rb_intern("transa");
    id_transb = rb_intern("transb");
    id_uplo = rb_intern("uplo");


#line 1 "/opt/local/var/macports/build/rb31-numo-linalg-003c080d/work/destroot/opt/local/lib/ruby3.1/gems/3.1.0/gems/numo-linalg-0.1.7/ext/numo/linalg/blas/gen/../tmpl/init_module.c"
    /*
      Document-module: Numo::Linalg
      
    */
    
    mLinalg = rb_define_module_under(mN, "Linalg");
    
    

#line 11 "/opt/local/var/macports/build/rb31-numo-linalg-003c080d/work/destroot/opt/local/lib/ruby3.1/gems/3.1.0/gems/numo-linalg-0.1.7/ext/numo/linalg/blas/gen/../tmpl/init_module.c"
    //  how to do this?
    //rb_extend_object(cT, mTM);

#line 1 "/opt/local/var/macports/build/rb31-numo-linalg-003c080d/work/destroot/opt/local/lib/ruby3.1/gems/3.1.0/gems/numo-linalg-0.1.7/ext/numo/linalg/blas/gen/../tmpl/init_module.c"
    /*
      Document-module: Numo::Linalg::Blas
      
    */
    
    mBlas = rb_define_module_under(mLinalg, "Blas");
    
    
    
    rb_define_module_function(mBlas, "cdotc", blas_s_cdotc, 2);
    rb_define_module_function(mBlas, "cdotu", blas_s_cdotu, 2);
    rb_define_module_function(mBlas, "scnrm2", blas_s_scnrm2, -1);
    rb_define_module_function(mBlas, "scasum", blas_s_scasum, -1);
    rb_define_module_function(mBlas, "cswap", blas_s_cswap, 2);
    rb_define_module_function(mBlas, "ccopy", blas_s_ccopy, 2);
    rb_define_module_function(mBlas, "caxpy", blas_s_caxpy, -1);
    rb_define_module_function(mBlas, "cscal", blas_s_cscal, 2);
    rb_define_module_function(mBlas, "csscal", blas_s_csscal, 2);
    rb_define_module_function(mBlas, "cgemv", blas_s_cgemv, -1);
    rb_define_module_function(mBlas, "ctrmv", blas_s_ctrmv, -1);
    rb_define_module_function(mBlas, "chemv", blas_s_chemv, -1);
    rb_define_module_function(mBlas, "cgerc", blas_s_cgerc, -1);
    rb_define_module_function(mBlas, "cgeru", blas_s_cgeru, -1);
    rb_define_module_function(mBlas, "cher", blas_s_cher, -1);
    rb_define_module_function(mBlas, "cher2", blas_s_cher2, -1);
    rb_define_module_function(mBlas, "cherk", blas_s_cherk, -1);
    rb_define_module_function(mBlas, "cgemm", blas_s_cgemm, -1);
    rb_define_module_function(mBlas, "csymm", blas_s_csymm, -1);
    rb_define_module_function(mBlas, "ctrmm", blas_s_ctrmm, -1);
    rb_define_module_function(mBlas, "chemm", blas_s_chemm, -1);
    rb_define_module_function(mBlas, "csyrk", blas_s_csyrk, -1);
    rb_define_module_function(mBlas, "csyr2k", blas_s_csyr2k, -1);

#line 11 "/opt/local/var/macports/build/rb31-numo-linalg-003c080d/work/destroot/opt/local/lib/ruby3.1/gems/3.1.0/gems/numo-linalg-0.1.7/ext/numo/linalg/blas/gen/../tmpl/init_module.c"
    //  how to do this?
    //rb_extend_object(cT, mTM);
#line 40 "/opt/local/var/macports/build/rb31-numo-linalg-003c080d/work/destroot/opt/local/lib/ruby3.1/gems/3.1.0/gems/numo-linalg-0.1.7/ext/numo/linalg/blas/gen/../tmpl/lib.c"
}
