117
117
subroutine CLARTG ( f , g , c , s , r )
118
118
use LA_CONSTANTS, &
119
119
only: wp= >sp, zero= >szero, one= >sone, two= >stwo, czero, &
120
- rtmin = >srtmin, rtmax = >srtmax, safmin= >ssafmin, safmax= >ssafmax
120
+ safmin= >ssafmin, safmax= >ssafmax
121
121
!
122
122
! -- LAPACK auxiliary routine (version 3.10.0) --
123
123
! -- LAPACK is a software package provided by Univ. of Tennessee, --
@@ -129,7 +129,7 @@ subroutine CLARTG( f, g, c, s, r )
129
129
complex (wp) f, g, r, s
130
130
! ..
131
131
! .. Local Scalars ..
132
- real (wp) :: d, f1, f2, g1, g2, h2, u, v, w
132
+ real (wp) :: d, f1, f2, g1, g2, h2, u, v, w, rtmin, rtmax
133
133
complex (wp) :: fs, gs, t
134
134
! ..
135
135
! .. Intrinsic Functions ..
@@ -141,6 +141,9 @@ subroutine CLARTG( f, g, c, s, r )
141
141
! .. Statement Function definitions ..
142
142
ABSSQ( t ) = real ( t )** 2 + aimag ( t )** 2
143
143
! ..
144
+ ! .. Constants ..
145
+ rtmin = sqrt ( safmin )
146
+ ! ..
144
147
! .. Executable Statements ..
145
148
!
146
149
if ( g == czero ) then
@@ -150,6 +153,7 @@ subroutine CLARTG( f, g, c, s, r )
150
153
else if ( f == czero ) then
151
154
c = zero
152
155
g1 = max ( abs (real (g)), abs (aimag (g)) )
156
+ rtmax = sqrt ( safmax/ 2 )
153
157
if ( g1 > rtmin .and. g1 < rtmax ) then
154
158
!
155
159
! Use unscaled algorithm
@@ -170,6 +174,7 @@ subroutine CLARTG( f, g, c, s, r )
170
174
else
171
175
f1 = max ( abs (real (f)), abs (aimag (f)) )
172
176
g1 = max ( abs (real (g)), abs (aimag (g)) )
177
+ rtmax = sqrt ( safmax/ 4 )
173
178
if ( f1 > rtmin .and. f1 < rtmax .and. &
174
179
g1 > rtmin .and. g1 < rtmax ) then
175
180
!
@@ -178,14 +183,36 @@ subroutine CLARTG( f, g, c, s, r )
178
183
f2 = ABSSQ( f )
179
184
g2 = ABSSQ( g )
180
185
h2 = f2 + g2
181
- if ( f2 > rtmin .and. h2 < rtmax ) then
182
- d = sqrt ( f2* h2 )
186
+ ! safmin <= f2 <= h2 <= safmax
187
+ if ( f2 >= h2 * safmin ) then
188
+ ! safmin <= f2/h2 <= 1, and h2/f2 is finite
189
+ c = sqrt ( f2 / h2 )
190
+ r = f / c
191
+ rtmax = rtmax * 2
192
+ if ( f2 > rtmin .and. h2 < rtmax ) then
193
+ ! safmin <= sqrt( f2*h2 ) <= safmax
194
+ s = conjg ( g ) * ( f / sqrt ( f2* h2 ) )
195
+ else
196
+ s = conjg ( g ) * ( r / h2 )
197
+ end if
183
198
else
184
- d = sqrt ( f2 )* sqrt ( h2 )
199
+ ! f2/h2 <= safmin may be subnormal, and h2/f2 may overflow.
200
+ ! Moreover,
201
+ ! safmin <= f2*f2 * safmax < f2 * h2 < h2*h2 * safmin <= safmax,
202
+ ! sqrt(safmin) <= sqrt(f2 * h2) <= sqrt(safmax).
203
+ ! Also,
204
+ ! g2 >> f2, which means that h2 = g2.
205
+ d = sqrt ( f2 * h2 )
206
+ c = f2 / d
207
+ if ( c >= safmin ) then
208
+ r = f / c
209
+ else
210
+ ! f2 / sqrt(f2 * h2) < safmin, then
211
+ ! h2 / sqrt(f2 * h2) <= h2 * (safmin / f2) <= h2 <= safmax
212
+ r = f * ( h2 / d )
213
+ end if
214
+ s = conjg ( g ) * ( f / d )
185
215
end if
186
- c = f2 / d
187
- s = conjg ( g )* ( f / d )
188
- r = f* ( h2 / d )
189
216
else
190
217
!
191
218
! Use scaled algorithm
@@ -212,14 +239,39 @@ subroutine CLARTG( f, g, c, s, r )
212
239
f2 = ABSSQ( fs )
213
240
h2 = f2 + g2
214
241
end if
215
- if ( f2 > rtmin .and. h2 < rtmax ) then
216
- d = sqrt ( f2* h2 )
242
+ ! safmin <= f2 <= h2 <= safmax
243
+ if ( f2 >= h2 * safmin ) then
244
+ ! safmin <= f2/h2 <= 1, and h2/f2 is finite
245
+ c = sqrt ( f2 / h2 )
246
+ r = fs / c
247
+ rtmax = rtmax * 2
248
+ if ( f2 > rtmin .and. h2 < rtmax ) then
249
+ ! safmin <= sqrt( f2*h2 ) <= safmax
250
+ s = conjg ( gs ) * ( fs / sqrt ( f2* h2 ) )
251
+ else
252
+ s = conjg ( gs ) * ( r / h2 )
253
+ end if
217
254
else
218
- d = sqrt ( f2 )* sqrt ( h2 )
255
+ ! f2/h2 <= safmin may be subnormal, and h2/f2 may overflow.
256
+ ! Moreover,
257
+ ! safmin <= f2*f2 * safmax < f2 * h2 < h2*h2 * safmin <= safmax,
258
+ ! sqrt(safmin) <= sqrt(f2 * h2) <= sqrt(safmax).
259
+ ! Also,
260
+ ! g2 >> f2, which means that h2 = g2.
261
+ d = sqrt ( f2 * h2 )
262
+ c = f2 / d
263
+ if ( c >= safmin ) then
264
+ r = fs / c
265
+ else
266
+ ! f2 / sqrt(f2 * h2) < safmin, then
267
+ ! h2 / sqrt(f2 * h2) <= h2 * (safmin / f2) <= h2 <= safmax
268
+ r = fs * ( h2 / d )
269
+ end if
270
+ s = conjg ( gs ) * ( fs / d )
219
271
end if
220
- c = ( f2 / d ) * w
221
- s = conjg ( gs ) * ( fs / d )
222
- r = ( fs * ( h2 / d ) ) * u
272
+ ! Rescale c and r
273
+ c = c * w
274
+ r = r * u
223
275
end if
224
276
end if
225
277
return
0 commit comments