Skip to content

Commit 467a9e0

Browse files
{C,Z}LARFGP: re-scale input vector more often
Re-scale the input vector even if `X` is negligibly small in norm if the imaginary part of `ALPHA` is nonzero. For otherwise `XNORM` will not be computed with a small _relative_ error. fixes Reference-LAPACK#980
1 parent 6621e8c commit 467a9e0

File tree

2 files changed

+20
-40
lines changed

2 files changed

+20
-40
lines changed

SRC/clarfgp.f

+10-20
Original file line numberDiff line numberDiff line change
@@ -148,33 +148,23 @@ SUBROUTINE CLARFGP( N, ALPHA, X, INCX, TAU )
148148
ALPHR = REAL( ALPHA )
149149
ALPHI = AIMAG( ALPHA )
150150
*
151-
IF( XNORM.LE.EPS*ABS(ALPHA) ) THEN
151+
IF( XNORM.LE.EPS*ABS(ALPHA) .AND. ALPHI.EQ.ZERO ) THEN
152152
*
153153
* H = [1-alpha/abs(alpha) 0; 0 I], sign chosen so ALPHA >= 0.
154154
*
155-
IF( ALPHI.EQ.ZERO ) THEN
156-
IF( ALPHR.GE.ZERO ) THEN
157-
* When TAU.eq.ZERO, the vector is special-cased to be
158-
* all zeros in the application routines. We do not need
159-
* to clear it.
160-
TAU = ZERO
161-
ELSE
162-
* However, the application routines rely on explicit
163-
* zero checks when TAU.ne.ZERO, and we must clear X.
164-
TAU = TWO
165-
DO J = 1, N-1
166-
X( 1 + (J-1)*INCX ) = ZERO
167-
END DO
168-
ALPHA = -ALPHA
169-
END IF
155+
IF( ALPHR.GE.ZERO ) THEN
156+
* When TAU.eq.ZERO, the vector is special-cased to be
157+
* all zeros in the application routines. We do not need
158+
* to clear it.
159+
TAU = ZERO
170160
ELSE
171-
* Only "reflecting" the diagonal entry to be real and non-negative.
172-
XNORM = SLAPY2( ALPHR, ALPHI )
173-
TAU = CMPLX( ONE - ALPHR / XNORM, -ALPHI / XNORM )
161+
* However, the application routines rely on explicit
162+
* zero checks when TAU.ne.ZERO, and we must clear X.
163+
TAU = TWO
174164
DO J = 1, N-1
175165
X( 1 + (J-1)*INCX ) = ZERO
176166
END DO
177-
ALPHA = XNORM
167+
ALPHA = -ALPHA
178168
END IF
179169
ELSE
180170
*

SRC/zlarfgp.f

+10-20
Original file line numberDiff line numberDiff line change
@@ -148,33 +148,23 @@ SUBROUTINE ZLARFGP( N, ALPHA, X, INCX, TAU )
148148
ALPHR = DBLE( ALPHA )
149149
ALPHI = DIMAG( ALPHA )
150150
*
151-
IF( XNORM.LE.EPS*ABS(ALPHA) ) THEN
151+
IF( XNORM.LE.EPS*ABS(ALPHA) .AND. ALPHI.EQ.ZERO ) THEN
152152
*
153153
* H = [1-alpha/abs(alpha) 0; 0 I], sign chosen so ALPHA >= 0.
154154
*
155-
IF( ALPHI.EQ.ZERO ) THEN
156-
IF( ALPHR.GE.ZERO ) THEN
157-
* When TAU.eq.ZERO, the vector is special-cased to be
158-
* all zeros in the application routines. We do not need
159-
* to clear it.
160-
TAU = ZERO
161-
ELSE
162-
* However, the application routines rely on explicit
163-
* zero checks when TAU.ne.ZERO, and we must clear X.
164-
TAU = TWO
165-
DO J = 1, N-1
166-
X( 1 + (J-1)*INCX ) = ZERO
167-
END DO
168-
ALPHA = -ALPHA
169-
END IF
155+
IF( ALPHR.GE.ZERO ) THEN
156+
* When TAU.eq.ZERO, the vector is special-cased to be
157+
* all zeros in the application routines. We do not need
158+
* to clear it.
159+
TAU = ZERO
170160
ELSE
171-
* Only "reflecting" the diagonal entry to be real and non-negative.
172-
XNORM = DLAPY2( ALPHR, ALPHI )
173-
TAU = DCMPLX( ONE - ALPHR / XNORM, -ALPHI / XNORM )
161+
* However, the application routines rely on explicit
162+
* zero checks when TAU.ne.ZERO, and we must clear X.
163+
TAU = TWO
174164
DO J = 1, N-1
175165
X( 1 + (J-1)*INCX ) = ZERO
176166
END DO
177-
ALPHA = XNORM
167+
ALPHA = -ALPHA
178168
END IF
179169
ELSE
180170
*

0 commit comments

Comments
 (0)