4
5
6
7
8
9
10
11 INTEGER DCOL, DROW, ICTXT, INFO, K, LDU, N, NB, NPCOL
12 REAL RHO
13
14
15 INTEGER CTOT( 0: NPCOL-1, 4 ), INDCOL( * ),
16 $ INDROW( * ), INDX( * ), INDXC( * ), INDXR( * )
17 REAL BUF( * ), D( * ), DLAMDA( * ), U( LDU, * ),
18 $ W( * ), Z( * )
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130 REAL ONE
131 parameter( one = 1.0e0 )
132
133
134 INTEGER COL, GI, I, IINFO, IIU, IPD, IU, J, JJU, JU,
135 $ KK, KL, KLC, KLR, MYCOL, MYKL, MYKLR, MYROW,
136 $ NPROW, PDC, PDR, ROW
137 REAL AUX, TEMP
138
139
140 INTEGER INDXG2L
141 REAL SLAMC3, SNRM2
143
144
145 EXTERNAL blacs_gridinfo, scopy, sgebr2d, sgebs2d,
146 $ sgerv2d, sgesd2d, slaed4
147
148
149 INTRINSIC mod, sign, sqrt
150
151
152
153
154
155 iinfo = 0
156
157
158
159 IF( k.EQ.0 )
160 $ RETURN
161
162 CALL blacs_gridinfo( ictxt, nprow, npcol, myrow, mycol )
163
164 row = drow
165 col = dcol
166 DO 20 i = 1, n, nb
167 DO 10 j = 0, nb - 1
168 indrow( i+j ) = row
169 indcol( i+j ) = col
170 10 CONTINUE
171 row = mod( row+1, nprow )
172 col = mod( col+1, npcol )
173 20 CONTINUE
174
175 mykl = ctot( mycol, 1 ) + ctot( mycol, 2 ) + ctot( mycol, 3 )
176 klr = mykl / nprow
177 IF( myrow.EQ.drow ) THEN
178 myklr = klr + mod( mykl, nprow )
179 ELSE
180 myklr = klr
181 END IF
182 pdc = 1
183 col = dcol
184 30 CONTINUE
185 IF( mycol.NE.col ) THEN
186 pdc = pdc + ctot( col, 1 ) + ctot( col, 2 ) + ctot( col, 3 )
187 col = mod( col+1, npcol )
188 GO TO 30
189 END IF
190 pdr = pdc
191 kl = klr + mod( mykl, nprow )
192 row = drow
193 40 CONTINUE
194 IF( myrow.NE.row ) THEN
195 pdr = pdr + kl
196 kl = klr
197 row = mod( row+1, nprow )
198 GO TO 40
199 END IF
200
201 DO 50 i = 1, k
202 dlamda( i ) =
slamc3( dlamda( i ), dlamda( i ) ) - dlamda( i )
203 z( i ) = one
204 50 CONTINUE
205 IF( myklr.GT.0 ) THEN
206 kk = pdr
207 DO 80 i = 1, myklr
208 CALL slaed4( k, kk, dlamda, w, buf, rho, buf( k+i ), iinfo )
209 IF( iinfo.NE.0 ) THEN
210 info = kk
211 END IF
212
213
214
215 DO 60 j = 1, kk - 1
216 z( j ) = z( j )*( buf( j ) /
217 $ ( dlamda( j )-dlamda( kk ) ) )
218 60 CONTINUE
219 z( kk ) = z( kk )*buf( kk )
220 DO 70 j = kk + 1, k
221 z( j ) = z( j )*( buf( j ) /
222 $ ( dlamda( j )-dlamda( kk ) ) )
223 70 CONTINUE
224 kk = kk + 1
225 80 CONTINUE
226
227 IF( myrow.NE.drow ) THEN
228 CALL scopy( k, z, 1, buf, 1 )
229 CALL sgesd2d( ictxt, k+myklr, 1, buf, k+myklr, drow, mycol )
230 ELSE
231 ipd = 2*k + 1
232 CALL scopy( myklr, buf( k+1 ), 1, buf( ipd ), 1 )
233 IF( klr.GT.0 ) THEN
234 ipd = myklr + ipd
235 row = mod( drow+1, nprow )
236 DO 100 i = 1, nprow - 1
237 CALL sgerv2d( ictxt, k+klr, 1, buf, k+klr, row,
238 $ mycol )
239 CALL scopy( klr, buf( k+1 ), 1, buf( ipd ), 1 )
240 DO 90 j = 1, k
241 z( j ) = z( j )*buf( j )
242 90 CONTINUE
243 ipd = ipd + klr
244 row = mod( row+1, nprow )
245 100 CONTINUE
246 END IF
247 END IF
248 END IF
249
250 IF( myrow.EQ.drow ) THEN
251 IF( mycol.NE.dcol .AND. mykl.NE.0 ) THEN
252 CALL scopy( k, z, 1, buf, 1 )
253 CALL scopy( mykl, buf( 2*k+1 ), 1, buf( k+1 ), 1 )
254 CALL sgesd2d( ictxt, k+mykl, 1, buf, k+mykl, myrow, dcol )
255 ELSE IF( mycol.EQ.dcol ) THEN
256 ipd = 2*k + 1
257 col = dcol
258 kl = mykl
259 DO 120 i = 1, npcol - 1
260 ipd = ipd + kl
261 col = mod( col+1, npcol )
262 kl = ctot( col, 1 ) + ctot( col, 2 ) + ctot( col, 3 )
263 IF( kl.NE.0 ) THEN
264 CALL sgerv2d( ictxt, k+kl, 1, buf, k+kl, myrow, col )
265 CALL scopy( kl, buf( k+1 ), 1, buf( ipd ), 1 )
266 DO 110 j = 1, k
267 z( j ) = z( j )*buf( j )
268 110 CONTINUE
269 END IF
270 120 CONTINUE
271 DO 130 i = 1, k
272 z( i ) = sign( sqrt( -z( i ) ), w( i ) )
273 130 CONTINUE
274
275 END IF
276 END IF
277
278
279
280 IF( myrow.EQ.drow .AND. mycol.EQ.dcol ) THEN
281 CALL scopy( k, z, 1, buf, 1 )
282 CALL scopy( k, buf( 2*k+1 ), 1, buf( k+1 ), 1 )
283 CALL sgebs2d( ictxt, 'All', ' ', 2*k, 1, buf, 2*k )
284 ELSE
285 CALL sgebr2d( ictxt, 'All', ' ', 2*k, 1, buf, 2*k, drow, dcol )
286 CALL scopy( k, buf, 1, z, 1 )
287 END IF
288
289
290
291 klc = 0
292 klr = 0
293 DO 140 i = 1, k
294 gi = indx( i )
295 d( gi ) = buf( k+i )
296 col = indcol( gi )
297 row = indrow( gi )
298 IF( col.EQ.mycol ) THEN
299 klc = klc + 1
300 indxc( klc ) = i
301 END IF
302 IF( row.EQ.myrow ) THEN
303 klr = klr + 1
304 indxr( klr ) = i
305 END IF
306 140 CONTINUE
307
308
309
310 IF( mykl.NE.0 ) THEN
311 DO 180 j = 1, mykl
312 kk = indxc( j )
313 ju = indx( kk )
314 jju =
indxg2l( ju, nb, j, j, npcol )
315 CALL slaed4( k, kk, dlamda, w, buf, rho, aux, iinfo )
316 IF( iinfo.NE.0 ) THEN
317 info = kk
318 END IF
319 IF( k.EQ.1 .OR. k.EQ.2 ) THEN
320 DO 150 i = 1, klr
321 kk = indxr( i )
322 iu = indx( kk )
323 iiu =
indxg2l( iu, nb, j, j, nprow )
324 u( iiu, jju ) = buf( kk )
325 150 CONTINUE
326 GO TO 180
327 END IF
328
329 DO 160 i = 1, k
330 buf( i ) = z( i ) / buf( i )
331 160 CONTINUE
332 temp = snrm2( k, buf, 1 )
333 DO 170 i = 1, klr
334 kk = indxr( i )
335 iu = indx( kk )
336 iiu =
indxg2l( iu, nb, j, j, nprow )
337 u( iiu, jju ) = buf( kk ) / temp
338 170 CONTINUE
339 180 CONTINUE
340 END IF
341
342 190 CONTINUE
343 RETURN
344
345
346
integer function indxg2l(indxglob, nb, iproc, isrcproc, nprocs)