MAGMA  1.2.0
MatrixAlgebraonGPUandMulticoreArchitectures
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Macros Groups
dgetrs_gpu.cpp
Go to the documentation of this file.
1 /*
2  -- MAGMA (version 1.2.0) --
3  Univ. of Tennessee, Knoxville
4  Univ. of California, Berkeley
5  Univ. of Colorado, Denver
6  May 2012
7 
8  @generated d Thu May 10 22:26:47 2012
9 
10 */
11 #include "common_magma.h"
12 
13 // === Define what BLAS to use ============================================
14 #define PRECISION_d
15 #if (defined(PRECISION_s) || defined(PRECISION_d))
16  #define magma_dtrsm magmablas_dtrsm
17 #endif
18 // === End defining what BLAS to use =======================================
19 
20 extern "C" magma_int_t
22  double *dA, magma_int_t ldda,
23  magma_int_t *ipiv,
24  double *dB, magma_int_t lddb,
25  magma_int_t *info)
26 {
27 /* -- MAGMA (version 1.2.0) --
28  Univ. of Tennessee, Knoxville
29  Univ. of California, Berkeley
30  Univ. of Colorado, Denver
31  May 2012
32 
33  Purpose
34  =======
35 
36  Solves a system of linear equations
37  A * X = B or A' * X = B
38  with a general N-by-N matrix A using the LU factorization computed by DGETRF_GPU.
39 
40  Arguments
41  =========
42 
43  TRANS (input) CHARACTER*1
44  Specifies the form of the system of equations:
45  = 'N': A * X = B (No transpose)
46  = 'T': A'* X = B (Transpose)
47  = 'C': A'* X = B (Conjugate transpose = Transpose)
48 
49  N (input) INTEGER
50  The order of the matrix A. N >= 0.
51 
52  NRHS (input) INTEGER
53  The number of right hand sides, i.e., the number of columns
54  of the matrix B. NRHS >= 0.
55 
56  A (input) DOUBLE_PRECISION array on the GPU, dimension (LDA,N)
57  The factors L and U from the factorization A = P*L*U as computed
58  by DGETRF_GPU.
59 
60  LDA (input) INTEGER
61  The leading dimension of the array A. LDA >= max(1,N).
62 
63  IPIV (input) INTEGER array, dimension (N)
64  The pivot indices from DGETRF; for 1<=i<=N, row i of the
65  matrix was interchanged with row IPIV(i).
66 
67  B (input/output) DOUBLE_PRECISION array on the GPU, dimension (LDB,NRHS)
68  On entry, the right hand side matrix B.
69  On exit, the solution matrix X.
70 
71  LDB (input) INTEGER
72  The leading dimension of the array B. LDB >= max(1,N).
73 
74  INFO (output) INTEGER
75  = 0: successful exit
76  < 0: if INFO = -i, the i-th argument had an illegal value
77 
78  HWORK (workspace) DOUBLE_PRECISION array, dimension N*NRHS
79  ===================================================================== */
80 
81 
82  double c_one = MAGMA_D_ONE;
83  double *work = NULL;
84  char trans_[2] = {trans, 0};
85  long int notran = lapackf77_lsame(trans_, "N");
86  magma_int_t i1, i2, inc;
87 
88  *info = 0;
89  if ( (! notran) &&
90  (! lapackf77_lsame(trans_, "T")) &&
91  (! lapackf77_lsame(trans_, "C")) ) {
92  *info = -1;
93  } else if (n < 0) {
94  *info = -2;
95  } else if (nrhs < 0) {
96  *info = -3;
97  } else if (ldda < max(1,n)) {
98  *info = -5;
99  } else if (lddb < max(1,n)) {
100  *info = -8;
101  }
102  if (*info != 0) {
103  magma_xerbla( __func__, -(*info) );
104  return *info;
105  }
106 
107  /* Quick return if possible */
108  if (n == 0 || nrhs == 0) {
109  return *info;
110  }
111 
112  work = (double*)malloc(n * nrhs * sizeof(double));
113  if ( !work ) {
114  *info = MAGMA_ERR_HOST_ALLOC;
115  return *info;
116  }
117 
118  i1 = 1;
119  i2 = n;
120  if (notran) {
121  inc = 1;
122 
123  /* Solve A * X = B. */
124  magma_dgetmatrix( n, nrhs, dB, lddb, work, n );
125  lapackf77_dlaswp(&nrhs, work, &n, &i1, &i2, ipiv, &inc);
126  magma_dsetmatrix( n, nrhs, work, n, dB, lddb );
127 
128  if ( nrhs == 1) {
129  magma_dtrsv(MagmaLower, MagmaNoTrans, MagmaUnit, n, dA, ldda, dB, 1 );
130  magma_dtrsv(MagmaUpper, MagmaNoTrans, MagmaNonUnit, n, dA, ldda, dB, 1 );
131  } else {
132  magma_dtrsm(MagmaLeft, MagmaLower, MagmaNoTrans, MagmaUnit, n, nrhs, c_one, dA, ldda, dB, lddb );
133  magma_dtrsm(MagmaLeft, MagmaUpper, MagmaNoTrans, MagmaNonUnit, n, nrhs, c_one, dA, ldda, dB, lddb );
134  }
135  } else {
136  inc = -1;
137 
138  /* Solve A' * X = B. */
139  if ( nrhs == 1) {
140  magma_dtrsv(MagmaUpper, trans, MagmaNonUnit, n, dA, ldda, dB, 1 );
141  magma_dtrsv(MagmaLower, trans, MagmaUnit, n, dA, ldda, dB, 1 );
142  } else {
143  magma_dtrsm(MagmaLeft, MagmaUpper, trans, MagmaNonUnit, n, nrhs, c_one, dA, ldda, dB, lddb );
144  magma_dtrsm(MagmaLeft, MagmaLower, trans, MagmaUnit, n, nrhs, c_one, dA, ldda, dB, lddb );
145  }
146 
147  magma_dgetmatrix( n, nrhs, dB, lddb, work, n );
148  lapackf77_dlaswp(&nrhs, work, &n, &i1, &i2, ipiv, &inc);
149  magma_dsetmatrix( n, nrhs, work, n, dB, lddb );
150  }
151  free(work);
152 
153  return *info;
154 }
155