summaryrefslogtreecommitdiff
path: root/src/lib
diff options
context:
space:
mode:
Diffstat (limited to 'src/lib')
-rw-r--r--src/lib/lapack/Makefile.am322
-rw-r--r--src/lib/lapack/Makefile.in838
-rw-r--r--src/lib/lapack/README5
-rw-r--r--src/lib/lapack/dbdsqr.f742
-rw-r--r--src/lib/lapack/dgebak.f188
-rw-r--r--src/lib/lapack/dgebal.f322
-rw-r--r--src/lib/lapack/dgebd2.f239
-rw-r--r--src/lib/lapack/dgebrd.f268
-rw-r--r--src/lib/lapack/dgecon.f185
-rw-r--r--src/lib/lapack/dgeequ.f225
-rw-r--r--src/lib/lapack/dgees.f434
-rw-r--r--src/lib/lapack/dgeesx.f527
-rw-r--r--src/lib/lapack/dgeev.f423
-rw-r--r--src/lib/lapack/dgegs.f438
-rw-r--r--src/lib/lapack/dgehd2.f149
-rw-r--r--src/lib/lapack/dgehrd.f273
-rw-r--r--src/lib/lapack/dgelq2.f121
-rw-r--r--src/lib/lapack/dgelqf.f195
-rw-r--r--src/lib/lapack/dgels.f422
-rw-r--r--src/lib/lapack/dgelss.f617
-rw-r--r--src/lib/lapack/dgelsx.f349
-rw-r--r--src/lib/lapack/dgelsy.f391
-rw-r--r--src/lib/lapack/dgeql2.f122
-rw-r--r--src/lib/lapack/dgeqlf.f213
-rw-r--r--src/lib/lapack/dgeqp3.f287
-rw-r--r--src/lib/lapack/dgeqpf.f231
-rw-r--r--src/lib/lapack/dgeqr2.f121
-rw-r--r--src/lib/lapack/dgeqrf.f196
-rw-r--r--src/lib/lapack/dgerfs.f336
-rw-r--r--src/lib/lapack/dgerq2.f122
-rw-r--r--src/lib/lapack/dgerqf.f213
-rw-r--r--src/lib/lapack/dgesc2.f132
-rw-r--r--src/lib/lapack/dgesv.f107
-rw-r--r--src/lib/lapack/dgesvd.f3401
-rw-r--r--src/lib/lapack/dgesvx.f479
-rw-r--r--src/lib/lapack/dgetc2.f146
-rw-r--r--src/lib/lapack/dgetf2.f147
-rw-r--r--src/lib/lapack/dgetrf.f159
-rw-r--r--src/lib/lapack/dgetri.f192
-rw-r--r--src/lib/lapack/dgetrs.f149
-rw-r--r--src/lib/lapack/dggbak.f220
-rw-r--r--src/lib/lapack/dggbal.f469
-rw-r--r--src/lib/lapack/dgges.f550
-rw-r--r--src/lib/lapack/dggev.f489
-rw-r--r--src/lib/lapack/dgghrd.f264
-rw-r--r--src/lib/lapack/dhgeqz.f1243
-rw-r--r--src/lib/lapack/dhseqr.f407
-rw-r--r--src/lib/lapack/disnan.f33
-rw-r--r--src/lib/lapack/dlabad.f55
-rw-r--r--src/lib/lapack/dlabrd.f290
-rw-r--r--src/lib/lapack/dlacn2.f214
-rw-r--r--src/lib/lapack/dlacon.f205
-rw-r--r--src/lib/lapack/dlacpy.f87
-rw-r--r--src/lib/lapack/dladiv.f62
-rw-r--r--src/lib/lapack/dlae2.f123
-rw-r--r--src/lib/lapack/dlaev2.f169
-rw-r--r--src/lib/lapack/dlaexc.f354
-rw-r--r--src/lib/lapack/dlag2.f300
-rw-r--r--src/lib/lapack/dlagv2.f287
-rw-r--r--src/lib/lapack/dlahqr.f501
-rw-r--r--src/lib/lapack/dlahr2.f238
-rw-r--r--src/lib/lapack/dlahrd.f207
-rw-r--r--src/lib/lapack/dlaic1.f292
-rw-r--r--src/lib/lapack/dlaisnan.f41
-rw-r--r--src/lib/lapack/dlaln2.f507
-rw-r--r--src/lib/lapack/dlamch.f857
-rw-r--r--src/lib/lapack/dlange.f144
-rw-r--r--src/lib/lapack/dlanhs.f141
-rw-r--r--src/lib/lapack/dlansp.f196
-rw-r--r--src/lib/lapack/dlanst.f124
-rw-r--r--src/lib/lapack/dlansy.f173
-rw-r--r--src/lib/lapack/dlantr.f276
-rw-r--r--src/lib/lapack/dlanv2.f205
-rw-r--r--src/lib/lapack/dlapmt.f136
-rw-r--r--src/lib/lapack/dlapy2.f53
-rw-r--r--src/lib/lapack/dlapy3.f56
-rw-r--r--src/lib/lapack/dlaqge.f154
-rw-r--r--src/lib/lapack/dlaqp2.f175
-rw-r--r--src/lib/lapack/dlaqps.f259
-rw-r--r--src/lib/lapack/dlaqr0.f642
-rw-r--r--src/lib/lapack/dlaqr1.f97
-rw-r--r--src/lib/lapack/dlaqr2.f551
-rw-r--r--src/lib/lapack/dlaqr3.f561
-rw-r--r--src/lib/lapack/dlaqr4.f640
-rw-r--r--src/lib/lapack/dlaqr5.f812
-rw-r--r--src/lib/lapack/dlarf.f115
-rw-r--r--src/lib/lapack/dlarfb.f587
-rw-r--r--src/lib/lapack/dlarfg.f137
-rw-r--r--src/lib/lapack/dlarft.f217
-rw-r--r--src/lib/lapack/dlarfx.f638
-rw-r--r--src/lib/lapack/dlartg.f145
-rw-r--r--src/lib/lapack/dlarz.f152
-rw-r--r--src/lib/lapack/dlarzb.f220
-rw-r--r--src/lib/lapack/dlarzt.f184
-rw-r--r--src/lib/lapack/dlas2.f121
-rw-r--r--src/lib/lapack/dlascl.f267
-rw-r--r--src/lib/lapack/dlaset.f114
-rw-r--r--src/lib/lapack/dlasq1.f148
-rw-r--r--src/lib/lapack/dlasq2.f448
-rw-r--r--src/lib/lapack/dlasq3.f295
-rw-r--r--src/lib/lapack/dlasq4.f329
-rw-r--r--src/lib/lapack/dlasq5.f195
-rw-r--r--src/lib/lapack/dlasq6.f175
-rw-r--r--src/lib/lapack/dlasr.f361
-rw-r--r--src/lib/lapack/dlasrt.f243
-rw-r--r--src/lib/lapack/dlassq.f88
-rw-r--r--src/lib/lapack/dlasv2.f249
-rw-r--r--src/lib/lapack/dlaswp.f119
-rw-r--r--src/lib/lapack/dlasy2.f381
-rw-r--r--src/lib/lapack/dlasyf.f587
-rw-r--r--src/lib/lapack/dlatdf.f237
-rw-r--r--src/lib/lapack/dlatrd.f258
-rw-r--r--src/lib/lapack/dlatrs.f701
-rw-r--r--src/lib/lapack/dlatrz.f127
-rw-r--r--src/lib/lapack/dlatzm.f142
-rw-r--r--src/lib/lapack/dlazq3.f302
-rw-r--r--src/lib/lapack/dlazq4.f330
-rw-r--r--src/lib/lapack/dopgtr.f160
-rw-r--r--src/lib/lapack/dorg2l.f127
-rw-r--r--src/lib/lapack/dorg2r.f129
-rw-r--r--src/lib/lapack/dorgbr.f244
-rw-r--r--src/lib/lapack/dorghr.f164
-rw-r--r--src/lib/lapack/dorgl2.f133
-rw-r--r--src/lib/lapack/dorglq.f215
-rw-r--r--src/lib/lapack/dorgql.f222
-rw-r--r--src/lib/lapack/dorgqr.f216
-rw-r--r--src/lib/lapack/dorgr2.f131
-rw-r--r--src/lib/lapack/dorgrq.f222
-rw-r--r--src/lib/lapack/dorgtr.f183
-rw-r--r--src/lib/lapack/dorm2l.f193
-rw-r--r--src/lib/lapack/dorm2r.f197
-rw-r--r--src/lib/lapack/dormbr.f281
-rw-r--r--src/lib/lapack/dormhr.f201
-rw-r--r--src/lib/lapack/dorml2.f197
-rw-r--r--src/lib/lapack/dormlq.f267
-rw-r--r--src/lib/lapack/dormql.f261
-rw-r--r--src/lib/lapack/dormqr.f260
-rw-r--r--src/lib/lapack/dormr2.f193
-rw-r--r--src/lib/lapack/dormr3.f206
-rw-r--r--src/lib/lapack/dormrq.f268
-rw-r--r--src/lib/lapack/dormrz.f292
-rw-r--r--src/lib/lapack/dpocon.f177
-rw-r--r--src/lib/lapack/dpotf2.f167
-rw-r--r--src/lib/lapack/dpotrf.f183
-rw-r--r--src/lib/lapack/dpotrs.f132
-rw-r--r--src/lib/lapack/dpptrf.f177
-rw-r--r--src/lib/lapack/drscl.f114
-rw-r--r--src/lib/lapack/dspev.f187
-rw-r--r--src/lib/lapack/dspgst.f208
-rw-r--r--src/lib/lapack/dspgv.f195
-rw-r--r--src/lib/lapack/dsptrd.f228
-rw-r--r--src/lib/lapack/dsptrf.f547
-rw-r--r--src/lib/lapack/dsteqr.f500
-rw-r--r--src/lib/lapack/dsterf.f364
-rw-r--r--src/lib/lapack/dsycon.f165
-rw-r--r--src/lib/lapack/dsyev.f211
-rw-r--r--src/lib/lapack/dsysv.f174
-rw-r--r--src/lib/lapack/dsytd2.f248
-rw-r--r--src/lib/lapack/dsytf2.f521
-rw-r--r--src/lib/lapack/dsytrd.f294
-rw-r--r--src/lib/lapack/dsytrf.f287
-rw-r--r--src/lib/lapack/dsytri.f312
-rw-r--r--src/lib/lapack/dsytrs.f369
-rw-r--r--src/lib/lapack/dtgevc.f1147
-rw-r--r--src/lib/lapack/dtgex2.f581
-rw-r--r--src/lib/lapack/dtgexc.f440
-rw-r--r--src/lib/lapack/dtgsen.f723
-rw-r--r--src/lib/lapack/dtgsy2.f956
-rw-r--r--src/lib/lapack/dtgsyl.f556
-rw-r--r--src/lib/lapack/dtrcon.f197
-rw-r--r--src/lib/lapack/dtrevc.f980
-rw-r--r--src/lib/lapack/dtrexc.f345
-rw-r--r--src/lib/lapack/dtrsen.f459
-rw-r--r--src/lib/lapack/dtrsyl.f913
-rw-r--r--src/lib/lapack/dtrti2.f146
-rw-r--r--src/lib/lapack/dtrtri.f176
-rw-r--r--src/lib/lapack/dtrtrs.f147
-rw-r--r--src/lib/lapack/dtzrqf.f164
-rw-r--r--src/lib/lapack/dtzrzf.f244
-rw-r--r--src/lib/lapack/dzsum1.f81
-rw-r--r--src/lib/lapack/ieeeck.f147
-rw-r--r--src/lib/lapack/ilaenv.f552
-rw-r--r--src/lib/lapack/iparmq.f253
-rw-r--r--src/lib/lapack/izmax1.f95
-rw-r--r--src/lib/lapack/lapack_f/lapack.def306
-rw-r--r--src/lib/lapack/lapack_f/lapack_DLL.vfproj348
-rw-r--r--src/lib/lapack/lapack_f/lapack_DLL_f2c.vcproj2779
-rw-r--r--src/lib/lapack/lsame.f87
-rw-r--r--src/lib/lapack/slamch.f857
-rw-r--r--src/lib/lapack/xerbla.f45
-rw-r--r--src/lib/lapack/zbdsqr.f742
-rw-r--r--src/lib/lapack/zdrot.f96
-rw-r--r--src/lib/lapack/zdrscl.f114
-rw-r--r--src/lib/lapack/zgebak.f189
-rw-r--r--src/lib/lapack/zgebal.f330
-rw-r--r--src/lib/lapack/zgebd2.f250
-rw-r--r--src/lib/lapack/zgebrd.f268
-rw-r--r--src/lib/lapack/zgecon.f193
-rw-r--r--src/lib/lapack/zgees.f324
-rw-r--r--src/lib/lapack/zgeev.f396
-rw-r--r--src/lib/lapack/zgehd2.f148
-rw-r--r--src/lib/lapack/zgehrd.f273
-rw-r--r--src/lib/lapack/zgelq2.f123
-rw-r--r--src/lib/lapack/zgelqf.f195
-rw-r--r--src/lib/lapack/zgelsy.f385
-rw-r--r--src/lib/lapack/zgeqp3.f293
-rw-r--r--src/lib/lapack/zgeqpf.f234
-rw-r--r--src/lib/lapack/zgeqr2.f121
-rw-r--r--src/lib/lapack/zgeqrf.f196
-rw-r--r--src/lib/lapack/zgesc2.f133
-rw-r--r--src/lib/lapack/zgesvd.f3602
-rw-r--r--src/lib/lapack/zgetc2.f145
-rw-r--r--src/lib/lapack/zgetf2.f148
-rw-r--r--src/lib/lapack/zgetrf.f159
-rw-r--r--src/lib/lapack/zgetri.f193
-rw-r--r--src/lib/lapack/zgetrs.f149
-rw-r--r--src/lib/lapack/zggbak.f220
-rw-r--r--src/lib/lapack/zggbal.f482
-rw-r--r--src/lib/lapack/zgges.f477
-rw-r--r--src/lib/lapack/zggev.f454
-rw-r--r--src/lib/lapack/zgghrd.f264
-rw-r--r--src/lib/lapack/zheev.f218
-rw-r--r--src/lib/lapack/zhetd2.f258
-rw-r--r--src/lib/lapack/zhetrd.f296
-rw-r--r--src/lib/lapack/zhgeqz.f759
-rw-r--r--src/lib/lapack/zhseqr.f395
-rw-r--r--src/lib/lapack/zlabrd.f328
-rw-r--r--src/lib/lapack/zlacgv.f60
-rw-r--r--src/lib/lapack/zlacn2.f221
-rw-r--r--src/lib/lapack/zlacon.f212
-rw-r--r--src/lib/lapack/zlacpy.f90
-rw-r--r--src/lib/lapack/zladiv.f46
-rw-r--r--src/lib/lapack/zlahqr.f470
-rw-r--r--src/lib/lapack/zlahr2.f240
-rw-r--r--src/lib/lapack/zlahrd.f213
-rw-r--r--src/lib/lapack/zlaic1.f295
-rw-r--r--src/lib/lapack/zlange.f145
-rw-r--r--src/lib/lapack/zlanhe.f187
-rw-r--r--src/lib/lapack/zlanhs.f142
-rw-r--r--src/lib/lapack/zlaqp2.f179
-rw-r--r--src/lib/lapack/zlaqps.f266
-rw-r--r--src/lib/lapack/zlaqr0.f601
-rw-r--r--src/lib/lapack/zlaqr1.f97
-rw-r--r--src/lib/lapack/zlaqr2.f437
-rw-r--r--src/lib/lapack/zlaqr3.f448
-rw-r--r--src/lib/lapack/zlaqr4.f602
-rw-r--r--src/lib/lapack/zlaqr5.f809
-rw-r--r--src/lib/lapack/zlarf.f120
-rw-r--r--src/lib/lapack/zlarfb.f608
-rw-r--r--src/lib/lapack/zlarfg.f145
-rw-r--r--src/lib/lapack/zlarft.f224
-rw-r--r--src/lib/lapack/zlarfx.f641
-rw-r--r--src/lib/lapack/zlartg.f195
-rw-r--r--src/lib/lapack/zlarz.f157
-rw-r--r--src/lib/lapack/zlarzb.f234
-rw-r--r--src/lib/lapack/zlarzt.f186
-rw-r--r--src/lib/lapack/zlascl.f267
-rw-r--r--src/lib/lapack/zlaset.f114
-rw-r--r--src/lib/lapack/zlasr.f363
-rw-r--r--src/lib/lapack/zlassq.f101
-rw-r--r--src/lib/lapack/zlaswp.f119
-rw-r--r--src/lib/lapack/zlatdf.f241
-rw-r--r--src/lib/lapack/zlatrd.f279
-rw-r--r--src/lib/lapack/zlatrs.f879
-rw-r--r--src/lib/lapack/zlatrz.f133
-rw-r--r--src/lib/lapack/zpotf2.f174
-rw-r--r--src/lib/lapack/zpotrf.f186
-rw-r--r--src/lib/lapack/zrot.f91
-rw-r--r--src/lib/lapack/zsteqr.f503
-rw-r--r--src/lib/lapack/ztgevc.f633
-rw-r--r--src/lib/lapack/ztgex2.f265
-rw-r--r--src/lib/lapack/ztgexc.f206
-rw-r--r--src/lib/lapack/ztgsen.f652
-rw-r--r--src/lib/lapack/ztgsy2.f361
-rw-r--r--src/lib/lapack/ztgsyl.f575
-rw-r--r--src/lib/lapack/ztrevc.f386
-rw-r--r--src/lib/lapack/ztrexc.f162
-rw-r--r--src/lib/lapack/ztrsen.f359
-rw-r--r--src/lib/lapack/ztrsyl.f365
-rw-r--r--src/lib/lapack/ztrti2.f146
-rw-r--r--src/lib/lapack/ztrtri.f177
-rw-r--r--src/lib/lapack/ztzrzf.f244
-rw-r--r--src/lib/lapack/zung2l.f128
-rw-r--r--src/lib/lapack/zung2r.f130
-rw-r--r--src/lib/lapack/zungbr.f245
-rw-r--r--src/lib/lapack/zunghr.f165
-rw-r--r--src/lib/lapack/zungl2.f136
-rw-r--r--src/lib/lapack/zunglq.f215
-rw-r--r--src/lib/lapack/zungql.f222
-rw-r--r--src/lib/lapack/zungqr.f216
-rw-r--r--src/lib/lapack/zungtr.f184
-rw-r--r--src/lib/lapack/zunm2r.f201
-rw-r--r--src/lib/lapack/zunmbr.f288
-rw-r--r--src/lib/lapack/zunml2.f205
-rw-r--r--src/lib/lapack/zunmlq.f267
-rw-r--r--src/lib/lapack/zunmqr.f260
-rw-r--r--src/lib/lapack/zunmr3.f212
-rw-r--r--src/lib/lapack/zunmrz.f296
298 files changed, 0 insertions, 94514 deletions
diff --git a/src/lib/lapack/Makefile.am b/src/lib/lapack/Makefile.am
deleted file mode 100644
index 13904af1..00000000
--- a/src/lib/lapack/Makefile.am
+++ /dev/null
@@ -1,322 +0,0 @@
-##########
-### Sylvestre Ledru <sylvestre.ledru@inria.fr>
-### INRIA - Scilab 2006
-##########
-
-#### Target ######
-modulename=lapack
-
-pkglib_LTLIBRARIES = libscilapack.la
-
-noinst_LTLIBRARIES = libdummy-lapack.la
-
-LAPACK_FORTRAN_SOURCES = dlasv2.f \
-zgeqpf.f \
-zrot.f \
-dpotrf.f \
-zunmr3.f \
-zlanhs.f \
-zgebak.f \
-zbdsqr.f \
-zunmrz.f \
-dgetc2.f \
-zlaqp2.f \
-dsytrd.f \
-dsytd2.f \
-zlange.f \
-dlansp.f \
-dhgeqz.f \
-dlasq2.f \
-dtrevc.f \
-dgelsy.f \
-zladiv.f \
-dlaswp.f \
-dormlq.f \
-dorml2.f \
-dlaexc.f \
-zlahqr.f \
-zdrot.f \
-dlabad.f \
-dlarft.f \
-zlassq.f \
-dlartg.f \
-zlarf.f \
-ztrexc.f \
-zgeev.f \
-dggbal.f \
-dtrtrs.f \
-zlatdf.f \
-dgeqr2.f \
-zlarfg.f \
-dgetrs.f \
-dlag2.f \
-dlaqge.f \
-dpotf2.f \
-zgetrf.f \
-ztgsy2.f \
-zgebal.f \
-dspgst.f \
-dormqr.f \
-drscl.f \
-dtrti2.f \
-dlaset.f \
-dgeesx.f \
-dpocon.f \
-dlasyf.f \
-dgerq2.f \
-dlasq3.f \
-dlansy.f \
-dgehrd.f \
-dgehd2.f \
-dsptrd.f \
-dorgtr.f \
-dormrq.f \
-dorm2r.f \
-dormr2.f \
-zgges.f \
-zunglq.f \
-zlanhe.f \
-zungl2.f \
-zhetrd.f \
-zhetd2.f \
-dlacon.f \
-dgesvx.f \
-zgetf2.f \
-ztgevc.f \
-dsteqr.f \
-dgelqf.f \
-zlarzb.f \
-zlarfx.f \
-dsysv.f \
-zlaqps.f \
-dtzrqf.f \
-dsytrf.f \
-xerbla.f \
-dtrsyl.f \
-dgelss.f \
-dtgsen.f \
-zgecon.f \
-dormbr.f \
-zlatrz.f \
-zungqr.f \
-dlabrd.f \
-dlasq4.f \
-dggev.f \
-dpptrf.f \
-zgelq2.f \
-dgeqpf.f \
-dormr3.f \
-dlanhs.f \
-dgerfs.f \
-dlarz.f \
-zgebrd.f \
-zgebd2.f \
-dgebak.f \
-dormrz.f \
-dbdsqr.f \
-dspev.f \
-dlaqp2.f \
-zung2r.f \
-dlange.f \
-zgeqrf.f \
-dormql.f \
-zgesvd.f \
-dladiv.f \
-dlas2.f \
-dgeequ.f \
-dsytf2.f \
-dlahqr.f \
-zlatrs.f \
-zheev.f \
-ztgex2.f \
-zlaic1.f \
-ztrsen.f \
-zlacgv.f \
-dgees.f \
-dlassq.f \
-zlascl.f \
-dtrexc.f \
-dlasq5.f \
-dormhr.f \
-zgesc2.f \
-dlatdf.f \
-dsycon.f \
-dlarfg.f \
-dorm2l.f \
-dsptrf.f \
-zungbr.f \
-dgesv.f \
-dgetrf.f \
-zhseqr.f \
-dtgsy2.f \
-dlaev2.f \
-dgebal.f \
-zlarfb.f \
-zlahrd.f \
-dlantr.f \
-zgghrd.f \
-dlatzm.f \
-ztgsyl.f \
-ztrtri.f \
-zlatrd.f \
-zlacpy.f \
-zgetri.f \
-dlasr.f \
-zgeqp3.f \
-zungql.f \
-dlanst.f \
-zlarzt.f \
-dorglq.f \
-dorgl2.f \
-dlasq6.f \
-dlasy2.f \
-dopgtr.f \
-dgeqlf.f \
-dgetf2.f \
-dtgevc.f \
-zunghr.f \
-dlarzb.f \
-dlarfx.f \
-zung2l.f \
-zggev.f \
-dzsum1.f \
-dlaqps.f \
-dtrcon.f \
-dlasrt.f \
-dsyev.f \
-dorgqr.f \
-dgecon.f \
-dlatrz.f \
-zlarz.f \
-ztgexc.f \
-zggbak.f \
-ztzrzf.f \
-dpotrs.f \
-dsytri.f \
-dgelq2.f \
-zpotrf.f \
-dgebrd.f \
-dgebd2.f \
-zgetc2.f \
-dorgrq.f \
-dorg2r.f \
-dorgr2.f \
-zhgeqz.f \
-dgeqrf.f \
-dlaln2.f \
-dgesvd.f \
-ztrevc.f \
-zgelsy.f \
-zgees.f \
-zlaswp.f \
-dspgv.f \
-dlanv2.f \
-zunmlq.f \
-dlae2.f \
-zunml2.f \
-dlatrs.f \
-dtgex2.f \
-dlaic1.f \
-dgels.f \
-dtrsen.f \
-zdrscl.f \
-zlarft.f \
-dlascl.f \
-zlartg.f \
-zggbal.f \
-dgesc2.f \
-dgerqf.f \
-zgeqr2.f \
-zgetrs.f \
-ilaenv.f \
-dorgbr.f \
-zpotf2.f \
-dhseqr.f \
-dlarf.f \
-dgegs.f \
-dgeev.f \
-dlarfb.f \
-zlasr.f \
-dlapy2.f \
-zunmqr.f \
-ztrti2.f \
-dlahrd.f \
-dgghrd.f \
-zlaset.f \
-dtgsyl.f \
-dtrtri.f \
-dlatrd.f \
-dlacpy.f \
-dgetri.f \
-zgehrd.f \
-zgehd2.f \
-dgeqp3.f \
-dorgql.f \
-zungtr.f \
-zunm2r.f \
-dlarzt.f \
-dlapmt.f \
-ieeeck.f \
-dlasq1.f \
-dorghr.f \
-zlacon.f \
-dgelsx.f \
-dsterf.f \
-zsteqr.f \
-zgelqf.f \
-dsytrs.f \
-dgges.f \
-dorg2l.f \
-dlapy3.f \
-lsame.f \
-ztrsyl.f \
-izmax1.f \
-ztgsen.f \
-zunmbr.f \
-zlabrd.f \
-dtgexc.f \
-dgeql2.f \
-dlagv2.f \
-dggbak.f \
-dtzrzf.f \
-zlaqr0.f \
-dlacn2.f \
-zlacn2.f \
-dlazq3.f \
-zlahr2.f \
-dlaqr0.f \
-iparmq.f \
-disnan.f \
-dlaisnan.f \
-dlahr2.f \
-zlaqr3.f \
-zlaqr4.f \
-zlaqr5.f \
-dlazq4.f \
-dlaqr3.f \
-dlaqr4.f \
-dlaqr5.f \
-zlaqr2.f \
-zlaqr1.f \
-dlaqr2.f \
-dlaqr1.f
-
-HEAD = $(top_builddir)/includes/lapack.h
-
-libscilapack_la_SOURCES = $(HEAD) $(LAPACK_FORTRAN_SOURCES)
-
-libdummy_lapack_la_SOURCES = dlamch.f slamch.f
-
-libdummy_lapack_la_FFLAGS = `echo "@FFLAGS@"| sed -e 's|-O[0-9+]|-O0|'`
-
-
-libscilapack_la_LIBADD = libdummy-lapack.la \
- $(top_builddir)/lib/blas/libsciblas.la
-
-libscilapack_la_PKGCONFIG = lapack.pc
-
-libdummy_lapack_la-dlamch.lo: dlamch.f
- $(LIBTOOL) --tag=F77 --mode=compile $(F77) $(libdummy_lapack_la_FFLAGS) -c -o libdummy_lapack_la-dlamch.lo `test -f 'dlamch.f' || echo '$(srcdir)/'`dlamch.f
-
-libdummy_lapack_la-slamch.lo: slamch.f
- $(LIBTOOL) --tag=F77 --mode=compile $(F77) $(libdummy_lapack_la_FFLAGS) -c -o libdummy_lapack_la-slamch.lo `test -f 'slamch.f' || echo '$(srcdir)/'`slamch.f
diff --git a/src/lib/lapack/Makefile.in b/src/lib/lapack/Makefile.in
deleted file mode 100644
index 51b22b91..00000000
--- a/src/lib/lapack/Makefile.in
+++ /dev/null
@@ -1,838 +0,0 @@
-# Makefile.in generated by automake 1.10.1 from Makefile.am.
-# @configure_input@
-
-# Copyright (C) 1994, 1995, 1996, 1997, 1998, 1999, 2000, 2001, 2002,
-# 2003, 2004, 2005, 2006, 2007, 2008 Free Software Foundation, Inc.
-# This Makefile.in is free software; the Free Software Foundation
-# gives unlimited permission to copy and/or distribute it,
-# with or without modifications, as long as this notice is preserved.
-
-# This program is distributed in the hope that it will be useful,
-# but WITHOUT ANY WARRANTY, to the extent permitted by law; without
-# even the implied warranty of MERCHANTABILITY or FITNESS FOR A
-# PARTICULAR PURPOSE.
-
-@SET_MAKE@
-
-##########
-### Sylvestre Ledru <sylvestre.ledru@inria.fr>
-### INRIA - Scilab 2006
-##########
-
-VPATH = @srcdir@
-pkgdatadir = $(datadir)/@PACKAGE@
-pkglibdir = $(libdir)/@PACKAGE@
-pkgincludedir = $(includedir)/@PACKAGE@
-am__cd = CDPATH="$${ZSH_VERSION+.}$(PATH_SEPARATOR)" && cd
-install_sh_DATA = $(install_sh) -c -m 644
-install_sh_PROGRAM = $(install_sh) -c
-install_sh_SCRIPT = $(install_sh) -c
-INSTALL_HEADER = $(INSTALL_DATA)
-transform = $(program_transform_name)
-NORMAL_INSTALL = :
-PRE_INSTALL = :
-POST_INSTALL = :
-NORMAL_UNINSTALL = :
-PRE_UNINSTALL = :
-POST_UNINSTALL = :
-build_triplet = @build@
-host_triplet = @host@
-subdir = lib/lapack
-DIST_COMMON = README $(srcdir)/Makefile.am $(srcdir)/Makefile.in
-ACLOCAL_M4 = $(top_srcdir)/aclocal.m4
-am__aclocal_m4_deps = $(top_srcdir)/configure.ac
-am__configure_deps = $(am__aclocal_m4_deps) $(CONFIGURE_DEPENDENCIES) \
- $(ACLOCAL_M4)
-mkinstalldirs = $(install_sh) -d
-CONFIG_HEADER = $(top_builddir)/includes/machine.h
-CONFIG_CLEAN_FILES =
-am__vpath_adj_setup = srcdirstrip=`echo "$(srcdir)" | sed 's|.|.|g'`;
-am__vpath_adj = case $$p in \
- $(srcdir)/*) f=`echo "$$p" | sed "s|^$$srcdirstrip/||"`;; \
- *) f=$$p;; \
- esac;
-am__strip_dir = `echo $$p | sed -e 's|^.*/||'`;
-am__installdirs = "$(DESTDIR)$(pkglibdir)"
-pkglibLTLIBRARIES_INSTALL = $(INSTALL)
-LTLIBRARIES = $(noinst_LTLIBRARIES) $(pkglib_LTLIBRARIES)
-libdummy_lapack_la_LIBADD =
-am_libdummy_lapack_la_OBJECTS = libdummy_lapack_la-dlamch.lo \
- libdummy_lapack_la-slamch.lo
-libdummy_lapack_la_OBJECTS = $(am_libdummy_lapack_la_OBJECTS)
-libdummy_lapack_la_LINK = $(LIBTOOL) --tag=F77 $(AM_LIBTOOLFLAGS) \
- $(LIBTOOLFLAGS) --mode=link $(F77LD) \
- $(libdummy_lapack_la_FFLAGS) $(FFLAGS) $(AM_LDFLAGS) \
- $(LDFLAGS) -o $@
-libscilapack_la_DEPENDENCIES = libdummy-lapack.la \
- $(top_builddir)/lib/blas/libsciblas.la
-am__objects_1 =
-am__objects_2 = dlasv2.lo zgeqpf.lo zrot.lo dpotrf.lo zunmr3.lo \
- zlanhs.lo zgebak.lo zbdsqr.lo zunmrz.lo dgetc2.lo zlaqp2.lo \
- dsytrd.lo dsytd2.lo zlange.lo dlansp.lo dhgeqz.lo dlasq2.lo \
- dtrevc.lo dgelsy.lo zladiv.lo dlaswp.lo dormlq.lo dorml2.lo \
- dlaexc.lo zlahqr.lo zdrot.lo dlabad.lo dlarft.lo zlassq.lo \
- dlartg.lo zlarf.lo ztrexc.lo zgeev.lo dggbal.lo dtrtrs.lo \
- zlatdf.lo dgeqr2.lo zlarfg.lo dgetrs.lo dlag2.lo dlaqge.lo \
- dpotf2.lo zgetrf.lo ztgsy2.lo zgebal.lo dspgst.lo dormqr.lo \
- drscl.lo dtrti2.lo dlaset.lo dgeesx.lo dpocon.lo dlasyf.lo \
- dgerq2.lo dlasq3.lo dlansy.lo dgehrd.lo dgehd2.lo dsptrd.lo \
- dorgtr.lo dormrq.lo dorm2r.lo dormr2.lo zgges.lo zunglq.lo \
- zlanhe.lo zungl2.lo zhetrd.lo zhetd2.lo dlacon.lo dgesvx.lo \
- zgetf2.lo ztgevc.lo dsteqr.lo dgelqf.lo zlarzb.lo zlarfx.lo \
- dsysv.lo zlaqps.lo dtzrqf.lo dsytrf.lo xerbla.lo dtrsyl.lo \
- dgelss.lo dtgsen.lo zgecon.lo dormbr.lo zlatrz.lo zungqr.lo \
- dlabrd.lo dlasq4.lo dggev.lo dpptrf.lo zgelq2.lo dgeqpf.lo \
- dormr3.lo dlanhs.lo dgerfs.lo dlarz.lo zgebrd.lo zgebd2.lo \
- dgebak.lo dormrz.lo dbdsqr.lo dspev.lo dlaqp2.lo zung2r.lo \
- dlange.lo zgeqrf.lo dormql.lo zgesvd.lo dladiv.lo dlas2.lo \
- dgeequ.lo dsytf2.lo dlahqr.lo zlatrs.lo zheev.lo ztgex2.lo \
- zlaic1.lo ztrsen.lo zlacgv.lo dgees.lo dlassq.lo zlascl.lo \
- dtrexc.lo dlasq5.lo dormhr.lo zgesc2.lo dlatdf.lo dsycon.lo \
- dlarfg.lo dorm2l.lo dsptrf.lo zungbr.lo dgesv.lo dgetrf.lo \
- zhseqr.lo dtgsy2.lo dlaev2.lo dgebal.lo zlarfb.lo zlahrd.lo \
- dlantr.lo zgghrd.lo dlatzm.lo ztgsyl.lo ztrtri.lo zlatrd.lo \
- zlacpy.lo zgetri.lo dlasr.lo zgeqp3.lo zungql.lo dlanst.lo \
- zlarzt.lo dorglq.lo dorgl2.lo dlasq6.lo dlasy2.lo dopgtr.lo \
- dgeqlf.lo dgetf2.lo dtgevc.lo zunghr.lo dlarzb.lo dlarfx.lo \
- zung2l.lo zggev.lo dzsum1.lo dlaqps.lo dtrcon.lo dlasrt.lo \
- dsyev.lo dorgqr.lo dgecon.lo dlatrz.lo zlarz.lo ztgexc.lo \
- zggbak.lo ztzrzf.lo dpotrs.lo dsytri.lo dgelq2.lo zpotrf.lo \
- dgebrd.lo dgebd2.lo zgetc2.lo dorgrq.lo dorg2r.lo dorgr2.lo \
- zhgeqz.lo dgeqrf.lo dlaln2.lo dgesvd.lo ztrevc.lo zgelsy.lo \
- zgees.lo zlaswp.lo dspgv.lo dlanv2.lo zunmlq.lo dlae2.lo \
- zunml2.lo dlatrs.lo dtgex2.lo dlaic1.lo dgels.lo dtrsen.lo \
- zdrscl.lo zlarft.lo dlascl.lo zlartg.lo zggbal.lo dgesc2.lo \
- dgerqf.lo zgeqr2.lo zgetrs.lo ilaenv.lo dorgbr.lo zpotf2.lo \
- dhseqr.lo dlarf.lo dgegs.lo dgeev.lo dlarfb.lo zlasr.lo \
- dlapy2.lo zunmqr.lo ztrti2.lo dlahrd.lo dgghrd.lo zlaset.lo \
- dtgsyl.lo dtrtri.lo dlatrd.lo dlacpy.lo dgetri.lo zgehrd.lo \
- zgehd2.lo dgeqp3.lo dorgql.lo zungtr.lo zunm2r.lo dlarzt.lo \
- dlapmt.lo ieeeck.lo dlasq1.lo dorghr.lo zlacon.lo dgelsx.lo \
- dsterf.lo zsteqr.lo zgelqf.lo dsytrs.lo dgges.lo dorg2l.lo \
- dlapy3.lo lsame.lo ztrsyl.lo izmax1.lo ztgsen.lo zunmbr.lo \
- zlabrd.lo dtgexc.lo dgeql2.lo dlagv2.lo dggbak.lo dtzrzf.lo \
- zlaqr0.lo dlacn2.lo zlacn2.lo dlazq3.lo zlahr2.lo dlaqr0.lo \
- iparmq.lo disnan.lo dlaisnan.lo dlahr2.lo zlaqr3.lo zlaqr4.lo \
- zlaqr5.lo dlazq4.lo dlaqr3.lo dlaqr4.lo dlaqr5.lo zlaqr2.lo \
- zlaqr1.lo dlaqr2.lo dlaqr1.lo
-am_libscilapack_la_OBJECTS = $(am__objects_1) $(am__objects_2)
-libscilapack_la_OBJECTS = $(am_libscilapack_la_OBJECTS)
-DEFAULT_INCLUDES = -I.@am__isrc@ -I$(top_builddir)/includes
-F77COMPILE = $(F77) $(AM_FFLAGS) $(FFLAGS)
-LTF77COMPILE = $(LIBTOOL) --tag=F77 $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) \
- --mode=compile $(F77) $(AM_FFLAGS) $(FFLAGS)
-F77LD = $(F77)
-F77LINK = $(LIBTOOL) --tag=F77 $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) \
- --mode=link $(F77LD) $(AM_FFLAGS) $(FFLAGS) $(AM_LDFLAGS) \
- $(LDFLAGS) -o $@
-COMPILE = $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) \
- $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS)
-LTCOMPILE = $(LIBTOOL) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) \
- --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) \
- $(AM_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS)
-CCLD = $(CC)
-LINK = $(LIBTOOL) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) \
- --mode=link $(CCLD) $(AM_CFLAGS) $(CFLAGS) $(AM_LDFLAGS) \
- $(LDFLAGS) -o $@
-SOURCES = $(libdummy_lapack_la_SOURCES) $(libscilapack_la_SOURCES)
-DIST_SOURCES = $(libdummy_lapack_la_SOURCES) \
- $(libscilapack_la_SOURCES)
-ETAGS = etags
-CTAGS = ctags
-DISTFILES = $(DIST_COMMON) $(DIST_SOURCES) $(TEXINFOS) $(EXTRA_DIST)
-ACLOCAL = @ACLOCAL@
-AMTAR = @AMTAR@
-AR = @AR@
-AUTOCONF = @AUTOCONF@
-AUTOHEADER = @AUTOHEADER@
-AUTOMAKE = @AUTOMAKE@
-AWK = @AWK@
-CC = @CC@
-CCDEPMODE = @CCDEPMODE@
-CFLAGS = @CFLAGS@
-CPP = @CPP@
-CPPFLAGS = @CPPFLAGS@
-CXX = @CXX@
-CXXCPP = @CXXCPP@
-CXXDEPMODE = @CXXDEPMODE@
-CXXFLAGS = @CXXFLAGS@
-CYGPATH_W = @CYGPATH_W@
-DEFS = @DEFS@
-DEPDIR = @DEPDIR@
-DSYMUTIL = @DSYMUTIL@
-ECHO = @ECHO@
-ECHO_C = @ECHO_C@
-ECHO_N = @ECHO_N@
-ECHO_T = @ECHO_T@
-EGREP = @EGREP@
-EXEEXT = @EXEEXT@
-F77 = @F77@
-FFLAGS = @FFLAGS@
-GREP = @GREP@
-INSTALL = @INSTALL@
-INSTALL_DATA = @INSTALL_DATA@
-INSTALL_PROGRAM = @INSTALL_PROGRAM@
-INSTALL_SCRIPT = @INSTALL_SCRIPT@
-INSTALL_STRIP_PROGRAM = @INSTALL_STRIP_PROGRAM@
-LDFLAGS = @LDFLAGS@
-LIBMATH = @LIBMATH@
-LIBOBJS = @LIBOBJS@
-LIBS = @LIBS@
-LIBTOOL = @LIBTOOL@
-LN_S = @LN_S@
-LTLIBOBJS = @LTLIBOBJS@
-MAINT = @MAINT@
-MAKEINFO = @MAKEINFO@
-MKDIR_P = @MKDIR_P@
-NMEDIT = @NMEDIT@
-OBJEXT = @OBJEXT@
-PACKAGE = @PACKAGE@
-PACKAGE_BUGREPORT = @PACKAGE_BUGREPORT@
-PACKAGE_NAME = @PACKAGE_NAME@
-PACKAGE_STRING = @PACKAGE_STRING@
-PACKAGE_TARNAME = @PACKAGE_TARNAME@
-PACKAGE_VERSION = @PACKAGE_VERSION@
-PATH_SEPARATOR = @PATH_SEPARATOR@
-RANLIB = @RANLIB@
-SED = @SED@
-SET_MAKE = @SET_MAKE@
-SHELL = @SHELL@
-STRIP = @STRIP@
-VERSION = @VERSION@
-abs_builddir = @abs_builddir@
-abs_srcdir = @abs_srcdir@
-abs_top_builddir = @abs_top_builddir@
-abs_top_srcdir = @abs_top_srcdir@
-ac_ct_CC = @ac_ct_CC@
-ac_ct_CXX = @ac_ct_CXX@
-ac_ct_F77 = @ac_ct_F77@
-am__include = @am__include@
-am__leading_dot = @am__leading_dot@
-am__quote = @am__quote@
-am__tar = @am__tar@
-am__untar = @am__untar@
-bindir = @bindir@
-build = @build@
-build_alias = @build_alias@
-build_cpu = @build_cpu@
-build_os = @build_os@
-build_vendor = @build_vendor@
-builddir = @builddir@
-datadir = @datadir@
-datarootdir = @datarootdir@
-docdir = @docdir@
-dvidir = @dvidir@
-exec_prefix = @exec_prefix@
-host = @host@
-host_alias = @host_alias@
-host_cpu = @host_cpu@
-host_os = @host_os@
-host_vendor = @host_vendor@
-htmldir = @htmldir@
-includedir = @includedir@
-infodir = @infodir@
-install_sh = @install_sh@
-libdir = @libdir@
-libexecdir = @libexecdir@
-localedir = @localedir@
-localstatedir = @localstatedir@
-mandir = @mandir@
-mkdir_p = @mkdir_p@
-oldincludedir = @oldincludedir@
-pdfdir = @pdfdir@
-prefix = @prefix@
-program_transform_name = @program_transform_name@
-psdir = @psdir@
-sbindir = @sbindir@
-sharedstatedir = @sharedstatedir@
-srcdir = @srcdir@
-sysconfdir = @sysconfdir@
-target_alias = @target_alias@
-top_builddir = @top_builddir@
-top_srcdir = @top_srcdir@
-
-#### Target ######
-modulename = lapack
-pkglib_LTLIBRARIES = libscilapack.la
-noinst_LTLIBRARIES = libdummy-lapack.la
-LAPACK_FORTRAN_SOURCES = dlasv2.f \
-zgeqpf.f \
-zrot.f \
-dpotrf.f \
-zunmr3.f \
-zlanhs.f \
-zgebak.f \
-zbdsqr.f \
-zunmrz.f \
-dgetc2.f \
-zlaqp2.f \
-dsytrd.f \
-dsytd2.f \
-zlange.f \
-dlansp.f \
-dhgeqz.f \
-dlasq2.f \
-dtrevc.f \
-dgelsy.f \
-zladiv.f \
-dlaswp.f \
-dormlq.f \
-dorml2.f \
-dlaexc.f \
-zlahqr.f \
-zdrot.f \
-dlabad.f \
-dlarft.f \
-zlassq.f \
-dlartg.f \
-zlarf.f \
-ztrexc.f \
-zgeev.f \
-dggbal.f \
-dtrtrs.f \
-zlatdf.f \
-dgeqr2.f \
-zlarfg.f \
-dgetrs.f \
-dlag2.f \
-dlaqge.f \
-dpotf2.f \
-zgetrf.f \
-ztgsy2.f \
-zgebal.f \
-dspgst.f \
-dormqr.f \
-drscl.f \
-dtrti2.f \
-dlaset.f \
-dgeesx.f \
-dpocon.f \
-dlasyf.f \
-dgerq2.f \
-dlasq3.f \
-dlansy.f \
-dgehrd.f \
-dgehd2.f \
-dsptrd.f \
-dorgtr.f \
-dormrq.f \
-dorm2r.f \
-dormr2.f \
-zgges.f \
-zunglq.f \
-zlanhe.f \
-zungl2.f \
-zhetrd.f \
-zhetd2.f \
-dlacon.f \
-dgesvx.f \
-zgetf2.f \
-ztgevc.f \
-dsteqr.f \
-dgelqf.f \
-zlarzb.f \
-zlarfx.f \
-dsysv.f \
-zlaqps.f \
-dtzrqf.f \
-dsytrf.f \
-xerbla.f \
-dtrsyl.f \
-dgelss.f \
-dtgsen.f \
-zgecon.f \
-dormbr.f \
-zlatrz.f \
-zungqr.f \
-dlabrd.f \
-dlasq4.f \
-dggev.f \
-dpptrf.f \
-zgelq2.f \
-dgeqpf.f \
-dormr3.f \
-dlanhs.f \
-dgerfs.f \
-dlarz.f \
-zgebrd.f \
-zgebd2.f \
-dgebak.f \
-dormrz.f \
-dbdsqr.f \
-dspev.f \
-dlaqp2.f \
-zung2r.f \
-dlange.f \
-zgeqrf.f \
-dormql.f \
-zgesvd.f \
-dladiv.f \
-dlas2.f \
-dgeequ.f \
-dsytf2.f \
-dlahqr.f \
-zlatrs.f \
-zheev.f \
-ztgex2.f \
-zlaic1.f \
-ztrsen.f \
-zlacgv.f \
-dgees.f \
-dlassq.f \
-zlascl.f \
-dtrexc.f \
-dlasq5.f \
-dormhr.f \
-zgesc2.f \
-dlatdf.f \
-dsycon.f \
-dlarfg.f \
-dorm2l.f \
-dsptrf.f \
-zungbr.f \
-dgesv.f \
-dgetrf.f \
-zhseqr.f \
-dtgsy2.f \
-dlaev2.f \
-dgebal.f \
-zlarfb.f \
-zlahrd.f \
-dlantr.f \
-zgghrd.f \
-dlatzm.f \
-ztgsyl.f \
-ztrtri.f \
-zlatrd.f \
-zlacpy.f \
-zgetri.f \
-dlasr.f \
-zgeqp3.f \
-zungql.f \
-dlanst.f \
-zlarzt.f \
-dorglq.f \
-dorgl2.f \
-dlasq6.f \
-dlasy2.f \
-dopgtr.f \
-dgeqlf.f \
-dgetf2.f \
-dtgevc.f \
-zunghr.f \
-dlarzb.f \
-dlarfx.f \
-zung2l.f \
-zggev.f \
-dzsum1.f \
-dlaqps.f \
-dtrcon.f \
-dlasrt.f \
-dsyev.f \
-dorgqr.f \
-dgecon.f \
-dlatrz.f \
-zlarz.f \
-ztgexc.f \
-zggbak.f \
-ztzrzf.f \
-dpotrs.f \
-dsytri.f \
-dgelq2.f \
-zpotrf.f \
-dgebrd.f \
-dgebd2.f \
-zgetc2.f \
-dorgrq.f \
-dorg2r.f \
-dorgr2.f \
-zhgeqz.f \
-dgeqrf.f \
-dlaln2.f \
-dgesvd.f \
-ztrevc.f \
-zgelsy.f \
-zgees.f \
-zlaswp.f \
-dspgv.f \
-dlanv2.f \
-zunmlq.f \
-dlae2.f \
-zunml2.f \
-dlatrs.f \
-dtgex2.f \
-dlaic1.f \
-dgels.f \
-dtrsen.f \
-zdrscl.f \
-zlarft.f \
-dlascl.f \
-zlartg.f \
-zggbal.f \
-dgesc2.f \
-dgerqf.f \
-zgeqr2.f \
-zgetrs.f \
-ilaenv.f \
-dorgbr.f \
-zpotf2.f \
-dhseqr.f \
-dlarf.f \
-dgegs.f \
-dgeev.f \
-dlarfb.f \
-zlasr.f \
-dlapy2.f \
-zunmqr.f \
-ztrti2.f \
-dlahrd.f \
-dgghrd.f \
-zlaset.f \
-dtgsyl.f \
-dtrtri.f \
-dlatrd.f \
-dlacpy.f \
-dgetri.f \
-zgehrd.f \
-zgehd2.f \
-dgeqp3.f \
-dorgql.f \
-zungtr.f \
-zunm2r.f \
-dlarzt.f \
-dlapmt.f \
-ieeeck.f \
-dlasq1.f \
-dorghr.f \
-zlacon.f \
-dgelsx.f \
-dsterf.f \
-zsteqr.f \
-zgelqf.f \
-dsytrs.f \
-dgges.f \
-dorg2l.f \
-dlapy3.f \
-lsame.f \
-ztrsyl.f \
-izmax1.f \
-ztgsen.f \
-zunmbr.f \
-zlabrd.f \
-dtgexc.f \
-dgeql2.f \
-dlagv2.f \
-dggbak.f \
-dtzrzf.f \
-zlaqr0.f \
-dlacn2.f \
-zlacn2.f \
-dlazq3.f \
-zlahr2.f \
-dlaqr0.f \
-iparmq.f \
-disnan.f \
-dlaisnan.f \
-dlahr2.f \
-zlaqr3.f \
-zlaqr4.f \
-zlaqr5.f \
-dlazq4.f \
-dlaqr3.f \
-dlaqr4.f \
-dlaqr5.f \
-zlaqr2.f \
-zlaqr1.f \
-dlaqr2.f \
-dlaqr1.f
-
-HEAD = $(top_builddir)/includes/lapack.h
-libscilapack_la_SOURCES = $(HEAD) $(LAPACK_FORTRAN_SOURCES)
-libdummy_lapack_la_SOURCES = dlamch.f slamch.f
-libdummy_lapack_la_FFLAGS = `echo "@FFLAGS@"| sed -e 's|-O[0-9+]|-O0|'`
-libscilapack_la_LIBADD = libdummy-lapack.la \
- $(top_builddir)/lib/blas/libsciblas.la
-
-libscilapack_la_PKGCONFIG = lapack.pc
-all: all-am
-
-.SUFFIXES:
-.SUFFIXES: .f .lo .o .obj
-$(srcdir)/Makefile.in: @MAINTAINER_MODE_TRUE@ $(srcdir)/Makefile.am $(am__configure_deps)
- @for dep in $?; do \
- case '$(am__configure_deps)' in \
- *$$dep*) \
- cd $(top_builddir) && $(MAKE) $(AM_MAKEFLAGS) am--refresh \
- && exit 0; \
- exit 1;; \
- esac; \
- done; \
- echo ' cd $(top_srcdir) && $(AUTOMAKE) --foreign lib/lapack/Makefile'; \
- cd $(top_srcdir) && \
- $(AUTOMAKE) --foreign lib/lapack/Makefile
-.PRECIOUS: Makefile
-Makefile: $(srcdir)/Makefile.in $(top_builddir)/config.status
- @case '$?' in \
- *config.status*) \
- cd $(top_builddir) && $(MAKE) $(AM_MAKEFLAGS) am--refresh;; \
- *) \
- echo ' cd $(top_builddir) && $(SHELL) ./config.status $(subdir)/$@ $(am__depfiles_maybe)'; \
- cd $(top_builddir) && $(SHELL) ./config.status $(subdir)/$@ $(am__depfiles_maybe);; \
- esac;
-
-$(top_builddir)/config.status: $(top_srcdir)/configure $(CONFIG_STATUS_DEPENDENCIES)
- cd $(top_builddir) && $(MAKE) $(AM_MAKEFLAGS) am--refresh
-
-$(top_srcdir)/configure: @MAINTAINER_MODE_TRUE@ $(am__configure_deps)
- cd $(top_builddir) && $(MAKE) $(AM_MAKEFLAGS) am--refresh
-$(ACLOCAL_M4): @MAINTAINER_MODE_TRUE@ $(am__aclocal_m4_deps)
- cd $(top_builddir) && $(MAKE) $(AM_MAKEFLAGS) am--refresh
-
-clean-noinstLTLIBRARIES:
- -test -z "$(noinst_LTLIBRARIES)" || rm -f $(noinst_LTLIBRARIES)
- @list='$(noinst_LTLIBRARIES)'; for p in $$list; do \
- dir="`echo $$p | sed -e 's|/[^/]*$$||'`"; \
- test "$$dir" != "$$p" || dir=.; \
- echo "rm -f \"$${dir}/so_locations\""; \
- rm -f "$${dir}/so_locations"; \
- done
-install-pkglibLTLIBRARIES: $(pkglib_LTLIBRARIES)
- @$(NORMAL_INSTALL)
- test -z "$(pkglibdir)" || $(MKDIR_P) "$(DESTDIR)$(pkglibdir)"
- @list='$(pkglib_LTLIBRARIES)'; for p in $$list; do \
- if test -f $$p; then \
- f=$(am__strip_dir) \
- echo " $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(pkglibLTLIBRARIES_INSTALL) $(INSTALL_STRIP_FLAG) '$$p' '$(DESTDIR)$(pkglibdir)/$$f'"; \
- $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(pkglibLTLIBRARIES_INSTALL) $(INSTALL_STRIP_FLAG) "$$p" "$(DESTDIR)$(pkglibdir)/$$f"; \
- else :; fi; \
- done
-
-uninstall-pkglibLTLIBRARIES:
- @$(NORMAL_UNINSTALL)
- @list='$(pkglib_LTLIBRARIES)'; for p in $$list; do \
- p=$(am__strip_dir) \
- echo " $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=uninstall rm -f '$(DESTDIR)$(pkglibdir)/$$p'"; \
- $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=uninstall rm -f "$(DESTDIR)$(pkglibdir)/$$p"; \
- done
-
-clean-pkglibLTLIBRARIES:
- -test -z "$(pkglib_LTLIBRARIES)" || rm -f $(pkglib_LTLIBRARIES)
- @list='$(pkglib_LTLIBRARIES)'; for p in $$list; do \
- dir="`echo $$p | sed -e 's|/[^/]*$$||'`"; \
- test "$$dir" != "$$p" || dir=.; \
- echo "rm -f \"$${dir}/so_locations\""; \
- rm -f "$${dir}/so_locations"; \
- done
-libdummy-lapack.la: $(libdummy_lapack_la_OBJECTS) $(libdummy_lapack_la_DEPENDENCIES)
- $(libdummy_lapack_la_LINK) $(libdummy_lapack_la_OBJECTS) $(libdummy_lapack_la_LIBADD) $(LIBS)
-libscilapack.la: $(libscilapack_la_OBJECTS) $(libscilapack_la_DEPENDENCIES)
- $(F77LINK) -rpath $(pkglibdir) $(libscilapack_la_OBJECTS) $(libscilapack_la_LIBADD) $(LIBS)
-
-mostlyclean-compile:
- -rm -f *.$(OBJEXT)
-
-distclean-compile:
- -rm -f *.tab.c
-
-.f.o:
- $(F77COMPILE) -c -o $@ $<
-
-.f.obj:
- $(F77COMPILE) -c -o $@ `$(CYGPATH_W) '$<'`
-
-.f.lo:
- $(LTF77COMPILE) -c -o $@ $<
-
-mostlyclean-libtool:
- -rm -f *.lo
-
-clean-libtool:
- -rm -rf .libs _libs
-
-ID: $(HEADERS) $(SOURCES) $(LISP) $(TAGS_FILES)
- list='$(SOURCES) $(HEADERS) $(LISP) $(TAGS_FILES)'; \
- unique=`for i in $$list; do \
- if test -f "$$i"; then echo $$i; else echo $(srcdir)/$$i; fi; \
- done | \
- $(AWK) '{ files[$$0] = 1; nonemtpy = 1; } \
- END { if (nonempty) { for (i in files) print i; }; }'`; \
- mkid -fID $$unique
-tags: TAGS
-
-TAGS: $(HEADERS) $(SOURCES) $(TAGS_DEPENDENCIES) \
- $(TAGS_FILES) $(LISP)
- tags=; \
- here=`pwd`; \
- list='$(SOURCES) $(HEADERS) $(LISP) $(TAGS_FILES)'; \
- unique=`for i in $$list; do \
- if test -f "$$i"; then echo $$i; else echo $(srcdir)/$$i; fi; \
- done | \
- $(AWK) '{ files[$$0] = 1; nonempty = 1; } \
- END { if (nonempty) { for (i in files) print i; }; }'`; \
- if test -z "$(ETAGS_ARGS)$$tags$$unique"; then :; else \
- test -n "$$unique" || unique=$$empty_fix; \
- $(ETAGS) $(ETAGSFLAGS) $(AM_ETAGSFLAGS) $(ETAGS_ARGS) \
- $$tags $$unique; \
- fi
-ctags: CTAGS
-CTAGS: $(HEADERS) $(SOURCES) $(TAGS_DEPENDENCIES) \
- $(TAGS_FILES) $(LISP)
- tags=; \
- list='$(SOURCES) $(HEADERS) $(LISP) $(TAGS_FILES)'; \
- unique=`for i in $$list; do \
- if test -f "$$i"; then echo $$i; else echo $(srcdir)/$$i; fi; \
- done | \
- $(AWK) '{ files[$$0] = 1; nonempty = 1; } \
- END { if (nonempty) { for (i in files) print i; }; }'`; \
- test -z "$(CTAGS_ARGS)$$tags$$unique" \
- || $(CTAGS) $(CTAGSFLAGS) $(AM_CTAGSFLAGS) $(CTAGS_ARGS) \
- $$tags $$unique
-
-GTAGS:
- here=`$(am__cd) $(top_builddir) && pwd` \
- && cd $(top_srcdir) \
- && gtags -i $(GTAGS_ARGS) $$here
-
-distclean-tags:
- -rm -f TAGS ID GTAGS GRTAGS GSYMS GPATH tags
-
-distdir: $(DISTFILES)
- @srcdirstrip=`echo "$(srcdir)" | sed 's/[].[^$$\\*]/\\\\&/g'`; \
- topsrcdirstrip=`echo "$(top_srcdir)" | sed 's/[].[^$$\\*]/\\\\&/g'`; \
- list='$(DISTFILES)'; \
- dist_files=`for file in $$list; do echo $$file; done | \
- sed -e "s|^$$srcdirstrip/||;t" \
- -e "s|^$$topsrcdirstrip/|$(top_builddir)/|;t"`; \
- case $$dist_files in \
- */*) $(MKDIR_P) `echo "$$dist_files" | \
- sed '/\//!d;s|^|$(distdir)/|;s,/[^/]*$$,,' | \
- sort -u` ;; \
- esac; \
- for file in $$dist_files; do \
- if test -f $$file || test -d $$file; then d=.; else d=$(srcdir); fi; \
- if test -d $$d/$$file; then \
- dir=`echo "/$$file" | sed -e 's,/[^/]*$$,,'`; \
- if test -d $(srcdir)/$$file && test $$d != $(srcdir); then \
- cp -pR $(srcdir)/$$file $(distdir)$$dir || exit 1; \
- fi; \
- cp -pR $$d/$$file $(distdir)$$dir || exit 1; \
- else \
- test -f $(distdir)/$$file \
- || cp -p $$d/$$file $(distdir)/$$file \
- || exit 1; \
- fi; \
- done
-check-am: all-am
-check: check-am
-all-am: Makefile $(LTLIBRARIES)
-installdirs:
- for dir in "$(DESTDIR)$(pkglibdir)"; do \
- test -z "$$dir" || $(MKDIR_P) "$$dir"; \
- done
-install: install-am
-install-exec: install-exec-am
-install-data: install-data-am
-uninstall: uninstall-am
-
-install-am: all-am
- @$(MAKE) $(AM_MAKEFLAGS) install-exec-am install-data-am
-
-installcheck: installcheck-am
-install-strip:
- $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \
- install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \
- `test -z '$(STRIP)' || \
- echo "INSTALL_PROGRAM_ENV=STRIPPROG='$(STRIP)'"` install
-mostlyclean-generic:
-
-clean-generic:
-
-distclean-generic:
- -test -z "$(CONFIG_CLEAN_FILES)" || rm -f $(CONFIG_CLEAN_FILES)
-
-maintainer-clean-generic:
- @echo "This command is intended for maintainers to use"
- @echo "it deletes files that may require special tools to rebuild."
-clean: clean-am
-
-clean-am: clean-generic clean-libtool clean-noinstLTLIBRARIES \
- clean-pkglibLTLIBRARIES mostlyclean-am
-
-distclean: distclean-am
- -rm -f Makefile
-distclean-am: clean-am distclean-compile distclean-generic \
- distclean-tags
-
-dvi: dvi-am
-
-dvi-am:
-
-html: html-am
-
-info: info-am
-
-info-am:
-
-install-data-am:
-
-install-dvi: install-dvi-am
-
-install-exec-am: install-pkglibLTLIBRARIES
-
-install-html: install-html-am
-
-install-info: install-info-am
-
-install-man:
-
-install-pdf: install-pdf-am
-
-install-ps: install-ps-am
-
-installcheck-am:
-
-maintainer-clean: maintainer-clean-am
- -rm -f Makefile
-maintainer-clean-am: distclean-am maintainer-clean-generic
-
-mostlyclean: mostlyclean-am
-
-mostlyclean-am: mostlyclean-compile mostlyclean-generic \
- mostlyclean-libtool
-
-pdf: pdf-am
-
-pdf-am:
-
-ps: ps-am
-
-ps-am:
-
-uninstall-am: uninstall-pkglibLTLIBRARIES
-
-.MAKE: install-am install-strip
-
-.PHONY: CTAGS GTAGS all all-am check check-am clean clean-generic \
- clean-libtool clean-noinstLTLIBRARIES clean-pkglibLTLIBRARIES \
- ctags distclean distclean-compile distclean-generic \
- distclean-libtool distclean-tags distdir dvi dvi-am html \
- html-am info info-am install install-am install-data \
- install-data-am install-dvi install-dvi-am install-exec \
- install-exec-am install-html install-html-am install-info \
- install-info-am install-man install-pdf install-pdf-am \
- install-pkglibLTLIBRARIES install-ps install-ps-am \
- install-strip installcheck installcheck-am installdirs \
- maintainer-clean maintainer-clean-generic mostlyclean \
- mostlyclean-compile mostlyclean-generic mostlyclean-libtool \
- pdf pdf-am ps ps-am tags uninstall uninstall-am \
- uninstall-pkglibLTLIBRARIES
-
-
-libdummy_lapack_la-dlamch.lo: dlamch.f
- $(LIBTOOL) --tag=F77 --mode=compile $(F77) $(libdummy_lapack_la_FFLAGS) -c -o libdummy_lapack_la-dlamch.lo `test -f 'dlamch.f' || echo '$(srcdir)/'`dlamch.f
-
-libdummy_lapack_la-slamch.lo: slamch.f
- $(LIBTOOL) --tag=F77 --mode=compile $(F77) $(libdummy_lapack_la_FFLAGS) -c -o libdummy_lapack_la-slamch.lo `test -f 'slamch.f' || echo '$(srcdir)/'`slamch.f
-# Tell versions [3.59,3.63) of GNU make to not export all variables.
-# Otherwise a system limit (for SysV at least) may be exceeded.
-.NOEXPORT:
diff --git a/src/lib/lapack/README b/src/lib/lapack/README
deleted file mode 100644
index c14fb64f..00000000
--- a/src/lib/lapack/README
+++ /dev/null
@@ -1,5 +0,0 @@
-This directory contains LAPACK routines.
-File xerbla.f is not used.
-A customized version of xerbla
-for Scilab is in SCIDIR/system/xerbla.f
-
diff --git a/src/lib/lapack/dbdsqr.f b/src/lib/lapack/dbdsqr.f
deleted file mode 100644
index b9f87ec1..00000000
--- a/src/lib/lapack/dbdsqr.f
+++ /dev/null
@@ -1,742 +0,0 @@
- SUBROUTINE DBDSQR( UPLO, N, NCVT, NRU, NCC, D, E, VT, LDVT, U,
- $ LDU, C, LDC, WORK, INFO )
-*
-* -- LAPACK routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- CHARACTER UPLO
- INTEGER INFO, LDC, LDU, LDVT, N, NCC, NCVT, NRU
-* ..
-* .. Array Arguments ..
- DOUBLE PRECISION C( LDC, * ), D( * ), E( * ), U( LDU, * ),
- $ VT( LDVT, * ), WORK( * )
-* ..
-*
-* Purpose
-* =======
-*
-* DBDSQR computes the singular values and, optionally, the right and/or
-* left singular vectors from the singular value decomposition (SVD) of
-* a real N-by-N (upper or lower) bidiagonal matrix B using the implicit
-* zero-shift QR algorithm. The SVD of B has the form
-*
-* B = Q * S * P**T
-*
-* where S is the diagonal matrix of singular values, Q is an orthogonal
-* matrix of left singular vectors, and P is an orthogonal matrix of
-* right singular vectors. If left singular vectors are requested, this
-* subroutine actually returns U*Q instead of Q, and, if right singular
-* vectors are requested, this subroutine returns P**T*VT instead of
-* P**T, for given real input matrices U and VT. When U and VT are the
-* orthogonal matrices that reduce a general matrix A to bidiagonal
-* form: A = U*B*VT, as computed by DGEBRD, then
-*
-* A = (U*Q) * S * (P**T*VT)
-*
-* is the SVD of A. Optionally, the subroutine may also compute Q**T*C
-* for a given real input matrix C.
-*
-* See "Computing Small Singular Values of Bidiagonal Matrices With
-* Guaranteed High Relative Accuracy," by J. Demmel and W. Kahan,
-* LAPACK Working Note #3 (or SIAM J. Sci. Statist. Comput. vol. 11,
-* no. 5, pp. 873-912, Sept 1990) and
-* "Accurate singular values and differential qd algorithms," by
-* B. Parlett and V. Fernando, Technical Report CPAM-554, Mathematics
-* Department, University of California at Berkeley, July 1992
-* for a detailed description of the algorithm.
-*
-* Arguments
-* =========
-*
-* UPLO (input) CHARACTER*1
-* = 'U': B is upper bidiagonal;
-* = 'L': B is lower bidiagonal.
-*
-* N (input) INTEGER
-* The order of the matrix B. N >= 0.
-*
-* NCVT (input) INTEGER
-* The number of columns of the matrix VT. NCVT >= 0.
-*
-* NRU (input) INTEGER
-* The number of rows of the matrix U. NRU >= 0.
-*
-* NCC (input) INTEGER
-* The number of columns of the matrix C. NCC >= 0.
-*
-* D (input/output) DOUBLE PRECISION array, dimension (N)
-* On entry, the n diagonal elements of the bidiagonal matrix B.
-* On exit, if INFO=0, the singular values of B in decreasing
-* order.
-*
-* E (input/output) DOUBLE PRECISION array, dimension (N-1)
-* On entry, the N-1 offdiagonal elements of the bidiagonal
-* matrix B.
-* On exit, if INFO = 0, E is destroyed; if INFO > 0, D and E
-* will contain the diagonal and superdiagonal elements of a
-* bidiagonal matrix orthogonally equivalent to the one given
-* as input.
-*
-* VT (input/output) DOUBLE PRECISION array, dimension (LDVT, NCVT)
-* On entry, an N-by-NCVT matrix VT.
-* On exit, VT is overwritten by P**T * VT.
-* Not referenced if NCVT = 0.
-*
-* LDVT (input) INTEGER
-* The leading dimension of the array VT.
-* LDVT >= max(1,N) if NCVT > 0; LDVT >= 1 if NCVT = 0.
-*
-* U (input/output) DOUBLE PRECISION array, dimension (LDU, N)
-* On entry, an NRU-by-N matrix U.
-* On exit, U is overwritten by U * Q.
-* Not referenced if NRU = 0.
-*
-* LDU (input) INTEGER
-* The leading dimension of the array U. LDU >= max(1,NRU).
-*
-* C (input/output) DOUBLE PRECISION array, dimension (LDC, NCC)
-* On entry, an N-by-NCC matrix C.
-* On exit, C is overwritten by Q**T * C.
-* Not referenced if NCC = 0.
-*
-* LDC (input) INTEGER
-* The leading dimension of the array C.
-* LDC >= max(1,N) if NCC > 0; LDC >=1 if NCC = 0.
-*
-* WORK (workspace) DOUBLE PRECISION array, dimension (2*N)
-* if NCVT = NRU = NCC = 0, (max(1, 4*N-4)) otherwise
-*
-* INFO (output) INTEGER
-* = 0: successful exit
-* < 0: If INFO = -i, the i-th argument had an illegal value
-* > 0: the algorithm did not converge; D and E contain the
-* elements of a bidiagonal matrix which is orthogonally
-* similar to the input matrix B; if INFO = i, i
-* elements of E have not converged to zero.
-*
-* Internal Parameters
-* ===================
-*
-* TOLMUL DOUBLE PRECISION, default = max(10,min(100,EPS**(-1/8)))
-* TOLMUL controls the convergence criterion of the QR loop.
-* If it is positive, TOLMUL*EPS is the desired relative
-* precision in the computed singular values.
-* If it is negative, abs(TOLMUL*EPS*sigma_max) is the
-* desired absolute accuracy in the computed singular
-* values (corresponds to relative accuracy
-* abs(TOLMUL*EPS) in the largest singular value.
-* abs(TOLMUL) should be between 1 and 1/EPS, and preferably
-* between 10 (for fast convergence) and .1/EPS
-* (for there to be some accuracy in the results).
-* Default is to lose at either one eighth or 2 of the
-* available decimal digits in each computed singular value
-* (whichever is smaller).
-*
-* MAXITR INTEGER, default = 6
-* MAXITR controls the maximum number of passes of the
-* algorithm through its inner loop. The algorithms stops
-* (and so fails to converge) if the number of passes
-* through the inner loop exceeds MAXITR*N**2.
-*
-* =====================================================================
-*
-* .. Parameters ..
- DOUBLE PRECISION ZERO
- PARAMETER ( ZERO = 0.0D0 )
- DOUBLE PRECISION ONE
- PARAMETER ( ONE = 1.0D0 )
- DOUBLE PRECISION NEGONE
- PARAMETER ( NEGONE = -1.0D0 )
- DOUBLE PRECISION HNDRTH
- PARAMETER ( HNDRTH = 0.01D0 )
- DOUBLE PRECISION TEN
- PARAMETER ( TEN = 10.0D0 )
- DOUBLE PRECISION HNDRD
- PARAMETER ( HNDRD = 100.0D0 )
- DOUBLE PRECISION MEIGTH
- PARAMETER ( MEIGTH = -0.125D0 )
- INTEGER MAXITR
- PARAMETER ( MAXITR = 6 )
-* ..
-* .. Local Scalars ..
- LOGICAL LOWER, ROTATE
- INTEGER I, IDIR, ISUB, ITER, J, LL, LLL, M, MAXIT, NM1,
- $ NM12, NM13, OLDLL, OLDM
- DOUBLE PRECISION ABSE, ABSS, COSL, COSR, CS, EPS, F, G, H, MU,
- $ OLDCS, OLDSN, R, SHIFT, SIGMN, SIGMX, SINL,
- $ SINR, SLL, SMAX, SMIN, SMINL, SMINOA,
- $ SN, THRESH, TOL, TOLMUL, UNFL
-* ..
-* .. External Functions ..
- LOGICAL LSAME
- DOUBLE PRECISION DLAMCH
- EXTERNAL LSAME, DLAMCH
-* ..
-* .. External Subroutines ..
- EXTERNAL DLARTG, DLAS2, DLASQ1, DLASR, DLASV2, DROT,
- $ DSCAL, DSWAP, XERBLA
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC ABS, DBLE, MAX, MIN, SIGN, SQRT
-* ..
-* .. Executable Statements ..
-*
-* Test the input parameters.
-*
- INFO = 0
- LOWER = LSAME( UPLO, 'L' )
- IF( .NOT.LSAME( UPLO, 'U' ) .AND. .NOT.LOWER ) THEN
- INFO = -1
- ELSE IF( N.LT.0 ) THEN
- INFO = -2
- ELSE IF( NCVT.LT.0 ) THEN
- INFO = -3
- ELSE IF( NRU.LT.0 ) THEN
- INFO = -4
- ELSE IF( NCC.LT.0 ) THEN
- INFO = -5
- ELSE IF( ( NCVT.EQ.0 .AND. LDVT.LT.1 ) .OR.
- $ ( NCVT.GT.0 .AND. LDVT.LT.MAX( 1, N ) ) ) THEN
- INFO = -9
- ELSE IF( LDU.LT.MAX( 1, NRU ) ) THEN
- INFO = -11
- ELSE IF( ( NCC.EQ.0 .AND. LDC.LT.1 ) .OR.
- $ ( NCC.GT.0 .AND. LDC.LT.MAX( 1, N ) ) ) THEN
- INFO = -13
- END IF
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'DBDSQR', -INFO )
- RETURN
- END IF
- IF( N.EQ.0 )
- $ RETURN
- IF( N.EQ.1 )
- $ GO TO 160
-*
-* ROTATE is true if any singular vectors desired, false otherwise
-*
- ROTATE = ( NCVT.GT.0 ) .OR. ( NRU.GT.0 ) .OR. ( NCC.GT.0 )
-*
-* If no singular vectors desired, use qd algorithm
-*
- IF( .NOT.ROTATE ) THEN
- CALL DLASQ1( N, D, E, WORK, INFO )
- RETURN
- END IF
-*
- NM1 = N - 1
- NM12 = NM1 + NM1
- NM13 = NM12 + NM1
- IDIR = 0
-*
-* Get machine constants
-*
- EPS = DLAMCH( 'Epsilon' )
- UNFL = DLAMCH( 'Safe minimum' )
-*
-* If matrix lower bidiagonal, rotate to be upper bidiagonal
-* by applying Givens rotations on the left
-*
- IF( LOWER ) THEN
- DO 10 I = 1, N - 1
- CALL DLARTG( D( I ), E( I ), CS, SN, R )
- D( I ) = R
- E( I ) = SN*D( I+1 )
- D( I+1 ) = CS*D( I+1 )
- WORK( I ) = CS
- WORK( NM1+I ) = SN
- 10 CONTINUE
-*
-* Update singular vectors if desired
-*
- IF( NRU.GT.0 )
- $ CALL DLASR( 'R', 'V', 'F', NRU, N, WORK( 1 ), WORK( N ), U,
- $ LDU )
- IF( NCC.GT.0 )
- $ CALL DLASR( 'L', 'V', 'F', N, NCC, WORK( 1 ), WORK( N ), C,
- $ LDC )
- END IF
-*
-* Compute singular values to relative accuracy TOL
-* (By setting TOL to be negative, algorithm will compute
-* singular values to absolute accuracy ABS(TOL)*norm(input matrix))
-*
- TOLMUL = MAX( TEN, MIN( HNDRD, EPS**MEIGTH ) )
- TOL = TOLMUL*EPS
-*
-* Compute approximate maximum, minimum singular values
-*
- SMAX = ZERO
- DO 20 I = 1, N
- SMAX = MAX( SMAX, ABS( D( I ) ) )
- 20 CONTINUE
- DO 30 I = 1, N - 1
- SMAX = MAX( SMAX, ABS( E( I ) ) )
- 30 CONTINUE
- SMINL = ZERO
- IF( TOL.GE.ZERO ) THEN
-*
-* Relative accuracy desired
-*
- SMINOA = ABS( D( 1 ) )
- IF( SMINOA.EQ.ZERO )
- $ GO TO 50
- MU = SMINOA
- DO 40 I = 2, N
- MU = ABS( D( I ) )*( MU / ( MU+ABS( E( I-1 ) ) ) )
- SMINOA = MIN( SMINOA, MU )
- IF( SMINOA.EQ.ZERO )
- $ GO TO 50
- 40 CONTINUE
- 50 CONTINUE
- SMINOA = SMINOA / SQRT( DBLE( N ) )
- THRESH = MAX( TOL*SMINOA, MAXITR*N*N*UNFL )
- ELSE
-*
-* Absolute accuracy desired
-*
- THRESH = MAX( ABS( TOL )*SMAX, MAXITR*N*N*UNFL )
- END IF
-*
-* Prepare for main iteration loop for the singular values
-* (MAXIT is the maximum number of passes through the inner
-* loop permitted before nonconvergence signalled.)
-*
- MAXIT = MAXITR*N*N
- ITER = 0
- OLDLL = -1
- OLDM = -1
-*
-* M points to last element of unconverged part of matrix
-*
- M = N
-*
-* Begin main iteration loop
-*
- 60 CONTINUE
-*
-* Check for convergence or exceeding iteration count
-*
- IF( M.LE.1 )
- $ GO TO 160
- IF( ITER.GT.MAXIT )
- $ GO TO 200
-*
-* Find diagonal block of matrix to work on
-*
- IF( TOL.LT.ZERO .AND. ABS( D( M ) ).LE.THRESH )
- $ D( M ) = ZERO
- SMAX = ABS( D( M ) )
- SMIN = SMAX
- DO 70 LLL = 1, M - 1
- LL = M - LLL
- ABSS = ABS( D( LL ) )
- ABSE = ABS( E( LL ) )
- IF( TOL.LT.ZERO .AND. ABSS.LE.THRESH )
- $ D( LL ) = ZERO
- IF( ABSE.LE.THRESH )
- $ GO TO 80
- SMIN = MIN( SMIN, ABSS )
- SMAX = MAX( SMAX, ABSS, ABSE )
- 70 CONTINUE
- LL = 0
- GO TO 90
- 80 CONTINUE
- E( LL ) = ZERO
-*
-* Matrix splits since E(LL) = 0
-*
- IF( LL.EQ.M-1 ) THEN
-*
-* Convergence of bottom singular value, return to top of loop
-*
- M = M - 1
- GO TO 60
- END IF
- 90 CONTINUE
- LL = LL + 1
-*
-* E(LL) through E(M-1) are nonzero, E(LL-1) is zero
-*
- IF( LL.EQ.M-1 ) THEN
-*
-* 2 by 2 block, handle separately
-*
- CALL DLASV2( D( M-1 ), E( M-1 ), D( M ), SIGMN, SIGMX, SINR,
- $ COSR, SINL, COSL )
- D( M-1 ) = SIGMX
- E( M-1 ) = ZERO
- D( M ) = SIGMN
-*
-* Compute singular vectors, if desired
-*
- IF( NCVT.GT.0 )
- $ CALL DROT( NCVT, VT( M-1, 1 ), LDVT, VT( M, 1 ), LDVT, COSR,
- $ SINR )
- IF( NRU.GT.0 )
- $ CALL DROT( NRU, U( 1, M-1 ), 1, U( 1, M ), 1, COSL, SINL )
- IF( NCC.GT.0 )
- $ CALL DROT( NCC, C( M-1, 1 ), LDC, C( M, 1 ), LDC, COSL,
- $ SINL )
- M = M - 2
- GO TO 60
- END IF
-*
-* If working on new submatrix, choose shift direction
-* (from larger end diagonal element towards smaller)
-*
- IF( LL.GT.OLDM .OR. M.LT.OLDLL ) THEN
- IF( ABS( D( LL ) ).GE.ABS( D( M ) ) ) THEN
-*
-* Chase bulge from top (big end) to bottom (small end)
-*
- IDIR = 1
- ELSE
-*
-* Chase bulge from bottom (big end) to top (small end)
-*
- IDIR = 2
- END IF
- END IF
-*
-* Apply convergence tests
-*
- IF( IDIR.EQ.1 ) THEN
-*
-* Run convergence test in forward direction
-* First apply standard test to bottom of matrix
-*
- IF( ABS( E( M-1 ) ).LE.ABS( TOL )*ABS( D( M ) ) .OR.
- $ ( TOL.LT.ZERO .AND. ABS( E( M-1 ) ).LE.THRESH ) ) THEN
- E( M-1 ) = ZERO
- GO TO 60
- END IF
-*
- IF( TOL.GE.ZERO ) THEN
-*
-* If relative accuracy desired,
-* apply convergence criterion forward
-*
- MU = ABS( D( LL ) )
- SMINL = MU
- DO 100 LLL = LL, M - 1
- IF( ABS( E( LLL ) ).LE.TOL*MU ) THEN
- E( LLL ) = ZERO
- GO TO 60
- END IF
- MU = ABS( D( LLL+1 ) )*( MU / ( MU+ABS( E( LLL ) ) ) )
- SMINL = MIN( SMINL, MU )
- 100 CONTINUE
- END IF
-*
- ELSE
-*
-* Run convergence test in backward direction
-* First apply standard test to top of matrix
-*
- IF( ABS( E( LL ) ).LE.ABS( TOL )*ABS( D( LL ) ) .OR.
- $ ( TOL.LT.ZERO .AND. ABS( E( LL ) ).LE.THRESH ) ) THEN
- E( LL ) = ZERO
- GO TO 60
- END IF
-*
- IF( TOL.GE.ZERO ) THEN
-*
-* If relative accuracy desired,
-* apply convergence criterion backward
-*
- MU = ABS( D( M ) )
- SMINL = MU
- DO 110 LLL = M - 1, LL, -1
- IF( ABS( E( LLL ) ).LE.TOL*MU ) THEN
- E( LLL ) = ZERO
- GO TO 60
- END IF
- MU = ABS( D( LLL ) )*( MU / ( MU+ABS( E( LLL ) ) ) )
- SMINL = MIN( SMINL, MU )
- 110 CONTINUE
- END IF
- END IF
- OLDLL = LL
- OLDM = M
-*
-* Compute shift. First, test if shifting would ruin relative
-* accuracy, and if so set the shift to zero.
-*
- IF( TOL.GE.ZERO .AND. N*TOL*( SMINL / SMAX ).LE.
- $ MAX( EPS, HNDRTH*TOL ) ) THEN
-*
-* Use a zero shift to avoid loss of relative accuracy
-*
- SHIFT = ZERO
- ELSE
-*
-* Compute the shift from 2-by-2 block at end of matrix
-*
- IF( IDIR.EQ.1 ) THEN
- SLL = ABS( D( LL ) )
- CALL DLAS2( D( M-1 ), E( M-1 ), D( M ), SHIFT, R )
- ELSE
- SLL = ABS( D( M ) )
- CALL DLAS2( D( LL ), E( LL ), D( LL+1 ), SHIFT, R )
- END IF
-*
-* Test if shift negligible, and if so set to zero
-*
- IF( SLL.GT.ZERO ) THEN
- IF( ( SHIFT / SLL )**2.LT.EPS )
- $ SHIFT = ZERO
- END IF
- END IF
-*
-* Increment iteration count
-*
- ITER = ITER + M - LL
-*
-* If SHIFT = 0, do simplified QR iteration
-*
- IF( SHIFT.EQ.ZERO ) THEN
- IF( IDIR.EQ.1 ) THEN
-*
-* Chase bulge from top to bottom
-* Save cosines and sines for later singular vector updates
-*
- CS = ONE
- OLDCS = ONE
- DO 120 I = LL, M - 1
- CALL DLARTG( D( I )*CS, E( I ), CS, SN, R )
- IF( I.GT.LL )
- $ E( I-1 ) = OLDSN*R
- CALL DLARTG( OLDCS*R, D( I+1 )*SN, OLDCS, OLDSN, D( I ) )
- WORK( I-LL+1 ) = CS
- WORK( I-LL+1+NM1 ) = SN
- WORK( I-LL+1+NM12 ) = OLDCS
- WORK( I-LL+1+NM13 ) = OLDSN
- 120 CONTINUE
- H = D( M )*CS
- D( M ) = H*OLDCS
- E( M-1 ) = H*OLDSN
-*
-* Update singular vectors
-*
- IF( NCVT.GT.0 )
- $ CALL DLASR( 'L', 'V', 'F', M-LL+1, NCVT, WORK( 1 ),
- $ WORK( N ), VT( LL, 1 ), LDVT )
- IF( NRU.GT.0 )
- $ CALL DLASR( 'R', 'V', 'F', NRU, M-LL+1, WORK( NM12+1 ),
- $ WORK( NM13+1 ), U( 1, LL ), LDU )
- IF( NCC.GT.0 )
- $ CALL DLASR( 'L', 'V', 'F', M-LL+1, NCC, WORK( NM12+1 ),
- $ WORK( NM13+1 ), C( LL, 1 ), LDC )
-*
-* Test convergence
-*
- IF( ABS( E( M-1 ) ).LE.THRESH )
- $ E( M-1 ) = ZERO
-*
- ELSE
-*
-* Chase bulge from bottom to top
-* Save cosines and sines for later singular vector updates
-*
- CS = ONE
- OLDCS = ONE
- DO 130 I = M, LL + 1, -1
- CALL DLARTG( D( I )*CS, E( I-1 ), CS, SN, R )
- IF( I.LT.M )
- $ E( I ) = OLDSN*R
- CALL DLARTG( OLDCS*R, D( I-1 )*SN, OLDCS, OLDSN, D( I ) )
- WORK( I-LL ) = CS
- WORK( I-LL+NM1 ) = -SN
- WORK( I-LL+NM12 ) = OLDCS
- WORK( I-LL+NM13 ) = -OLDSN
- 130 CONTINUE
- H = D( LL )*CS
- D( LL ) = H*OLDCS
- E( LL ) = H*OLDSN
-*
-* Update singular vectors
-*
- IF( NCVT.GT.0 )
- $ CALL DLASR( 'L', 'V', 'B', M-LL+1, NCVT, WORK( NM12+1 ),
- $ WORK( NM13+1 ), VT( LL, 1 ), LDVT )
- IF( NRU.GT.0 )
- $ CALL DLASR( 'R', 'V', 'B', NRU, M-LL+1, WORK( 1 ),
- $ WORK( N ), U( 1, LL ), LDU )
- IF( NCC.GT.0 )
- $ CALL DLASR( 'L', 'V', 'B', M-LL+1, NCC, WORK( 1 ),
- $ WORK( N ), C( LL, 1 ), LDC )
-*
-* Test convergence
-*
- IF( ABS( E( LL ) ).LE.THRESH )
- $ E( LL ) = ZERO
- END IF
- ELSE
-*
-* Use nonzero shift
-*
- IF( IDIR.EQ.1 ) THEN
-*
-* Chase bulge from top to bottom
-* Save cosines and sines for later singular vector updates
-*
- F = ( ABS( D( LL ) )-SHIFT )*
- $ ( SIGN( ONE, D( LL ) )+SHIFT / D( LL ) )
- G = E( LL )
- DO 140 I = LL, M - 1
- CALL DLARTG( F, G, COSR, SINR, R )
- IF( I.GT.LL )
- $ E( I-1 ) = R
- F = COSR*D( I ) + SINR*E( I )
- E( I ) = COSR*E( I ) - SINR*D( I )
- G = SINR*D( I+1 )
- D( I+1 ) = COSR*D( I+1 )
- CALL DLARTG( F, G, COSL, SINL, R )
- D( I ) = R
- F = COSL*E( I ) + SINL*D( I+1 )
- D( I+1 ) = COSL*D( I+1 ) - SINL*E( I )
- IF( I.LT.M-1 ) THEN
- G = SINL*E( I+1 )
- E( I+1 ) = COSL*E( I+1 )
- END IF
- WORK( I-LL+1 ) = COSR
- WORK( I-LL+1+NM1 ) = SINR
- WORK( I-LL+1+NM12 ) = COSL
- WORK( I-LL+1+NM13 ) = SINL
- 140 CONTINUE
- E( M-1 ) = F
-*
-* Update singular vectors
-*
- IF( NCVT.GT.0 )
- $ CALL DLASR( 'L', 'V', 'F', M-LL+1, NCVT, WORK( 1 ),
- $ WORK( N ), VT( LL, 1 ), LDVT )
- IF( NRU.GT.0 )
- $ CALL DLASR( 'R', 'V', 'F', NRU, M-LL+1, WORK( NM12+1 ),
- $ WORK( NM13+1 ), U( 1, LL ), LDU )
- IF( NCC.GT.0 )
- $ CALL DLASR( 'L', 'V', 'F', M-LL+1, NCC, WORK( NM12+1 ),
- $ WORK( NM13+1 ), C( LL, 1 ), LDC )
-*
-* Test convergence
-*
- IF( ABS( E( M-1 ) ).LE.THRESH )
- $ E( M-1 ) = ZERO
-*
- ELSE
-*
-* Chase bulge from bottom to top
-* Save cosines and sines for later singular vector updates
-*
- F = ( ABS( D( M ) )-SHIFT )*( SIGN( ONE, D( M ) )+SHIFT /
- $ D( M ) )
- G = E( M-1 )
- DO 150 I = M, LL + 1, -1
- CALL DLARTG( F, G, COSR, SINR, R )
- IF( I.LT.M )
- $ E( I ) = R
- F = COSR*D( I ) + SINR*E( I-1 )
- E( I-1 ) = COSR*E( I-1 ) - SINR*D( I )
- G = SINR*D( I-1 )
- D( I-1 ) = COSR*D( I-1 )
- CALL DLARTG( F, G, COSL, SINL, R )
- D( I ) = R
- F = COSL*E( I-1 ) + SINL*D( I-1 )
- D( I-1 ) = COSL*D( I-1 ) - SINL*E( I-1 )
- IF( I.GT.LL+1 ) THEN
- G = SINL*E( I-2 )
- E( I-2 ) = COSL*E( I-2 )
- END IF
- WORK( I-LL ) = COSR
- WORK( I-LL+NM1 ) = -SINR
- WORK( I-LL+NM12 ) = COSL
- WORK( I-LL+NM13 ) = -SINL
- 150 CONTINUE
- E( LL ) = F
-*
-* Test convergence
-*
- IF( ABS( E( LL ) ).LE.THRESH )
- $ E( LL ) = ZERO
-*
-* Update singular vectors if desired
-*
- IF( NCVT.GT.0 )
- $ CALL DLASR( 'L', 'V', 'B', M-LL+1, NCVT, WORK( NM12+1 ),
- $ WORK( NM13+1 ), VT( LL, 1 ), LDVT )
- IF( NRU.GT.0 )
- $ CALL DLASR( 'R', 'V', 'B', NRU, M-LL+1, WORK( 1 ),
- $ WORK( N ), U( 1, LL ), LDU )
- IF( NCC.GT.0 )
- $ CALL DLASR( 'L', 'V', 'B', M-LL+1, NCC, WORK( 1 ),
- $ WORK( N ), C( LL, 1 ), LDC )
- END IF
- END IF
-*
-* QR iteration finished, go back and check convergence
-*
- GO TO 60
-*
-* All singular values converged, so make them positive
-*
- 160 CONTINUE
- DO 170 I = 1, N
- IF( D( I ).LT.ZERO ) THEN
- D( I ) = -D( I )
-*
-* Change sign of singular vectors, if desired
-*
- IF( NCVT.GT.0 )
- $ CALL DSCAL( NCVT, NEGONE, VT( I, 1 ), LDVT )
- END IF
- 170 CONTINUE
-*
-* Sort the singular values into decreasing order (insertion sort on
-* singular values, but only one transposition per singular vector)
-*
- DO 190 I = 1, N - 1
-*
-* Scan for smallest D(I)
-*
- ISUB = 1
- SMIN = D( 1 )
- DO 180 J = 2, N + 1 - I
- IF( D( J ).LE.SMIN ) THEN
- ISUB = J
- SMIN = D( J )
- END IF
- 180 CONTINUE
- IF( ISUB.NE.N+1-I ) THEN
-*
-* Swap singular values and vectors
-*
- D( ISUB ) = D( N+1-I )
- D( N+1-I ) = SMIN
- IF( NCVT.GT.0 )
- $ CALL DSWAP( NCVT, VT( ISUB, 1 ), LDVT, VT( N+1-I, 1 ),
- $ LDVT )
- IF( NRU.GT.0 )
- $ CALL DSWAP( NRU, U( 1, ISUB ), 1, U( 1, N+1-I ), 1 )
- IF( NCC.GT.0 )
- $ CALL DSWAP( NCC, C( ISUB, 1 ), LDC, C( N+1-I, 1 ), LDC )
- END IF
- 190 CONTINUE
- GO TO 220
-*
-* Maximum number of iterations exceeded, failure to converge
-*
- 200 CONTINUE
- INFO = 0
- DO 210 I = 1, N - 1
- IF( E( I ).NE.ZERO )
- $ INFO = INFO + 1
- 210 CONTINUE
- 220 CONTINUE
- RETURN
-*
-* End of DBDSQR
-*
- END
diff --git a/src/lib/lapack/dgebak.f b/src/lib/lapack/dgebak.f
deleted file mode 100644
index b8e9be56..00000000
--- a/src/lib/lapack/dgebak.f
+++ /dev/null
@@ -1,188 +0,0 @@
- SUBROUTINE DGEBAK( JOB, SIDE, N, ILO, IHI, SCALE, M, V, LDV,
- $ INFO )
-*
-* -- LAPACK routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- CHARACTER JOB, SIDE
- INTEGER IHI, ILO, INFO, LDV, M, N
-* ..
-* .. Array Arguments ..
- DOUBLE PRECISION SCALE( * ), V( LDV, * )
-* ..
-*
-* Purpose
-* =======
-*
-* DGEBAK forms the right or left eigenvectors of a real general matrix
-* by backward transformation on the computed eigenvectors of the
-* balanced matrix output by DGEBAL.
-*
-* Arguments
-* =========
-*
-* JOB (input) CHARACTER*1
-* Specifies the type of backward transformation required:
-* = 'N', do nothing, return immediately;
-* = 'P', do backward transformation for permutation only;
-* = 'S', do backward transformation for scaling only;
-* = 'B', do backward transformations for both permutation and
-* scaling.
-* JOB must be the same as the argument JOB supplied to DGEBAL.
-*
-* SIDE (input) CHARACTER*1
-* = 'R': V contains right eigenvectors;
-* = 'L': V contains left eigenvectors.
-*
-* N (input) INTEGER
-* The number of rows of the matrix V. N >= 0.
-*
-* ILO (input) INTEGER
-* IHI (input) INTEGER
-* The integers ILO and IHI determined by DGEBAL.
-* 1 <= ILO <= IHI <= N, if N > 0; ILO=1 and IHI=0, if N=0.
-*
-* SCALE (input) DOUBLE PRECISION array, dimension (N)
-* Details of the permutation and scaling factors, as returned
-* by DGEBAL.
-*
-* M (input) INTEGER
-* The number of columns of the matrix V. M >= 0.
-*
-* V (input/output) DOUBLE PRECISION array, dimension (LDV,M)
-* On entry, the matrix of right or left eigenvectors to be
-* transformed, as returned by DHSEIN or DTREVC.
-* On exit, V is overwritten by the transformed eigenvectors.
-*
-* LDV (input) INTEGER
-* The leading dimension of the array V. LDV >= max(1,N).
-*
-* INFO (output) INTEGER
-* = 0: successful exit
-* < 0: if INFO = -i, the i-th argument had an illegal value.
-*
-* =====================================================================
-*
-* .. Parameters ..
- DOUBLE PRECISION ONE
- PARAMETER ( ONE = 1.0D+0 )
-* ..
-* .. Local Scalars ..
- LOGICAL LEFTV, RIGHTV
- INTEGER I, II, K
- DOUBLE PRECISION S
-* ..
-* .. External Functions ..
- LOGICAL LSAME
- EXTERNAL LSAME
-* ..
-* .. External Subroutines ..
- EXTERNAL DSCAL, DSWAP, XERBLA
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC MAX, MIN
-* ..
-* .. Executable Statements ..
-*
-* Decode and Test the input parameters
-*
- RIGHTV = LSAME( SIDE, 'R' )
- LEFTV = LSAME( SIDE, 'L' )
-*
- INFO = 0
- IF( .NOT.LSAME( JOB, 'N' ) .AND. .NOT.LSAME( JOB, 'P' ) .AND.
- $ .NOT.LSAME( JOB, 'S' ) .AND. .NOT.LSAME( JOB, 'B' ) ) THEN
- INFO = -1
- ELSE IF( .NOT.RIGHTV .AND. .NOT.LEFTV ) THEN
- INFO = -2
- ELSE IF( N.LT.0 ) THEN
- INFO = -3
- ELSE IF( ILO.LT.1 .OR. ILO.GT.MAX( 1, N ) ) THEN
- INFO = -4
- ELSE IF( IHI.LT.MIN( ILO, N ) .OR. IHI.GT.N ) THEN
- INFO = -5
- ELSE IF( M.LT.0 ) THEN
- INFO = -7
- ELSE IF( LDV.LT.MAX( 1, N ) ) THEN
- INFO = -9
- END IF
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'DGEBAK', -INFO )
- RETURN
- END IF
-*
-* Quick return if possible
-*
- IF( N.EQ.0 )
- $ RETURN
- IF( M.EQ.0 )
- $ RETURN
- IF( LSAME( JOB, 'N' ) )
- $ RETURN
-*
- IF( ILO.EQ.IHI )
- $ GO TO 30
-*
-* Backward balance
-*
- IF( LSAME( JOB, 'S' ) .OR. LSAME( JOB, 'B' ) ) THEN
-*
- IF( RIGHTV ) THEN
- DO 10 I = ILO, IHI
- S = SCALE( I )
- CALL DSCAL( M, S, V( I, 1 ), LDV )
- 10 CONTINUE
- END IF
-*
- IF( LEFTV ) THEN
- DO 20 I = ILO, IHI
- S = ONE / SCALE( I )
- CALL DSCAL( M, S, V( I, 1 ), LDV )
- 20 CONTINUE
- END IF
-*
- END IF
-*
-* Backward permutation
-*
-* For I = ILO-1 step -1 until 1,
-* IHI+1 step 1 until N do --
-*
- 30 CONTINUE
- IF( LSAME( JOB, 'P' ) .OR. LSAME( JOB, 'B' ) ) THEN
- IF( RIGHTV ) THEN
- DO 40 II = 1, N
- I = II
- IF( I.GE.ILO .AND. I.LE.IHI )
- $ GO TO 40
- IF( I.LT.ILO )
- $ I = ILO - II
- K = SCALE( I )
- IF( K.EQ.I )
- $ GO TO 40
- CALL DSWAP( M, V( I, 1 ), LDV, V( K, 1 ), LDV )
- 40 CONTINUE
- END IF
-*
- IF( LEFTV ) THEN
- DO 50 II = 1, N
- I = II
- IF( I.GE.ILO .AND. I.LE.IHI )
- $ GO TO 50
- IF( I.LT.ILO )
- $ I = ILO - II
- K = SCALE( I )
- IF( K.EQ.I )
- $ GO TO 50
- CALL DSWAP( M, V( I, 1 ), LDV, V( K, 1 ), LDV )
- 50 CONTINUE
- END IF
- END IF
-*
- RETURN
-*
-* End of DGEBAK
-*
- END
diff --git a/src/lib/lapack/dgebal.f b/src/lib/lapack/dgebal.f
deleted file mode 100644
index 1796577b..00000000
--- a/src/lib/lapack/dgebal.f
+++ /dev/null
@@ -1,322 +0,0 @@
- SUBROUTINE DGEBAL( JOB, N, A, LDA, ILO, IHI, SCALE, INFO )
-*
-* -- LAPACK routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- CHARACTER JOB
- INTEGER IHI, ILO, INFO, LDA, N
-* ..
-* .. Array Arguments ..
- DOUBLE PRECISION A( LDA, * ), SCALE( * )
-* ..
-*
-* Purpose
-* =======
-*
-* DGEBAL balances a general real matrix A. This involves, first,
-* permuting A by a similarity transformation to isolate eigenvalues
-* in the first 1 to ILO-1 and last IHI+1 to N elements on the
-* diagonal; and second, applying a diagonal similarity transformation
-* to rows and columns ILO to IHI to make the rows and columns as
-* close in norm as possible. Both steps are optional.
-*
-* Balancing may reduce the 1-norm of the matrix, and improve the
-* accuracy of the computed eigenvalues and/or eigenvectors.
-*
-* Arguments
-* =========
-*
-* JOB (input) CHARACTER*1
-* Specifies the operations to be performed on A:
-* = 'N': none: simply set ILO = 1, IHI = N, SCALE(I) = 1.0
-* for i = 1,...,N;
-* = 'P': permute only;
-* = 'S': scale only;
-* = 'B': both permute and scale.
-*
-* N (input) INTEGER
-* The order of the matrix A. N >= 0.
-*
-* A (input/output) DOUBLE PRECISION array, dimension (LDA,N)
-* On entry, the input matrix A.
-* On exit, A is overwritten by the balanced matrix.
-* If JOB = 'N', A is not referenced.
-* See Further Details.
-*
-* LDA (input) INTEGER
-* The leading dimension of the array A. LDA >= max(1,N).
-*
-* ILO (output) INTEGER
-* IHI (output) INTEGER
-* ILO and IHI are set to integers such that on exit
-* A(i,j) = 0 if i > j and j = 1,...,ILO-1 or I = IHI+1,...,N.
-* If JOB = 'N' or 'S', ILO = 1 and IHI = N.
-*
-* SCALE (output) DOUBLE PRECISION array, dimension (N)
-* Details of the permutations and scaling factors applied to
-* A. If P(j) is the index of the row and column interchanged
-* with row and column j and D(j) is the scaling factor
-* applied to row and column j, then
-* SCALE(j) = P(j) for j = 1,...,ILO-1
-* = D(j) for j = ILO,...,IHI
-* = P(j) for j = IHI+1,...,N.
-* The order in which the interchanges are made is N to IHI+1,
-* then 1 to ILO-1.
-*
-* INFO (output) INTEGER
-* = 0: successful exit.
-* < 0: if INFO = -i, the i-th argument had an illegal value.
-*
-* Further Details
-* ===============
-*
-* The permutations consist of row and column interchanges which put
-* the matrix in the form
-*
-* ( T1 X Y )
-* P A P = ( 0 B Z )
-* ( 0 0 T2 )
-*
-* where T1 and T2 are upper triangular matrices whose eigenvalues lie
-* along the diagonal. The column indices ILO and IHI mark the starting
-* and ending columns of the submatrix B. Balancing consists of applying
-* a diagonal similarity transformation inv(D) * B * D to make the
-* 1-norms of each row of B and its corresponding column nearly equal.
-* The output matrix is
-*
-* ( T1 X*D Y )
-* ( 0 inv(D)*B*D inv(D)*Z ).
-* ( 0 0 T2 )
-*
-* Information about the permutations P and the diagonal matrix D is
-* returned in the vector SCALE.
-*
-* This subroutine is based on the EISPACK routine BALANC.
-*
-* Modified by Tzu-Yi Chen, Computer Science Division, University of
-* California at Berkeley, USA
-*
-* =====================================================================
-*
-* .. Parameters ..
- DOUBLE PRECISION ZERO, ONE
- PARAMETER ( ZERO = 0.0D+0, ONE = 1.0D+0 )
- DOUBLE PRECISION SCLFAC
- PARAMETER ( SCLFAC = 2.0D+0 )
- DOUBLE PRECISION FACTOR
- PARAMETER ( FACTOR = 0.95D+0 )
-* ..
-* .. Local Scalars ..
- LOGICAL NOCONV
- INTEGER I, ICA, IEXC, IRA, J, K, L, M
- DOUBLE PRECISION C, CA, F, G, R, RA, S, SFMAX1, SFMAX2, SFMIN1,
- $ SFMIN2
-* ..
-* .. External Functions ..
- LOGICAL LSAME
- INTEGER IDAMAX
- DOUBLE PRECISION DLAMCH
- EXTERNAL LSAME, IDAMAX, DLAMCH
-* ..
-* .. External Subroutines ..
- EXTERNAL DSCAL, DSWAP, XERBLA
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC ABS, MAX, MIN
-* ..
-* .. Executable Statements ..
-*
-* Test the input parameters
-*
- INFO = 0
- IF( .NOT.LSAME( JOB, 'N' ) .AND. .NOT.LSAME( JOB, 'P' ) .AND.
- $ .NOT.LSAME( JOB, 'S' ) .AND. .NOT.LSAME( JOB, 'B' ) ) THEN
- INFO = -1
- ELSE IF( N.LT.0 ) THEN
- INFO = -2
- ELSE IF( LDA.LT.MAX( 1, N ) ) THEN
- INFO = -4
- END IF
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'DGEBAL', -INFO )
- RETURN
- END IF
-*
- K = 1
- L = N
-*
- IF( N.EQ.0 )
- $ GO TO 210
-*
- IF( LSAME( JOB, 'N' ) ) THEN
- DO 10 I = 1, N
- SCALE( I ) = ONE
- 10 CONTINUE
- GO TO 210
- END IF
-*
- IF( LSAME( JOB, 'S' ) )
- $ GO TO 120
-*
-* Permutation to isolate eigenvalues if possible
-*
- GO TO 50
-*
-* Row and column exchange.
-*
- 20 CONTINUE
- SCALE( M ) = J
- IF( J.EQ.M )
- $ GO TO 30
-*
- CALL DSWAP( L, A( 1, J ), 1, A( 1, M ), 1 )
- CALL DSWAP( N-K+1, A( J, K ), LDA, A( M, K ), LDA )
-*
- 30 CONTINUE
- GO TO ( 40, 80 )IEXC
-*
-* Search for rows isolating an eigenvalue and push them down.
-*
- 40 CONTINUE
- IF( L.EQ.1 )
- $ GO TO 210
- L = L - 1
-*
- 50 CONTINUE
- DO 70 J = L, 1, -1
-*
- DO 60 I = 1, L
- IF( I.EQ.J )
- $ GO TO 60
- IF( A( J, I ).NE.ZERO )
- $ GO TO 70
- 60 CONTINUE
-*
- M = L
- IEXC = 1
- GO TO 20
- 70 CONTINUE
-*
- GO TO 90
-*
-* Search for columns isolating an eigenvalue and push them left.
-*
- 80 CONTINUE
- K = K + 1
-*
- 90 CONTINUE
- DO 110 J = K, L
-*
- DO 100 I = K, L
- IF( I.EQ.J )
- $ GO TO 100
- IF( A( I, J ).NE.ZERO )
- $ GO TO 110
- 100 CONTINUE
-*
- M = K
- IEXC = 2
- GO TO 20
- 110 CONTINUE
-*
- 120 CONTINUE
- DO 130 I = K, L
- SCALE( I ) = ONE
- 130 CONTINUE
-*
- IF( LSAME( JOB, 'P' ) )
- $ GO TO 210
-*
-* Balance the submatrix in rows K to L.
-*
-* Iterative loop for norm reduction
-*
- SFMIN1 = DLAMCH( 'S' ) / DLAMCH( 'P' )
- SFMAX1 = ONE / SFMIN1
- SFMIN2 = SFMIN1*SCLFAC
- SFMAX2 = ONE / SFMIN2
- 140 CONTINUE
- NOCONV = .FALSE.
-*
- DO 200 I = K, L
- C = ZERO
- R = ZERO
-*
- DO 150 J = K, L
- IF( J.EQ.I )
- $ GO TO 150
- C = C + ABS( A( J, I ) )
- R = R + ABS( A( I, J ) )
- 150 CONTINUE
- ICA = IDAMAX( L, A( 1, I ), 1 )
- CA = ABS( A( ICA, I ) )
- IRA = IDAMAX( N-K+1, A( I, K ), LDA )
- RA = ABS( A( I, IRA+K-1 ) )
-*
-* Guard against zero C or R due to underflow.
-*
- IF( C.EQ.ZERO .OR. R.EQ.ZERO )
- $ GO TO 200
- G = R / SCLFAC
- F = ONE
- S = C + R
- 160 CONTINUE
- IF( C.GE.G .OR. MAX( F, C, CA ).GE.SFMAX2 .OR.
- $ MIN( R, G, RA ).LE.SFMIN2 )GO TO 170
- F = F*SCLFAC
- C = C*SCLFAC
- CA = CA*SCLFAC
- R = R / SCLFAC
- G = G / SCLFAC
- RA = RA / SCLFAC
- GO TO 160
-*
- 170 CONTINUE
- G = C / SCLFAC
- 180 CONTINUE
- IF( G.LT.R .OR. MAX( R, RA ).GE.SFMAX2 .OR.
- $ MIN( F, C, G, CA ).LE.SFMIN2 )GO TO 190
- F = F / SCLFAC
- C = C / SCLFAC
- G = G / SCLFAC
- CA = CA / SCLFAC
- R = R*SCLFAC
- RA = RA*SCLFAC
- GO TO 180
-*
-* Now balance.
-*
- 190 CONTINUE
- IF( ( C+R ).GE.FACTOR*S )
- $ GO TO 200
- IF( F.LT.ONE .AND. SCALE( I ).LT.ONE ) THEN
- IF( F*SCALE( I ).LE.SFMIN1 )
- $ GO TO 200
- END IF
- IF( F.GT.ONE .AND. SCALE( I ).GT.ONE ) THEN
- IF( SCALE( I ).GE.SFMAX1 / F )
- $ GO TO 200
- END IF
- G = ONE / F
- SCALE( I ) = SCALE( I )*F
- NOCONV = .TRUE.
-*
- CALL DSCAL( N-K+1, G, A( I, K ), LDA )
- CALL DSCAL( L, F, A( 1, I ), 1 )
-*
- 200 CONTINUE
-*
- IF( NOCONV )
- $ GO TO 140
-*
- 210 CONTINUE
- ILO = K
- IHI = L
-*
- RETURN
-*
-* End of DGEBAL
-*
- END
diff --git a/src/lib/lapack/dgebd2.f b/src/lib/lapack/dgebd2.f
deleted file mode 100644
index b9eb6387..00000000
--- a/src/lib/lapack/dgebd2.f
+++ /dev/null
@@ -1,239 +0,0 @@
- SUBROUTINE DGEBD2( M, N, A, LDA, D, E, TAUQ, TAUP, WORK, INFO )
-*
-* -- LAPACK routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- INTEGER INFO, LDA, M, N
-* ..
-* .. Array Arguments ..
- DOUBLE PRECISION A( LDA, * ), D( * ), E( * ), TAUP( * ),
- $ TAUQ( * ), WORK( * )
-* ..
-*
-* Purpose
-* =======
-*
-* DGEBD2 reduces a real general m by n matrix A to upper or lower
-* bidiagonal form B by an orthogonal transformation: Q' * A * P = B.
-*
-* If m >= n, B is upper bidiagonal; if m < n, B is lower bidiagonal.
-*
-* Arguments
-* =========
-*
-* M (input) INTEGER
-* The number of rows in the matrix A. M >= 0.
-*
-* N (input) INTEGER
-* The number of columns in the matrix A. N >= 0.
-*
-* A (input/output) DOUBLE PRECISION array, dimension (LDA,N)
-* On entry, the m by n general matrix to be reduced.
-* On exit,
-* if m >= n, the diagonal and the first superdiagonal are
-* overwritten with the upper bidiagonal matrix B; the
-* elements below the diagonal, with the array TAUQ, represent
-* the orthogonal matrix Q as a product of elementary
-* reflectors, and the elements above the first superdiagonal,
-* with the array TAUP, represent the orthogonal matrix P as
-* a product of elementary reflectors;
-* if m < n, the diagonal and the first subdiagonal are
-* overwritten with the lower bidiagonal matrix B; the
-* elements below the first subdiagonal, with the array TAUQ,
-* represent the orthogonal matrix Q as a product of
-* elementary reflectors, and the elements above the diagonal,
-* with the array TAUP, represent the orthogonal matrix P as
-* a product of elementary reflectors.
-* See Further Details.
-*
-* LDA (input) INTEGER
-* The leading dimension of the array A. LDA >= max(1,M).
-*
-* D (output) DOUBLE PRECISION array, dimension (min(M,N))
-* The diagonal elements of the bidiagonal matrix B:
-* D(i) = A(i,i).
-*
-* E (output) DOUBLE PRECISION array, dimension (min(M,N)-1)
-* The off-diagonal elements of the bidiagonal matrix B:
-* if m >= n, E(i) = A(i,i+1) for i = 1,2,...,n-1;
-* if m < n, E(i) = A(i+1,i) for i = 1,2,...,m-1.
-*
-* TAUQ (output) DOUBLE PRECISION array dimension (min(M,N))
-* The scalar factors of the elementary reflectors which
-* represent the orthogonal matrix Q. See Further Details.
-*
-* TAUP (output) DOUBLE PRECISION array, dimension (min(M,N))
-* The scalar factors of the elementary reflectors which
-* represent the orthogonal matrix P. See Further Details.
-*
-* WORK (workspace) DOUBLE PRECISION array, dimension (max(M,N))
-*
-* INFO (output) INTEGER
-* = 0: successful exit.
-* < 0: if INFO = -i, the i-th argument had an illegal value.
-*
-* Further Details
-* ===============
-*
-* The matrices Q and P are represented as products of elementary
-* reflectors:
-*
-* If m >= n,
-*
-* Q = H(1) H(2) . . . H(n) and P = G(1) G(2) . . . G(n-1)
-*
-* Each H(i) and G(i) has the form:
-*
-* H(i) = I - tauq * v * v' and G(i) = I - taup * u * u'
-*
-* where tauq and taup are real scalars, and v and u are real vectors;
-* v(1:i-1) = 0, v(i) = 1, and v(i+1:m) is stored on exit in A(i+1:m,i);
-* u(1:i) = 0, u(i+1) = 1, and u(i+2:n) is stored on exit in A(i,i+2:n);
-* tauq is stored in TAUQ(i) and taup in TAUP(i).
-*
-* If m < n,
-*
-* Q = H(1) H(2) . . . H(m-1) and P = G(1) G(2) . . . G(m)
-*
-* Each H(i) and G(i) has the form:
-*
-* H(i) = I - tauq * v * v' and G(i) = I - taup * u * u'
-*
-* where tauq and taup are real scalars, and v and u are real vectors;
-* v(1:i) = 0, v(i+1) = 1, and v(i+2:m) is stored on exit in A(i+2:m,i);
-* u(1:i-1) = 0, u(i) = 1, and u(i+1:n) is stored on exit in A(i,i+1:n);
-* tauq is stored in TAUQ(i) and taup in TAUP(i).
-*
-* The contents of A on exit are illustrated by the following examples:
-*
-* m = 6 and n = 5 (m > n): m = 5 and n = 6 (m < n):
-*
-* ( d e u1 u1 u1 ) ( d u1 u1 u1 u1 u1 )
-* ( v1 d e u2 u2 ) ( e d u2 u2 u2 u2 )
-* ( v1 v2 d e u3 ) ( v1 e d u3 u3 u3 )
-* ( v1 v2 v3 d e ) ( v1 v2 e d u4 u4 )
-* ( v1 v2 v3 v4 d ) ( v1 v2 v3 e d u5 )
-* ( v1 v2 v3 v4 v5 )
-*
-* where d and e denote diagonal and off-diagonal elements of B, vi
-* denotes an element of the vector defining H(i), and ui an element of
-* the vector defining G(i).
-*
-* =====================================================================
-*
-* .. Parameters ..
- DOUBLE PRECISION ZERO, ONE
- PARAMETER ( ZERO = 0.0D+0, ONE = 1.0D+0 )
-* ..
-* .. Local Scalars ..
- INTEGER I
-* ..
-* .. External Subroutines ..
- EXTERNAL DLARF, DLARFG, XERBLA
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC MAX, MIN
-* ..
-* .. Executable Statements ..
-*
-* Test the input parameters
-*
- INFO = 0
- IF( M.LT.0 ) THEN
- INFO = -1
- ELSE IF( N.LT.0 ) THEN
- INFO = -2
- ELSE IF( LDA.LT.MAX( 1, M ) ) THEN
- INFO = -4
- END IF
- IF( INFO.LT.0 ) THEN
- CALL XERBLA( 'DGEBD2', -INFO )
- RETURN
- END IF
-*
- IF( M.GE.N ) THEN
-*
-* Reduce to upper bidiagonal form
-*
- DO 10 I = 1, N
-*
-* Generate elementary reflector H(i) to annihilate A(i+1:m,i)
-*
- CALL DLARFG( M-I+1, A( I, I ), A( MIN( I+1, M ), I ), 1,
- $ TAUQ( I ) )
- D( I ) = A( I, I )
- A( I, I ) = ONE
-*
-* Apply H(i) to A(i:m,i+1:n) from the left
-*
- IF( I.LT.N )
- $ CALL DLARF( 'Left', M-I+1, N-I, A( I, I ), 1, TAUQ( I ),
- $ A( I, I+1 ), LDA, WORK )
- A( I, I ) = D( I )
-*
- IF( I.LT.N ) THEN
-*
-* Generate elementary reflector G(i) to annihilate
-* A(i,i+2:n)
-*
- CALL DLARFG( N-I, A( I, I+1 ), A( I, MIN( I+2, N ) ),
- $ LDA, TAUP( I ) )
- E( I ) = A( I, I+1 )
- A( I, I+1 ) = ONE
-*
-* Apply G(i) to A(i+1:m,i+1:n) from the right
-*
- CALL DLARF( 'Right', M-I, N-I, A( I, I+1 ), LDA,
- $ TAUP( I ), A( I+1, I+1 ), LDA, WORK )
- A( I, I+1 ) = E( I )
- ELSE
- TAUP( I ) = ZERO
- END IF
- 10 CONTINUE
- ELSE
-*
-* Reduce to lower bidiagonal form
-*
- DO 20 I = 1, M
-*
-* Generate elementary reflector G(i) to annihilate A(i,i+1:n)
-*
- CALL DLARFG( N-I+1, A( I, I ), A( I, MIN( I+1, N ) ), LDA,
- $ TAUP( I ) )
- D( I ) = A( I, I )
- A( I, I ) = ONE
-*
-* Apply G(i) to A(i+1:m,i:n) from the right
-*
- IF( I.LT.M )
- $ CALL DLARF( 'Right', M-I, N-I+1, A( I, I ), LDA,
- $ TAUP( I ), A( I+1, I ), LDA, WORK )
- A( I, I ) = D( I )
-*
- IF( I.LT.M ) THEN
-*
-* Generate elementary reflector H(i) to annihilate
-* A(i+2:m,i)
-*
- CALL DLARFG( M-I, A( I+1, I ), A( MIN( I+2, M ), I ), 1,
- $ TAUQ( I ) )
- E( I ) = A( I+1, I )
- A( I+1, I ) = ONE
-*
-* Apply H(i) to A(i+1:m,i+1:n) from the left
-*
- CALL DLARF( 'Left', M-I, N-I, A( I+1, I ), 1, TAUQ( I ),
- $ A( I+1, I+1 ), LDA, WORK )
- A( I+1, I ) = E( I )
- ELSE
- TAUQ( I ) = ZERO
- END IF
- 20 CONTINUE
- END IF
- RETURN
-*
-* End of DGEBD2
-*
- END
diff --git a/src/lib/lapack/dgebrd.f b/src/lib/lapack/dgebrd.f
deleted file mode 100644
index 6544715d..00000000
--- a/src/lib/lapack/dgebrd.f
+++ /dev/null
@@ -1,268 +0,0 @@
- SUBROUTINE DGEBRD( M, N, A, LDA, D, E, TAUQ, TAUP, WORK, LWORK,
- $ INFO )
-*
-* -- LAPACK routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- INTEGER INFO, LDA, LWORK, M, N
-* ..
-* .. Array Arguments ..
- DOUBLE PRECISION A( LDA, * ), D( * ), E( * ), TAUP( * ),
- $ TAUQ( * ), WORK( * )
-* ..
-*
-* Purpose
-* =======
-*
-* DGEBRD reduces a general real M-by-N matrix A to upper or lower
-* bidiagonal form B by an orthogonal transformation: Q**T * A * P = B.
-*
-* If m >= n, B is upper bidiagonal; if m < n, B is lower bidiagonal.
-*
-* Arguments
-* =========
-*
-* M (input) INTEGER
-* The number of rows in the matrix A. M >= 0.
-*
-* N (input) INTEGER
-* The number of columns in the matrix A. N >= 0.
-*
-* A (input/output) DOUBLE PRECISION array, dimension (LDA,N)
-* On entry, the M-by-N general matrix to be reduced.
-* On exit,
-* if m >= n, the diagonal and the first superdiagonal are
-* overwritten with the upper bidiagonal matrix B; the
-* elements below the diagonal, with the array TAUQ, represent
-* the orthogonal matrix Q as a product of elementary
-* reflectors, and the elements above the first superdiagonal,
-* with the array TAUP, represent the orthogonal matrix P as
-* a product of elementary reflectors;
-* if m < n, the diagonal and the first subdiagonal are
-* overwritten with the lower bidiagonal matrix B; the
-* elements below the first subdiagonal, with the array TAUQ,
-* represent the orthogonal matrix Q as a product of
-* elementary reflectors, and the elements above the diagonal,
-* with the array TAUP, represent the orthogonal matrix P as
-* a product of elementary reflectors.
-* See Further Details.
-*
-* LDA (input) INTEGER
-* The leading dimension of the array A. LDA >= max(1,M).
-*
-* D (output) DOUBLE PRECISION array, dimension (min(M,N))
-* The diagonal elements of the bidiagonal matrix B:
-* D(i) = A(i,i).
-*
-* E (output) DOUBLE PRECISION array, dimension (min(M,N)-1)
-* The off-diagonal elements of the bidiagonal matrix B:
-* if m >= n, E(i) = A(i,i+1) for i = 1,2,...,n-1;
-* if m < n, E(i) = A(i+1,i) for i = 1,2,...,m-1.
-*
-* TAUQ (output) DOUBLE PRECISION array dimension (min(M,N))
-* The scalar factors of the elementary reflectors which
-* represent the orthogonal matrix Q. See Further Details.
-*
-* TAUP (output) DOUBLE PRECISION array, dimension (min(M,N))
-* The scalar factors of the elementary reflectors which
-* represent the orthogonal matrix P. See Further Details.
-*
-* WORK (workspace/output) DOUBLE PRECISION array, dimension (MAX(1,LWORK))
-* On exit, if INFO = 0, WORK(1) returns the optimal LWORK.
-*
-* LWORK (input) INTEGER
-* The length of the array WORK. LWORK >= max(1,M,N).
-* For optimum performance LWORK >= (M+N)*NB, where NB
-* is the optimal blocksize.
-*
-* If LWORK = -1, then a workspace query is assumed; the routine
-* only calculates the optimal size of the WORK array, returns
-* this value as the first entry of the WORK array, and no error
-* message related to LWORK is issued by XERBLA.
-*
-* INFO (output) INTEGER
-* = 0: successful exit
-* < 0: if INFO = -i, the i-th argument had an illegal value.
-*
-* Further Details
-* ===============
-*
-* The matrices Q and P are represented as products of elementary
-* reflectors:
-*
-* If m >= n,
-*
-* Q = H(1) H(2) . . . H(n) and P = G(1) G(2) . . . G(n-1)
-*
-* Each H(i) and G(i) has the form:
-*
-* H(i) = I - tauq * v * v' and G(i) = I - taup * u * u'
-*
-* where tauq and taup are real scalars, and v and u are real vectors;
-* v(1:i-1) = 0, v(i) = 1, and v(i+1:m) is stored on exit in A(i+1:m,i);
-* u(1:i) = 0, u(i+1) = 1, and u(i+2:n) is stored on exit in A(i,i+2:n);
-* tauq is stored in TAUQ(i) and taup in TAUP(i).
-*
-* If m < n,
-*
-* Q = H(1) H(2) . . . H(m-1) and P = G(1) G(2) . . . G(m)
-*
-* Each H(i) and G(i) has the form:
-*
-* H(i) = I - tauq * v * v' and G(i) = I - taup * u * u'
-*
-* where tauq and taup are real scalars, and v and u are real vectors;
-* v(1:i) = 0, v(i+1) = 1, and v(i+2:m) is stored on exit in A(i+2:m,i);
-* u(1:i-1) = 0, u(i) = 1, and u(i+1:n) is stored on exit in A(i,i+1:n);
-* tauq is stored in TAUQ(i) and taup in TAUP(i).
-*
-* The contents of A on exit are illustrated by the following examples:
-*
-* m = 6 and n = 5 (m > n): m = 5 and n = 6 (m < n):
-*
-* ( d e u1 u1 u1 ) ( d u1 u1 u1 u1 u1 )
-* ( v1 d e u2 u2 ) ( e d u2 u2 u2 u2 )
-* ( v1 v2 d e u3 ) ( v1 e d u3 u3 u3 )
-* ( v1 v2 v3 d e ) ( v1 v2 e d u4 u4 )
-* ( v1 v2 v3 v4 d ) ( v1 v2 v3 e d u5 )
-* ( v1 v2 v3 v4 v5 )
-*
-* where d and e denote diagonal and off-diagonal elements of B, vi
-* denotes an element of the vector defining H(i), and ui an element of
-* the vector defining G(i).
-*
-* =====================================================================
-*
-* .. Parameters ..
- DOUBLE PRECISION ONE
- PARAMETER ( ONE = 1.0D+0 )
-* ..
-* .. Local Scalars ..
- LOGICAL LQUERY
- INTEGER I, IINFO, J, LDWRKX, LDWRKY, LWKOPT, MINMN, NB,
- $ NBMIN, NX
- DOUBLE PRECISION WS
-* ..
-* .. External Subroutines ..
- EXTERNAL DGEBD2, DGEMM, DLABRD, XERBLA
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC DBLE, MAX, MIN
-* ..
-* .. External Functions ..
- INTEGER ILAENV
- EXTERNAL ILAENV
-* ..
-* .. Executable Statements ..
-*
-* Test the input parameters
-*
- INFO = 0
- NB = MAX( 1, ILAENV( 1, 'DGEBRD', ' ', M, N, -1, -1 ) )
- LWKOPT = ( M+N )*NB
- WORK( 1 ) = DBLE( LWKOPT )
- LQUERY = ( LWORK.EQ.-1 )
- IF( M.LT.0 ) THEN
- INFO = -1
- ELSE IF( N.LT.0 ) THEN
- INFO = -2
- ELSE IF( LDA.LT.MAX( 1, M ) ) THEN
- INFO = -4
- ELSE IF( LWORK.LT.MAX( 1, M, N ) .AND. .NOT.LQUERY ) THEN
- INFO = -10
- END IF
- IF( INFO.LT.0 ) THEN
- CALL XERBLA( 'DGEBRD', -INFO )
- RETURN
- ELSE IF( LQUERY ) THEN
- RETURN
- END IF
-*
-* Quick return if possible
-*
- MINMN = MIN( M, N )
- IF( MINMN.EQ.0 ) THEN
- WORK( 1 ) = 1
- RETURN
- END IF
-*
- WS = MAX( M, N )
- LDWRKX = M
- LDWRKY = N
-*
- IF( NB.GT.1 .AND. NB.LT.MINMN ) THEN
-*
-* Set the crossover point NX.
-*
- NX = MAX( NB, ILAENV( 3, 'DGEBRD', ' ', M, N, -1, -1 ) )
-*
-* Determine when to switch from blocked to unblocked code.
-*
- IF( NX.LT.MINMN ) THEN
- WS = ( M+N )*NB
- IF( LWORK.LT.WS ) THEN
-*
-* Not enough work space for the optimal NB, consider using
-* a smaller block size.
-*
- NBMIN = ILAENV( 2, 'DGEBRD', ' ', M, N, -1, -1 )
- IF( LWORK.GE.( M+N )*NBMIN ) THEN
- NB = LWORK / ( M+N )
- ELSE
- NB = 1
- NX = MINMN
- END IF
- END IF
- END IF
- ELSE
- NX = MINMN
- END IF
-*
- DO 30 I = 1, MINMN - NX, NB
-*
-* Reduce rows and columns i:i+nb-1 to bidiagonal form and return
-* the matrices X and Y which are needed to update the unreduced
-* part of the matrix
-*
- CALL DLABRD( M-I+1, N-I+1, NB, A( I, I ), LDA, D( I ), E( I ),
- $ TAUQ( I ), TAUP( I ), WORK, LDWRKX,
- $ WORK( LDWRKX*NB+1 ), LDWRKY )
-*
-* Update the trailing submatrix A(i+nb:m,i+nb:n), using an update
-* of the form A := A - V*Y' - X*U'
-*
- CALL DGEMM( 'No transpose', 'Transpose', M-I-NB+1, N-I-NB+1,
- $ NB, -ONE, A( I+NB, I ), LDA,
- $ WORK( LDWRKX*NB+NB+1 ), LDWRKY, ONE,
- $ A( I+NB, I+NB ), LDA )
- CALL DGEMM( 'No transpose', 'No transpose', M-I-NB+1, N-I-NB+1,
- $ NB, -ONE, WORK( NB+1 ), LDWRKX, A( I, I+NB ), LDA,
- $ ONE, A( I+NB, I+NB ), LDA )
-*
-* Copy diagonal and off-diagonal elements of B back into A
-*
- IF( M.GE.N ) THEN
- DO 10 J = I, I + NB - 1
- A( J, J ) = D( J )
- A( J, J+1 ) = E( J )
- 10 CONTINUE
- ELSE
- DO 20 J = I, I + NB - 1
- A( J, J ) = D( J )
- A( J+1, J ) = E( J )
- 20 CONTINUE
- END IF
- 30 CONTINUE
-*
-* Use unblocked code to reduce the remainder of the matrix
-*
- CALL DGEBD2( M-I+1, N-I+1, A( I, I ), LDA, D( I ), E( I ),
- $ TAUQ( I ), TAUP( I ), WORK, IINFO )
- WORK( 1 ) = WS
- RETURN
-*
-* End of DGEBRD
-*
- END
diff --git a/src/lib/lapack/dgecon.f b/src/lib/lapack/dgecon.f
deleted file mode 100644
index 807cafca..00000000
--- a/src/lib/lapack/dgecon.f
+++ /dev/null
@@ -1,185 +0,0 @@
- SUBROUTINE DGECON( NORM, N, A, LDA, ANORM, RCOND, WORK, IWORK,
- $ INFO )
-*
-* -- LAPACK routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* Modified to call DLACN2 in place of DLACON, 5 Feb 03, SJH.
-*
-* .. Scalar Arguments ..
- CHARACTER NORM
- INTEGER INFO, LDA, N
- DOUBLE PRECISION ANORM, RCOND
-* ..
-* .. Array Arguments ..
- INTEGER IWORK( * )
- DOUBLE PRECISION A( LDA, * ), WORK( * )
-* ..
-*
-* Purpose
-* =======
-*
-* DGECON estimates the reciprocal of the condition number of a general
-* real matrix A, in either the 1-norm or the infinity-norm, using
-* the LU factorization computed by DGETRF.
-*
-* An estimate is obtained for norm(inv(A)), and the reciprocal of the
-* condition number is computed as
-* RCOND = 1 / ( norm(A) * norm(inv(A)) ).
-*
-* Arguments
-* =========
-*
-* NORM (input) CHARACTER*1
-* Specifies whether the 1-norm condition number or the
-* infinity-norm condition number is required:
-* = '1' or 'O': 1-norm;
-* = 'I': Infinity-norm.
-*
-* N (input) INTEGER
-* The order of the matrix A. N >= 0.
-*
-* A (input) DOUBLE PRECISION array, dimension (LDA,N)
-* The factors L and U from the factorization A = P*L*U
-* as computed by DGETRF.
-*
-* LDA (input) INTEGER
-* The leading dimension of the array A. LDA >= max(1,N).
-*
-* ANORM (input) DOUBLE PRECISION
-* If NORM = '1' or 'O', the 1-norm of the original matrix A.
-* If NORM = 'I', the infinity-norm of the original matrix A.
-*
-* RCOND (output) DOUBLE PRECISION
-* The reciprocal of the condition number of the matrix A,
-* computed as RCOND = 1/(norm(A) * norm(inv(A))).
-*
-* WORK (workspace) DOUBLE PRECISION array, dimension (4*N)
-*
-* IWORK (workspace) INTEGER array, dimension (N)
-*
-* INFO (output) INTEGER
-* = 0: successful exit
-* < 0: if INFO = -i, the i-th argument had an illegal value
-*
-* =====================================================================
-*
-* .. Parameters ..
- DOUBLE PRECISION ONE, ZERO
- PARAMETER ( ONE = 1.0D+0, ZERO = 0.0D+0 )
-* ..
-* .. Local Scalars ..
- LOGICAL ONENRM
- CHARACTER NORMIN
- INTEGER IX, KASE, KASE1
- DOUBLE PRECISION AINVNM, SCALE, SL, SMLNUM, SU
-* ..
-* .. Local Arrays ..
- INTEGER ISAVE( 3 )
-* ..
-* .. External Functions ..
- LOGICAL LSAME
- INTEGER IDAMAX
- DOUBLE PRECISION DLAMCH
- EXTERNAL LSAME, IDAMAX, DLAMCH
-* ..
-* .. External Subroutines ..
- EXTERNAL DLACN2, DLATRS, DRSCL, XERBLA
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC ABS, MAX
-* ..
-* .. Executable Statements ..
-*
-* Test the input parameters.
-*
- INFO = 0
- ONENRM = NORM.EQ.'1' .OR. LSAME( NORM, 'O' )
- IF( .NOT.ONENRM .AND. .NOT.LSAME( NORM, 'I' ) ) THEN
- INFO = -1
- ELSE IF( N.LT.0 ) THEN
- INFO = -2
- ELSE IF( LDA.LT.MAX( 1, N ) ) THEN
- INFO = -4
- ELSE IF( ANORM.LT.ZERO ) THEN
- INFO = -5
- END IF
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'DGECON', -INFO )
- RETURN
- END IF
-*
-* Quick return if possible
-*
- RCOND = ZERO
- IF( N.EQ.0 ) THEN
- RCOND = ONE
- RETURN
- ELSE IF( ANORM.EQ.ZERO ) THEN
- RETURN
- END IF
-*
- SMLNUM = DLAMCH( 'Safe minimum' )
-*
-* Estimate the norm of inv(A).
-*
- AINVNM = ZERO
- NORMIN = 'N'
- IF( ONENRM ) THEN
- KASE1 = 1
- ELSE
- KASE1 = 2
- END IF
- KASE = 0
- 10 CONTINUE
- CALL DLACN2( N, WORK( N+1 ), WORK, IWORK, AINVNM, KASE, ISAVE )
- IF( KASE.NE.0 ) THEN
- IF( KASE.EQ.KASE1 ) THEN
-*
-* Multiply by inv(L).
-*
- CALL DLATRS( 'Lower', 'No transpose', 'Unit', NORMIN, N, A,
- $ LDA, WORK, SL, WORK( 2*N+1 ), INFO )
-*
-* Multiply by inv(U).
-*
- CALL DLATRS( 'Upper', 'No transpose', 'Non-unit', NORMIN, N,
- $ A, LDA, WORK, SU, WORK( 3*N+1 ), INFO )
- ELSE
-*
-* Multiply by inv(U').
-*
- CALL DLATRS( 'Upper', 'Transpose', 'Non-unit', NORMIN, N, A,
- $ LDA, WORK, SU, WORK( 3*N+1 ), INFO )
-*
-* Multiply by inv(L').
-*
- CALL DLATRS( 'Lower', 'Transpose', 'Unit', NORMIN, N, A,
- $ LDA, WORK, SL, WORK( 2*N+1 ), INFO )
- END IF
-*
-* Divide X by 1/(SL*SU) if doing so will not cause overflow.
-*
- SCALE = SL*SU
- NORMIN = 'Y'
- IF( SCALE.NE.ONE ) THEN
- IX = IDAMAX( N, WORK, 1 )
- IF( SCALE.LT.ABS( WORK( IX ) )*SMLNUM .OR. SCALE.EQ.ZERO )
- $ GO TO 20
- CALL DRSCL( N, SCALE, WORK, 1 )
- END IF
- GO TO 10
- END IF
-*
-* Compute the estimate of the reciprocal condition number.
-*
- IF( AINVNM.NE.ZERO )
- $ RCOND = ( ONE / AINVNM ) / ANORM
-*
- 20 CONTINUE
- RETURN
-*
-* End of DGECON
-*
- END
diff --git a/src/lib/lapack/dgeequ.f b/src/lib/lapack/dgeequ.f
deleted file mode 100644
index b703116e..00000000
--- a/src/lib/lapack/dgeequ.f
+++ /dev/null
@@ -1,225 +0,0 @@
- SUBROUTINE DGEEQU( M, N, A, LDA, R, C, ROWCND, COLCND, AMAX,
- $ INFO )
-*
-* -- LAPACK routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- INTEGER INFO, LDA, M, N
- DOUBLE PRECISION AMAX, COLCND, ROWCND
-* ..
-* .. Array Arguments ..
- DOUBLE PRECISION A( LDA, * ), C( * ), R( * )
-* ..
-*
-* Purpose
-* =======
-*
-* DGEEQU computes row and column scalings intended to equilibrate an
-* M-by-N matrix A and reduce its condition number. R returns the row
-* scale factors and C the column scale factors, chosen to try to make
-* the largest element in each row and column of the matrix B with
-* elements B(i,j)=R(i)*A(i,j)*C(j) have absolute value 1.
-*
-* R(i) and C(j) are restricted to be between SMLNUM = smallest safe
-* number and BIGNUM = largest safe number. Use of these scaling
-* factors is not guaranteed to reduce the condition number of A but
-* works well in practice.
-*
-* Arguments
-* =========
-*
-* M (input) INTEGER
-* The number of rows of the matrix A. M >= 0.
-*
-* N (input) INTEGER
-* The number of columns of the matrix A. N >= 0.
-*
-* A (input) DOUBLE PRECISION array, dimension (LDA,N)
-* The M-by-N matrix whose equilibration factors are
-* to be computed.
-*
-* LDA (input) INTEGER
-* The leading dimension of the array A. LDA >= max(1,M).
-*
-* R (output) DOUBLE PRECISION array, dimension (M)
-* If INFO = 0 or INFO > M, R contains the row scale factors
-* for A.
-*
-* C (output) DOUBLE PRECISION array, dimension (N)
-* If INFO = 0, C contains the column scale factors for A.
-*
-* ROWCND (output) DOUBLE PRECISION
-* If INFO = 0 or INFO > M, ROWCND contains the ratio of the
-* smallest R(i) to the largest R(i). If ROWCND >= 0.1 and
-* AMAX is neither too large nor too small, it is not worth
-* scaling by R.
-*
-* COLCND (output) DOUBLE PRECISION
-* If INFO = 0, COLCND contains the ratio of the smallest
-* C(i) to the largest C(i). If COLCND >= 0.1, it is not
-* worth scaling by C.
-*
-* AMAX (output) DOUBLE PRECISION
-* Absolute value of largest matrix element. If AMAX is very
-* close to overflow or very close to underflow, the matrix
-* should be scaled.
-*
-* INFO (output) INTEGER
-* = 0: successful exit
-* < 0: if INFO = -i, the i-th argument had an illegal value
-* > 0: if INFO = i, and i is
-* <= M: the i-th row of A is exactly zero
-* > M: the (i-M)-th column of A is exactly zero
-*
-* =====================================================================
-*
-* .. Parameters ..
- DOUBLE PRECISION ONE, ZERO
- PARAMETER ( ONE = 1.0D+0, ZERO = 0.0D+0 )
-* ..
-* .. Local Scalars ..
- INTEGER I, J
- DOUBLE PRECISION BIGNUM, RCMAX, RCMIN, SMLNUM
-* ..
-* .. External Functions ..
- DOUBLE PRECISION DLAMCH
- EXTERNAL DLAMCH
-* ..
-* .. External Subroutines ..
- EXTERNAL XERBLA
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC ABS, MAX, MIN
-* ..
-* .. Executable Statements ..
-*
-* Test the input parameters.
-*
- INFO = 0
- IF( M.LT.0 ) THEN
- INFO = -1
- ELSE IF( N.LT.0 ) THEN
- INFO = -2
- ELSE IF( LDA.LT.MAX( 1, M ) ) THEN
- INFO = -4
- END IF
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'DGEEQU', -INFO )
- RETURN
- END IF
-*
-* Quick return if possible
-*
- IF( M.EQ.0 .OR. N.EQ.0 ) THEN
- ROWCND = ONE
- COLCND = ONE
- AMAX = ZERO
- RETURN
- END IF
-*
-* Get machine constants.
-*
- SMLNUM = DLAMCH( 'S' )
- BIGNUM = ONE / SMLNUM
-*
-* Compute row scale factors.
-*
- DO 10 I = 1, M
- R( I ) = ZERO
- 10 CONTINUE
-*
-* Find the maximum element in each row.
-*
- DO 30 J = 1, N
- DO 20 I = 1, M
- R( I ) = MAX( R( I ), ABS( A( I, J ) ) )
- 20 CONTINUE
- 30 CONTINUE
-*
-* Find the maximum and minimum scale factors.
-*
- RCMIN = BIGNUM
- RCMAX = ZERO
- DO 40 I = 1, M
- RCMAX = MAX( RCMAX, R( I ) )
- RCMIN = MIN( RCMIN, R( I ) )
- 40 CONTINUE
- AMAX = RCMAX
-*
- IF( RCMIN.EQ.ZERO ) THEN
-*
-* Find the first zero scale factor and return an error code.
-*
- DO 50 I = 1, M
- IF( R( I ).EQ.ZERO ) THEN
- INFO = I
- RETURN
- END IF
- 50 CONTINUE
- ELSE
-*
-* Invert the scale factors.
-*
- DO 60 I = 1, M
- R( I ) = ONE / MIN( MAX( R( I ), SMLNUM ), BIGNUM )
- 60 CONTINUE
-*
-* Compute ROWCND = min(R(I)) / max(R(I))
-*
- ROWCND = MAX( RCMIN, SMLNUM ) / MIN( RCMAX, BIGNUM )
- END IF
-*
-* Compute column scale factors
-*
- DO 70 J = 1, N
- C( J ) = ZERO
- 70 CONTINUE
-*
-* Find the maximum element in each column,
-* assuming the row scaling computed above.
-*
- DO 90 J = 1, N
- DO 80 I = 1, M
- C( J ) = MAX( C( J ), ABS( A( I, J ) )*R( I ) )
- 80 CONTINUE
- 90 CONTINUE
-*
-* Find the maximum and minimum scale factors.
-*
- RCMIN = BIGNUM
- RCMAX = ZERO
- DO 100 J = 1, N
- RCMIN = MIN( RCMIN, C( J ) )
- RCMAX = MAX( RCMAX, C( J ) )
- 100 CONTINUE
-*
- IF( RCMIN.EQ.ZERO ) THEN
-*
-* Find the first zero scale factor and return an error code.
-*
- DO 110 J = 1, N
- IF( C( J ).EQ.ZERO ) THEN
- INFO = M + J
- RETURN
- END IF
- 110 CONTINUE
- ELSE
-*
-* Invert the scale factors.
-*
- DO 120 J = 1, N
- C( J ) = ONE / MIN( MAX( C( J ), SMLNUM ), BIGNUM )
- 120 CONTINUE
-*
-* Compute COLCND = min(C(J)) / max(C(J))
-*
- COLCND = MAX( RCMIN, SMLNUM ) / MIN( RCMAX, BIGNUM )
- END IF
-*
- RETURN
-*
-* End of DGEEQU
-*
- END
diff --git a/src/lib/lapack/dgees.f b/src/lib/lapack/dgees.f
deleted file mode 100644
index 96ba8019..00000000
--- a/src/lib/lapack/dgees.f
+++ /dev/null
@@ -1,434 +0,0 @@
- SUBROUTINE DGEES( JOBVS, SORT, SELECT, N, A, LDA, SDIM, WR, WI,
- $ VS, LDVS, WORK, LWORK, BWORK, INFO )
-*
-* -- LAPACK driver routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- CHARACTER JOBVS, SORT
- INTEGER INFO, LDA, LDVS, LWORK, N, SDIM
-* ..
-* .. Array Arguments ..
- LOGICAL BWORK( * )
- DOUBLE PRECISION A( LDA, * ), VS( LDVS, * ), WI( * ), WORK( * ),
- $ WR( * )
-* ..
-* .. Function Arguments ..
- LOGICAL SELECT
- EXTERNAL SELECT
-* ..
-*
-* Purpose
-* =======
-*
-* DGEES computes for an N-by-N real nonsymmetric matrix A, the
-* eigenvalues, the real Schur form T, and, optionally, the matrix of
-* Schur vectors Z. This gives the Schur factorization A = Z*T*(Z**T).
-*
-* Optionally, it also orders the eigenvalues on the diagonal of the
-* real Schur form so that selected eigenvalues are at the top left.
-* The leading columns of Z then form an orthonormal basis for the
-* invariant subspace corresponding to the selected eigenvalues.
-*
-* A matrix is in real Schur form if it is upper quasi-triangular with
-* 1-by-1 and 2-by-2 blocks. 2-by-2 blocks will be standardized in the
-* form
-* [ a b ]
-* [ c a ]
-*
-* where b*c < 0. The eigenvalues of such a block are a +- sqrt(bc).
-*
-* Arguments
-* =========
-*
-* JOBVS (input) CHARACTER*1
-* = 'N': Schur vectors are not computed;
-* = 'V': Schur vectors are computed.
-*
-* SORT (input) CHARACTER*1
-* Specifies whether or not to order the eigenvalues on the
-* diagonal of the Schur form.
-* = 'N': Eigenvalues are not ordered;
-* = 'S': Eigenvalues are ordered (see SELECT).
-*
-* SELECT (external procedure) LOGICAL FUNCTION of two DOUBLE PRECISION arguments
-* SELECT must be declared EXTERNAL in the calling subroutine.
-* If SORT = 'S', SELECT is used to select eigenvalues to sort
-* to the top left of the Schur form.
-* If SORT = 'N', SELECT is not referenced.
-* An eigenvalue WR(j)+sqrt(-1)*WI(j) is selected if
-* SELECT(WR(j),WI(j)) is true; i.e., if either one of a complex
-* conjugate pair of eigenvalues is selected, then both complex
-* eigenvalues are selected.
-* Note that a selected complex eigenvalue may no longer
-* satisfy SELECT(WR(j),WI(j)) = .TRUE. after ordering, since
-* ordering may change the value of complex eigenvalues
-* (especially if the eigenvalue is ill-conditioned); in this
-* case INFO is set to N+2 (see INFO below).
-*
-* N (input) INTEGER
-* The order of the matrix A. N >= 0.
-*
-* A (input/output) DOUBLE PRECISION array, dimension (LDA,N)
-* On entry, the N-by-N matrix A.
-* On exit, A has been overwritten by its real Schur form T.
-*
-* LDA (input) INTEGER
-* The leading dimension of the array A. LDA >= max(1,N).
-*
-* SDIM (output) INTEGER
-* If SORT = 'N', SDIM = 0.
-* If SORT = 'S', SDIM = number of eigenvalues (after sorting)
-* for which SELECT is true. (Complex conjugate
-* pairs for which SELECT is true for either
-* eigenvalue count as 2.)
-*
-* WR (output) DOUBLE PRECISION array, dimension (N)
-* WI (output) DOUBLE PRECISION array, dimension (N)
-* WR and WI contain the real and imaginary parts,
-* respectively, of the computed eigenvalues in the same order
-* that they appear on the diagonal of the output Schur form T.
-* Complex conjugate pairs of eigenvalues will appear
-* consecutively with the eigenvalue having the positive
-* imaginary part first.
-*
-* VS (output) DOUBLE PRECISION array, dimension (LDVS,N)
-* If JOBVS = 'V', VS contains the orthogonal matrix Z of Schur
-* vectors.
-* If JOBVS = 'N', VS is not referenced.
-*
-* LDVS (input) INTEGER
-* The leading dimension of the array VS. LDVS >= 1; if
-* JOBVS = 'V', LDVS >= N.
-*
-* WORK (workspace/output) DOUBLE PRECISION array, dimension (MAX(1,LWORK))
-* On exit, if INFO = 0, WORK(1) contains the optimal LWORK.
-*
-* LWORK (input) INTEGER
-* The dimension of the array WORK. LWORK >= max(1,3*N).
-* For good performance, LWORK must generally be larger.
-*
-* If LWORK = -1, then a workspace query is assumed; the routine
-* only calculates the optimal size of the WORK array, returns
-* this value as the first entry of the WORK array, and no error
-* message related to LWORK is issued by XERBLA.
-*
-* BWORK (workspace) LOGICAL array, dimension (N)
-* Not referenced if SORT = 'N'.
-*
-* INFO (output) INTEGER
-* = 0: successful exit
-* < 0: if INFO = -i, the i-th argument had an illegal value.
-* > 0: if INFO = i, and i is
-* <= N: the QR algorithm failed to compute all the
-* eigenvalues; elements 1:ILO-1 and i+1:N of WR and WI
-* contain those eigenvalues which have converged; if
-* JOBVS = 'V', VS contains the matrix which reduces A
-* to its partially converged Schur form.
-* = N+1: the eigenvalues could not be reordered because some
-* eigenvalues were too close to separate (the problem
-* is very ill-conditioned);
-* = N+2: after reordering, roundoff changed values of some
-* complex eigenvalues so that leading eigenvalues in
-* the Schur form no longer satisfy SELECT=.TRUE. This
-* could also be caused by underflow due to scaling.
-*
-* =====================================================================
-*
-* .. Parameters ..
- DOUBLE PRECISION ZERO, ONE
- PARAMETER ( ZERO = 0.0D0, ONE = 1.0D0 )
-* ..
-* .. Local Scalars ..
- LOGICAL CURSL, LASTSL, LQUERY, LST2SL, SCALEA, WANTST,
- $ WANTVS
- INTEGER HSWORK, I, I1, I2, IBAL, ICOND, IERR, IEVAL,
- $ IHI, ILO, INXT, IP, ITAU, IWRK, MAXWRK, MINWRK
- DOUBLE PRECISION ANRM, BIGNUM, CSCALE, EPS, S, SEP, SMLNUM
-* ..
-* .. Local Arrays ..
- INTEGER IDUM( 1 )
- DOUBLE PRECISION DUM( 1 )
-* ..
-* .. External Subroutines ..
- EXTERNAL DCOPY, DGEBAK, DGEBAL, DGEHRD, DHSEQR, DLACPY,
- $ DLABAD, DLASCL, DORGHR, DSWAP, DTRSEN, XERBLA
-* ..
-* .. External Functions ..
- LOGICAL LSAME
- INTEGER ILAENV
- DOUBLE PRECISION DLAMCH, DLANGE
- EXTERNAL LSAME, ILAENV, DLAMCH, DLANGE
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC MAX, SQRT
-* ..
-* .. Executable Statements ..
-*
-* Test the input arguments
-*
- INFO = 0
- LQUERY = ( LWORK.EQ.-1 )
- WANTVS = LSAME( JOBVS, 'V' )
- WANTST = LSAME( SORT, 'S' )
- IF( ( .NOT.WANTVS ) .AND. ( .NOT.LSAME( JOBVS, 'N' ) ) ) THEN
- INFO = -1
- ELSE IF( ( .NOT.WANTST ) .AND. ( .NOT.LSAME( SORT, 'N' ) ) ) THEN
- INFO = -2
- ELSE IF( N.LT.0 ) THEN
- INFO = -4
- ELSE IF( LDA.LT.MAX( 1, N ) ) THEN
- INFO = -6
- ELSE IF( LDVS.LT.1 .OR. ( WANTVS .AND. LDVS.LT.N ) ) THEN
- INFO = -11
- END IF
-*
-* Compute workspace
-* (Note: Comments in the code beginning "Workspace:" describe the
-* minimal amount of workspace needed at that point in the code,
-* as well as the preferred amount for good performance.
-* NB refers to the optimal block size for the immediately
-* following subroutine, as returned by ILAENV.
-* HSWORK refers to the workspace preferred by DHSEQR, as
-* calculated below. HSWORK is computed assuming ILO=1 and IHI=N,
-* the worst case.)
-*
- IF( INFO.EQ.0 ) THEN
- IF( N.EQ.0 ) THEN
- MINWRK = 1
- MAXWRK = 1
- ELSE
- MAXWRK = 2*N + N*ILAENV( 1, 'DGEHRD', ' ', N, 1, N, 0 )
- MINWRK = 3*N
-*
- CALL DHSEQR( 'S', JOBVS, N, 1, N, A, LDA, WR, WI, VS, LDVS,
- $ WORK, -1, IEVAL )
- HSWORK = WORK( 1 )
-*
- IF( .NOT.WANTVS ) THEN
- MAXWRK = MAX( MAXWRK, N + HSWORK )
- ELSE
- MAXWRK = MAX( MAXWRK, 2*N + ( N - 1 )*ILAENV( 1,
- $ 'DORGHR', ' ', N, 1, N, -1 ) )
- MAXWRK = MAX( MAXWRK, N + HSWORK )
- END IF
- END IF
- WORK( 1 ) = MAXWRK
-*
- IF( LWORK.LT.MINWRK .AND. .NOT.LQUERY ) THEN
- INFO = -13
- END IF
- END IF
-*
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'DGEES ', -INFO )
- RETURN
- ELSE IF( LQUERY ) THEN
- RETURN
- END IF
-*
-* Quick return if possible
-*
- IF( N.EQ.0 ) THEN
- SDIM = 0
- RETURN
- END IF
-*
-* Get machine constants
-*
- EPS = DLAMCH( 'P' )
- SMLNUM = DLAMCH( 'S' )
- BIGNUM = ONE / SMLNUM
- CALL DLABAD( SMLNUM, BIGNUM )
- SMLNUM = SQRT( SMLNUM ) / EPS
- BIGNUM = ONE / SMLNUM
-*
-* Scale A if max element outside range [SMLNUM,BIGNUM]
-*
- ANRM = DLANGE( 'M', N, N, A, LDA, DUM )
- SCALEA = .FALSE.
- IF( ANRM.GT.ZERO .AND. ANRM.LT.SMLNUM ) THEN
- SCALEA = .TRUE.
- CSCALE = SMLNUM
- ELSE IF( ANRM.GT.BIGNUM ) THEN
- SCALEA = .TRUE.
- CSCALE = BIGNUM
- END IF
- IF( SCALEA )
- $ CALL DLASCL( 'G', 0, 0, ANRM, CSCALE, N, N, A, LDA, IERR )
-*
-* Permute the matrix to make it more nearly triangular
-* (Workspace: need N)
-*
- IBAL = 1
- CALL DGEBAL( 'P', N, A, LDA, ILO, IHI, WORK( IBAL ), IERR )
-*
-* Reduce to upper Hessenberg form
-* (Workspace: need 3*N, prefer 2*N+N*NB)
-*
- ITAU = N + IBAL
- IWRK = N + ITAU
- CALL DGEHRD( N, ILO, IHI, A, LDA, WORK( ITAU ), WORK( IWRK ),
- $ LWORK-IWRK+1, IERR )
-*
- IF( WANTVS ) THEN
-*
-* Copy Householder vectors to VS
-*
- CALL DLACPY( 'L', N, N, A, LDA, VS, LDVS )
-*
-* Generate orthogonal matrix in VS
-* (Workspace: need 3*N-1, prefer 2*N+(N-1)*NB)
-*
- CALL DORGHR( N, ILO, IHI, VS, LDVS, WORK( ITAU ), WORK( IWRK ),
- $ LWORK-IWRK+1, IERR )
- END IF
-*
- SDIM = 0
-*
-* Perform QR iteration, accumulating Schur vectors in VS if desired
-* (Workspace: need N+1, prefer N+HSWORK (see comments) )
-*
- IWRK = ITAU
- CALL DHSEQR( 'S', JOBVS, N, ILO, IHI, A, LDA, WR, WI, VS, LDVS,
- $ WORK( IWRK ), LWORK-IWRK+1, IEVAL )
- IF( IEVAL.GT.0 )
- $ INFO = IEVAL
-*
-* Sort eigenvalues if desired
-*
- IF( WANTST .AND. INFO.EQ.0 ) THEN
- IF( SCALEA ) THEN
- CALL DLASCL( 'G', 0, 0, CSCALE, ANRM, N, 1, WR, N, IERR )
- CALL DLASCL( 'G', 0, 0, CSCALE, ANRM, N, 1, WI, N, IERR )
- END IF
- DO 10 I = 1, N
- BWORK( I ) = SELECT( WR( I ), WI( I ) )
- 10 CONTINUE
-*
-* Reorder eigenvalues and transform Schur vectors
-* (Workspace: none needed)
-*
- CALL DTRSEN( 'N', JOBVS, BWORK, N, A, LDA, VS, LDVS, WR, WI,
- $ SDIM, S, SEP, WORK( IWRK ), LWORK-IWRK+1, IDUM, 1,
- $ ICOND )
- IF( ICOND.GT.0 )
- $ INFO = N + ICOND
- END IF
-*
- IF( WANTVS ) THEN
-*
-* Undo balancing
-* (Workspace: need N)
-*
- CALL DGEBAK( 'P', 'R', N, ILO, IHI, WORK( IBAL ), N, VS, LDVS,
- $ IERR )
- END IF
-*
- IF( SCALEA ) THEN
-*
-* Undo scaling for the Schur form of A
-*
- CALL DLASCL( 'H', 0, 0, CSCALE, ANRM, N, N, A, LDA, IERR )
- CALL DCOPY( N, A, LDA+1, WR, 1 )
- IF( CSCALE.EQ.SMLNUM ) THEN
-*
-* If scaling back towards underflow, adjust WI if an
-* offdiagonal element of a 2-by-2 block in the Schur form
-* underflows.
-*
- IF( IEVAL.GT.0 ) THEN
- I1 = IEVAL + 1
- I2 = IHI - 1
- CALL DLASCL( 'G', 0, 0, CSCALE, ANRM, ILO-1, 1, WI,
- $ MAX( ILO-1, 1 ), IERR )
- ELSE IF( WANTST ) THEN
- I1 = 1
- I2 = N - 1
- ELSE
- I1 = ILO
- I2 = IHI - 1
- END IF
- INXT = I1 - 1
- DO 20 I = I1, I2
- IF( I.LT.INXT )
- $ GO TO 20
- IF( WI( I ).EQ.ZERO ) THEN
- INXT = I + 1
- ELSE
- IF( A( I+1, I ).EQ.ZERO ) THEN
- WI( I ) = ZERO
- WI( I+1 ) = ZERO
- ELSE IF( A( I+1, I ).NE.ZERO .AND. A( I, I+1 ).EQ.
- $ ZERO ) THEN
- WI( I ) = ZERO
- WI( I+1 ) = ZERO
- IF( I.GT.1 )
- $ CALL DSWAP( I-1, A( 1, I ), 1, A( 1, I+1 ), 1 )
- IF( N.GT.I+1 )
- $ CALL DSWAP( N-I-1, A( I, I+2 ), LDA,
- $ A( I+1, I+2 ), LDA )
- IF( WANTVS ) THEN
- CALL DSWAP( N, VS( 1, I ), 1, VS( 1, I+1 ), 1 )
- END IF
- A( I, I+1 ) = A( I+1, I )
- A( I+1, I ) = ZERO
- END IF
- INXT = I + 2
- END IF
- 20 CONTINUE
- END IF
-*
-* Undo scaling for the imaginary part of the eigenvalues
-*
- CALL DLASCL( 'G', 0, 0, CSCALE, ANRM, N-IEVAL, 1,
- $ WI( IEVAL+1 ), MAX( N-IEVAL, 1 ), IERR )
- END IF
-*
- IF( WANTST .AND. INFO.EQ.0 ) THEN
-*
-* Check if reordering successful
-*
- LASTSL = .TRUE.
- LST2SL = .TRUE.
- SDIM = 0
- IP = 0
- DO 30 I = 1, N
- CURSL = SELECT( WR( I ), WI( I ) )
- IF( WI( I ).EQ.ZERO ) THEN
- IF( CURSL )
- $ SDIM = SDIM + 1
- IP = 0
- IF( CURSL .AND. .NOT.LASTSL )
- $ INFO = N + 2
- ELSE
- IF( IP.EQ.1 ) THEN
-*
-* Last eigenvalue of conjugate pair
-*
- CURSL = CURSL .OR. LASTSL
- LASTSL = CURSL
- IF( CURSL )
- $ SDIM = SDIM + 2
- IP = -1
- IF( CURSL .AND. .NOT.LST2SL )
- $ INFO = N + 2
- ELSE
-*
-* First eigenvalue of conjugate pair
-*
- IP = 1
- END IF
- END IF
- LST2SL = LASTSL
- LASTSL = CURSL
- 30 CONTINUE
- END IF
-*
- WORK( 1 ) = MAXWRK
- RETURN
-*
-* End of DGEES
-*
- END
diff --git a/src/lib/lapack/dgeesx.f b/src/lib/lapack/dgeesx.f
deleted file mode 100644
index deb30ab2..00000000
--- a/src/lib/lapack/dgeesx.f
+++ /dev/null
@@ -1,527 +0,0 @@
- SUBROUTINE DGEESX( JOBVS, SORT, SELECT, SENSE, N, A, LDA, SDIM,
- $ WR, WI, VS, LDVS, RCONDE, RCONDV, WORK, LWORK,
- $ IWORK, LIWORK, BWORK, INFO )
-*
-* -- LAPACK driver routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- CHARACTER JOBVS, SENSE, SORT
- INTEGER INFO, LDA, LDVS, LIWORK, LWORK, N, SDIM
- DOUBLE PRECISION RCONDE, RCONDV
-* ..
-* .. Array Arguments ..
- LOGICAL BWORK( * )
- INTEGER IWORK( * )
- DOUBLE PRECISION A( LDA, * ), VS( LDVS, * ), WI( * ), WORK( * ),
- $ WR( * )
-* ..
-* .. Function Arguments ..
- LOGICAL SELECT
- EXTERNAL SELECT
-* ..
-*
-* Purpose
-* =======
-*
-* DGEESX computes for an N-by-N real nonsymmetric matrix A, the
-* eigenvalues, the real Schur form T, and, optionally, the matrix of
-* Schur vectors Z. This gives the Schur factorization A = Z*T*(Z**T).
-*
-* Optionally, it also orders the eigenvalues on the diagonal of the
-* real Schur form so that selected eigenvalues are at the top left;
-* computes a reciprocal condition number for the average of the
-* selected eigenvalues (RCONDE); and computes a reciprocal condition
-* number for the right invariant subspace corresponding to the
-* selected eigenvalues (RCONDV). The leading columns of Z form an
-* orthonormal basis for this invariant subspace.
-*
-* For further explanation of the reciprocal condition numbers RCONDE
-* and RCONDV, see Section 4.10 of the LAPACK Users' Guide (where
-* these quantities are called s and sep respectively).
-*
-* A real matrix is in real Schur form if it is upper quasi-triangular
-* with 1-by-1 and 2-by-2 blocks. 2-by-2 blocks will be standardized in
-* the form
-* [ a b ]
-* [ c a ]
-*
-* where b*c < 0. The eigenvalues of such a block are a +- sqrt(bc).
-*
-* Arguments
-* =========
-*
-* JOBVS (input) CHARACTER*1
-* = 'N': Schur vectors are not computed;
-* = 'V': Schur vectors are computed.
-*
-* SORT (input) CHARACTER*1
-* Specifies whether or not to order the eigenvalues on the
-* diagonal of the Schur form.
-* = 'N': Eigenvalues are not ordered;
-* = 'S': Eigenvalues are ordered (see SELECT).
-*
-* SELECT (external procedure) LOGICAL FUNCTION of two DOUBLE PRECISION arguments
-* SELECT must be declared EXTERNAL in the calling subroutine.
-* If SORT = 'S', SELECT is used to select eigenvalues to sort
-* to the top left of the Schur form.
-* If SORT = 'N', SELECT is not referenced.
-* An eigenvalue WR(j)+sqrt(-1)*WI(j) is selected if
-* SELECT(WR(j),WI(j)) is true; i.e., if either one of a
-* complex conjugate pair of eigenvalues is selected, then both
-* are. Note that a selected complex eigenvalue may no longer
-* satisfy SELECT(WR(j),WI(j)) = .TRUE. after ordering, since
-* ordering may change the value of complex eigenvalues
-* (especially if the eigenvalue is ill-conditioned); in this
-* case INFO may be set to N+3 (see INFO below).
-*
-* SENSE (input) CHARACTER*1
-* Determines which reciprocal condition numbers are computed.
-* = 'N': None are computed;
-* = 'E': Computed for average of selected eigenvalues only;
-* = 'V': Computed for selected right invariant subspace only;
-* = 'B': Computed for both.
-* If SENSE = 'E', 'V' or 'B', SORT must equal 'S'.
-*
-* N (input) INTEGER
-* The order of the matrix A. N >= 0.
-*
-* A (input/output) DOUBLE PRECISION array, dimension (LDA, N)
-* On entry, the N-by-N matrix A.
-* On exit, A is overwritten by its real Schur form T.
-*
-* LDA (input) INTEGER
-* The leading dimension of the array A. LDA >= max(1,N).
-*
-* SDIM (output) INTEGER
-* If SORT = 'N', SDIM = 0.
-* If SORT = 'S', SDIM = number of eigenvalues (after sorting)
-* for which SELECT is true. (Complex conjugate
-* pairs for which SELECT is true for either
-* eigenvalue count as 2.)
-*
-* WR (output) DOUBLE PRECISION array, dimension (N)
-* WI (output) DOUBLE PRECISION array, dimension (N)
-* WR and WI contain the real and imaginary parts, respectively,
-* of the computed eigenvalues, in the same order that they
-* appear on the diagonal of the output Schur form T. Complex
-* conjugate pairs of eigenvalues appear consecutively with the
-* eigenvalue having the positive imaginary part first.
-*
-* VS (output) DOUBLE PRECISION array, dimension (LDVS,N)
-* If JOBVS = 'V', VS contains the orthogonal matrix Z of Schur
-* vectors.
-* If JOBVS = 'N', VS is not referenced.
-*
-* LDVS (input) INTEGER
-* The leading dimension of the array VS. LDVS >= 1, and if
-* JOBVS = 'V', LDVS >= N.
-*
-* RCONDE (output) DOUBLE PRECISION
-* If SENSE = 'E' or 'B', RCONDE contains the reciprocal
-* condition number for the average of the selected eigenvalues.
-* Not referenced if SENSE = 'N' or 'V'.
-*
-* RCONDV (output) DOUBLE PRECISION
-* If SENSE = 'V' or 'B', RCONDV contains the reciprocal
-* condition number for the selected right invariant subspace.
-* Not referenced if SENSE = 'N' or 'E'.
-*
-* WORK (workspace/output) DOUBLE PRECISION array, dimension (MAX(1,LWORK))
-* On exit, if INFO = 0, WORK(1) returns the optimal LWORK.
-*
-* LWORK (input) INTEGER
-* The dimension of the array WORK. LWORK >= max(1,3*N).
-* Also, if SENSE = 'E' or 'V' or 'B',
-* LWORK >= N+2*SDIM*(N-SDIM), where SDIM is the number of
-* selected eigenvalues computed by this routine. Note that
-* N+2*SDIM*(N-SDIM) <= N+N*N/2. Note also that an error is only
-* returned if LWORK < max(1,3*N), but if SENSE = 'E' or 'V' or
-* 'B' this may not be large enough.
-* For good performance, LWORK must generally be larger.
-*
-* If LWORK = -1, then a workspace query is assumed; the routine
-* only calculates upper bounds on the optimal sizes of the
-* arrays WORK and IWORK, returns these values as the first
-* entries of the WORK and IWORK arrays, and no error messages
-* related to LWORK or LIWORK are issued by XERBLA.
-*
-* IWORK (workspace/output) INTEGER array, dimension (MAX(1,LIWORK))
-* On exit, if INFO = 0, IWORK(1) returns the optimal LIWORK.
-*
-* LIWORK (input) INTEGER
-* The dimension of the array IWORK.
-* LIWORK >= 1; if SENSE = 'V' or 'B', LIWORK >= SDIM*(N-SDIM).
-* Note that SDIM*(N-SDIM) <= N*N/4. Note also that an error is
-* only returned if LIWORK < 1, but if SENSE = 'V' or 'B' this
-* may not be large enough.
-*
-* If LIWORK = -1, then a workspace query is assumed; the
-* routine only calculates upper bounds on the optimal sizes of
-* the arrays WORK and IWORK, returns these values as the first
-* entries of the WORK and IWORK arrays, and no error messages
-* related to LWORK or LIWORK are issued by XERBLA.
-*
-* BWORK (workspace) LOGICAL array, dimension (N)
-* Not referenced if SORT = 'N'.
-*
-* INFO (output) INTEGER
-* = 0: successful exit
-* < 0: if INFO = -i, the i-th argument had an illegal value.
-* > 0: if INFO = i, and i is
-* <= N: the QR algorithm failed to compute all the
-* eigenvalues; elements 1:ILO-1 and i+1:N of WR and WI
-* contain those eigenvalues which have converged; if
-* JOBVS = 'V', VS contains the transformation which
-* reduces A to its partially converged Schur form.
-* = N+1: the eigenvalues could not be reordered because some
-* eigenvalues were too close to separate (the problem
-* is very ill-conditioned);
-* = N+2: after reordering, roundoff changed values of some
-* complex eigenvalues so that leading eigenvalues in
-* the Schur form no longer satisfy SELECT=.TRUE. This
-* could also be caused by underflow due to scaling.
-*
-* =====================================================================
-*
-* .. Parameters ..
- DOUBLE PRECISION ZERO, ONE
- PARAMETER ( ZERO = 0.0D0, ONE = 1.0D0 )
-* ..
-* .. Local Scalars ..
- LOGICAL CURSL, LASTSL, LQUERY, LST2SL, SCALEA, WANTSB,
- $ WANTSE, WANTSN, WANTST, WANTSV, WANTVS
- INTEGER HSWORK, I, I1, I2, IBAL, ICOND, IERR, IEVAL,
- $ IHI, ILO, INXT, IP, ITAU, IWRK, LIWRK, LWRK,
- $ MAXWRK, MINWRK
- DOUBLE PRECISION ANRM, BIGNUM, CSCALE, EPS, SMLNUM
-* ..
-* .. Local Arrays ..
- DOUBLE PRECISION DUM( 1 )
-* ..
-* .. External Subroutines ..
- EXTERNAL DCOPY, DGEBAK, DGEBAL, DGEHRD, DHSEQR, DLACPY,
- $ DLASCL, DORGHR, DSWAP, DTRSEN, XERBLA
-* ..
-* .. External Functions ..
- LOGICAL LSAME
- INTEGER ILAENV
- DOUBLE PRECISION DLAMCH, DLANGE
- EXTERNAL LSAME, ILAENV, DLABAD, DLAMCH, DLANGE
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC MAX, SQRT
-* ..
-* .. Executable Statements ..
-*
-* Test the input arguments
-*
- INFO = 0
- WANTVS = LSAME( JOBVS, 'V' )
- WANTST = LSAME( SORT, 'S' )
- WANTSN = LSAME( SENSE, 'N' )
- WANTSE = LSAME( SENSE, 'E' )
- WANTSV = LSAME( SENSE, 'V' )
- WANTSB = LSAME( SENSE, 'B' )
- LQUERY = ( LWORK.EQ.-1 .OR. LIWORK.EQ.-1 )
- IF( ( .NOT.WANTVS ) .AND. ( .NOT.LSAME( JOBVS, 'N' ) ) ) THEN
- INFO = -1
- ELSE IF( ( .NOT.WANTST ) .AND. ( .NOT.LSAME( SORT, 'N' ) ) ) THEN
- INFO = -2
- ELSE IF( .NOT.( WANTSN .OR. WANTSE .OR. WANTSV .OR. WANTSB ) .OR.
- $ ( .NOT.WANTST .AND. .NOT.WANTSN ) ) THEN
- INFO = -4
- ELSE IF( N.LT.0 ) THEN
- INFO = -5
- ELSE IF( LDA.LT.MAX( 1, N ) ) THEN
- INFO = -7
- ELSE IF( LDVS.LT.1 .OR. ( WANTVS .AND. LDVS.LT.N ) ) THEN
- INFO = -12
- END IF
-*
-* Compute workspace
-* (Note: Comments in the code beginning "RWorkspace:" describe the
-* minimal amount of real workspace needed at that point in the
-* code, as well as the preferred amount for good performance.
-* IWorkspace refers to integer workspace.
-* NB refers to the optimal block size for the immediately
-* following subroutine, as returned by ILAENV.
-* HSWORK refers to the workspace preferred by DHSEQR, as
-* calculated below. HSWORK is computed assuming ILO=1 and IHI=N,
-* the worst case.
-* If SENSE = 'E', 'V' or 'B', then the amount of workspace needed
-* depends on SDIM, which is computed by the routine DTRSEN later
-* in the code.)
-*
- IF( INFO.EQ.0 ) THEN
- LIWRK = 1
- IF( N.EQ.0 ) THEN
- MINWRK = 1
- LWRK = 1
- ELSE
- MAXWRK = 2*N + N*ILAENV( 1, 'DGEHRD', ' ', N, 1, N, 0 )
- MINWRK = 3*N
-*
- CALL DHSEQR( 'S', JOBVS, N, 1, N, A, LDA, WR, WI, VS, LDVS,
- $ WORK, -1, IEVAL )
- HSWORK = WORK( 1 )
-*
- IF( .NOT.WANTVS ) THEN
- MAXWRK = MAX( MAXWRK, N + HSWORK )
- ELSE
- MAXWRK = MAX( MAXWRK, 2*N + ( N - 1 )*ILAENV( 1,
- $ 'DORGHR', ' ', N, 1, N, -1 ) )
- MAXWRK = MAX( MAXWRK, N + HSWORK )
- END IF
- LWRK = MAXWRK
- IF( .NOT.WANTSN )
- $ LWRK = MAX( LWRK, N + ( N*N )/2 )
- IF( WANTSV .OR. WANTSB )
- $ LIWRK = ( N*N )/4
- END IF
- IWORK( 1 ) = LIWRK
- WORK( 1 ) = LWRK
-*
- IF( LWORK.LT.MINWRK .AND. .NOT.LQUERY ) THEN
- INFO = -16
- ELSE IF( LIWORK.LT.1 .AND. .NOT.LQUERY ) THEN
- INFO = -18
- END IF
- END IF
-*
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'DGEESX', -INFO )
- RETURN
- END IF
-*
-* Quick return if possible
-*
- IF( N.EQ.0 ) THEN
- SDIM = 0
- RETURN
- END IF
-*
-* Get machine constants
-*
- EPS = DLAMCH( 'P' )
- SMLNUM = DLAMCH( 'S' )
- BIGNUM = ONE / SMLNUM
- CALL DLABAD( SMLNUM, BIGNUM )
- SMLNUM = SQRT( SMLNUM ) / EPS
- BIGNUM = ONE / SMLNUM
-*
-* Scale A if max element outside range [SMLNUM,BIGNUM]
-*
- ANRM = DLANGE( 'M', N, N, A, LDA, DUM )
- SCALEA = .FALSE.
- IF( ANRM.GT.ZERO .AND. ANRM.LT.SMLNUM ) THEN
- SCALEA = .TRUE.
- CSCALE = SMLNUM
- ELSE IF( ANRM.GT.BIGNUM ) THEN
- SCALEA = .TRUE.
- CSCALE = BIGNUM
- END IF
- IF( SCALEA )
- $ CALL DLASCL( 'G', 0, 0, ANRM, CSCALE, N, N, A, LDA, IERR )
-*
-* Permute the matrix to make it more nearly triangular
-* (RWorkspace: need N)
-*
- IBAL = 1
- CALL DGEBAL( 'P', N, A, LDA, ILO, IHI, WORK( IBAL ), IERR )
-*
-* Reduce to upper Hessenberg form
-* (RWorkspace: need 3*N, prefer 2*N+N*NB)
-*
- ITAU = N + IBAL
- IWRK = N + ITAU
- CALL DGEHRD( N, ILO, IHI, A, LDA, WORK( ITAU ), WORK( IWRK ),
- $ LWORK-IWRK+1, IERR )
-*
- IF( WANTVS ) THEN
-*
-* Copy Householder vectors to VS
-*
- CALL DLACPY( 'L', N, N, A, LDA, VS, LDVS )
-*
-* Generate orthogonal matrix in VS
-* (RWorkspace: need 3*N-1, prefer 2*N+(N-1)*NB)
-*
- CALL DORGHR( N, ILO, IHI, VS, LDVS, WORK( ITAU ), WORK( IWRK ),
- $ LWORK-IWRK+1, IERR )
- END IF
-*
- SDIM = 0
-*
-* Perform QR iteration, accumulating Schur vectors in VS if desired
-* (RWorkspace: need N+1, prefer N+HSWORK (see comments) )
-*
- IWRK = ITAU
- CALL DHSEQR( 'S', JOBVS, N, ILO, IHI, A, LDA, WR, WI, VS, LDVS,
- $ WORK( IWRK ), LWORK-IWRK+1, IEVAL )
- IF( IEVAL.GT.0 )
- $ INFO = IEVAL
-*
-* Sort eigenvalues if desired
-*
- IF( WANTST .AND. INFO.EQ.0 ) THEN
- IF( SCALEA ) THEN
- CALL DLASCL( 'G', 0, 0, CSCALE, ANRM, N, 1, WR, N, IERR )
- CALL DLASCL( 'G', 0, 0, CSCALE, ANRM, N, 1, WI, N, IERR )
- END IF
- DO 10 I = 1, N
- BWORK( I ) = SELECT( WR( I ), WI( I ) )
- 10 CONTINUE
-*
-* Reorder eigenvalues, transform Schur vectors, and compute
-* reciprocal condition numbers
-* (RWorkspace: if SENSE is not 'N', need N+2*SDIM*(N-SDIM)
-* otherwise, need N )
-* (IWorkspace: if SENSE is 'V' or 'B', need SDIM*(N-SDIM)
-* otherwise, need 0 )
-*
- CALL DTRSEN( SENSE, JOBVS, BWORK, N, A, LDA, VS, LDVS, WR, WI,
- $ SDIM, RCONDE, RCONDV, WORK( IWRK ), LWORK-IWRK+1,
- $ IWORK, LIWORK, ICOND )
- IF( .NOT.WANTSN )
- $ MAXWRK = MAX( MAXWRK, N+2*SDIM*( N-SDIM ) )
- IF( ICOND.EQ.-15 ) THEN
-*
-* Not enough real workspace
-*
- INFO = -16
- ELSE IF( ICOND.EQ.-17 ) THEN
-*
-* Not enough integer workspace
-*
- INFO = -18
- ELSE IF( ICOND.GT.0 ) THEN
-*
-* DTRSEN failed to reorder or to restore standard Schur form
-*
- INFO = ICOND + N
- END IF
- END IF
-*
- IF( WANTVS ) THEN
-*
-* Undo balancing
-* (RWorkspace: need N)
-*
- CALL DGEBAK( 'P', 'R', N, ILO, IHI, WORK( IBAL ), N, VS, LDVS,
- $ IERR )
- END IF
-*
- IF( SCALEA ) THEN
-*
-* Undo scaling for the Schur form of A
-*
- CALL DLASCL( 'H', 0, 0, CSCALE, ANRM, N, N, A, LDA, IERR )
- CALL DCOPY( N, A, LDA+1, WR, 1 )
- IF( ( WANTSV .OR. WANTSB ) .AND. INFO.EQ.0 ) THEN
- DUM( 1 ) = RCONDV
- CALL DLASCL( 'G', 0, 0, CSCALE, ANRM, 1, 1, DUM, 1, IERR )
- RCONDV = DUM( 1 )
- END IF
- IF( CSCALE.EQ.SMLNUM ) THEN
-*
-* If scaling back towards underflow, adjust WI if an
-* offdiagonal element of a 2-by-2 block in the Schur form
-* underflows.
-*
- IF( IEVAL.GT.0 ) THEN
- I1 = IEVAL + 1
- I2 = IHI - 1
- CALL DLASCL( 'G', 0, 0, CSCALE, ANRM, ILO-1, 1, WI, N,
- $ IERR )
- ELSE IF( WANTST ) THEN
- I1 = 1
- I2 = N - 1
- ELSE
- I1 = ILO
- I2 = IHI - 1
- END IF
- INXT = I1 - 1
- DO 20 I = I1, I2
- IF( I.LT.INXT )
- $ GO TO 20
- IF( WI( I ).EQ.ZERO ) THEN
- INXT = I + 1
- ELSE
- IF( A( I+1, I ).EQ.ZERO ) THEN
- WI( I ) = ZERO
- WI( I+1 ) = ZERO
- ELSE IF( A( I+1, I ).NE.ZERO .AND. A( I, I+1 ).EQ.
- $ ZERO ) THEN
- WI( I ) = ZERO
- WI( I+1 ) = ZERO
- IF( I.GT.1 )
- $ CALL DSWAP( I-1, A( 1, I ), 1, A( 1, I+1 ), 1 )
- IF( N.GT.I+1 )
- $ CALL DSWAP( N-I-1, A( I, I+2 ), LDA,
- $ A( I+1, I+2 ), LDA )
- CALL DSWAP( N, VS( 1, I ), 1, VS( 1, I+1 ), 1 )
- A( I, I+1 ) = A( I+1, I )
- A( I+1, I ) = ZERO
- END IF
- INXT = I + 2
- END IF
- 20 CONTINUE
- END IF
- CALL DLASCL( 'G', 0, 0, CSCALE, ANRM, N-IEVAL, 1,
- $ WI( IEVAL+1 ), MAX( N-IEVAL, 1 ), IERR )
- END IF
-*
- IF( WANTST .AND. INFO.EQ.0 ) THEN
-*
-* Check if reordering successful
-*
- LASTSL = .TRUE.
- LST2SL = .TRUE.
- SDIM = 0
- IP = 0
- DO 30 I = 1, N
- CURSL = SELECT( WR( I ), WI( I ) )
- IF( WI( I ).EQ.ZERO ) THEN
- IF( CURSL )
- $ SDIM = SDIM + 1
- IP = 0
- IF( CURSL .AND. .NOT.LASTSL )
- $ INFO = N + 2
- ELSE
- IF( IP.EQ.1 ) THEN
-*
-* Last eigenvalue of conjugate pair
-*
- CURSL = CURSL .OR. LASTSL
- LASTSL = CURSL
- IF( CURSL )
- $ SDIM = SDIM + 2
- IP = -1
- IF( CURSL .AND. .NOT.LST2SL )
- $ INFO = N + 2
- ELSE
-*
-* First eigenvalue of conjugate pair
-*
- IP = 1
- END IF
- END IF
- LST2SL = LASTSL
- LASTSL = CURSL
- 30 CONTINUE
- END IF
-*
- WORK( 1 ) = MAXWRK
- IF( WANTSV .OR. WANTSB ) THEN
- IWORK( 1 ) = MAX( 1, SDIM*( N-SDIM ) )
- ELSE
- IWORK( 1 ) = 1
- END IF
-*
- RETURN
-*
-* End of DGEESX
-*
- END
diff --git a/src/lib/lapack/dgeev.f b/src/lib/lapack/dgeev.f
deleted file mode 100644
index 50e08a9c..00000000
--- a/src/lib/lapack/dgeev.f
+++ /dev/null
@@ -1,423 +0,0 @@
- SUBROUTINE DGEEV( JOBVL, JOBVR, N, A, LDA, WR, WI, VL, LDVL, VR,
- $ LDVR, WORK, LWORK, INFO )
-*
-* -- LAPACK driver routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- CHARACTER JOBVL, JOBVR
- INTEGER INFO, LDA, LDVL, LDVR, LWORK, N
-* ..
-* .. Array Arguments ..
- DOUBLE PRECISION A( LDA, * ), VL( LDVL, * ), VR( LDVR, * ),
- $ WI( * ), WORK( * ), WR( * )
-* ..
-*
-* Purpose
-* =======
-*
-* DGEEV computes for an N-by-N real nonsymmetric matrix A, the
-* eigenvalues and, optionally, the left and/or right eigenvectors.
-*
-* The right eigenvector v(j) of A satisfies
-* A * v(j) = lambda(j) * v(j)
-* where lambda(j) is its eigenvalue.
-* The left eigenvector u(j) of A satisfies
-* u(j)**H * A = lambda(j) * u(j)**H
-* where u(j)**H denotes the conjugate transpose of u(j).
-*
-* The computed eigenvectors are normalized to have Euclidean norm
-* equal to 1 and largest component real.
-*
-* Arguments
-* =========
-*
-* JOBVL (input) CHARACTER*1
-* = 'N': left eigenvectors of A are not computed;
-* = 'V': left eigenvectors of A are computed.
-*
-* JOBVR (input) CHARACTER*1
-* = 'N': right eigenvectors of A are not computed;
-* = 'V': right eigenvectors of A are computed.
-*
-* N (input) INTEGER
-* The order of the matrix A. N >= 0.
-*
-* A (input/output) DOUBLE PRECISION array, dimension (LDA,N)
-* On entry, the N-by-N matrix A.
-* On exit, A has been overwritten.
-*
-* LDA (input) INTEGER
-* The leading dimension of the array A. LDA >= max(1,N).
-*
-* WR (output) DOUBLE PRECISION array, dimension (N)
-* WI (output) DOUBLE PRECISION array, dimension (N)
-* WR and WI contain the real and imaginary parts,
-* respectively, of the computed eigenvalues. Complex
-* conjugate pairs of eigenvalues appear consecutively
-* with the eigenvalue having the positive imaginary part
-* first.
-*
-* VL (output) DOUBLE PRECISION array, dimension (LDVL,N)
-* If JOBVL = 'V', the left eigenvectors u(j) are stored one
-* after another in the columns of VL, in the same order
-* as their eigenvalues.
-* If JOBVL = 'N', VL is not referenced.
-* If the j-th eigenvalue is real, then u(j) = VL(:,j),
-* the j-th column of VL.
-* If the j-th and (j+1)-st eigenvalues form a complex
-* conjugate pair, then u(j) = VL(:,j) + i*VL(:,j+1) and
-* u(j+1) = VL(:,j) - i*VL(:,j+1).
-*
-* LDVL (input) INTEGER
-* The leading dimension of the array VL. LDVL >= 1; if
-* JOBVL = 'V', LDVL >= N.
-*
-* VR (output) DOUBLE PRECISION array, dimension (LDVR,N)
-* If JOBVR = 'V', the right eigenvectors v(j) are stored one
-* after another in the columns of VR, in the same order
-* as their eigenvalues.
-* If JOBVR = 'N', VR is not referenced.
-* If the j-th eigenvalue is real, then v(j) = VR(:,j),
-* the j-th column of VR.
-* If the j-th and (j+1)-st eigenvalues form a complex
-* conjugate pair, then v(j) = VR(:,j) + i*VR(:,j+1) and
-* v(j+1) = VR(:,j) - i*VR(:,j+1).
-*
-* LDVR (input) INTEGER
-* The leading dimension of the array VR. LDVR >= 1; if
-* JOBVR = 'V', LDVR >= N.
-*
-* WORK (workspace/output) DOUBLE PRECISION array, dimension (MAX(1,LWORK))
-* On exit, if INFO = 0, WORK(1) returns the optimal LWORK.
-*
-* LWORK (input) INTEGER
-* The dimension of the array WORK. LWORK >= max(1,3*N), and
-* if JOBVL = 'V' or JOBVR = 'V', LWORK >= 4*N. For good
-* performance, LWORK must generally be larger.
-*
-* If LWORK = -1, then a workspace query is assumed; the routine
-* only calculates the optimal size of the WORK array, returns
-* this value as the first entry of the WORK array, and no error
-* message related to LWORK is issued by XERBLA.
-*
-* INFO (output) INTEGER
-* = 0: successful exit
-* < 0: if INFO = -i, the i-th argument had an illegal value.
-* > 0: if INFO = i, the QR algorithm failed to compute all the
-* eigenvalues, and no eigenvectors have been computed;
-* elements i+1:N of WR and WI contain eigenvalues which
-* have converged.
-*
-* =====================================================================
-*
-* .. Parameters ..
- DOUBLE PRECISION ZERO, ONE
- PARAMETER ( ZERO = 0.0D0, ONE = 1.0D0 )
-* ..
-* .. Local Scalars ..
- LOGICAL LQUERY, SCALEA, WANTVL, WANTVR
- CHARACTER SIDE
- INTEGER HSWORK, I, IBAL, IERR, IHI, ILO, ITAU, IWRK, K,
- $ MAXWRK, MINWRK, NOUT
- DOUBLE PRECISION ANRM, BIGNUM, CS, CSCALE, EPS, R, SCL, SMLNUM,
- $ SN
-* ..
-* .. Local Arrays ..
- LOGICAL SELECT( 1 )
- DOUBLE PRECISION DUM( 1 )
-* ..
-* .. External Subroutines ..
- EXTERNAL DGEBAK, DGEBAL, DGEHRD, DHSEQR, DLABAD, DLACPY,
- $ DLARTG, DLASCL, DORGHR, DROT, DSCAL, DTREVC,
- $ XERBLA
-* ..
-* .. External Functions ..
- LOGICAL LSAME
- INTEGER IDAMAX, ILAENV
- DOUBLE PRECISION DLAMCH, DLANGE, DLAPY2, DNRM2
- EXTERNAL LSAME, IDAMAX, ILAENV, DLAMCH, DLANGE, DLAPY2,
- $ DNRM2
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC MAX, SQRT
-* ..
-* .. Executable Statements ..
-*
-* Test the input arguments
-*
- INFO = 0
- LQUERY = ( LWORK.EQ.-1 )
- WANTVL = LSAME( JOBVL, 'V' )
- WANTVR = LSAME( JOBVR, 'V' )
- IF( ( .NOT.WANTVL ) .AND. ( .NOT.LSAME( JOBVL, 'N' ) ) ) THEN
- INFO = -1
- ELSE IF( ( .NOT.WANTVR ) .AND. ( .NOT.LSAME( JOBVR, 'N' ) ) ) THEN
- INFO = -2
- ELSE IF( N.LT.0 ) THEN
- INFO = -3
- ELSE IF( LDA.LT.MAX( 1, N ) ) THEN
- INFO = -5
- ELSE IF( LDVL.LT.1 .OR. ( WANTVL .AND. LDVL.LT.N ) ) THEN
- INFO = -9
- ELSE IF( LDVR.LT.1 .OR. ( WANTVR .AND. LDVR.LT.N ) ) THEN
- INFO = -11
- END IF
-*
-* Compute workspace
-* (Note: Comments in the code beginning "Workspace:" describe the
-* minimal amount of workspace needed at that point in the code,
-* as well as the preferred amount for good performance.
-* NB refers to the optimal block size for the immediately
-* following subroutine, as returned by ILAENV.
-* HSWORK refers to the workspace preferred by DHSEQR, as
-* calculated below. HSWORK is computed assuming ILO=1 and IHI=N,
-* the worst case.)
-*
- IF( INFO.EQ.0 ) THEN
- IF( N.EQ.0 ) THEN
- MINWRK = 1
- MAXWRK = 1
- ELSE
- MAXWRK = 2*N + N*ILAENV( 1, 'DGEHRD', ' ', N, 1, N, 0 )
- IF( WANTVL ) THEN
- MINWRK = 4*N
- MAXWRK = MAX( MAXWRK, 2*N + ( N - 1 )*ILAENV( 1,
- $ 'DORGHR', ' ', N, 1, N, -1 ) )
- CALL DHSEQR( 'S', 'V', N, 1, N, A, LDA, WR, WI, VL, LDVL,
- $ WORK, -1, INFO )
- HSWORK = WORK( 1 )
- MAXWRK = MAX( MAXWRK, N + 1, N + HSWORK )
- MAXWRK = MAX( MAXWRK, 4*N )
- ELSE IF( WANTVR ) THEN
- MINWRK = 4*N
- MAXWRK = MAX( MAXWRK, 2*N + ( N - 1 )*ILAENV( 1,
- $ 'DORGHR', ' ', N, 1, N, -1 ) )
- CALL DHSEQR( 'S', 'V', N, 1, N, A, LDA, WR, WI, VR, LDVR,
- $ WORK, -1, INFO )
- HSWORK = WORK( 1 )
- MAXWRK = MAX( MAXWRK, N + 1, N + HSWORK )
- MAXWRK = MAX( MAXWRK, 4*N )
- ELSE
- MINWRK = 3*N
- CALL DHSEQR( 'E', 'N', N, 1, N, A, LDA, WR, WI, VR, LDVR,
- $ WORK, -1, INFO )
- HSWORK = WORK( 1 )
- MAXWRK = MAX( MAXWRK, N + 1, N + HSWORK )
- END IF
- MAXWRK = MAX( MAXWRK, MINWRK )
- END IF
- WORK( 1 ) = MAXWRK
-*
- IF( LWORK.LT.MINWRK .AND. .NOT.LQUERY ) THEN
- INFO = -13
- END IF
- END IF
-*
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'DGEEV ', -INFO )
- RETURN
- ELSE IF( LQUERY ) THEN
- RETURN
- END IF
-*
-* Quick return if possible
-*
- IF( N.EQ.0 )
- $ RETURN
-*
-* Get machine constants
-*
- EPS = DLAMCH( 'P' )
- SMLNUM = DLAMCH( 'S' )
- BIGNUM = ONE / SMLNUM
- CALL DLABAD( SMLNUM, BIGNUM )
- SMLNUM = SQRT( SMLNUM ) / EPS
- BIGNUM = ONE / SMLNUM
-*
-* Scale A if max element outside range [SMLNUM,BIGNUM]
-*
- ANRM = DLANGE( 'M', N, N, A, LDA, DUM )
- SCALEA = .FALSE.
- IF( ANRM.GT.ZERO .AND. ANRM.LT.SMLNUM ) THEN
- SCALEA = .TRUE.
- CSCALE = SMLNUM
- ELSE IF( ANRM.GT.BIGNUM ) THEN
- SCALEA = .TRUE.
- CSCALE = BIGNUM
- END IF
- IF( SCALEA )
- $ CALL DLASCL( 'G', 0, 0, ANRM, CSCALE, N, N, A, LDA, IERR )
-*
-* Balance the matrix
-* (Workspace: need N)
-*
- IBAL = 1
- CALL DGEBAL( 'B', N, A, LDA, ILO, IHI, WORK( IBAL ), IERR )
-*
-* Reduce to upper Hessenberg form
-* (Workspace: need 3*N, prefer 2*N+N*NB)
-*
- ITAU = IBAL + N
- IWRK = ITAU + N
- CALL DGEHRD( N, ILO, IHI, A, LDA, WORK( ITAU ), WORK( IWRK ),
- $ LWORK-IWRK+1, IERR )
-*
- IF( WANTVL ) THEN
-*
-* Want left eigenvectors
-* Copy Householder vectors to VL
-*
- SIDE = 'L'
- CALL DLACPY( 'L', N, N, A, LDA, VL, LDVL )
-*
-* Generate orthogonal matrix in VL
-* (Workspace: need 3*N-1, prefer 2*N+(N-1)*NB)
-*
- CALL DORGHR( N, ILO, IHI, VL, LDVL, WORK( ITAU ), WORK( IWRK ),
- $ LWORK-IWRK+1, IERR )
-*
-* Perform QR iteration, accumulating Schur vectors in VL
-* (Workspace: need N+1, prefer N+HSWORK (see comments) )
-*
- IWRK = ITAU
- CALL DHSEQR( 'S', 'V', N, ILO, IHI, A, LDA, WR, WI, VL, LDVL,
- $ WORK( IWRK ), LWORK-IWRK+1, INFO )
-*
- IF( WANTVR ) THEN
-*
-* Want left and right eigenvectors
-* Copy Schur vectors to VR
-*
- SIDE = 'B'
- CALL DLACPY( 'F', N, N, VL, LDVL, VR, LDVR )
- END IF
-*
- ELSE IF( WANTVR ) THEN
-*
-* Want right eigenvectors
-* Copy Householder vectors to VR
-*
- SIDE = 'R'
- CALL DLACPY( 'L', N, N, A, LDA, VR, LDVR )
-*
-* Generate orthogonal matrix in VR
-* (Workspace: need 3*N-1, prefer 2*N+(N-1)*NB)
-*
- CALL DORGHR( N, ILO, IHI, VR, LDVR, WORK( ITAU ), WORK( IWRK ),
- $ LWORK-IWRK+1, IERR )
-*
-* Perform QR iteration, accumulating Schur vectors in VR
-* (Workspace: need N+1, prefer N+HSWORK (see comments) )
-*
- IWRK = ITAU
- CALL DHSEQR( 'S', 'V', N, ILO, IHI, A, LDA, WR, WI, VR, LDVR,
- $ WORK( IWRK ), LWORK-IWRK+1, INFO )
-*
- ELSE
-*
-* Compute eigenvalues only
-* (Workspace: need N+1, prefer N+HSWORK (see comments) )
-*
- IWRK = ITAU
- CALL DHSEQR( 'E', 'N', N, ILO, IHI, A, LDA, WR, WI, VR, LDVR,
- $ WORK( IWRK ), LWORK-IWRK+1, INFO )
- END IF
-*
-* If INFO > 0 from DHSEQR, then quit
-*
- IF( INFO.GT.0 )
- $ GO TO 50
-*
- IF( WANTVL .OR. WANTVR ) THEN
-*
-* Compute left and/or right eigenvectors
-* (Workspace: need 4*N)
-*
- CALL DTREVC( SIDE, 'B', SELECT, N, A, LDA, VL, LDVL, VR, LDVR,
- $ N, NOUT, WORK( IWRK ), IERR )
- END IF
-*
- IF( WANTVL ) THEN
-*
-* Undo balancing of left eigenvectors
-* (Workspace: need N)
-*
- CALL DGEBAK( 'B', 'L', N, ILO, IHI, WORK( IBAL ), N, VL, LDVL,
- $ IERR )
-*
-* Normalize left eigenvectors and make largest component real
-*
- DO 20 I = 1, N
- IF( WI( I ).EQ.ZERO ) THEN
- SCL = ONE / DNRM2( N, VL( 1, I ), 1 )
- CALL DSCAL( N, SCL, VL( 1, I ), 1 )
- ELSE IF( WI( I ).GT.ZERO ) THEN
- SCL = ONE / DLAPY2( DNRM2( N, VL( 1, I ), 1 ),
- $ DNRM2( N, VL( 1, I+1 ), 1 ) )
- CALL DSCAL( N, SCL, VL( 1, I ), 1 )
- CALL DSCAL( N, SCL, VL( 1, I+1 ), 1 )
- DO 10 K = 1, N
- WORK( IWRK+K-1 ) = VL( K, I )**2 + VL( K, I+1 )**2
- 10 CONTINUE
- K = IDAMAX( N, WORK( IWRK ), 1 )
- CALL DLARTG( VL( K, I ), VL( K, I+1 ), CS, SN, R )
- CALL DROT( N, VL( 1, I ), 1, VL( 1, I+1 ), 1, CS, SN )
- VL( K, I+1 ) = ZERO
- END IF
- 20 CONTINUE
- END IF
-*
- IF( WANTVR ) THEN
-*
-* Undo balancing of right eigenvectors
-* (Workspace: need N)
-*
- CALL DGEBAK( 'B', 'R', N, ILO, IHI, WORK( IBAL ), N, VR, LDVR,
- $ IERR )
-*
-* Normalize right eigenvectors and make largest component real
-*
- DO 40 I = 1, N
- IF( WI( I ).EQ.ZERO ) THEN
- SCL = ONE / DNRM2( N, VR( 1, I ), 1 )
- CALL DSCAL( N, SCL, VR( 1, I ), 1 )
- ELSE IF( WI( I ).GT.ZERO ) THEN
- SCL = ONE / DLAPY2( DNRM2( N, VR( 1, I ), 1 ),
- $ DNRM2( N, VR( 1, I+1 ), 1 ) )
- CALL DSCAL( N, SCL, VR( 1, I ), 1 )
- CALL DSCAL( N, SCL, VR( 1, I+1 ), 1 )
- DO 30 K = 1, N
- WORK( IWRK+K-1 ) = VR( K, I )**2 + VR( K, I+1 )**2
- 30 CONTINUE
- K = IDAMAX( N, WORK( IWRK ), 1 )
- CALL DLARTG( VR( K, I ), VR( K, I+1 ), CS, SN, R )
- CALL DROT( N, VR( 1, I ), 1, VR( 1, I+1 ), 1, CS, SN )
- VR( K, I+1 ) = ZERO
- END IF
- 40 CONTINUE
- END IF
-*
-* Undo scaling if necessary
-*
- 50 CONTINUE
- IF( SCALEA ) THEN
- CALL DLASCL( 'G', 0, 0, CSCALE, ANRM, N-INFO, 1, WR( INFO+1 ),
- $ MAX( N-INFO, 1 ), IERR )
- CALL DLASCL( 'G', 0, 0, CSCALE, ANRM, N-INFO, 1, WI( INFO+1 ),
- $ MAX( N-INFO, 1 ), IERR )
- IF( INFO.GT.0 ) THEN
- CALL DLASCL( 'G', 0, 0, CSCALE, ANRM, ILO-1, 1, WR, N,
- $ IERR )
- CALL DLASCL( 'G', 0, 0, CSCALE, ANRM, ILO-1, 1, WI, N,
- $ IERR )
- END IF
- END IF
-*
- WORK( 1 ) = MAXWRK
- RETURN
-*
-* End of DGEEV
-*
- END
diff --git a/src/lib/lapack/dgegs.f b/src/lib/lapack/dgegs.f
deleted file mode 100644
index 85c32531..00000000
--- a/src/lib/lapack/dgegs.f
+++ /dev/null
@@ -1,438 +0,0 @@
- SUBROUTINE DGEGS( JOBVSL, JOBVSR, N, A, LDA, B, LDB, ALPHAR,
- $ ALPHAI, BETA, VSL, LDVSL, VSR, LDVSR, WORK,
- $ LWORK, INFO )
-*
-* -- LAPACK driver routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- CHARACTER JOBVSL, JOBVSR
- INTEGER INFO, LDA, LDB, LDVSL, LDVSR, LWORK, N
-* ..
-* .. Array Arguments ..
- DOUBLE PRECISION A( LDA, * ), ALPHAI( * ), ALPHAR( * ),
- $ B( LDB, * ), BETA( * ), VSL( LDVSL, * ),
- $ VSR( LDVSR, * ), WORK( * )
-* ..
-*
-* Purpose
-* =======
-*
-* This routine is deprecated and has been replaced by routine DGGES.
-*
-* DGEGS computes the eigenvalues, real Schur form, and, optionally,
-* left and or/right Schur vectors of a real matrix pair (A,B).
-* Given two square matrices A and B, the generalized real Schur
-* factorization has the form
-*
-* A = Q*S*Z**T, B = Q*T*Z**T
-*
-* where Q and Z are orthogonal matrices, T is upper triangular, and S
-* is an upper quasi-triangular matrix with 1-by-1 and 2-by-2 diagonal
-* blocks, the 2-by-2 blocks corresponding to complex conjugate pairs
-* of eigenvalues of (A,B). The columns of Q are the left Schur vectors
-* and the columns of Z are the right Schur vectors.
-*
-* If only the eigenvalues of (A,B) are needed, the driver routine
-* DGEGV should be used instead. See DGEGV for a description of the
-* eigenvalues of the generalized nonsymmetric eigenvalue problem
-* (GNEP).
-*
-* Arguments
-* =========
-*
-* JOBVSL (input) CHARACTER*1
-* = 'N': do not compute the left Schur vectors;
-* = 'V': compute the left Schur vectors (returned in VSL).
-*
-* JOBVSR (input) CHARACTER*1
-* = 'N': do not compute the right Schur vectors;
-* = 'V': compute the right Schur vectors (returned in VSR).
-*
-* N (input) INTEGER
-* The order of the matrices A, B, VSL, and VSR. N >= 0.
-*
-* A (input/output) DOUBLE PRECISION array, dimension (LDA, N)
-* On entry, the matrix A.
-* On exit, the upper quasi-triangular matrix S from the
-* generalized real Schur factorization.
-*
-* LDA (input) INTEGER
-* The leading dimension of A. LDA >= max(1,N).
-*
-* B (input/output) DOUBLE PRECISION array, dimension (LDB, N)
-* On entry, the matrix B.
-* On exit, the upper triangular matrix T from the generalized
-* real Schur factorization.
-*
-* LDB (input) INTEGER
-* The leading dimension of B. LDB >= max(1,N).
-*
-* ALPHAR (output) DOUBLE PRECISION array, dimension (N)
-* The real parts of each scalar alpha defining an eigenvalue
-* of GNEP.
-*
-* ALPHAI (output) DOUBLE PRECISION array, dimension (N)
-* The imaginary parts of each scalar alpha defining an
-* eigenvalue of GNEP. If ALPHAI(j) is zero, then the j-th
-* eigenvalue is real; if positive, then the j-th and (j+1)-st
-* eigenvalues are a complex conjugate pair, with
-* ALPHAI(j+1) = -ALPHAI(j).
-*
-* BETA (output) DOUBLE PRECISION array, dimension (N)
-* The scalars beta that define the eigenvalues of GNEP.
-* Together, the quantities alpha = (ALPHAR(j),ALPHAI(j)) and
-* beta = BETA(j) represent the j-th eigenvalue of the matrix
-* pair (A,B), in one of the forms lambda = alpha/beta or
-* mu = beta/alpha. Since either lambda or mu may overflow,
-* they should not, in general, be computed.
-*
-* VSL (output) DOUBLE PRECISION array, dimension (LDVSL,N)
-* If JOBVSL = 'V', the matrix of left Schur vectors Q.
-* Not referenced if JOBVSL = 'N'.
-*
-* LDVSL (input) INTEGER
-* The leading dimension of the matrix VSL. LDVSL >=1, and
-* if JOBVSL = 'V', LDVSL >= N.
-*
-* VSR (output) DOUBLE PRECISION array, dimension (LDVSR,N)
-* If JOBVSR = 'V', the matrix of right Schur vectors Z.
-* Not referenced if JOBVSR = 'N'.
-*
-* LDVSR (input) INTEGER
-* The leading dimension of the matrix VSR. LDVSR >= 1, and
-* if JOBVSR = 'V', LDVSR >= N.
-*
-* WORK (workspace/output) DOUBLE PRECISION array, dimension (MAX(1,LWORK))
-* On exit, if INFO = 0, WORK(1) returns the optimal LWORK.
-*
-* LWORK (input) INTEGER
-* The dimension of the array WORK. LWORK >= max(1,4*N).
-* For good performance, LWORK must generally be larger.
-* To compute the optimal value of LWORK, call ILAENV to get
-* blocksizes (for DGEQRF, DORMQR, and DORGQR.) Then compute:
-* NB -- MAX of the blocksizes for DGEQRF, DORMQR, and DORGQR
-* The optimal LWORK is 2*N + N*(NB+1).
-*
-* If LWORK = -1, then a workspace query is assumed; the routine
-* only calculates the optimal size of the WORK array, returns
-* this value as the first entry of the WORK array, and no error
-* message related to LWORK is issued by XERBLA.
-*
-* INFO (output) INTEGER
-* = 0: successful exit
-* < 0: if INFO = -i, the i-th argument had an illegal value.
-* = 1,...,N:
-* The QZ iteration failed. (A,B) are not in Schur
-* form, but ALPHAR(j), ALPHAI(j), and BETA(j) should
-* be correct for j=INFO+1,...,N.
-* > N: errors that usually indicate LAPACK problems:
-* =N+1: error return from DGGBAL
-* =N+2: error return from DGEQRF
-* =N+3: error return from DORMQR
-* =N+4: error return from DORGQR
-* =N+5: error return from DGGHRD
-* =N+6: error return from DHGEQZ (other than failed
-* iteration)
-* =N+7: error return from DGGBAK (computing VSL)
-* =N+8: error return from DGGBAK (computing VSR)
-* =N+9: error return from DLASCL (various places)
-*
-* =====================================================================
-*
-* .. Parameters ..
- DOUBLE PRECISION ZERO, ONE
- PARAMETER ( ZERO = 0.0D0, ONE = 1.0D0 )
-* ..
-* .. Local Scalars ..
- LOGICAL ILASCL, ILBSCL, ILVSL, ILVSR, LQUERY
- INTEGER ICOLS, IHI, IINFO, IJOBVL, IJOBVR, ILEFT, ILO,
- $ IRIGHT, IROWS, ITAU, IWORK, LOPT, LWKMIN,
- $ LWKOPT, NB, NB1, NB2, NB3
- DOUBLE PRECISION ANRM, ANRMTO, BIGNUM, BNRM, BNRMTO, EPS,
- $ SAFMIN, SMLNUM
-* ..
-* .. External Subroutines ..
- EXTERNAL DGEQRF, DGGBAK, DGGBAL, DGGHRD, DHGEQZ, DLACPY,
- $ DLASCL, DLASET, DORGQR, DORMQR, XERBLA
-* ..
-* .. External Functions ..
- LOGICAL LSAME
- INTEGER ILAENV
- DOUBLE PRECISION DLAMCH, DLANGE
- EXTERNAL LSAME, ILAENV, DLAMCH, DLANGE
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC INT, MAX
-* ..
-* .. Executable Statements ..
-*
-* Decode the input arguments
-*
- IF( LSAME( JOBVSL, 'N' ) ) THEN
- IJOBVL = 1
- ILVSL = .FALSE.
- ELSE IF( LSAME( JOBVSL, 'V' ) ) THEN
- IJOBVL = 2
- ILVSL = .TRUE.
- ELSE
- IJOBVL = -1
- ILVSL = .FALSE.
- END IF
-*
- IF( LSAME( JOBVSR, 'N' ) ) THEN
- IJOBVR = 1
- ILVSR = .FALSE.
- ELSE IF( LSAME( JOBVSR, 'V' ) ) THEN
- IJOBVR = 2
- ILVSR = .TRUE.
- ELSE
- IJOBVR = -1
- ILVSR = .FALSE.
- END IF
-*
-* Test the input arguments
-*
- LWKMIN = MAX( 4*N, 1 )
- LWKOPT = LWKMIN
- WORK( 1 ) = LWKOPT
- LQUERY = ( LWORK.EQ.-1 )
- INFO = 0
- IF( IJOBVL.LE.0 ) THEN
- INFO = -1
- ELSE IF( IJOBVR.LE.0 ) THEN
- INFO = -2
- ELSE IF( N.LT.0 ) THEN
- INFO = -3
- ELSE IF( LDA.LT.MAX( 1, N ) ) THEN
- INFO = -5
- ELSE IF( LDB.LT.MAX( 1, N ) ) THEN
- INFO = -7
- ELSE IF( LDVSL.LT.1 .OR. ( ILVSL .AND. LDVSL.LT.N ) ) THEN
- INFO = -12
- ELSE IF( LDVSR.LT.1 .OR. ( ILVSR .AND. LDVSR.LT.N ) ) THEN
- INFO = -14
- ELSE IF( LWORK.LT.LWKMIN .AND. .NOT.LQUERY ) THEN
- INFO = -16
- END IF
-*
- IF( INFO.EQ.0 ) THEN
- NB1 = ILAENV( 1, 'DGEQRF', ' ', N, N, -1, -1 )
- NB2 = ILAENV( 1, 'DORMQR', ' ', N, N, N, -1 )
- NB3 = ILAENV( 1, 'DORGQR', ' ', N, N, N, -1 )
- NB = MAX( NB1, NB2, NB3 )
- LOPT = 2*N + N*( NB+1 )
- WORK( 1 ) = LOPT
- END IF
-*
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'DGEGS ', -INFO )
- RETURN
- ELSE IF( LQUERY ) THEN
- RETURN
- END IF
-*
-* Quick return if possible
-*
- IF( N.EQ.0 )
- $ RETURN
-*
-* Get machine constants
-*
- EPS = DLAMCH( 'E' )*DLAMCH( 'B' )
- SAFMIN = DLAMCH( 'S' )
- SMLNUM = N*SAFMIN / EPS
- BIGNUM = ONE / SMLNUM
-*
-* Scale A if max element outside range [SMLNUM,BIGNUM]
-*
- ANRM = DLANGE( 'M', N, N, A, LDA, WORK )
- ILASCL = .FALSE.
- IF( ANRM.GT.ZERO .AND. ANRM.LT.SMLNUM ) THEN
- ANRMTO = SMLNUM
- ILASCL = .TRUE.
- ELSE IF( ANRM.GT.BIGNUM ) THEN
- ANRMTO = BIGNUM
- ILASCL = .TRUE.
- END IF
-*
- IF( ILASCL ) THEN
- CALL DLASCL( 'G', -1, -1, ANRM, ANRMTO, N, N, A, LDA, IINFO )
- IF( IINFO.NE.0 ) THEN
- INFO = N + 9
- RETURN
- END IF
- END IF
-*
-* Scale B if max element outside range [SMLNUM,BIGNUM]
-*
- BNRM = DLANGE( 'M', N, N, B, LDB, WORK )
- ILBSCL = .FALSE.
- IF( BNRM.GT.ZERO .AND. BNRM.LT.SMLNUM ) THEN
- BNRMTO = SMLNUM
- ILBSCL = .TRUE.
- ELSE IF( BNRM.GT.BIGNUM ) THEN
- BNRMTO = BIGNUM
- ILBSCL = .TRUE.
- END IF
-*
- IF( ILBSCL ) THEN
- CALL DLASCL( 'G', -1, -1, BNRM, BNRMTO, N, N, B, LDB, IINFO )
- IF( IINFO.NE.0 ) THEN
- INFO = N + 9
- RETURN
- END IF
- END IF
-*
-* Permute the matrix to make it more nearly triangular
-* Workspace layout: (2*N words -- "work..." not actually used)
-* left_permutation, right_permutation, work...
-*
- ILEFT = 1
- IRIGHT = N + 1
- IWORK = IRIGHT + N
- CALL DGGBAL( 'P', N, A, LDA, B, LDB, ILO, IHI, WORK( ILEFT ),
- $ WORK( IRIGHT ), WORK( IWORK ), IINFO )
- IF( IINFO.NE.0 ) THEN
- INFO = N + 1
- GO TO 10
- END IF
-*
-* Reduce B to triangular form, and initialize VSL and/or VSR
-* Workspace layout: ("work..." must have at least N words)
-* left_permutation, right_permutation, tau, work...
-*
- IROWS = IHI + 1 - ILO
- ICOLS = N + 1 - ILO
- ITAU = IWORK
- IWORK = ITAU + IROWS
- CALL DGEQRF( IROWS, ICOLS, B( ILO, ILO ), LDB, WORK( ITAU ),
- $ WORK( IWORK ), LWORK+1-IWORK, IINFO )
- IF( IINFO.GE.0 )
- $ LWKOPT = MAX( LWKOPT, INT( WORK( IWORK ) )+IWORK-1 )
- IF( IINFO.NE.0 ) THEN
- INFO = N + 2
- GO TO 10
- END IF
-*
- CALL DORMQR( 'L', 'T', IROWS, ICOLS, IROWS, B( ILO, ILO ), LDB,
- $ WORK( ITAU ), A( ILO, ILO ), LDA, WORK( IWORK ),
- $ LWORK+1-IWORK, IINFO )
- IF( IINFO.GE.0 )
- $ LWKOPT = MAX( LWKOPT, INT( WORK( IWORK ) )+IWORK-1 )
- IF( IINFO.NE.0 ) THEN
- INFO = N + 3
- GO TO 10
- END IF
-*
- IF( ILVSL ) THEN
- CALL DLASET( 'Full', N, N, ZERO, ONE, VSL, LDVSL )
- CALL DLACPY( 'L', IROWS-1, IROWS-1, B( ILO+1, ILO ), LDB,
- $ VSL( ILO+1, ILO ), LDVSL )
- CALL DORGQR( IROWS, IROWS, IROWS, VSL( ILO, ILO ), LDVSL,
- $ WORK( ITAU ), WORK( IWORK ), LWORK+1-IWORK,
- $ IINFO )
- IF( IINFO.GE.0 )
- $ LWKOPT = MAX( LWKOPT, INT( WORK( IWORK ) )+IWORK-1 )
- IF( IINFO.NE.0 ) THEN
- INFO = N + 4
- GO TO 10
- END IF
- END IF
-*
- IF( ILVSR )
- $ CALL DLASET( 'Full', N, N, ZERO, ONE, VSR, LDVSR )
-*
-* Reduce to generalized Hessenberg form
-*
- CALL DGGHRD( JOBVSL, JOBVSR, N, ILO, IHI, A, LDA, B, LDB, VSL,
- $ LDVSL, VSR, LDVSR, IINFO )
- IF( IINFO.NE.0 ) THEN
- INFO = N + 5
- GO TO 10
- END IF
-*
-* Perform QZ algorithm, computing Schur vectors if desired
-* Workspace layout: ("work..." must have at least 1 word)
-* left_permutation, right_permutation, work...
-*
- IWORK = ITAU
- CALL DHGEQZ( 'S', JOBVSL, JOBVSR, N, ILO, IHI, A, LDA, B, LDB,
- $ ALPHAR, ALPHAI, BETA, VSL, LDVSL, VSR, LDVSR,
- $ WORK( IWORK ), LWORK+1-IWORK, IINFO )
- IF( IINFO.GE.0 )
- $ LWKOPT = MAX( LWKOPT, INT( WORK( IWORK ) )+IWORK-1 )
- IF( IINFO.NE.0 ) THEN
- IF( IINFO.GT.0 .AND. IINFO.LE.N ) THEN
- INFO = IINFO
- ELSE IF( IINFO.GT.N .AND. IINFO.LE.2*N ) THEN
- INFO = IINFO - N
- ELSE
- INFO = N + 6
- END IF
- GO TO 10
- END IF
-*
-* Apply permutation to VSL and VSR
-*
- IF( ILVSL ) THEN
- CALL DGGBAK( 'P', 'L', N, ILO, IHI, WORK( ILEFT ),
- $ WORK( IRIGHT ), N, VSL, LDVSL, IINFO )
- IF( IINFO.NE.0 ) THEN
- INFO = N + 7
- GO TO 10
- END IF
- END IF
- IF( ILVSR ) THEN
- CALL DGGBAK( 'P', 'R', N, ILO, IHI, WORK( ILEFT ),
- $ WORK( IRIGHT ), N, VSR, LDVSR, IINFO )
- IF( IINFO.NE.0 ) THEN
- INFO = N + 8
- GO TO 10
- END IF
- END IF
-*
-* Undo scaling
-*
- IF( ILASCL ) THEN
- CALL DLASCL( 'H', -1, -1, ANRMTO, ANRM, N, N, A, LDA, IINFO )
- IF( IINFO.NE.0 ) THEN
- INFO = N + 9
- RETURN
- END IF
- CALL DLASCL( 'G', -1, -1, ANRMTO, ANRM, N, 1, ALPHAR, N,
- $ IINFO )
- IF( IINFO.NE.0 ) THEN
- INFO = N + 9
- RETURN
- END IF
- CALL DLASCL( 'G', -1, -1, ANRMTO, ANRM, N, 1, ALPHAI, N,
- $ IINFO )
- IF( IINFO.NE.0 ) THEN
- INFO = N + 9
- RETURN
- END IF
- END IF
-*
- IF( ILBSCL ) THEN
- CALL DLASCL( 'U', -1, -1, BNRMTO, BNRM, N, N, B, LDB, IINFO )
- IF( IINFO.NE.0 ) THEN
- INFO = N + 9
- RETURN
- END IF
- CALL DLASCL( 'G', -1, -1, BNRMTO, BNRM, N, 1, BETA, N, IINFO )
- IF( IINFO.NE.0 ) THEN
- INFO = N + 9
- RETURN
- END IF
- END IF
-*
- 10 CONTINUE
- WORK( 1 ) = LWKOPT
-*
- RETURN
-*
-* End of DGEGS
-*
- END
diff --git a/src/lib/lapack/dgehd2.f b/src/lib/lapack/dgehd2.f
deleted file mode 100644
index 28d1cc8d..00000000
--- a/src/lib/lapack/dgehd2.f
+++ /dev/null
@@ -1,149 +0,0 @@
- SUBROUTINE DGEHD2( N, ILO, IHI, A, LDA, TAU, WORK, INFO )
-*
-* -- LAPACK routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- INTEGER IHI, ILO, INFO, LDA, N
-* ..
-* .. Array Arguments ..
- DOUBLE PRECISION A( LDA, * ), TAU( * ), WORK( * )
-* ..
-*
-* Purpose
-* =======
-*
-* DGEHD2 reduces a real general matrix A to upper Hessenberg form H by
-* an orthogonal similarity transformation: Q' * A * Q = H .
-*
-* Arguments
-* =========
-*
-* N (input) INTEGER
-* The order of the matrix A. N >= 0.
-*
-* ILO (input) INTEGER
-* IHI (input) INTEGER
-* It is assumed that A is already upper triangular in rows
-* and columns 1:ILO-1 and IHI+1:N. ILO and IHI are normally
-* set by a previous call to DGEBAL; otherwise they should be
-* set to 1 and N respectively. See Further Details.
-* 1 <= ILO <= IHI <= max(1,N).
-*
-* A (input/output) DOUBLE PRECISION array, dimension (LDA,N)
-* On entry, the n by n general matrix to be reduced.
-* On exit, the upper triangle and the first subdiagonal of A
-* are overwritten with the upper Hessenberg matrix H, and the
-* elements below the first subdiagonal, with the array TAU,
-* represent the orthogonal matrix Q as a product of elementary
-* reflectors. See Further Details.
-*
-* LDA (input) INTEGER
-* The leading dimension of the array A. LDA >= max(1,N).
-*
-* TAU (output) DOUBLE PRECISION array, dimension (N-1)
-* The scalar factors of the elementary reflectors (see Further
-* Details).
-*
-* WORK (workspace) DOUBLE PRECISION array, dimension (N)
-*
-* INFO (output) INTEGER
-* = 0: successful exit.
-* < 0: if INFO = -i, the i-th argument had an illegal value.
-*
-* Further Details
-* ===============
-*
-* The matrix Q is represented as a product of (ihi-ilo) elementary
-* reflectors
-*
-* Q = H(ilo) H(ilo+1) . . . H(ihi-1).
-*
-* Each H(i) has the form
-*
-* H(i) = I - tau * v * v'
-*
-* where tau is a real scalar, and v is a real vector with
-* v(1:i) = 0, v(i+1) = 1 and v(ihi+1:n) = 0; v(i+2:ihi) is stored on
-* exit in A(i+2:ihi,i), and tau in TAU(i).
-*
-* The contents of A are illustrated by the following example, with
-* n = 7, ilo = 2 and ihi = 6:
-*
-* on entry, on exit,
-*
-* ( a a a a a a a ) ( a a h h h h a )
-* ( a a a a a a ) ( a h h h h a )
-* ( a a a a a a ) ( h h h h h h )
-* ( a a a a a a ) ( v2 h h h h h )
-* ( a a a a a a ) ( v2 v3 h h h h )
-* ( a a a a a a ) ( v2 v3 v4 h h h )
-* ( a ) ( a )
-*
-* where a denotes an element of the original matrix A, h denotes a
-* modified element of the upper Hessenberg matrix H, and vi denotes an
-* element of the vector defining H(i).
-*
-* =====================================================================
-*
-* .. Parameters ..
- DOUBLE PRECISION ONE
- PARAMETER ( ONE = 1.0D+0 )
-* ..
-* .. Local Scalars ..
- INTEGER I
- DOUBLE PRECISION AII
-* ..
-* .. External Subroutines ..
- EXTERNAL DLARF, DLARFG, XERBLA
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC MAX, MIN
-* ..
-* .. Executable Statements ..
-*
-* Test the input parameters
-*
- INFO = 0
- IF( N.LT.0 ) THEN
- INFO = -1
- ELSE IF( ILO.LT.1 .OR. ILO.GT.MAX( 1, N ) ) THEN
- INFO = -2
- ELSE IF( IHI.LT.MIN( ILO, N ) .OR. IHI.GT.N ) THEN
- INFO = -3
- ELSE IF( LDA.LT.MAX( 1, N ) ) THEN
- INFO = -5
- END IF
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'DGEHD2', -INFO )
- RETURN
- END IF
-*
- DO 10 I = ILO, IHI - 1
-*
-* Compute elementary reflector H(i) to annihilate A(i+2:ihi,i)
-*
- CALL DLARFG( IHI-I, A( I+1, I ), A( MIN( I+2, N ), I ), 1,
- $ TAU( I ) )
- AII = A( I+1, I )
- A( I+1, I ) = ONE
-*
-* Apply H(i) to A(1:ihi,i+1:ihi) from the right
-*
- CALL DLARF( 'Right', IHI, IHI-I, A( I+1, I ), 1, TAU( I ),
- $ A( 1, I+1 ), LDA, WORK )
-*
-* Apply H(i) to A(i+1:ihi,i+1:n) from the left
-*
- CALL DLARF( 'Left', IHI-I, N-I, A( I+1, I ), 1, TAU( I ),
- $ A( I+1, I+1 ), LDA, WORK )
-*
- A( I+1, I ) = AII
- 10 CONTINUE
-*
- RETURN
-*
-* End of DGEHD2
-*
- END
diff --git a/src/lib/lapack/dgehrd.f b/src/lib/lapack/dgehrd.f
deleted file mode 100644
index 339ee400..00000000
--- a/src/lib/lapack/dgehrd.f
+++ /dev/null
@@ -1,273 +0,0 @@
- SUBROUTINE DGEHRD( N, ILO, IHI, A, LDA, TAU, WORK, LWORK, INFO )
-*
-* -- LAPACK routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- INTEGER IHI, ILO, INFO, LDA, LWORK, N
-* ..
-* .. Array Arguments ..
- DOUBLE PRECISION A( LDA, * ), TAU( * ), WORK( * )
-* ..
-*
-* Purpose
-* =======
-*
-* DGEHRD reduces a real general matrix A to upper Hessenberg form H by
-* an orthogonal similarity transformation: Q' * A * Q = H .
-*
-* Arguments
-* =========
-*
-* N (input) INTEGER
-* The order of the matrix A. N >= 0.
-*
-* ILO (input) INTEGER
-* IHI (input) INTEGER
-* It is assumed that A is already upper triangular in rows
-* and columns 1:ILO-1 and IHI+1:N. ILO and IHI are normally
-* set by a previous call to DGEBAL; otherwise they should be
-* set to 1 and N respectively. See Further Details.
-* 1 <= ILO <= IHI <= N, if N > 0; ILO=1 and IHI=0, if N=0.
-*
-* A (input/output) DOUBLE PRECISION array, dimension (LDA,N)
-* On entry, the N-by-N general matrix to be reduced.
-* On exit, the upper triangle and the first subdiagonal of A
-* are overwritten with the upper Hessenberg matrix H, and the
-* elements below the first subdiagonal, with the array TAU,
-* represent the orthogonal matrix Q as a product of elementary
-* reflectors. See Further Details.
-*
-* LDA (input) INTEGER
-* The leading dimension of the array A. LDA >= max(1,N).
-*
-* TAU (output) DOUBLE PRECISION array, dimension (N-1)
-* The scalar factors of the elementary reflectors (see Further
-* Details). Elements 1:ILO-1 and IHI:N-1 of TAU are set to
-* zero.
-*
-* WORK (workspace/output) DOUBLE PRECISION array, dimension (LWORK)
-* On exit, if INFO = 0, WORK(1) returns the optimal LWORK.
-*
-* LWORK (input) INTEGER
-* The length of the array WORK. LWORK >= max(1,N).
-* For optimum performance LWORK >= N*NB, where NB is the
-* optimal blocksize.
-*
-* If LWORK = -1, then a workspace query is assumed; the routine
-* only calculates the optimal size of the WORK array, returns
-* this value as the first entry of the WORK array, and no error
-* message related to LWORK is issued by XERBLA.
-*
-* INFO (output) INTEGER
-* = 0: successful exit
-* < 0: if INFO = -i, the i-th argument had an illegal value.
-*
-* Further Details
-* ===============
-*
-* The matrix Q is represented as a product of (ihi-ilo) elementary
-* reflectors
-*
-* Q = H(ilo) H(ilo+1) . . . H(ihi-1).
-*
-* Each H(i) has the form
-*
-* H(i) = I - tau * v * v'
-*
-* where tau is a real scalar, and v is a real vector with
-* v(1:i) = 0, v(i+1) = 1 and v(ihi+1:n) = 0; v(i+2:ihi) is stored on
-* exit in A(i+2:ihi,i), and tau in TAU(i).
-*
-* The contents of A are illustrated by the following example, with
-* n = 7, ilo = 2 and ihi = 6:
-*
-* on entry, on exit,
-*
-* ( a a a a a a a ) ( a a h h h h a )
-* ( a a a a a a ) ( a h h h h a )
-* ( a a a a a a ) ( h h h h h h )
-* ( a a a a a a ) ( v2 h h h h h )
-* ( a a a a a a ) ( v2 v3 h h h h )
-* ( a a a a a a ) ( v2 v3 v4 h h h )
-* ( a ) ( a )
-*
-* where a denotes an element of the original matrix A, h denotes a
-* modified element of the upper Hessenberg matrix H, and vi denotes an
-* element of the vector defining H(i).
-*
-* This file is a slight modification of LAPACK-3.0's DGEHRD
-* subroutine incorporating improvements proposed by Quintana-Orti and
-* Van de Geijn (2005).
-*
-* =====================================================================
-*
-* .. Parameters ..
- INTEGER NBMAX, LDT
- PARAMETER ( NBMAX = 64, LDT = NBMAX+1 )
- DOUBLE PRECISION ZERO, ONE
- PARAMETER ( ZERO = 0.0D+0,
- $ ONE = 1.0D+0 )
-* ..
-* .. Local Scalars ..
- LOGICAL LQUERY
- INTEGER I, IB, IINFO, IWS, J, LDWORK, LWKOPT, NB,
- $ NBMIN, NH, NX
- DOUBLE PRECISION EI
-* ..
-* .. Local Arrays ..
- DOUBLE PRECISION T( LDT, NBMAX )
-* ..
-* .. External Subroutines ..
- EXTERNAL DAXPY, DGEHD2, DGEMM, DLAHR2, DLARFB, DTRMM,
- $ XERBLA
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC MAX, MIN
-* ..
-* .. External Functions ..
- INTEGER ILAENV
- EXTERNAL ILAENV
-* ..
-* .. Executable Statements ..
-*
-* Test the input parameters
-*
- INFO = 0
- NB = MIN( NBMAX, ILAENV( 1, 'DGEHRD', ' ', N, ILO, IHI, -1 ) )
- LWKOPT = N*NB
- WORK( 1 ) = LWKOPT
- LQUERY = ( LWORK.EQ.-1 )
- IF( N.LT.0 ) THEN
- INFO = -1
- ELSE IF( ILO.LT.1 .OR. ILO.GT.MAX( 1, N ) ) THEN
- INFO = -2
- ELSE IF( IHI.LT.MIN( ILO, N ) .OR. IHI.GT.N ) THEN
- INFO = -3
- ELSE IF( LDA.LT.MAX( 1, N ) ) THEN
- INFO = -5
- ELSE IF( LWORK.LT.MAX( 1, N ) .AND. .NOT.LQUERY ) THEN
- INFO = -8
- END IF
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'DGEHRD', -INFO )
- RETURN
- ELSE IF( LQUERY ) THEN
- RETURN
- END IF
-*
-* Set elements 1:ILO-1 and IHI:N-1 of TAU to zero
-*
- DO 10 I = 1, ILO - 1
- TAU( I ) = ZERO
- 10 CONTINUE
- DO 20 I = MAX( 1, IHI ), N - 1
- TAU( I ) = ZERO
- 20 CONTINUE
-*
-* Quick return if possible
-*
- NH = IHI - ILO + 1
- IF( NH.LE.1 ) THEN
- WORK( 1 ) = 1
- RETURN
- END IF
-*
-* Determine the block size
-*
- NB = MIN( NBMAX, ILAENV( 1, 'DGEHRD', ' ', N, ILO, IHI, -1 ) )
- NBMIN = 2
- IWS = 1
- IF( NB.GT.1 .AND. NB.LT.NH ) THEN
-*
-* Determine when to cross over from blocked to unblocked code
-* (last block is always handled by unblocked code)
-*
- NX = MAX( NB, ILAENV( 3, 'DGEHRD', ' ', N, ILO, IHI, -1 ) )
- IF( NX.LT.NH ) THEN
-*
-* Determine if workspace is large enough for blocked code
-*
- IWS = N*NB
- IF( LWORK.LT.IWS ) THEN
-*
-* Not enough workspace to use optimal NB: determine the
-* minimum value of NB, and reduce NB or force use of
-* unblocked code
-*
- NBMIN = MAX( 2, ILAENV( 2, 'DGEHRD', ' ', N, ILO, IHI,
- $ -1 ) )
- IF( LWORK.GE.N*NBMIN ) THEN
- NB = LWORK / N
- ELSE
- NB = 1
- END IF
- END IF
- END IF
- END IF
- LDWORK = N
-*
- IF( NB.LT.NBMIN .OR. NB.GE.NH ) THEN
-*
-* Use unblocked code below
-*
- I = ILO
-*
- ELSE
-*
-* Use blocked code
-*
- DO 40 I = ILO, IHI - 1 - NX, NB
- IB = MIN( NB, IHI-I )
-*
-* Reduce columns i:i+ib-1 to Hessenberg form, returning the
-* matrices V and T of the block reflector H = I - V*T*V'
-* which performs the reduction, and also the matrix Y = A*V*T
-*
- CALL DLAHR2( IHI, I, IB, A( 1, I ), LDA, TAU( I ), T, LDT,
- $ WORK, LDWORK )
-*
-* Apply the block reflector H to A(1:ihi,i+ib:ihi) from the
-* right, computing A := A - Y * V'. V(i+ib,ib-1) must be set
-* to 1
-*
- EI = A( I+IB, I+IB-1 )
- A( I+IB, I+IB-1 ) = ONE
- CALL DGEMM( 'No transpose', 'Transpose',
- $ IHI, IHI-I-IB+1,
- $ IB, -ONE, WORK, LDWORK, A( I+IB, I ), LDA, ONE,
- $ A( 1, I+IB ), LDA )
- A( I+IB, I+IB-1 ) = EI
-*
-* Apply the block reflector H to A(1:i,i+1:i+ib-1) from the
-* right
-*
- CALL DTRMM( 'Right', 'Lower', 'Transpose',
- $ 'Unit', I, IB-1,
- $ ONE, A( I+1, I ), LDA, WORK, LDWORK )
- DO 30 J = 0, IB-2
- CALL DAXPY( I, -ONE, WORK( LDWORK*J+1 ), 1,
- $ A( 1, I+J+1 ), 1 )
- 30 CONTINUE
-*
-* Apply the block reflector H to A(i+1:ihi,i+ib:n) from the
-* left
-*
- CALL DLARFB( 'Left', 'Transpose', 'Forward',
- $ 'Columnwise',
- $ IHI-I, N-I-IB+1, IB, A( I+1, I ), LDA, T, LDT,
- $ A( I+1, I+IB ), LDA, WORK, LDWORK )
- 40 CONTINUE
- END IF
-*
-* Use unblocked code to reduce the rest of the matrix
-*
- CALL DGEHD2( N, I, IHI, A, LDA, TAU, WORK, IINFO )
- WORK( 1 ) = IWS
-*
- RETURN
-*
-* End of DGEHRD
-*
- END
diff --git a/src/lib/lapack/dgelq2.f b/src/lib/lapack/dgelq2.f
deleted file mode 100644
index f3540505..00000000
--- a/src/lib/lapack/dgelq2.f
+++ /dev/null
@@ -1,121 +0,0 @@
- SUBROUTINE DGELQ2( M, N, A, LDA, TAU, WORK, INFO )
-*
-* -- LAPACK routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- INTEGER INFO, LDA, M, N
-* ..
-* .. Array Arguments ..
- DOUBLE PRECISION A( LDA, * ), TAU( * ), WORK( * )
-* ..
-*
-* Purpose
-* =======
-*
-* DGELQ2 computes an LQ factorization of a real m by n matrix A:
-* A = L * Q.
-*
-* Arguments
-* =========
-*
-* M (input) INTEGER
-* The number of rows of the matrix A. M >= 0.
-*
-* N (input) INTEGER
-* The number of columns of the matrix A. N >= 0.
-*
-* A (input/output) DOUBLE PRECISION array, dimension (LDA,N)
-* On entry, the m by n matrix A.
-* On exit, the elements on and below the diagonal of the array
-* contain the m by min(m,n) lower trapezoidal matrix L (L is
-* lower triangular if m <= n); the elements above the diagonal,
-* with the array TAU, represent the orthogonal matrix Q as a
-* product of elementary reflectors (see Further Details).
-*
-* LDA (input) INTEGER
-* The leading dimension of the array A. LDA >= max(1,M).
-*
-* TAU (output) DOUBLE PRECISION array, dimension (min(M,N))
-* The scalar factors of the elementary reflectors (see Further
-* Details).
-*
-* WORK (workspace) DOUBLE PRECISION array, dimension (M)
-*
-* INFO (output) INTEGER
-* = 0: successful exit
-* < 0: if INFO = -i, the i-th argument had an illegal value
-*
-* Further Details
-* ===============
-*
-* The matrix Q is represented as a product of elementary reflectors
-*
-* Q = H(k) . . . H(2) H(1), where k = min(m,n).
-*
-* Each H(i) has the form
-*
-* H(i) = I - tau * v * v'
-*
-* where tau is a real scalar, and v is a real vector with
-* v(1:i-1) = 0 and v(i) = 1; v(i+1:n) is stored on exit in A(i,i+1:n),
-* and tau in TAU(i).
-*
-* =====================================================================
-*
-* .. Parameters ..
- DOUBLE PRECISION ONE
- PARAMETER ( ONE = 1.0D+0 )
-* ..
-* .. Local Scalars ..
- INTEGER I, K
- DOUBLE PRECISION AII
-* ..
-* .. External Subroutines ..
- EXTERNAL DLARF, DLARFG, XERBLA
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC MAX, MIN
-* ..
-* .. Executable Statements ..
-*
-* Test the input arguments
-*
- INFO = 0
- IF( M.LT.0 ) THEN
- INFO = -1
- ELSE IF( N.LT.0 ) THEN
- INFO = -2
- ELSE IF( LDA.LT.MAX( 1, M ) ) THEN
- INFO = -4
- END IF
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'DGELQ2', -INFO )
- RETURN
- END IF
-*
- K = MIN( M, N )
-*
- DO 10 I = 1, K
-*
-* Generate elementary reflector H(i) to annihilate A(i,i+1:n)
-*
- CALL DLARFG( N-I+1, A( I, I ), A( I, MIN( I+1, N ) ), LDA,
- $ TAU( I ) )
- IF( I.LT.M ) THEN
-*
-* Apply H(i) to A(i+1:m,i:n) from the right
-*
- AII = A( I, I )
- A( I, I ) = ONE
- CALL DLARF( 'Right', M-I, N-I+1, A( I, I ), LDA, TAU( I ),
- $ A( I+1, I ), LDA, WORK )
- A( I, I ) = AII
- END IF
- 10 CONTINUE
- RETURN
-*
-* End of DGELQ2
-*
- END
diff --git a/src/lib/lapack/dgelqf.f b/src/lib/lapack/dgelqf.f
deleted file mode 100644
index 063a38ba..00000000
--- a/src/lib/lapack/dgelqf.f
+++ /dev/null
@@ -1,195 +0,0 @@
- SUBROUTINE DGELQF( M, N, A, LDA, TAU, WORK, LWORK, INFO )
-*
-* -- LAPACK routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- INTEGER INFO, LDA, LWORK, M, N
-* ..
-* .. Array Arguments ..
- DOUBLE PRECISION A( LDA, * ), TAU( * ), WORK( * )
-* ..
-*
-* Purpose
-* =======
-*
-* DGELQF computes an LQ factorization of a real M-by-N matrix A:
-* A = L * Q.
-*
-* Arguments
-* =========
-*
-* M (input) INTEGER
-* The number of rows of the matrix A. M >= 0.
-*
-* N (input) INTEGER
-* The number of columns of the matrix A. N >= 0.
-*
-* A (input/output) DOUBLE PRECISION array, dimension (LDA,N)
-* On entry, the M-by-N matrix A.
-* On exit, the elements on and below the diagonal of the array
-* contain the m-by-min(m,n) lower trapezoidal matrix L (L is
-* lower triangular if m <= n); the elements above the diagonal,
-* with the array TAU, represent the orthogonal matrix Q as a
-* product of elementary reflectors (see Further Details).
-*
-* LDA (input) INTEGER
-* The leading dimension of the array A. LDA >= max(1,M).
-*
-* TAU (output) DOUBLE PRECISION array, dimension (min(M,N))
-* The scalar factors of the elementary reflectors (see Further
-* Details).
-*
-* WORK (workspace/output) DOUBLE PRECISION array, dimension (MAX(1,LWORK))
-* On exit, if INFO = 0, WORK(1) returns the optimal LWORK.
-*
-* LWORK (input) INTEGER
-* The dimension of the array WORK. LWORK >= max(1,M).
-* For optimum performance LWORK >= M*NB, where NB is the
-* optimal blocksize.
-*
-* If LWORK = -1, then a workspace query is assumed; the routine
-* only calculates the optimal size of the WORK array, returns
-* this value as the first entry of the WORK array, and no error
-* message related to LWORK is issued by XERBLA.
-*
-* INFO (output) INTEGER
-* = 0: successful exit
-* < 0: if INFO = -i, the i-th argument had an illegal value
-*
-* Further Details
-* ===============
-*
-* The matrix Q is represented as a product of elementary reflectors
-*
-* Q = H(k) . . . H(2) H(1), where k = min(m,n).
-*
-* Each H(i) has the form
-*
-* H(i) = I - tau * v * v'
-*
-* where tau is a real scalar, and v is a real vector with
-* v(1:i-1) = 0 and v(i) = 1; v(i+1:n) is stored on exit in A(i,i+1:n),
-* and tau in TAU(i).
-*
-* =====================================================================
-*
-* .. Local Scalars ..
- LOGICAL LQUERY
- INTEGER I, IB, IINFO, IWS, K, LDWORK, LWKOPT, NB,
- $ NBMIN, NX
-* ..
-* .. External Subroutines ..
- EXTERNAL DGELQ2, DLARFB, DLARFT, XERBLA
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC MAX, MIN
-* ..
-* .. External Functions ..
- INTEGER ILAENV
- EXTERNAL ILAENV
-* ..
-* .. Executable Statements ..
-*
-* Test the input arguments
-*
- INFO = 0
- NB = ILAENV( 1, 'DGELQF', ' ', M, N, -1, -1 )
- LWKOPT = M*NB
- WORK( 1 ) = LWKOPT
- LQUERY = ( LWORK.EQ.-1 )
- IF( M.LT.0 ) THEN
- INFO = -1
- ELSE IF( N.LT.0 ) THEN
- INFO = -2
- ELSE IF( LDA.LT.MAX( 1, M ) ) THEN
- INFO = -4
- ELSE IF( LWORK.LT.MAX( 1, M ) .AND. .NOT.LQUERY ) THEN
- INFO = -7
- END IF
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'DGELQF', -INFO )
- RETURN
- ELSE IF( LQUERY ) THEN
- RETURN
- END IF
-*
-* Quick return if possible
-*
- K = MIN( M, N )
- IF( K.EQ.0 ) THEN
- WORK( 1 ) = 1
- RETURN
- END IF
-*
- NBMIN = 2
- NX = 0
- IWS = M
- IF( NB.GT.1 .AND. NB.LT.K ) THEN
-*
-* Determine when to cross over from blocked to unblocked code.
-*
- NX = MAX( 0, ILAENV( 3, 'DGELQF', ' ', M, N, -1, -1 ) )
- IF( NX.LT.K ) THEN
-*
-* Determine if workspace is large enough for blocked code.
-*
- LDWORK = M
- IWS = LDWORK*NB
- IF( LWORK.LT.IWS ) THEN
-*
-* Not enough workspace to use optimal NB: reduce NB and
-* determine the minimum value of NB.
-*
- NB = LWORK / LDWORK
- NBMIN = MAX( 2, ILAENV( 2, 'DGELQF', ' ', M, N, -1,
- $ -1 ) )
- END IF
- END IF
- END IF
-*
- IF( NB.GE.NBMIN .AND. NB.LT.K .AND. NX.LT.K ) THEN
-*
-* Use blocked code initially
-*
- DO 10 I = 1, K - NX, NB
- IB = MIN( K-I+1, NB )
-*
-* Compute the LQ factorization of the current block
-* A(i:i+ib-1,i:n)
-*
- CALL DGELQ2( IB, N-I+1, A( I, I ), LDA, TAU( I ), WORK,
- $ IINFO )
- IF( I+IB.LE.M ) THEN
-*
-* Form the triangular factor of the block reflector
-* H = H(i) H(i+1) . . . H(i+ib-1)
-*
- CALL DLARFT( 'Forward', 'Rowwise', N-I+1, IB, A( I, I ),
- $ LDA, TAU( I ), WORK, LDWORK )
-*
-* Apply H to A(i+ib:m,i:n) from the right
-*
- CALL DLARFB( 'Right', 'No transpose', 'Forward',
- $ 'Rowwise', M-I-IB+1, N-I+1, IB, A( I, I ),
- $ LDA, WORK, LDWORK, A( I+IB, I ), LDA,
- $ WORK( IB+1 ), LDWORK )
- END IF
- 10 CONTINUE
- ELSE
- I = 1
- END IF
-*
-* Use unblocked code to factor the last or only block.
-*
- IF( I.LE.K )
- $ CALL DGELQ2( M-I+1, N-I+1, A( I, I ), LDA, TAU( I ), WORK,
- $ IINFO )
-*
- WORK( 1 ) = IWS
- RETURN
-*
-* End of DGELQF
-*
- END
diff --git a/src/lib/lapack/dgels.f b/src/lib/lapack/dgels.f
deleted file mode 100644
index 4fa1e229..00000000
--- a/src/lib/lapack/dgels.f
+++ /dev/null
@@ -1,422 +0,0 @@
- SUBROUTINE DGELS( TRANS, M, N, NRHS, A, LDA, B, LDB, WORK, LWORK,
- $ INFO )
-*
-* -- LAPACK driver routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- CHARACTER TRANS
- INTEGER INFO, LDA, LDB, LWORK, M, N, NRHS
-* ..
-* .. Array Arguments ..
- DOUBLE PRECISION A( LDA, * ), B( LDB, * ), WORK( * )
-* ..
-*
-* Purpose
-* =======
-*
-* DGELS solves overdetermined or underdetermined real linear systems
-* involving an M-by-N matrix A, or its transpose, using a QR or LQ
-* factorization of A. It is assumed that A has full rank.
-*
-* The following options are provided:
-*
-* 1. If TRANS = 'N' and m >= n: find the least squares solution of
-* an overdetermined system, i.e., solve the least squares problem
-* minimize || B - A*X ||.
-*
-* 2. If TRANS = 'N' and m < n: find the minimum norm solution of
-* an underdetermined system A * X = B.
-*
-* 3. If TRANS = 'T' and m >= n: find the minimum norm solution of
-* an undetermined system A**T * X = B.
-*
-* 4. If TRANS = 'T' and m < n: find the least squares solution of
-* an overdetermined system, i.e., solve the least squares problem
-* minimize || B - A**T * X ||.
-*
-* Several right hand side vectors b and solution vectors x can be
-* handled in a single call; they are stored as the columns of the
-* M-by-NRHS right hand side matrix B and the N-by-NRHS solution
-* matrix X.
-*
-* Arguments
-* =========
-*
-* TRANS (input) CHARACTER*1
-* = 'N': the linear system involves A;
-* = 'T': the linear system involves A**T.
-*
-* M (input) INTEGER
-* The number of rows of the matrix A. M >= 0.
-*
-* N (input) INTEGER
-* The number of columns of the matrix A. N >= 0.
-*
-* NRHS (input) INTEGER
-* The number of right hand sides, i.e., the number of
-* columns of the matrices B and X. NRHS >=0.
-*
-* A (input/output) DOUBLE PRECISION array, dimension (LDA,N)
-* On entry, the M-by-N matrix A.
-* On exit,
-* if M >= N, A is overwritten by details of its QR
-* factorization as returned by DGEQRF;
-* if M < N, A is overwritten by details of its LQ
-* factorization as returned by DGELQF.
-*
-* LDA (input) INTEGER
-* The leading dimension of the array A. LDA >= max(1,M).
-*
-* B (input/output) DOUBLE PRECISION array, dimension (LDB,NRHS)
-* On entry, the matrix B of right hand side vectors, stored
-* columnwise; B is M-by-NRHS if TRANS = 'N', or N-by-NRHS
-* if TRANS = 'T'.
-* On exit, if INFO = 0, B is overwritten by the solution
-* vectors, stored columnwise:
-* if TRANS = 'N' and m >= n, rows 1 to n of B contain the least
-* squares solution vectors; the residual sum of squares for the
-* solution in each column is given by the sum of squares of
-* elements N+1 to M in that column;
-* if TRANS = 'N' and m < n, rows 1 to N of B contain the
-* minimum norm solution vectors;
-* if TRANS = 'T' and m >= n, rows 1 to M of B contain the
-* minimum norm solution vectors;
-* if TRANS = 'T' and m < n, rows 1 to M of B contain the
-* least squares solution vectors; the residual sum of squares
-* for the solution in each column is given by the sum of
-* squares of elements M+1 to N in that column.
-*
-* LDB (input) INTEGER
-* The leading dimension of the array B. LDB >= MAX(1,M,N).
-*
-* WORK (workspace/output) DOUBLE PRECISION array, dimension (MAX(1,LWORK))
-* On exit, if INFO = 0, WORK(1) returns the optimal LWORK.
-*
-* LWORK (input) INTEGER
-* The dimension of the array WORK.
-* LWORK >= max( 1, MN + max( MN, NRHS ) ).
-* For optimal performance,
-* LWORK >= max( 1, MN + max( MN, NRHS )*NB ).
-* where MN = min(M,N) and NB is the optimum block size.
-*
-* If LWORK = -1, then a workspace query is assumed; the routine
-* only calculates the optimal size of the WORK array, returns
-* this value as the first entry of the WORK array, and no error
-* message related to LWORK is issued by XERBLA.
-*
-* INFO (output) INTEGER
-* = 0: successful exit
-* < 0: if INFO = -i, the i-th argument had an illegal value
-* > 0: if INFO = i, the i-th diagonal element of the
-* triangular factor of A is zero, so that A does not have
-* full rank; the least squares solution could not be
-* computed.
-*
-* =====================================================================
-*
-* .. Parameters ..
- DOUBLE PRECISION ZERO, ONE
- PARAMETER ( ZERO = 0.0D0, ONE = 1.0D0 )
-* ..
-* .. Local Scalars ..
- LOGICAL LQUERY, TPSD
- INTEGER BROW, I, IASCL, IBSCL, J, MN, NB, SCLLEN, WSIZE
- DOUBLE PRECISION ANRM, BIGNUM, BNRM, SMLNUM
-* ..
-* .. Local Arrays ..
- DOUBLE PRECISION RWORK( 1 )
-* ..
-* .. External Functions ..
- LOGICAL LSAME
- INTEGER ILAENV
- DOUBLE PRECISION DLAMCH, DLANGE
- EXTERNAL LSAME, ILAENV, DLABAD, DLAMCH, DLANGE
-* ..
-* .. External Subroutines ..
- EXTERNAL DGELQF, DGEQRF, DLASCL, DLASET, DORMLQ, DORMQR,
- $ DTRTRS, XERBLA
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC DBLE, MAX, MIN
-* ..
-* .. Executable Statements ..
-*
-* Test the input arguments.
-*
- INFO = 0
- MN = MIN( M, N )
- LQUERY = ( LWORK.EQ.-1 )
- IF( .NOT.( LSAME( TRANS, 'N' ) .OR. LSAME( TRANS, 'T' ) ) ) THEN
- INFO = -1
- ELSE IF( M.LT.0 ) THEN
- INFO = -2
- ELSE IF( N.LT.0 ) THEN
- INFO = -3
- ELSE IF( NRHS.LT.0 ) THEN
- INFO = -4
- ELSE IF( LDA.LT.MAX( 1, M ) ) THEN
- INFO = -6
- ELSE IF( LDB.LT.MAX( 1, M, N ) ) THEN
- INFO = -8
- ELSE IF( LWORK.LT.MAX( 1, MN+MAX( MN, NRHS ) ) .AND. .NOT.LQUERY )
- $ THEN
- INFO = -10
- END IF
-*
-* Figure out optimal block size
-*
- IF( INFO.EQ.0 .OR. INFO.EQ.-10 ) THEN
-*
- TPSD = .TRUE.
- IF( LSAME( TRANS, 'N' ) )
- $ TPSD = .FALSE.
-*
- IF( M.GE.N ) THEN
- NB = ILAENV( 1, 'DGEQRF', ' ', M, N, -1, -1 )
- IF( TPSD ) THEN
- NB = MAX( NB, ILAENV( 1, 'DORMQR', 'LN', M, NRHS, N,
- $ -1 ) )
- ELSE
- NB = MAX( NB, ILAENV( 1, 'DORMQR', 'LT', M, NRHS, N,
- $ -1 ) )
- END IF
- ELSE
- NB = ILAENV( 1, 'DGELQF', ' ', M, N, -1, -1 )
- IF( TPSD ) THEN
- NB = MAX( NB, ILAENV( 1, 'DORMLQ', 'LT', N, NRHS, M,
- $ -1 ) )
- ELSE
- NB = MAX( NB, ILAENV( 1, 'DORMLQ', 'LN', N, NRHS, M,
- $ -1 ) )
- END IF
- END IF
-*
- WSIZE = MAX( 1, MN+MAX( MN, NRHS )*NB )
- WORK( 1 ) = DBLE( WSIZE )
-*
- END IF
-*
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'DGELS ', -INFO )
- RETURN
- ELSE IF( LQUERY ) THEN
- RETURN
- END IF
-*
-* Quick return if possible
-*
- IF( MIN( M, N, NRHS ).EQ.0 ) THEN
- CALL DLASET( 'Full', MAX( M, N ), NRHS, ZERO, ZERO, B, LDB )
- RETURN
- END IF
-*
-* Get machine parameters
-*
- SMLNUM = DLAMCH( 'S' ) / DLAMCH( 'P' )
- BIGNUM = ONE / SMLNUM
- CALL DLABAD( SMLNUM, BIGNUM )
-*
-* Scale A, B if max element outside range [SMLNUM,BIGNUM]
-*
- ANRM = DLANGE( 'M', M, N, A, LDA, RWORK )
- IASCL = 0
- IF( ANRM.GT.ZERO .AND. ANRM.LT.SMLNUM ) THEN
-*
-* Scale matrix norm up to SMLNUM
-*
- CALL DLASCL( 'G', 0, 0, ANRM, SMLNUM, M, N, A, LDA, INFO )
- IASCL = 1
- ELSE IF( ANRM.GT.BIGNUM ) THEN
-*
-* Scale matrix norm down to BIGNUM
-*
- CALL DLASCL( 'G', 0, 0, ANRM, BIGNUM, M, N, A, LDA, INFO )
- IASCL = 2
- ELSE IF( ANRM.EQ.ZERO ) THEN
-*
-* Matrix all zero. Return zero solution.
-*
- CALL DLASET( 'F', MAX( M, N ), NRHS, ZERO, ZERO, B, LDB )
- GO TO 50
- END IF
-*
- BROW = M
- IF( TPSD )
- $ BROW = N
- BNRM = DLANGE( 'M', BROW, NRHS, B, LDB, RWORK )
- IBSCL = 0
- IF( BNRM.GT.ZERO .AND. BNRM.LT.SMLNUM ) THEN
-*
-* Scale matrix norm up to SMLNUM
-*
- CALL DLASCL( 'G', 0, 0, BNRM, SMLNUM, BROW, NRHS, B, LDB,
- $ INFO )
- IBSCL = 1
- ELSE IF( BNRM.GT.BIGNUM ) THEN
-*
-* Scale matrix norm down to BIGNUM
-*
- CALL DLASCL( 'G', 0, 0, BNRM, BIGNUM, BROW, NRHS, B, LDB,
- $ INFO )
- IBSCL = 2
- END IF
-*
- IF( M.GE.N ) THEN
-*
-* compute QR factorization of A
-*
- CALL DGEQRF( M, N, A, LDA, WORK( 1 ), WORK( MN+1 ), LWORK-MN,
- $ INFO )
-*
-* workspace at least N, optimally N*NB
-*
- IF( .NOT.TPSD ) THEN
-*
-* Least-Squares Problem min || A * X - B ||
-*
-* B(1:M,1:NRHS) := Q' * B(1:M,1:NRHS)
-*
- CALL DORMQR( 'Left', 'Transpose', M, NRHS, N, A, LDA,
- $ WORK( 1 ), B, LDB, WORK( MN+1 ), LWORK-MN,
- $ INFO )
-*
-* workspace at least NRHS, optimally NRHS*NB
-*
-* B(1:N,1:NRHS) := inv(R) * B(1:N,1:NRHS)
-*
- CALL DTRTRS( 'Upper', 'No transpose', 'Non-unit', N, NRHS,
- $ A, LDA, B, LDB, INFO )
-*
- IF( INFO.GT.0 ) THEN
- RETURN
- END IF
-*
- SCLLEN = N
-*
- ELSE
-*
-* Overdetermined system of equations A' * X = B
-*
-* B(1:N,1:NRHS) := inv(R') * B(1:N,1:NRHS)
-*
- CALL DTRTRS( 'Upper', 'Transpose', 'Non-unit', N, NRHS,
- $ A, LDA, B, LDB, INFO )
-*
- IF( INFO.GT.0 ) THEN
- RETURN
- END IF
-*
-* B(N+1:M,1:NRHS) = ZERO
-*
- DO 20 J = 1, NRHS
- DO 10 I = N + 1, M
- B( I, J ) = ZERO
- 10 CONTINUE
- 20 CONTINUE
-*
-* B(1:M,1:NRHS) := Q(1:N,:) * B(1:N,1:NRHS)
-*
- CALL DORMQR( 'Left', 'No transpose', M, NRHS, N, A, LDA,
- $ WORK( 1 ), B, LDB, WORK( MN+1 ), LWORK-MN,
- $ INFO )
-*
-* workspace at least NRHS, optimally NRHS*NB
-*
- SCLLEN = M
-*
- END IF
-*
- ELSE
-*
-* Compute LQ factorization of A
-*
- CALL DGELQF( M, N, A, LDA, WORK( 1 ), WORK( MN+1 ), LWORK-MN,
- $ INFO )
-*
-* workspace at least M, optimally M*NB.
-*
- IF( .NOT.TPSD ) THEN
-*
-* underdetermined system of equations A * X = B
-*
-* B(1:M,1:NRHS) := inv(L) * B(1:M,1:NRHS)
-*
- CALL DTRTRS( 'Lower', 'No transpose', 'Non-unit', M, NRHS,
- $ A, LDA, B, LDB, INFO )
-*
- IF( INFO.GT.0 ) THEN
- RETURN
- END IF
-*
-* B(M+1:N,1:NRHS) = 0
-*
- DO 40 J = 1, NRHS
- DO 30 I = M + 1, N
- B( I, J ) = ZERO
- 30 CONTINUE
- 40 CONTINUE
-*
-* B(1:N,1:NRHS) := Q(1:N,:)' * B(1:M,1:NRHS)
-*
- CALL DORMLQ( 'Left', 'Transpose', N, NRHS, M, A, LDA,
- $ WORK( 1 ), B, LDB, WORK( MN+1 ), LWORK-MN,
- $ INFO )
-*
-* workspace at least NRHS, optimally NRHS*NB
-*
- SCLLEN = N
-*
- ELSE
-*
-* overdetermined system min || A' * X - B ||
-*
-* B(1:N,1:NRHS) := Q * B(1:N,1:NRHS)
-*
- CALL DORMLQ( 'Left', 'No transpose', N, NRHS, M, A, LDA,
- $ WORK( 1 ), B, LDB, WORK( MN+1 ), LWORK-MN,
- $ INFO )
-*
-* workspace at least NRHS, optimally NRHS*NB
-*
-* B(1:M,1:NRHS) := inv(L') * B(1:M,1:NRHS)
-*
- CALL DTRTRS( 'Lower', 'Transpose', 'Non-unit', M, NRHS,
- $ A, LDA, B, LDB, INFO )
-*
- IF( INFO.GT.0 ) THEN
- RETURN
- END IF
-*
- SCLLEN = M
-*
- END IF
-*
- END IF
-*
-* Undo scaling
-*
- IF( IASCL.EQ.1 ) THEN
- CALL DLASCL( 'G', 0, 0, ANRM, SMLNUM, SCLLEN, NRHS, B, LDB,
- $ INFO )
- ELSE IF( IASCL.EQ.2 ) THEN
- CALL DLASCL( 'G', 0, 0, ANRM, BIGNUM, SCLLEN, NRHS, B, LDB,
- $ INFO )
- END IF
- IF( IBSCL.EQ.1 ) THEN
- CALL DLASCL( 'G', 0, 0, SMLNUM, BNRM, SCLLEN, NRHS, B, LDB,
- $ INFO )
- ELSE IF( IBSCL.EQ.2 ) THEN
- CALL DLASCL( 'G', 0, 0, BIGNUM, BNRM, SCLLEN, NRHS, B, LDB,
- $ INFO )
- END IF
-*
- 50 CONTINUE
- WORK( 1 ) = DBLE( WSIZE )
-*
- RETURN
-*
-* End of DGELS
-*
- END
diff --git a/src/lib/lapack/dgelss.f b/src/lib/lapack/dgelss.f
deleted file mode 100644
index f024e138..00000000
--- a/src/lib/lapack/dgelss.f
+++ /dev/null
@@ -1,617 +0,0 @@
- SUBROUTINE DGELSS( M, N, NRHS, A, LDA, B, LDB, S, RCOND, RANK,
- $ WORK, LWORK, INFO )
-*
-* -- LAPACK driver routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- INTEGER INFO, LDA, LDB, LWORK, M, N, NRHS, RANK
- DOUBLE PRECISION RCOND
-* ..
-* .. Array Arguments ..
- DOUBLE PRECISION A( LDA, * ), B( LDB, * ), S( * ), WORK( * )
-* ..
-*
-* Purpose
-* =======
-*
-* DGELSS computes the minimum norm solution to a real linear least
-* squares problem:
-*
-* Minimize 2-norm(| b - A*x |).
-*
-* using the singular value decomposition (SVD) of A. A is an M-by-N
-* matrix which may be rank-deficient.
-*
-* Several right hand side vectors b and solution vectors x can be
-* handled in a single call; they are stored as the columns of the
-* M-by-NRHS right hand side matrix B and the N-by-NRHS solution matrix
-* X.
-*
-* The effective rank of A is determined by treating as zero those
-* singular values which are less than RCOND times the largest singular
-* value.
-*
-* Arguments
-* =========
-*
-* M (input) INTEGER
-* The number of rows of the matrix A. M >= 0.
-*
-* N (input) INTEGER
-* The number of columns of the matrix A. N >= 0.
-*
-* NRHS (input) INTEGER
-* The number of right hand sides, i.e., the number of columns
-* of the matrices B and X. NRHS >= 0.
-*
-* A (input/output) DOUBLE PRECISION array, dimension (LDA,N)
-* On entry, the M-by-N matrix A.
-* On exit, the first min(m,n) rows of A are overwritten with
-* its right singular vectors, stored rowwise.
-*
-* LDA (input) INTEGER
-* The leading dimension of the array A. LDA >= max(1,M).
-*
-* B (input/output) DOUBLE PRECISION array, dimension (LDB,NRHS)
-* On entry, the M-by-NRHS right hand side matrix B.
-* On exit, B is overwritten by the N-by-NRHS solution
-* matrix X. If m >= n and RANK = n, the residual
-* sum-of-squares for the solution in the i-th column is given
-* by the sum of squares of elements n+1:m in that column.
-*
-* LDB (input) INTEGER
-* The leading dimension of the array B. LDB >= max(1,max(M,N)).
-*
-* S (output) DOUBLE PRECISION array, dimension (min(M,N))
-* The singular values of A in decreasing order.
-* The condition number of A in the 2-norm = S(1)/S(min(m,n)).
-*
-* RCOND (input) DOUBLE PRECISION
-* RCOND is used to determine the effective rank of A.
-* Singular values S(i) <= RCOND*S(1) are treated as zero.
-* If RCOND < 0, machine precision is used instead.
-*
-* RANK (output) INTEGER
-* The effective rank of A, i.e., the number of singular values
-* which are greater than RCOND*S(1).
-*
-* WORK (workspace/output) DOUBLE PRECISION array, dimension (MAX(1,LWORK))
-* On exit, if INFO = 0, WORK(1) returns the optimal LWORK.
-*
-* LWORK (input) INTEGER
-* The dimension of the array WORK. LWORK >= 1, and also:
-* LWORK >= 3*min(M,N) + max( 2*min(M,N), max(M,N), NRHS )
-* For good performance, LWORK should generally be larger.
-*
-* If LWORK = -1, then a workspace query is assumed; the routine
-* only calculates the optimal size of the WORK array, returns
-* this value as the first entry of the WORK array, and no error
-* message related to LWORK is issued by XERBLA.
-*
-* INFO (output) INTEGER
-* = 0: successful exit
-* < 0: if INFO = -i, the i-th argument had an illegal value.
-* > 0: the algorithm for computing the SVD failed to converge;
-* if INFO = i, i off-diagonal elements of an intermediate
-* bidiagonal form did not converge to zero.
-*
-* =====================================================================
-*
-* .. Parameters ..
- DOUBLE PRECISION ZERO, ONE
- PARAMETER ( ZERO = 0.0D+0, ONE = 1.0D+0 )
-* ..
-* .. Local Scalars ..
- LOGICAL LQUERY
- INTEGER BDSPAC, BL, CHUNK, I, IASCL, IBSCL, IE, IL,
- $ ITAU, ITAUP, ITAUQ, IWORK, LDWORK, MAXMN,
- $ MAXWRK, MINMN, MINWRK, MM, MNTHR
- DOUBLE PRECISION ANRM, BIGNUM, BNRM, EPS, SFMIN, SMLNUM, THR
-* ..
-* .. Local Arrays ..
- DOUBLE PRECISION VDUM( 1 )
-* ..
-* .. External Subroutines ..
- EXTERNAL DBDSQR, DCOPY, DGEBRD, DGELQF, DGEMM, DGEMV,
- $ DGEQRF, DLABAD, DLACPY, DLASCL, DLASET, DORGBR,
- $ DORMBR, DORMLQ, DORMQR, DRSCL, XERBLA
-* ..
-* .. External Functions ..
- INTEGER ILAENV
- DOUBLE PRECISION DLAMCH, DLANGE
- EXTERNAL ILAENV, DLAMCH, DLANGE
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC MAX, MIN
-* ..
-* .. Executable Statements ..
-*
-* Test the input arguments
-*
- INFO = 0
- MINMN = MIN( M, N )
- MAXMN = MAX( M, N )
- LQUERY = ( LWORK.EQ.-1 )
- IF( M.LT.0 ) THEN
- INFO = -1
- ELSE IF( N.LT.0 ) THEN
- INFO = -2
- ELSE IF( NRHS.LT.0 ) THEN
- INFO = -3
- ELSE IF( LDA.LT.MAX( 1, M ) ) THEN
- INFO = -5
- ELSE IF( LDB.LT.MAX( 1, MAXMN ) ) THEN
- INFO = -7
- END IF
-*
-* Compute workspace
-* (Note: Comments in the code beginning "Workspace:" describe the
-* minimal amount of workspace needed at that point in the code,
-* as well as the preferred amount for good performance.
-* NB refers to the optimal block size for the immediately
-* following subroutine, as returned by ILAENV.)
-*
- IF( INFO.EQ.0 ) THEN
- MINWRK = 1
- MAXWRK = 1
- IF( MINMN.GT.0 ) THEN
- MM = M
- MNTHR = ILAENV( 6, 'DGELSS', ' ', M, N, NRHS, -1 )
- IF( M.GE.N .AND. M.GE.MNTHR ) THEN
-*
-* Path 1a - overdetermined, with many more rows than
-* columns
-*
- MM = N
- MAXWRK = MAX( MAXWRK, N + N*ILAENV( 1, 'DGEQRF', ' ', M,
- $ N, -1, -1 ) )
- MAXWRK = MAX( MAXWRK, N + NRHS*ILAENV( 1, 'DORMQR', 'LT',
- $ M, NRHS, N, -1 ) )
- END IF
- IF( M.GE.N ) THEN
-*
-* Path 1 - overdetermined or exactly determined
-*
-* Compute workspace needed for DBDSQR
-*
- BDSPAC = MAX( 1, 5*N )
- MAXWRK = MAX( MAXWRK, 3*N + ( MM + N )*ILAENV( 1,
- $ 'DGEBRD', ' ', MM, N, -1, -1 ) )
- MAXWRK = MAX( MAXWRK, 3*N + NRHS*ILAENV( 1, 'DORMBR',
- $ 'QLT', MM, NRHS, N, -1 ) )
- MAXWRK = MAX( MAXWRK, 3*N + ( N - 1 )*ILAENV( 1,
- $ 'DORGBR', 'P', N, N, N, -1 ) )
- MAXWRK = MAX( MAXWRK, BDSPAC )
- MAXWRK = MAX( MAXWRK, N*NRHS )
- MINWRK = MAX( 3*N + MM, 3*N + NRHS, BDSPAC )
- MAXWRK = MAX( MINWRK, MAXWRK )
- END IF
- IF( N.GT.M ) THEN
-*
-* Compute workspace needed for DBDSQR
-*
- BDSPAC = MAX( 1, 5*M )
- MINWRK = MAX( 3*M+NRHS, 3*M+N, BDSPAC )
- IF( N.GE.MNTHR ) THEN
-*
-* Path 2a - underdetermined, with many more columns
-* than rows
-*
- MAXWRK = M + M*ILAENV( 1, 'DGELQF', ' ', M, N, -1,
- $ -1 )
- MAXWRK = MAX( MAXWRK, M*M + 4*M + 2*M*ILAENV( 1,
- $ 'DGEBRD', ' ', M, M, -1, -1 ) )
- MAXWRK = MAX( MAXWRK, M*M + 4*M + NRHS*ILAENV( 1,
- $ 'DORMBR', 'QLT', M, NRHS, M, -1 ) )
- MAXWRK = MAX( MAXWRK, M*M + 4*M +
- $ ( M - 1 )*ILAENV( 1, 'DORGBR', 'P', M,
- $ M, M, -1 ) )
- MAXWRK = MAX( MAXWRK, M*M + M + BDSPAC )
- IF( NRHS.GT.1 ) THEN
- MAXWRK = MAX( MAXWRK, M*M + M + M*NRHS )
- ELSE
- MAXWRK = MAX( MAXWRK, M*M + 2*M )
- END IF
- MAXWRK = MAX( MAXWRK, M + NRHS*ILAENV( 1, 'DORMLQ',
- $ 'LT', N, NRHS, M, -1 ) )
- ELSE
-*
-* Path 2 - underdetermined
-*
- MAXWRK = 3*M + ( N + M )*ILAENV( 1, 'DGEBRD', ' ', M,
- $ N, -1, -1 )
- MAXWRK = MAX( MAXWRK, 3*M + NRHS*ILAENV( 1, 'DORMBR',
- $ 'QLT', M, NRHS, M, -1 ) )
- MAXWRK = MAX( MAXWRK, 3*M + M*ILAENV( 1, 'DORGBR',
- $ 'P', M, N, M, -1 ) )
- MAXWRK = MAX( MAXWRK, BDSPAC )
- MAXWRK = MAX( MAXWRK, N*NRHS )
- END IF
- END IF
- MAXWRK = MAX( MINWRK, MAXWRK )
- END IF
- WORK( 1 ) = MAXWRK
-*
- IF( LWORK.LT.MINWRK .AND. .NOT.LQUERY )
- $ INFO = -12
- END IF
-*
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'DGELSS', -INFO )
- RETURN
- ELSE IF( LQUERY ) THEN
- RETURN
- END IF
-*
-* Quick return if possible
-*
- IF( M.EQ.0 .OR. N.EQ.0 ) THEN
- RANK = 0
- RETURN
- END IF
-*
-* Get machine parameters
-*
- EPS = DLAMCH( 'P' )
- SFMIN = DLAMCH( 'S' )
- SMLNUM = SFMIN / EPS
- BIGNUM = ONE / SMLNUM
- CALL DLABAD( SMLNUM, BIGNUM )
-*
-* Scale A if max element outside range [SMLNUM,BIGNUM]
-*
- ANRM = DLANGE( 'M', M, N, A, LDA, WORK )
- IASCL = 0
- IF( ANRM.GT.ZERO .AND. ANRM.LT.SMLNUM ) THEN
-*
-* Scale matrix norm up to SMLNUM
-*
- CALL DLASCL( 'G', 0, 0, ANRM, SMLNUM, M, N, A, LDA, INFO )
- IASCL = 1
- ELSE IF( ANRM.GT.BIGNUM ) THEN
-*
-* Scale matrix norm down to BIGNUM
-*
- CALL DLASCL( 'G', 0, 0, ANRM, BIGNUM, M, N, A, LDA, INFO )
- IASCL = 2
- ELSE IF( ANRM.EQ.ZERO ) THEN
-*
-* Matrix all zero. Return zero solution.
-*
- CALL DLASET( 'F', MAX( M, N ), NRHS, ZERO, ZERO, B, LDB )
- CALL DLASET( 'F', MINMN, 1, ZERO, ZERO, S, 1 )
- RANK = 0
- GO TO 70
- END IF
-*
-* Scale B if max element outside range [SMLNUM,BIGNUM]
-*
- BNRM = DLANGE( 'M', M, NRHS, B, LDB, WORK )
- IBSCL = 0
- IF( BNRM.GT.ZERO .AND. BNRM.LT.SMLNUM ) THEN
-*
-* Scale matrix norm up to SMLNUM
-*
- CALL DLASCL( 'G', 0, 0, BNRM, SMLNUM, M, NRHS, B, LDB, INFO )
- IBSCL = 1
- ELSE IF( BNRM.GT.BIGNUM ) THEN
-*
-* Scale matrix norm down to BIGNUM
-*
- CALL DLASCL( 'G', 0, 0, BNRM, BIGNUM, M, NRHS, B, LDB, INFO )
- IBSCL = 2
- END IF
-*
-* Overdetermined case
-*
- IF( M.GE.N ) THEN
-*
-* Path 1 - overdetermined or exactly determined
-*
- MM = M
- IF( M.GE.MNTHR ) THEN
-*
-* Path 1a - overdetermined, with many more rows than columns
-*
- MM = N
- ITAU = 1
- IWORK = ITAU + N
-*
-* Compute A=Q*R
-* (Workspace: need 2*N, prefer N+N*NB)
-*
- CALL DGEQRF( M, N, A, LDA, WORK( ITAU ), WORK( IWORK ),
- $ LWORK-IWORK+1, INFO )
-*
-* Multiply B by transpose(Q)
-* (Workspace: need N+NRHS, prefer N+NRHS*NB)
-*
- CALL DORMQR( 'L', 'T', M, NRHS, N, A, LDA, WORK( ITAU ), B,
- $ LDB, WORK( IWORK ), LWORK-IWORK+1, INFO )
-*
-* Zero out below R
-*
- IF( N.GT.1 )
- $ CALL DLASET( 'L', N-1, N-1, ZERO, ZERO, A( 2, 1 ), LDA )
- END IF
-*
- IE = 1
- ITAUQ = IE + N
- ITAUP = ITAUQ + N
- IWORK = ITAUP + N
-*
-* Bidiagonalize R in A
-* (Workspace: need 3*N+MM, prefer 3*N+(MM+N)*NB)
-*
- CALL DGEBRD( MM, N, A, LDA, S, WORK( IE ), WORK( ITAUQ ),
- $ WORK( ITAUP ), WORK( IWORK ), LWORK-IWORK+1,
- $ INFO )
-*
-* Multiply B by transpose of left bidiagonalizing vectors of R
-* (Workspace: need 3*N+NRHS, prefer 3*N+NRHS*NB)
-*
- CALL DORMBR( 'Q', 'L', 'T', MM, NRHS, N, A, LDA, WORK( ITAUQ ),
- $ B, LDB, WORK( IWORK ), LWORK-IWORK+1, INFO )
-*
-* Generate right bidiagonalizing vectors of R in A
-* (Workspace: need 4*N-1, prefer 3*N+(N-1)*NB)
-*
- CALL DORGBR( 'P', N, N, N, A, LDA, WORK( ITAUP ),
- $ WORK( IWORK ), LWORK-IWORK+1, INFO )
- IWORK = IE + N
-*
-* Perform bidiagonal QR iteration
-* multiply B by transpose of left singular vectors
-* compute right singular vectors in A
-* (Workspace: need BDSPAC)
-*
- CALL DBDSQR( 'U', N, N, 0, NRHS, S, WORK( IE ), A, LDA, VDUM,
- $ 1, B, LDB, WORK( IWORK ), INFO )
- IF( INFO.NE.0 )
- $ GO TO 70
-*
-* Multiply B by reciprocals of singular values
-*
- THR = MAX( RCOND*S( 1 ), SFMIN )
- IF( RCOND.LT.ZERO )
- $ THR = MAX( EPS*S( 1 ), SFMIN )
- RANK = 0
- DO 10 I = 1, N
- IF( S( I ).GT.THR ) THEN
- CALL DRSCL( NRHS, S( I ), B( I, 1 ), LDB )
- RANK = RANK + 1
- ELSE
- CALL DLASET( 'F', 1, NRHS, ZERO, ZERO, B( I, 1 ), LDB )
- END IF
- 10 CONTINUE
-*
-* Multiply B by right singular vectors
-* (Workspace: need N, prefer N*NRHS)
-*
- IF( LWORK.GE.LDB*NRHS .AND. NRHS.GT.1 ) THEN
- CALL DGEMM( 'T', 'N', N, NRHS, N, ONE, A, LDA, B, LDB, ZERO,
- $ WORK, LDB )
- CALL DLACPY( 'G', N, NRHS, WORK, LDB, B, LDB )
- ELSE IF( NRHS.GT.1 ) THEN
- CHUNK = LWORK / N
- DO 20 I = 1, NRHS, CHUNK
- BL = MIN( NRHS-I+1, CHUNK )
- CALL DGEMM( 'T', 'N', N, BL, N, ONE, A, LDA, B( 1, I ),
- $ LDB, ZERO, WORK, N )
- CALL DLACPY( 'G', N, BL, WORK, N, B( 1, I ), LDB )
- 20 CONTINUE
- ELSE
- CALL DGEMV( 'T', N, N, ONE, A, LDA, B, 1, ZERO, WORK, 1 )
- CALL DCOPY( N, WORK, 1, B, 1 )
- END IF
-*
- ELSE IF( N.GE.MNTHR .AND. LWORK.GE.4*M+M*M+
- $ MAX( M, 2*M-4, NRHS, N-3*M ) ) THEN
-*
-* Path 2a - underdetermined, with many more columns than rows
-* and sufficient workspace for an efficient algorithm
-*
- LDWORK = M
- IF( LWORK.GE.MAX( 4*M+M*LDA+MAX( M, 2*M-4, NRHS, N-3*M ),
- $ M*LDA+M+M*NRHS ) )LDWORK = LDA
- ITAU = 1
- IWORK = M + 1
-*
-* Compute A=L*Q
-* (Workspace: need 2*M, prefer M+M*NB)
-*
- CALL DGELQF( M, N, A, LDA, WORK( ITAU ), WORK( IWORK ),
- $ LWORK-IWORK+1, INFO )
- IL = IWORK
-*
-* Copy L to WORK(IL), zeroing out above it
-*
- CALL DLACPY( 'L', M, M, A, LDA, WORK( IL ), LDWORK )
- CALL DLASET( 'U', M-1, M-1, ZERO, ZERO, WORK( IL+LDWORK ),
- $ LDWORK )
- IE = IL + LDWORK*M
- ITAUQ = IE + M
- ITAUP = ITAUQ + M
- IWORK = ITAUP + M
-*
-* Bidiagonalize L in WORK(IL)
-* (Workspace: need M*M+5*M, prefer M*M+4*M+2*M*NB)
-*
- CALL DGEBRD( M, M, WORK( IL ), LDWORK, S, WORK( IE ),
- $ WORK( ITAUQ ), WORK( ITAUP ), WORK( IWORK ),
- $ LWORK-IWORK+1, INFO )
-*
-* Multiply B by transpose of left bidiagonalizing vectors of L
-* (Workspace: need M*M+4*M+NRHS, prefer M*M+4*M+NRHS*NB)
-*
- CALL DORMBR( 'Q', 'L', 'T', M, NRHS, M, WORK( IL ), LDWORK,
- $ WORK( ITAUQ ), B, LDB, WORK( IWORK ),
- $ LWORK-IWORK+1, INFO )
-*
-* Generate right bidiagonalizing vectors of R in WORK(IL)
-* (Workspace: need M*M+5*M-1, prefer M*M+4*M+(M-1)*NB)
-*
- CALL DORGBR( 'P', M, M, M, WORK( IL ), LDWORK, WORK( ITAUP ),
- $ WORK( IWORK ), LWORK-IWORK+1, INFO )
- IWORK = IE + M
-*
-* Perform bidiagonal QR iteration,
-* computing right singular vectors of L in WORK(IL) and
-* multiplying B by transpose of left singular vectors
-* (Workspace: need M*M+M+BDSPAC)
-*
- CALL DBDSQR( 'U', M, M, 0, NRHS, S, WORK( IE ), WORK( IL ),
- $ LDWORK, A, LDA, B, LDB, WORK( IWORK ), INFO )
- IF( INFO.NE.0 )
- $ GO TO 70
-*
-* Multiply B by reciprocals of singular values
-*
- THR = MAX( RCOND*S( 1 ), SFMIN )
- IF( RCOND.LT.ZERO )
- $ THR = MAX( EPS*S( 1 ), SFMIN )
- RANK = 0
- DO 30 I = 1, M
- IF( S( I ).GT.THR ) THEN
- CALL DRSCL( NRHS, S( I ), B( I, 1 ), LDB )
- RANK = RANK + 1
- ELSE
- CALL DLASET( 'F', 1, NRHS, ZERO, ZERO, B( I, 1 ), LDB )
- END IF
- 30 CONTINUE
- IWORK = IE
-*
-* Multiply B by right singular vectors of L in WORK(IL)
-* (Workspace: need M*M+2*M, prefer M*M+M+M*NRHS)
-*
- IF( LWORK.GE.LDB*NRHS+IWORK-1 .AND. NRHS.GT.1 ) THEN
- CALL DGEMM( 'T', 'N', M, NRHS, M, ONE, WORK( IL ), LDWORK,
- $ B, LDB, ZERO, WORK( IWORK ), LDB )
- CALL DLACPY( 'G', M, NRHS, WORK( IWORK ), LDB, B, LDB )
- ELSE IF( NRHS.GT.1 ) THEN
- CHUNK = ( LWORK-IWORK+1 ) / M
- DO 40 I = 1, NRHS, CHUNK
- BL = MIN( NRHS-I+1, CHUNK )
- CALL DGEMM( 'T', 'N', M, BL, M, ONE, WORK( IL ), LDWORK,
- $ B( 1, I ), LDB, ZERO, WORK( IWORK ), M )
- CALL DLACPY( 'G', M, BL, WORK( IWORK ), M, B( 1, I ),
- $ LDB )
- 40 CONTINUE
- ELSE
- CALL DGEMV( 'T', M, M, ONE, WORK( IL ), LDWORK, B( 1, 1 ),
- $ 1, ZERO, WORK( IWORK ), 1 )
- CALL DCOPY( M, WORK( IWORK ), 1, B( 1, 1 ), 1 )
- END IF
-*
-* Zero out below first M rows of B
-*
- CALL DLASET( 'F', N-M, NRHS, ZERO, ZERO, B( M+1, 1 ), LDB )
- IWORK = ITAU + M
-*
-* Multiply transpose(Q) by B
-* (Workspace: need M+NRHS, prefer M+NRHS*NB)
-*
- CALL DORMLQ( 'L', 'T', N, NRHS, M, A, LDA, WORK( ITAU ), B,
- $ LDB, WORK( IWORK ), LWORK-IWORK+1, INFO )
-*
- ELSE
-*
-* Path 2 - remaining underdetermined cases
-*
- IE = 1
- ITAUQ = IE + M
- ITAUP = ITAUQ + M
- IWORK = ITAUP + M
-*
-* Bidiagonalize A
-* (Workspace: need 3*M+N, prefer 3*M+(M+N)*NB)
-*
- CALL DGEBRD( M, N, A, LDA, S, WORK( IE ), WORK( ITAUQ ),
- $ WORK( ITAUP ), WORK( IWORK ), LWORK-IWORK+1,
- $ INFO )
-*
-* Multiply B by transpose of left bidiagonalizing vectors
-* (Workspace: need 3*M+NRHS, prefer 3*M+NRHS*NB)
-*
- CALL DORMBR( 'Q', 'L', 'T', M, NRHS, N, A, LDA, WORK( ITAUQ ),
- $ B, LDB, WORK( IWORK ), LWORK-IWORK+1, INFO )
-*
-* Generate right bidiagonalizing vectors in A
-* (Workspace: need 4*M, prefer 3*M+M*NB)
-*
- CALL DORGBR( 'P', M, N, M, A, LDA, WORK( ITAUP ),
- $ WORK( IWORK ), LWORK-IWORK+1, INFO )
- IWORK = IE + M
-*
-* Perform bidiagonal QR iteration,
-* computing right singular vectors of A in A and
-* multiplying B by transpose of left singular vectors
-* (Workspace: need BDSPAC)
-*
- CALL DBDSQR( 'L', M, N, 0, NRHS, S, WORK( IE ), A, LDA, VDUM,
- $ 1, B, LDB, WORK( IWORK ), INFO )
- IF( INFO.NE.0 )
- $ GO TO 70
-*
-* Multiply B by reciprocals of singular values
-*
- THR = MAX( RCOND*S( 1 ), SFMIN )
- IF( RCOND.LT.ZERO )
- $ THR = MAX( EPS*S( 1 ), SFMIN )
- RANK = 0
- DO 50 I = 1, M
- IF( S( I ).GT.THR ) THEN
- CALL DRSCL( NRHS, S( I ), B( I, 1 ), LDB )
- RANK = RANK + 1
- ELSE
- CALL DLASET( 'F', 1, NRHS, ZERO, ZERO, B( I, 1 ), LDB )
- END IF
- 50 CONTINUE
-*
-* Multiply B by right singular vectors of A
-* (Workspace: need N, prefer N*NRHS)
-*
- IF( LWORK.GE.LDB*NRHS .AND. NRHS.GT.1 ) THEN
- CALL DGEMM( 'T', 'N', N, NRHS, M, ONE, A, LDA, B, LDB, ZERO,
- $ WORK, LDB )
- CALL DLACPY( 'F', N, NRHS, WORK, LDB, B, LDB )
- ELSE IF( NRHS.GT.1 ) THEN
- CHUNK = LWORK / N
- DO 60 I = 1, NRHS, CHUNK
- BL = MIN( NRHS-I+1, CHUNK )
- CALL DGEMM( 'T', 'N', N, BL, M, ONE, A, LDA, B( 1, I ),
- $ LDB, ZERO, WORK, N )
- CALL DLACPY( 'F', N, BL, WORK, N, B( 1, I ), LDB )
- 60 CONTINUE
- ELSE
- CALL DGEMV( 'T', M, N, ONE, A, LDA, B, 1, ZERO, WORK, 1 )
- CALL DCOPY( N, WORK, 1, B, 1 )
- END IF
- END IF
-*
-* Undo scaling
-*
- IF( IASCL.EQ.1 ) THEN
- CALL DLASCL( 'G', 0, 0, ANRM, SMLNUM, N, NRHS, B, LDB, INFO )
- CALL DLASCL( 'G', 0, 0, SMLNUM, ANRM, MINMN, 1, S, MINMN,
- $ INFO )
- ELSE IF( IASCL.EQ.2 ) THEN
- CALL DLASCL( 'G', 0, 0, ANRM, BIGNUM, N, NRHS, B, LDB, INFO )
- CALL DLASCL( 'G', 0, 0, BIGNUM, ANRM, MINMN, 1, S, MINMN,
- $ INFO )
- END IF
- IF( IBSCL.EQ.1 ) THEN
- CALL DLASCL( 'G', 0, 0, SMLNUM, BNRM, N, NRHS, B, LDB, INFO )
- ELSE IF( IBSCL.EQ.2 ) THEN
- CALL DLASCL( 'G', 0, 0, BIGNUM, BNRM, N, NRHS, B, LDB, INFO )
- END IF
-*
- 70 CONTINUE
- WORK( 1 ) = MAXWRK
- RETURN
-*
-* End of DGELSS
-*
- END
diff --git a/src/lib/lapack/dgelsx.f b/src/lib/lapack/dgelsx.f
deleted file mode 100644
index a597cd47..00000000
--- a/src/lib/lapack/dgelsx.f
+++ /dev/null
@@ -1,349 +0,0 @@
- SUBROUTINE DGELSX( M, N, NRHS, A, LDA, B, LDB, JPVT, RCOND, RANK,
- $ WORK, INFO )
-*
-* -- LAPACK driver routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- INTEGER INFO, LDA, LDB, M, N, NRHS, RANK
- DOUBLE PRECISION RCOND
-* ..
-* .. Array Arguments ..
- INTEGER JPVT( * )
- DOUBLE PRECISION A( LDA, * ), B( LDB, * ), WORK( * )
-* ..
-*
-* Purpose
-* =======
-*
-* This routine is deprecated and has been replaced by routine DGELSY.
-*
-* DGELSX computes the minimum-norm solution to a real linear least
-* squares problem:
-* minimize || A * X - B ||
-* using a complete orthogonal factorization of A. A is an M-by-N
-* matrix which may be rank-deficient.
-*
-* Several right hand side vectors b and solution vectors x can be
-* handled in a single call; they are stored as the columns of the
-* M-by-NRHS right hand side matrix B and the N-by-NRHS solution
-* matrix X.
-*
-* The routine first computes a QR factorization with column pivoting:
-* A * P = Q * [ R11 R12 ]
-* [ 0 R22 ]
-* with R11 defined as the largest leading submatrix whose estimated
-* condition number is less than 1/RCOND. The order of R11, RANK,
-* is the effective rank of A.
-*
-* Then, R22 is considered to be negligible, and R12 is annihilated
-* by orthogonal transformations from the right, arriving at the
-* complete orthogonal factorization:
-* A * P = Q * [ T11 0 ] * Z
-* [ 0 0 ]
-* The minimum-norm solution is then
-* X = P * Z' [ inv(T11)*Q1'*B ]
-* [ 0 ]
-* where Q1 consists of the first RANK columns of Q.
-*
-* Arguments
-* =========
-*
-* M (input) INTEGER
-* The number of rows of the matrix A. M >= 0.
-*
-* N (input) INTEGER
-* The number of columns of the matrix A. N >= 0.
-*
-* NRHS (input) INTEGER
-* The number of right hand sides, i.e., the number of
-* columns of matrices B and X. NRHS >= 0.
-*
-* A (input/output) DOUBLE PRECISION array, dimension (LDA,N)
-* On entry, the M-by-N matrix A.
-* On exit, A has been overwritten by details of its
-* complete orthogonal factorization.
-*
-* LDA (input) INTEGER
-* The leading dimension of the array A. LDA >= max(1,M).
-*
-* B (input/output) DOUBLE PRECISION array, dimension (LDB,NRHS)
-* On entry, the M-by-NRHS right hand side matrix B.
-* On exit, the N-by-NRHS solution matrix X.
-* If m >= n and RANK = n, the residual sum-of-squares for
-* the solution in the i-th column is given by the sum of
-* squares of elements N+1:M in that column.
-*
-* LDB (input) INTEGER
-* The leading dimension of the array B. LDB >= max(1,M,N).
-*
-* JPVT (input/output) INTEGER array, dimension (N)
-* On entry, if JPVT(i) .ne. 0, the i-th column of A is an
-* initial column, otherwise it is a free column. Before
-* the QR factorization of A, all initial columns are
-* permuted to the leading positions; only the remaining
-* free columns are moved as a result of column pivoting
-* during the factorization.
-* On exit, if JPVT(i) = k, then the i-th column of A*P
-* was the k-th column of A.
-*
-* RCOND (input) DOUBLE PRECISION
-* RCOND is used to determine the effective rank of A, which
-* is defined as the order of the largest leading triangular
-* submatrix R11 in the QR factorization with pivoting of A,
-* whose estimated condition number < 1/RCOND.
-*
-* RANK (output) INTEGER
-* The effective rank of A, i.e., the order of the submatrix
-* R11. This is the same as the order of the submatrix T11
-* in the complete orthogonal factorization of A.
-*
-* WORK (workspace) DOUBLE PRECISION array, dimension
-* (max( min(M,N)+3*N, 2*min(M,N)+NRHS )),
-*
-* INFO (output) INTEGER
-* = 0: successful exit
-* < 0: if INFO = -i, the i-th argument had an illegal value
-*
-* =====================================================================
-*
-* .. Parameters ..
- INTEGER IMAX, IMIN
- PARAMETER ( IMAX = 1, IMIN = 2 )
- DOUBLE PRECISION ZERO, ONE, DONE, NTDONE
- PARAMETER ( ZERO = 0.0D0, ONE = 1.0D0, DONE = ZERO,
- $ NTDONE = ONE )
-* ..
-* .. Local Scalars ..
- INTEGER I, IASCL, IBSCL, ISMAX, ISMIN, J, K, MN
- DOUBLE PRECISION ANRM, BIGNUM, BNRM, C1, C2, S1, S2, SMAX,
- $ SMAXPR, SMIN, SMINPR, SMLNUM, T1, T2
-* ..
-* .. External Functions ..
- DOUBLE PRECISION DLAMCH, DLANGE
- EXTERNAL DLAMCH, DLANGE
-* ..
-* .. External Subroutines ..
- EXTERNAL DGEQPF, DLAIC1, DLASCL, DLASET, DLATZM, DORM2R,
- $ DTRSM, DTZRQF, XERBLA
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC ABS, MAX, MIN
-* ..
-* .. Executable Statements ..
-*
- MN = MIN( M, N )
- ISMIN = MN + 1
- ISMAX = 2*MN + 1
-*
-* Test the input arguments.
-*
- INFO = 0
- IF( M.LT.0 ) THEN
- INFO = -1
- ELSE IF( N.LT.0 ) THEN
- INFO = -2
- ELSE IF( NRHS.LT.0 ) THEN
- INFO = -3
- ELSE IF( LDA.LT.MAX( 1, M ) ) THEN
- INFO = -5
- ELSE IF( LDB.LT.MAX( 1, M, N ) ) THEN
- INFO = -7
- END IF
-*
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'DGELSX', -INFO )
- RETURN
- END IF
-*
-* Quick return if possible
-*
- IF( MIN( M, N, NRHS ).EQ.0 ) THEN
- RANK = 0
- RETURN
- END IF
-*
-* Get machine parameters
-*
- SMLNUM = DLAMCH( 'S' ) / DLAMCH( 'P' )
- BIGNUM = ONE / SMLNUM
- CALL DLABAD( SMLNUM, BIGNUM )
-*
-* Scale A, B if max elements outside range [SMLNUM,BIGNUM]
-*
- ANRM = DLANGE( 'M', M, N, A, LDA, WORK )
- IASCL = 0
- IF( ANRM.GT.ZERO .AND. ANRM.LT.SMLNUM ) THEN
-*
-* Scale matrix norm up to SMLNUM
-*
- CALL DLASCL( 'G', 0, 0, ANRM, SMLNUM, M, N, A, LDA, INFO )
- IASCL = 1
- ELSE IF( ANRM.GT.BIGNUM ) THEN
-*
-* Scale matrix norm down to BIGNUM
-*
- CALL DLASCL( 'G', 0, 0, ANRM, BIGNUM, M, N, A, LDA, INFO )
- IASCL = 2
- ELSE IF( ANRM.EQ.ZERO ) THEN
-*
-* Matrix all zero. Return zero solution.
-*
- CALL DLASET( 'F', MAX( M, N ), NRHS, ZERO, ZERO, B, LDB )
- RANK = 0
- GO TO 100
- END IF
-*
- BNRM = DLANGE( 'M', M, NRHS, B, LDB, WORK )
- IBSCL = 0
- IF( BNRM.GT.ZERO .AND. BNRM.LT.SMLNUM ) THEN
-*
-* Scale matrix norm up to SMLNUM
-*
- CALL DLASCL( 'G', 0, 0, BNRM, SMLNUM, M, NRHS, B, LDB, INFO )
- IBSCL = 1
- ELSE IF( BNRM.GT.BIGNUM ) THEN
-*
-* Scale matrix norm down to BIGNUM
-*
- CALL DLASCL( 'G', 0, 0, BNRM, BIGNUM, M, NRHS, B, LDB, INFO )
- IBSCL = 2
- END IF
-*
-* Compute QR factorization with column pivoting of A:
-* A * P = Q * R
-*
- CALL DGEQPF( M, N, A, LDA, JPVT, WORK( 1 ), WORK( MN+1 ), INFO )
-*
-* workspace 3*N. Details of Householder rotations stored
-* in WORK(1:MN).
-*
-* Determine RANK using incremental condition estimation
-*
- WORK( ISMIN ) = ONE
- WORK( ISMAX ) = ONE
- SMAX = ABS( A( 1, 1 ) )
- SMIN = SMAX
- IF( ABS( A( 1, 1 ) ).EQ.ZERO ) THEN
- RANK = 0
- CALL DLASET( 'F', MAX( M, N ), NRHS, ZERO, ZERO, B, LDB )
- GO TO 100
- ELSE
- RANK = 1
- END IF
-*
- 10 CONTINUE
- IF( RANK.LT.MN ) THEN
- I = RANK + 1
- CALL DLAIC1( IMIN, RANK, WORK( ISMIN ), SMIN, A( 1, I ),
- $ A( I, I ), SMINPR, S1, C1 )
- CALL DLAIC1( IMAX, RANK, WORK( ISMAX ), SMAX, A( 1, I ),
- $ A( I, I ), SMAXPR, S2, C2 )
-*
- IF( SMAXPR*RCOND.LE.SMINPR ) THEN
- DO 20 I = 1, RANK
- WORK( ISMIN+I-1 ) = S1*WORK( ISMIN+I-1 )
- WORK( ISMAX+I-1 ) = S2*WORK( ISMAX+I-1 )
- 20 CONTINUE
- WORK( ISMIN+RANK ) = C1
- WORK( ISMAX+RANK ) = C2
- SMIN = SMINPR
- SMAX = SMAXPR
- RANK = RANK + 1
- GO TO 10
- END IF
- END IF
-*
-* Logically partition R = [ R11 R12 ]
-* [ 0 R22 ]
-* where R11 = R(1:RANK,1:RANK)
-*
-* [R11,R12] = [ T11, 0 ] * Y
-*
- IF( RANK.LT.N )
- $ CALL DTZRQF( RANK, N, A, LDA, WORK( MN+1 ), INFO )
-*
-* Details of Householder rotations stored in WORK(MN+1:2*MN)
-*
-* B(1:M,1:NRHS) := Q' * B(1:M,1:NRHS)
-*
- CALL DORM2R( 'Left', 'Transpose', M, NRHS, MN, A, LDA, WORK( 1 ),
- $ B, LDB, WORK( 2*MN+1 ), INFO )
-*
-* workspace NRHS
-*
-* B(1:RANK,1:NRHS) := inv(T11) * B(1:RANK,1:NRHS)
-*
- CALL DTRSM( 'Left', 'Upper', 'No transpose', 'Non-unit', RANK,
- $ NRHS, ONE, A, LDA, B, LDB )
-*
- DO 40 I = RANK + 1, N
- DO 30 J = 1, NRHS
- B( I, J ) = ZERO
- 30 CONTINUE
- 40 CONTINUE
-*
-* B(1:N,1:NRHS) := Y' * B(1:N,1:NRHS)
-*
- IF( RANK.LT.N ) THEN
- DO 50 I = 1, RANK
- CALL DLATZM( 'Left', N-RANK+1, NRHS, A( I, RANK+1 ), LDA,
- $ WORK( MN+I ), B( I, 1 ), B( RANK+1, 1 ), LDB,
- $ WORK( 2*MN+1 ) )
- 50 CONTINUE
- END IF
-*
-* workspace NRHS
-*
-* B(1:N,1:NRHS) := P * B(1:N,1:NRHS)
-*
- DO 90 J = 1, NRHS
- DO 60 I = 1, N
- WORK( 2*MN+I ) = NTDONE
- 60 CONTINUE
- DO 80 I = 1, N
- IF( WORK( 2*MN+I ).EQ.NTDONE ) THEN
- IF( JPVT( I ).NE.I ) THEN
- K = I
- T1 = B( K, J )
- T2 = B( JPVT( K ), J )
- 70 CONTINUE
- B( JPVT( K ), J ) = T1
- WORK( 2*MN+K ) = DONE
- T1 = T2
- K = JPVT( K )
- T2 = B( JPVT( K ), J )
- IF( JPVT( K ).NE.I )
- $ GO TO 70
- B( I, J ) = T1
- WORK( 2*MN+K ) = DONE
- END IF
- END IF
- 80 CONTINUE
- 90 CONTINUE
-*
-* Undo scaling
-*
- IF( IASCL.EQ.1 ) THEN
- CALL DLASCL( 'G', 0, 0, ANRM, SMLNUM, N, NRHS, B, LDB, INFO )
- CALL DLASCL( 'U', 0, 0, SMLNUM, ANRM, RANK, RANK, A, LDA,
- $ INFO )
- ELSE IF( IASCL.EQ.2 ) THEN
- CALL DLASCL( 'G', 0, 0, ANRM, BIGNUM, N, NRHS, B, LDB, INFO )
- CALL DLASCL( 'U', 0, 0, BIGNUM, ANRM, RANK, RANK, A, LDA,
- $ INFO )
- END IF
- IF( IBSCL.EQ.1 ) THEN
- CALL DLASCL( 'G', 0, 0, SMLNUM, BNRM, N, NRHS, B, LDB, INFO )
- ELSE IF( IBSCL.EQ.2 ) THEN
- CALL DLASCL( 'G', 0, 0, BIGNUM, BNRM, N, NRHS, B, LDB, INFO )
- END IF
-*
- 100 CONTINUE
-*
- RETURN
-*
-* End of DGELSX
-*
- END
diff --git a/src/lib/lapack/dgelsy.f b/src/lib/lapack/dgelsy.f
deleted file mode 100644
index 4334650f..00000000
--- a/src/lib/lapack/dgelsy.f
+++ /dev/null
@@ -1,391 +0,0 @@
- SUBROUTINE DGELSY( M, N, NRHS, A, LDA, B, LDB, JPVT, RCOND, RANK,
- $ WORK, LWORK, INFO )
-*
-* -- LAPACK driver routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- INTEGER INFO, LDA, LDB, LWORK, M, N, NRHS, RANK
- DOUBLE PRECISION RCOND
-* ..
-* .. Array Arguments ..
- INTEGER JPVT( * )
- DOUBLE PRECISION A( LDA, * ), B( LDB, * ), WORK( * )
-* ..
-*
-* Purpose
-* =======
-*
-* DGELSY computes the minimum-norm solution to a real linear least
-* squares problem:
-* minimize || A * X - B ||
-* using a complete orthogonal factorization of A. A is an M-by-N
-* matrix which may be rank-deficient.
-*
-* Several right hand side vectors b and solution vectors x can be
-* handled in a single call; they are stored as the columns of the
-* M-by-NRHS right hand side matrix B and the N-by-NRHS solution
-* matrix X.
-*
-* The routine first computes a QR factorization with column pivoting:
-* A * P = Q * [ R11 R12 ]
-* [ 0 R22 ]
-* with R11 defined as the largest leading submatrix whose estimated
-* condition number is less than 1/RCOND. The order of R11, RANK,
-* is the effective rank of A.
-*
-* Then, R22 is considered to be negligible, and R12 is annihilated
-* by orthogonal transformations from the right, arriving at the
-* complete orthogonal factorization:
-* A * P = Q * [ T11 0 ] * Z
-* [ 0 0 ]
-* The minimum-norm solution is then
-* X = P * Z' [ inv(T11)*Q1'*B ]
-* [ 0 ]
-* where Q1 consists of the first RANK columns of Q.
-*
-* This routine is basically identical to the original xGELSX except
-* three differences:
-* o The call to the subroutine xGEQPF has been substituted by the
-* the call to the subroutine xGEQP3. This subroutine is a Blas-3
-* version of the QR factorization with column pivoting.
-* o Matrix B (the right hand side) is updated with Blas-3.
-* o The permutation of matrix B (the right hand side) is faster and
-* more simple.
-*
-* Arguments
-* =========
-*
-* M (input) INTEGER
-* The number of rows of the matrix A. M >= 0.
-*
-* N (input) INTEGER
-* The number of columns of the matrix A. N >= 0.
-*
-* NRHS (input) INTEGER
-* The number of right hand sides, i.e., the number of
-* columns of matrices B and X. NRHS >= 0.
-*
-* A (input/output) DOUBLE PRECISION array, dimension (LDA,N)
-* On entry, the M-by-N matrix A.
-* On exit, A has been overwritten by details of its
-* complete orthogonal factorization.
-*
-* LDA (input) INTEGER
-* The leading dimension of the array A. LDA >= max(1,M).
-*
-* B (input/output) DOUBLE PRECISION array, dimension (LDB,NRHS)
-* On entry, the M-by-NRHS right hand side matrix B.
-* On exit, the N-by-NRHS solution matrix X.
-*
-* LDB (input) INTEGER
-* The leading dimension of the array B. LDB >= max(1,M,N).
-*
-* JPVT (input/output) INTEGER array, dimension (N)
-* On entry, if JPVT(i) .ne. 0, the i-th column of A is permuted
-* to the front of AP, otherwise column i is a free column.
-* On exit, if JPVT(i) = k, then the i-th column of AP
-* was the k-th column of A.
-*
-* RCOND (input) DOUBLE PRECISION
-* RCOND is used to determine the effective rank of A, which
-* is defined as the order of the largest leading triangular
-* submatrix R11 in the QR factorization with pivoting of A,
-* whose estimated condition number < 1/RCOND.
-*
-* RANK (output) INTEGER
-* The effective rank of A, i.e., the order of the submatrix
-* R11. This is the same as the order of the submatrix T11
-* in the complete orthogonal factorization of A.
-*
-* WORK (workspace/output) DOUBLE PRECISION array, dimension (MAX(1,LWORK))
-* On exit, if INFO = 0, WORK(1) returns the optimal LWORK.
-*
-* LWORK (input) INTEGER
-* The dimension of the array WORK.
-* The unblocked strategy requires that:
-* LWORK >= MAX( MN+3*N+1, 2*MN+NRHS ),
-* where MN = min( M, N ).
-* The block algorithm requires that:
-* LWORK >= MAX( MN+2*N+NB*(N+1), 2*MN+NB*NRHS ),
-* where NB is an upper bound on the blocksize returned
-* by ILAENV for the routines DGEQP3, DTZRZF, STZRQF, DORMQR,
-* and DORMRZ.
-*
-* If LWORK = -1, then a workspace query is assumed; the routine
-* only calculates the optimal size of the WORK array, returns
-* this value as the first entry of the WORK array, and no error
-* message related to LWORK is issued by XERBLA.
-*
-* INFO (output) INTEGER
-* = 0: successful exit
-* < 0: If INFO = -i, the i-th argument had an illegal value.
-*
-* Further Details
-* ===============
-*
-* Based on contributions by
-* A. Petitet, Computer Science Dept., Univ. of Tenn., Knoxville, USA
-* E. Quintana-Orti, Depto. de Informatica, Universidad Jaime I, Spain
-* G. Quintana-Orti, Depto. de Informatica, Universidad Jaime I, Spain
-*
-* =====================================================================
-*
-* .. Parameters ..
- INTEGER IMAX, IMIN
- PARAMETER ( IMAX = 1, IMIN = 2 )
- DOUBLE PRECISION ZERO, ONE
- PARAMETER ( ZERO = 0.0D+0, ONE = 1.0D+0 )
-* ..
-* .. Local Scalars ..
- LOGICAL LQUERY
- INTEGER I, IASCL, IBSCL, ISMAX, ISMIN, J, LWKMIN,
- $ LWKOPT, MN, NB, NB1, NB2, NB3, NB4
- DOUBLE PRECISION ANRM, BIGNUM, BNRM, C1, C2, S1, S2, SMAX,
- $ SMAXPR, SMIN, SMINPR, SMLNUM, WSIZE
-* ..
-* .. External Functions ..
- INTEGER ILAENV
- DOUBLE PRECISION DLAMCH, DLANGE
- EXTERNAL ILAENV, DLAMCH, DLANGE
-* ..
-* .. External Subroutines ..
- EXTERNAL DCOPY, DGEQP3, DLABAD, DLAIC1, DLASCL, DLASET,
- $ DORMQR, DORMRZ, DTRSM, DTZRZF, XERBLA
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC ABS, MAX, MIN
-* ..
-* .. Executable Statements ..
-*
- MN = MIN( M, N )
- ISMIN = MN + 1
- ISMAX = 2*MN + 1
-*
-* Test the input arguments.
-*
- INFO = 0
- LQUERY = ( LWORK.EQ.-1 )
- IF( M.LT.0 ) THEN
- INFO = -1
- ELSE IF( N.LT.0 ) THEN
- INFO = -2
- ELSE IF( NRHS.LT.0 ) THEN
- INFO = -3
- ELSE IF( LDA.LT.MAX( 1, M ) ) THEN
- INFO = -5
- ELSE IF( LDB.LT.MAX( 1, M, N ) ) THEN
- INFO = -7
- END IF
-*
-* Figure out optimal block size
-*
- IF( INFO.EQ.0 ) THEN
- IF( MN.EQ.0 .OR. NRHS.EQ.0 ) THEN
- LWKMIN = 1
- LWKOPT = 1
- ELSE
- NB1 = ILAENV( 1, 'DGEQRF', ' ', M, N, -1, -1 )
- NB2 = ILAENV( 1, 'DGERQF', ' ', M, N, -1, -1 )
- NB3 = ILAENV( 1, 'DORMQR', ' ', M, N, NRHS, -1 )
- NB4 = ILAENV( 1, 'DORMRQ', ' ', M, N, NRHS, -1 )
- NB = MAX( NB1, NB2, NB3, NB4 )
- LWKMIN = MN + MAX( 2*MN, N + 1, MN + NRHS )
- LWKOPT = MAX( LWKMIN,
- $ MN + 2*N + NB*( N + 1 ), 2*MN + NB*NRHS )
- END IF
- WORK( 1 ) = LWKOPT
-*
- IF( LWORK.LT.LWKMIN .AND. .NOT.LQUERY ) THEN
- INFO = -12
- END IF
- END IF
-*
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'DGELSY', -INFO )
- RETURN
- ELSE IF( LQUERY ) THEN
- RETURN
- END IF
-*
-* Quick return if possible
-*
- IF( MN.EQ.0 .OR. NRHS.EQ.0 ) THEN
- RANK = 0
- RETURN
- END IF
-*
-* Get machine parameters
-*
- SMLNUM = DLAMCH( 'S' ) / DLAMCH( 'P' )
- BIGNUM = ONE / SMLNUM
- CALL DLABAD( SMLNUM, BIGNUM )
-*
-* Scale A, B if max entries outside range [SMLNUM,BIGNUM]
-*
- ANRM = DLANGE( 'M', M, N, A, LDA, WORK )
- IASCL = 0
- IF( ANRM.GT.ZERO .AND. ANRM.LT.SMLNUM ) THEN
-*
-* Scale matrix norm up to SMLNUM
-*
- CALL DLASCL( 'G', 0, 0, ANRM, SMLNUM, M, N, A, LDA, INFO )
- IASCL = 1
- ELSE IF( ANRM.GT.BIGNUM ) THEN
-*
-* Scale matrix norm down to BIGNUM
-*
- CALL DLASCL( 'G', 0, 0, ANRM, BIGNUM, M, N, A, LDA, INFO )
- IASCL = 2
- ELSE IF( ANRM.EQ.ZERO ) THEN
-*
-* Matrix all zero. Return zero solution.
-*
- CALL DLASET( 'F', MAX( M, N ), NRHS, ZERO, ZERO, B, LDB )
- RANK = 0
- GO TO 70
- END IF
-*
- BNRM = DLANGE( 'M', M, NRHS, B, LDB, WORK )
- IBSCL = 0
- IF( BNRM.GT.ZERO .AND. BNRM.LT.SMLNUM ) THEN
-*
-* Scale matrix norm up to SMLNUM
-*
- CALL DLASCL( 'G', 0, 0, BNRM, SMLNUM, M, NRHS, B, LDB, INFO )
- IBSCL = 1
- ELSE IF( BNRM.GT.BIGNUM ) THEN
-*
-* Scale matrix norm down to BIGNUM
-*
- CALL DLASCL( 'G', 0, 0, BNRM, BIGNUM, M, NRHS, B, LDB, INFO )
- IBSCL = 2
- END IF
-*
-* Compute QR factorization with column pivoting of A:
-* A * P = Q * R
-*
- CALL DGEQP3( M, N, A, LDA, JPVT, WORK( 1 ), WORK( MN+1 ),
- $ LWORK-MN, INFO )
- WSIZE = MN + WORK( MN+1 )
-*
-* workspace: MN+2*N+NB*(N+1).
-* Details of Householder rotations stored in WORK(1:MN).
-*
-* Determine RANK using incremental condition estimation
-*
- WORK( ISMIN ) = ONE
- WORK( ISMAX ) = ONE
- SMAX = ABS( A( 1, 1 ) )
- SMIN = SMAX
- IF( ABS( A( 1, 1 ) ).EQ.ZERO ) THEN
- RANK = 0
- CALL DLASET( 'F', MAX( M, N ), NRHS, ZERO, ZERO, B, LDB )
- GO TO 70
- ELSE
- RANK = 1
- END IF
-*
- 10 CONTINUE
- IF( RANK.LT.MN ) THEN
- I = RANK + 1
- CALL DLAIC1( IMIN, RANK, WORK( ISMIN ), SMIN, A( 1, I ),
- $ A( I, I ), SMINPR, S1, C1 )
- CALL DLAIC1( IMAX, RANK, WORK( ISMAX ), SMAX, A( 1, I ),
- $ A( I, I ), SMAXPR, S2, C2 )
-*
- IF( SMAXPR*RCOND.LE.SMINPR ) THEN
- DO 20 I = 1, RANK
- WORK( ISMIN+I-1 ) = S1*WORK( ISMIN+I-1 )
- WORK( ISMAX+I-1 ) = S2*WORK( ISMAX+I-1 )
- 20 CONTINUE
- WORK( ISMIN+RANK ) = C1
- WORK( ISMAX+RANK ) = C2
- SMIN = SMINPR
- SMAX = SMAXPR
- RANK = RANK + 1
- GO TO 10
- END IF
- END IF
-*
-* workspace: 3*MN.
-*
-* Logically partition R = [ R11 R12 ]
-* [ 0 R22 ]
-* where R11 = R(1:RANK,1:RANK)
-*
-* [R11,R12] = [ T11, 0 ] * Y
-*
- IF( RANK.LT.N )
- $ CALL DTZRZF( RANK, N, A, LDA, WORK( MN+1 ), WORK( 2*MN+1 ),
- $ LWORK-2*MN, INFO )
-*
-* workspace: 2*MN.
-* Details of Householder rotations stored in WORK(MN+1:2*MN)
-*
-* B(1:M,1:NRHS) := Q' * B(1:M,1:NRHS)
-*
- CALL DORMQR( 'Left', 'Transpose', M, NRHS, MN, A, LDA, WORK( 1 ),
- $ B, LDB, WORK( 2*MN+1 ), LWORK-2*MN, INFO )
- WSIZE = MAX( WSIZE, 2*MN+WORK( 2*MN+1 ) )
-*
-* workspace: 2*MN+NB*NRHS.
-*
-* B(1:RANK,1:NRHS) := inv(T11) * B(1:RANK,1:NRHS)
-*
- CALL DTRSM( 'Left', 'Upper', 'No transpose', 'Non-unit', RANK,
- $ NRHS, ONE, A, LDA, B, LDB )
-*
- DO 40 J = 1, NRHS
- DO 30 I = RANK + 1, N
- B( I, J ) = ZERO
- 30 CONTINUE
- 40 CONTINUE
-*
-* B(1:N,1:NRHS) := Y' * B(1:N,1:NRHS)
-*
- IF( RANK.LT.N ) THEN
- CALL DORMRZ( 'Left', 'Transpose', N, NRHS, RANK, N-RANK, A,
- $ LDA, WORK( MN+1 ), B, LDB, WORK( 2*MN+1 ),
- $ LWORK-2*MN, INFO )
- END IF
-*
-* workspace: 2*MN+NRHS.
-*
-* B(1:N,1:NRHS) := P * B(1:N,1:NRHS)
-*
- DO 60 J = 1, NRHS
- DO 50 I = 1, N
- WORK( JPVT( I ) ) = B( I, J )
- 50 CONTINUE
- CALL DCOPY( N, WORK( 1 ), 1, B( 1, J ), 1 )
- 60 CONTINUE
-*
-* workspace: N.
-*
-* Undo scaling
-*
- IF( IASCL.EQ.1 ) THEN
- CALL DLASCL( 'G', 0, 0, ANRM, SMLNUM, N, NRHS, B, LDB, INFO )
- CALL DLASCL( 'U', 0, 0, SMLNUM, ANRM, RANK, RANK, A, LDA,
- $ INFO )
- ELSE IF( IASCL.EQ.2 ) THEN
- CALL DLASCL( 'G', 0, 0, ANRM, BIGNUM, N, NRHS, B, LDB, INFO )
- CALL DLASCL( 'U', 0, 0, BIGNUM, ANRM, RANK, RANK, A, LDA,
- $ INFO )
- END IF
- IF( IBSCL.EQ.1 ) THEN
- CALL DLASCL( 'G', 0, 0, SMLNUM, BNRM, N, NRHS, B, LDB, INFO )
- ELSE IF( IBSCL.EQ.2 ) THEN
- CALL DLASCL( 'G', 0, 0, BIGNUM, BNRM, N, NRHS, B, LDB, INFO )
- END IF
-*
- 70 CONTINUE
- WORK( 1 ) = LWKOPT
-*
- RETURN
-*
-* End of DGELSY
-*
- END
diff --git a/src/lib/lapack/dgeql2.f b/src/lib/lapack/dgeql2.f
deleted file mode 100644
index aa45113c..00000000
--- a/src/lib/lapack/dgeql2.f
+++ /dev/null
@@ -1,122 +0,0 @@
- SUBROUTINE DGEQL2( M, N, A, LDA, TAU, WORK, INFO )
-*
-* -- LAPACK routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- INTEGER INFO, LDA, M, N
-* ..
-* .. Array Arguments ..
- DOUBLE PRECISION A( LDA, * ), TAU( * ), WORK( * )
-* ..
-*
-* Purpose
-* =======
-*
-* DGEQL2 computes a QL factorization of a real m by n matrix A:
-* A = Q * L.
-*
-* Arguments
-* =========
-*
-* M (input) INTEGER
-* The number of rows of the matrix A. M >= 0.
-*
-* N (input) INTEGER
-* The number of columns of the matrix A. N >= 0.
-*
-* A (input/output) DOUBLE PRECISION array, dimension (LDA,N)
-* On entry, the m by n matrix A.
-* On exit, if m >= n, the lower triangle of the subarray
-* A(m-n+1:m,1:n) contains the n by n lower triangular matrix L;
-* if m <= n, the elements on and below the (n-m)-th
-* superdiagonal contain the m by n lower trapezoidal matrix L;
-* the remaining elements, with the array TAU, represent the
-* orthogonal matrix Q as a product of elementary reflectors
-* (see Further Details).
-*
-* LDA (input) INTEGER
-* The leading dimension of the array A. LDA >= max(1,M).
-*
-* TAU (output) DOUBLE PRECISION array, dimension (min(M,N))
-* The scalar factors of the elementary reflectors (see Further
-* Details).
-*
-* WORK (workspace) DOUBLE PRECISION array, dimension (N)
-*
-* INFO (output) INTEGER
-* = 0: successful exit
-* < 0: if INFO = -i, the i-th argument had an illegal value
-*
-* Further Details
-* ===============
-*
-* The matrix Q is represented as a product of elementary reflectors
-*
-* Q = H(k) . . . H(2) H(1), where k = min(m,n).
-*
-* Each H(i) has the form
-*
-* H(i) = I - tau * v * v'
-*
-* where tau is a real scalar, and v is a real vector with
-* v(m-k+i+1:m) = 0 and v(m-k+i) = 1; v(1:m-k+i-1) is stored on exit in
-* A(1:m-k+i-1,n-k+i), and tau in TAU(i).
-*
-* =====================================================================
-*
-* .. Parameters ..
- DOUBLE PRECISION ONE
- PARAMETER ( ONE = 1.0D+0 )
-* ..
-* .. Local Scalars ..
- INTEGER I, K
- DOUBLE PRECISION AII
-* ..
-* .. External Subroutines ..
- EXTERNAL DLARF, DLARFG, XERBLA
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC MAX, MIN
-* ..
-* .. Executable Statements ..
-*
-* Test the input arguments
-*
- INFO = 0
- IF( M.LT.0 ) THEN
- INFO = -1
- ELSE IF( N.LT.0 ) THEN
- INFO = -2
- ELSE IF( LDA.LT.MAX( 1, M ) ) THEN
- INFO = -4
- END IF
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'DGEQL2', -INFO )
- RETURN
- END IF
-*
- K = MIN( M, N )
-*
- DO 10 I = K, 1, -1
-*
-* Generate elementary reflector H(i) to annihilate
-* A(1:m-k+i-1,n-k+i)
-*
- CALL DLARFG( M-K+I, A( M-K+I, N-K+I ), A( 1, N-K+I ), 1,
- $ TAU( I ) )
-*
-* Apply H(i) to A(1:m-k+i,1:n-k+i-1) from the left
-*
- AII = A( M-K+I, N-K+I )
- A( M-K+I, N-K+I ) = ONE
- CALL DLARF( 'Left', M-K+I, N-K+I-1, A( 1, N-K+I ), 1, TAU( I ),
- $ A, LDA, WORK )
- A( M-K+I, N-K+I ) = AII
- 10 CONTINUE
- RETURN
-*
-* End of DGEQL2
-*
- END
diff --git a/src/lib/lapack/dgeqlf.f b/src/lib/lapack/dgeqlf.f
deleted file mode 100644
index ec293574..00000000
--- a/src/lib/lapack/dgeqlf.f
+++ /dev/null
@@ -1,213 +0,0 @@
- SUBROUTINE DGEQLF( M, N, A, LDA, TAU, WORK, LWORK, INFO )
-*
-* -- LAPACK routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- INTEGER INFO, LDA, LWORK, M, N
-* ..
-* .. Array Arguments ..
- DOUBLE PRECISION A( LDA, * ), TAU( * ), WORK( * )
-* ..
-*
-* Purpose
-* =======
-*
-* DGEQLF computes a QL factorization of a real M-by-N matrix A:
-* A = Q * L.
-*
-* Arguments
-* =========
-*
-* M (input) INTEGER
-* The number of rows of the matrix A. M >= 0.
-*
-* N (input) INTEGER
-* The number of columns of the matrix A. N >= 0.
-*
-* A (input/output) DOUBLE PRECISION array, dimension (LDA,N)
-* On entry, the M-by-N matrix A.
-* On exit,
-* if m >= n, the lower triangle of the subarray
-* A(m-n+1:m,1:n) contains the N-by-N lower triangular matrix L;
-* if m <= n, the elements on and below the (n-m)-th
-* superdiagonal contain the M-by-N lower trapezoidal matrix L;
-* the remaining elements, with the array TAU, represent the
-* orthogonal matrix Q as a product of elementary reflectors
-* (see Further Details).
-*
-* LDA (input) INTEGER
-* The leading dimension of the array A. LDA >= max(1,M).
-*
-* TAU (output) DOUBLE PRECISION array, dimension (min(M,N))
-* The scalar factors of the elementary reflectors (see Further
-* Details).
-*
-* WORK (workspace/output) DOUBLE PRECISION array, dimension (MAX(1,LWORK))
-* On exit, if INFO = 0, WORK(1) returns the optimal LWORK.
-*
-* LWORK (input) INTEGER
-* The dimension of the array WORK. LWORK >= max(1,N).
-* For optimum performance LWORK >= N*NB, where NB is the
-* optimal blocksize.
-*
-* If LWORK = -1, then a workspace query is assumed; the routine
-* only calculates the optimal size of the WORK array, returns
-* this value as the first entry of the WORK array, and no error
-* message related to LWORK is issued by XERBLA.
-*
-* INFO (output) INTEGER
-* = 0: successful exit
-* < 0: if INFO = -i, the i-th argument had an illegal value
-*
-* Further Details
-* ===============
-*
-* The matrix Q is represented as a product of elementary reflectors
-*
-* Q = H(k) . . . H(2) H(1), where k = min(m,n).
-*
-* Each H(i) has the form
-*
-* H(i) = I - tau * v * v'
-*
-* where tau is a real scalar, and v is a real vector with
-* v(m-k+i+1:m) = 0 and v(m-k+i) = 1; v(1:m-k+i-1) is stored on exit in
-* A(1:m-k+i-1,n-k+i), and tau in TAU(i).
-*
-* =====================================================================
-*
-* .. Local Scalars ..
- LOGICAL LQUERY
- INTEGER I, IB, IINFO, IWS, K, KI, KK, LDWORK, LWKOPT,
- $ MU, NB, NBMIN, NU, NX
-* ..
-* .. External Subroutines ..
- EXTERNAL DGEQL2, DLARFB, DLARFT, XERBLA
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC MAX, MIN
-* ..
-* .. External Functions ..
- INTEGER ILAENV
- EXTERNAL ILAENV
-* ..
-* .. Executable Statements ..
-*
-* Test the input arguments
-*
- INFO = 0
- LQUERY = ( LWORK.EQ.-1 )
- IF( M.LT.0 ) THEN
- INFO = -1
- ELSE IF( N.LT.0 ) THEN
- INFO = -2
- ELSE IF( LDA.LT.MAX( 1, M ) ) THEN
- INFO = -4
- END IF
-*
- IF( INFO.EQ.0 ) THEN
- K = MIN( M, N )
- IF( K.EQ.0 ) THEN
- LWKOPT = 1
- ELSE
- NB = ILAENV( 1, 'DGEQLF', ' ', M, N, -1, -1 )
- LWKOPT = N*NB
- END IF
- WORK( 1 ) = LWKOPT
-*
- IF( LWORK.LT.MAX( 1, N ) .AND. .NOT.LQUERY ) THEN
- INFO = -7
- END IF
- END IF
-*
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'DGEQLF', -INFO )
- RETURN
- ELSE IF( LQUERY ) THEN
- RETURN
- END IF
-*
-* Quick return if possible
-*
- IF( K.EQ.0 ) THEN
- RETURN
- END IF
-*
- NBMIN = 2
- NX = 1
- IWS = N
- IF( NB.GT.1 .AND. NB.LT.K ) THEN
-*
-* Determine when to cross over from blocked to unblocked code.
-*
- NX = MAX( 0, ILAENV( 3, 'DGEQLF', ' ', M, N, -1, -1 ) )
- IF( NX.LT.K ) THEN
-*
-* Determine if workspace is large enough for blocked code.
-*
- LDWORK = N
- IWS = LDWORK*NB
- IF( LWORK.LT.IWS ) THEN
-*
-* Not enough workspace to use optimal NB: reduce NB and
-* determine the minimum value of NB.
-*
- NB = LWORK / LDWORK
- NBMIN = MAX( 2, ILAENV( 2, 'DGEQLF', ' ', M, N, -1,
- $ -1 ) )
- END IF
- END IF
- END IF
-*
- IF( NB.GE.NBMIN .AND. NB.LT.K .AND. NX.LT.K ) THEN
-*
-* Use blocked code initially.
-* The last kk columns are handled by the block method.
-*
- KI = ( ( K-NX-1 ) / NB )*NB
- KK = MIN( K, KI+NB )
-*
- DO 10 I = K - KK + KI + 1, K - KK + 1, -NB
- IB = MIN( K-I+1, NB )
-*
-* Compute the QL factorization of the current block
-* A(1:m-k+i+ib-1,n-k+i:n-k+i+ib-1)
-*
- CALL DGEQL2( M-K+I+IB-1, IB, A( 1, N-K+I ), LDA, TAU( I ),
- $ WORK, IINFO )
- IF( N-K+I.GT.1 ) THEN
-*
-* Form the triangular factor of the block reflector
-* H = H(i+ib-1) . . . H(i+1) H(i)
-*
- CALL DLARFT( 'Backward', 'Columnwise', M-K+I+IB-1, IB,
- $ A( 1, N-K+I ), LDA, TAU( I ), WORK, LDWORK )
-*
-* Apply H' to A(1:m-k+i+ib-1,1:n-k+i-1) from the left
-*
- CALL DLARFB( 'Left', 'Transpose', 'Backward',
- $ 'Columnwise', M-K+I+IB-1, N-K+I-1, IB,
- $ A( 1, N-K+I ), LDA, WORK, LDWORK, A, LDA,
- $ WORK( IB+1 ), LDWORK )
- END IF
- 10 CONTINUE
- MU = M - K + I + NB - 1
- NU = N - K + I + NB - 1
- ELSE
- MU = M
- NU = N
- END IF
-*
-* Use unblocked code to factor the last or only block
-*
- IF( MU.GT.0 .AND. NU.GT.0 )
- $ CALL DGEQL2( MU, NU, A, LDA, TAU, WORK, IINFO )
-*
- WORK( 1 ) = IWS
- RETURN
-*
-* End of DGEQLF
-*
- END
diff --git a/src/lib/lapack/dgeqp3.f b/src/lib/lapack/dgeqp3.f
deleted file mode 100644
index d6bc537d..00000000
--- a/src/lib/lapack/dgeqp3.f
+++ /dev/null
@@ -1,287 +0,0 @@
- SUBROUTINE DGEQP3( M, N, A, LDA, JPVT, TAU, WORK, LWORK, INFO )
-*
-* -- LAPACK routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- INTEGER INFO, LDA, LWORK, M, N
-* ..
-* .. Array Arguments ..
- INTEGER JPVT( * )
- DOUBLE PRECISION A( LDA, * ), TAU( * ), WORK( * )
-* ..
-*
-* Purpose
-* =======
-*
-* DGEQP3 computes a QR factorization with column pivoting of a
-* matrix A: A*P = Q*R using Level 3 BLAS.
-*
-* Arguments
-* =========
-*
-* M (input) INTEGER
-* The number of rows of the matrix A. M >= 0.
-*
-* N (input) INTEGER
-* The number of columns of the matrix A. N >= 0.
-*
-* A (input/output) DOUBLE PRECISION array, dimension (LDA,N)
-* On entry, the M-by-N matrix A.
-* On exit, the upper triangle of the array contains the
-* min(M,N)-by-N upper trapezoidal matrix R; the elements below
-* the diagonal, together with the array TAU, represent the
-* orthogonal matrix Q as a product of min(M,N) elementary
-* reflectors.
-*
-* LDA (input) INTEGER
-* The leading dimension of the array A. LDA >= max(1,M).
-*
-* JPVT (input/output) INTEGER array, dimension (N)
-* On entry, if JPVT(J).ne.0, the J-th column of A is permuted
-* to the front of A*P (a leading column); if JPVT(J)=0,
-* the J-th column of A is a free column.
-* On exit, if JPVT(J)=K, then the J-th column of A*P was the
-* the K-th column of A.
-*
-* TAU (output) DOUBLE PRECISION array, dimension (min(M,N))
-* The scalar factors of the elementary reflectors.
-*
-* WORK (workspace/output) DOUBLE PRECISION array, dimension (MAX(1,LWORK))
-* On exit, if INFO=0, WORK(1) returns the optimal LWORK.
-*
-* LWORK (input) INTEGER
-* The dimension of the array WORK. LWORK >= 3*N+1.
-* For optimal performance LWORK >= 2*N+( N+1 )*NB, where NB
-* is the optimal blocksize.
-*
-* If LWORK = -1, then a workspace query is assumed; the routine
-* only calculates the optimal size of the WORK array, returns
-* this value as the first entry of the WORK array, and no error
-* message related to LWORK is issued by XERBLA.
-*
-* INFO (output) INTEGER
-* = 0: successful exit.
-* < 0: if INFO = -i, the i-th argument had an illegal value.
-*
-* Further Details
-* ===============
-*
-* The matrix Q is represented as a product of elementary reflectors
-*
-* Q = H(1) H(2) . . . H(k), where k = min(m,n).
-*
-* Each H(i) has the form
-*
-* H(i) = I - tau * v * v'
-*
-* where tau is a real/complex scalar, and v is a real/complex vector
-* with v(1:i-1) = 0 and v(i) = 1; v(i+1:m) is stored on exit in
-* A(i+1:m,i), and tau in TAU(i).
-*
-* Based on contributions by
-* G. Quintana-Orti, Depto. de Informatica, Universidad Jaime I, Spain
-* X. Sun, Computer Science Dept., Duke University, USA
-*
-* =====================================================================
-*
-* .. Parameters ..
- INTEGER INB, INBMIN, IXOVER
- PARAMETER ( INB = 1, INBMIN = 2, IXOVER = 3 )
-* ..
-* .. Local Scalars ..
- LOGICAL LQUERY
- INTEGER FJB, IWS, J, JB, LWKOPT, MINMN, MINWS, NA, NB,
- $ NBMIN, NFXD, NX, SM, SMINMN, SN, TOPBMN
-* ..
-* .. External Subroutines ..
- EXTERNAL DGEQRF, DLAQP2, DLAQPS, DORMQR, DSWAP, XERBLA
-* ..
-* .. External Functions ..
- INTEGER ILAENV
- DOUBLE PRECISION DNRM2
- EXTERNAL ILAENV, DNRM2
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC INT, MAX, MIN
-* ..
-* .. Executable Statements ..
-*
-* Test input arguments
-* ====================
-*
- INFO = 0
- LQUERY = ( LWORK.EQ.-1 )
- IF( M.LT.0 ) THEN
- INFO = -1
- ELSE IF( N.LT.0 ) THEN
- INFO = -2
- ELSE IF( LDA.LT.MAX( 1, M ) ) THEN
- INFO = -4
- END IF
-*
- IF( INFO.EQ.0 ) THEN
- MINMN = MIN( M, N )
- IF( MINMN.EQ.0 ) THEN
- IWS = 1
- LWKOPT = 1
- ELSE
- IWS = 3*N + 1
- NB = ILAENV( INB, 'DGEQRF', ' ', M, N, -1, -1 )
- LWKOPT = 2*N + ( N + 1 )*NB
- END IF
- WORK( 1 ) = LWKOPT
-*
- IF( ( LWORK.LT.IWS ) .AND. .NOT.LQUERY ) THEN
- INFO = -8
- END IF
- END IF
-*
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'DGEQP3', -INFO )
- RETURN
- ELSE IF( LQUERY ) THEN
- RETURN
- END IF
-*
-* Quick return if possible.
-*
- IF( MINMN.EQ.0 ) THEN
- RETURN
- END IF
-*
-* Move initial columns up front.
-*
- NFXD = 1
- DO 10 J = 1, N
- IF( JPVT( J ).NE.0 ) THEN
- IF( J.NE.NFXD ) THEN
- CALL DSWAP( M, A( 1, J ), 1, A( 1, NFXD ), 1 )
- JPVT( J ) = JPVT( NFXD )
- JPVT( NFXD ) = J
- ELSE
- JPVT( J ) = J
- END IF
- NFXD = NFXD + 1
- ELSE
- JPVT( J ) = J
- END IF
- 10 CONTINUE
- NFXD = NFXD - 1
-*
-* Factorize fixed columns
-* =======================
-*
-* Compute the QR factorization of fixed columns and update
-* remaining columns.
-*
- IF( NFXD.GT.0 ) THEN
- NA = MIN( M, NFXD )
-*CC CALL DGEQR2( M, NA, A, LDA, TAU, WORK, INFO )
- CALL DGEQRF( M, NA, A, LDA, TAU, WORK, LWORK, INFO )
- IWS = MAX( IWS, INT( WORK( 1 ) ) )
- IF( NA.LT.N ) THEN
-*CC CALL DORM2R( 'Left', 'Transpose', M, N-NA, NA, A, LDA,
-*CC $ TAU, A( 1, NA+1 ), LDA, WORK, INFO )
- CALL DORMQR( 'Left', 'Transpose', M, N-NA, NA, A, LDA, TAU,
- $ A( 1, NA+1 ), LDA, WORK, LWORK, INFO )
- IWS = MAX( IWS, INT( WORK( 1 ) ) )
- END IF
- END IF
-*
-* Factorize free columns
-* ======================
-*
- IF( NFXD.LT.MINMN ) THEN
-*
- SM = M - NFXD
- SN = N - NFXD
- SMINMN = MINMN - NFXD
-*
-* Determine the block size.
-*
- NB = ILAENV( INB, 'DGEQRF', ' ', SM, SN, -1, -1 )
- NBMIN = 2
- NX = 0
-*
- IF( ( NB.GT.1 ) .AND. ( NB.LT.SMINMN ) ) THEN
-*
-* Determine when to cross over from blocked to unblocked code.
-*
- NX = MAX( 0, ILAENV( IXOVER, 'DGEQRF', ' ', SM, SN, -1,
- $ -1 ) )
-*
-*
- IF( NX.LT.SMINMN ) THEN
-*
-* Determine if workspace is large enough for blocked code.
-*
- MINWS = 2*SN + ( SN+1 )*NB
- IWS = MAX( IWS, MINWS )
- IF( LWORK.LT.MINWS ) THEN
-*
-* Not enough workspace to use optimal NB: Reduce NB and
-* determine the minimum value of NB.
-*
- NB = ( LWORK-2*SN ) / ( SN+1 )
- NBMIN = MAX( 2, ILAENV( INBMIN, 'DGEQRF', ' ', SM, SN,
- $ -1, -1 ) )
-*
-*
- END IF
- END IF
- END IF
-*
-* Initialize partial column norms. The first N elements of work
-* store the exact column norms.
-*
- DO 20 J = NFXD + 1, N
- WORK( J ) = DNRM2( SM, A( NFXD+1, J ), 1 )
- WORK( N+J ) = WORK( J )
- 20 CONTINUE
-*
- IF( ( NB.GE.NBMIN ) .AND. ( NB.LT.SMINMN ) .AND.
- $ ( NX.LT.SMINMN ) ) THEN
-*
-* Use blocked code initially.
-*
- J = NFXD + 1
-*
-* Compute factorization: while loop.
-*
-*
- TOPBMN = MINMN - NX
- 30 CONTINUE
- IF( J.LE.TOPBMN ) THEN
- JB = MIN( NB, TOPBMN-J+1 )
-*
-* Factorize JB columns among columns J:N.
-*
- CALL DLAQPS( M, N-J+1, J-1, JB, FJB, A( 1, J ), LDA,
- $ JPVT( J ), TAU( J ), WORK( J ), WORK( N+J ),
- $ WORK( 2*N+1 ), WORK( 2*N+JB+1 ), N-J+1 )
-*
- J = J + FJB
- GO TO 30
- END IF
- ELSE
- J = NFXD + 1
- END IF
-*
-* Use unblocked code to factor the last or only block.
-*
-*
- IF( J.LE.MINMN )
- $ CALL DLAQP2( M, N-J+1, J-1, A( 1, J ), LDA, JPVT( J ),
- $ TAU( J ), WORK( J ), WORK( N+J ),
- $ WORK( 2*N+1 ) )
-*
- END IF
-*
- WORK( 1 ) = IWS
- RETURN
-*
-* End of DGEQP3
-*
- END
diff --git a/src/lib/lapack/dgeqpf.f b/src/lib/lapack/dgeqpf.f
deleted file mode 100644
index 1b7acd6d..00000000
--- a/src/lib/lapack/dgeqpf.f
+++ /dev/null
@@ -1,231 +0,0 @@
- SUBROUTINE DGEQPF( M, N, A, LDA, JPVT, TAU, WORK, INFO )
-*
-* -- LAPACK deprecated driver routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- INTEGER INFO, LDA, M, N
-* ..
-* .. Array Arguments ..
- INTEGER JPVT( * )
- DOUBLE PRECISION A( LDA, * ), TAU( * ), WORK( * )
-* ..
-*
-* Purpose
-* =======
-*
-* This routine is deprecated and has been replaced by routine DGEQP3.
-*
-* DGEQPF computes a QR factorization with column pivoting of a
-* real M-by-N matrix A: A*P = Q*R.
-*
-* Arguments
-* =========
-*
-* M (input) INTEGER
-* The number of rows of the matrix A. M >= 0.
-*
-* N (input) INTEGER
-* The number of columns of the matrix A. N >= 0
-*
-* A (input/output) DOUBLE PRECISION array, dimension (LDA,N)
-* On entry, the M-by-N matrix A.
-* On exit, the upper triangle of the array contains the
-* min(M,N)-by-N upper triangular matrix R; the elements
-* below the diagonal, together with the array TAU,
-* represent the orthogonal matrix Q as a product of
-* min(m,n) elementary reflectors.
-*
-* LDA (input) INTEGER
-* The leading dimension of the array A. LDA >= max(1,M).
-*
-* JPVT (input/output) INTEGER array, dimension (N)
-* On entry, if JPVT(i) .ne. 0, the i-th column of A is permuted
-* to the front of A*P (a leading column); if JPVT(i) = 0,
-* the i-th column of A is a free column.
-* On exit, if JPVT(i) = k, then the i-th column of A*P
-* was the k-th column of A.
-*
-* TAU (output) DOUBLE PRECISION array, dimension (min(M,N))
-* The scalar factors of the elementary reflectors.
-*
-* WORK (workspace) DOUBLE PRECISION array, dimension (3*N)
-*
-* INFO (output) INTEGER
-* = 0: successful exit
-* < 0: if INFO = -i, the i-th argument had an illegal value
-*
-* Further Details
-* ===============
-*
-* The matrix Q is represented as a product of elementary reflectors
-*
-* Q = H(1) H(2) . . . H(n)
-*
-* Each H(i) has the form
-*
-* H = I - tau * v * v'
-*
-* where tau is a real scalar, and v is a real vector with
-* v(1:i-1) = 0 and v(i) = 1; v(i+1:m) is stored on exit in A(i+1:m,i).
-*
-* The matrix P is represented in jpvt as follows: If
-* jpvt(j) = i
-* then the jth column of P is the ith canonical unit vector.
-*
-* Partial column norm updating strategy modified by
-* Z. Drmac and Z. Bujanovic, Dept. of Mathematics,
-* University of Zagreb, Croatia.
-* June 2006.
-* For more details see LAPACK Working Note 176.
-*
-* =====================================================================
-*
-* .. Parameters ..
- DOUBLE PRECISION ZERO, ONE
- PARAMETER ( ZERO = 0.0D+0, ONE = 1.0D+0 )
-* ..
-* .. Local Scalars ..
- INTEGER I, ITEMP, J, MA, MN, PVT
- DOUBLE PRECISION AII, TEMP, TEMP2, TOL3Z
-* ..
-* .. External Subroutines ..
- EXTERNAL DGEQR2, DLARF, DLARFG, DORM2R, DSWAP, XERBLA
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC ABS, MAX, MIN, SQRT
-* ..
-* .. External Functions ..
- INTEGER IDAMAX
- DOUBLE PRECISION DLAMCH, DNRM2
- EXTERNAL IDAMAX, DLAMCH, DNRM2
-* ..
-* .. Executable Statements ..
-*
-* Test the input arguments
-*
- INFO = 0
- IF( M.LT.0 ) THEN
- INFO = -1
- ELSE IF( N.LT.0 ) THEN
- INFO = -2
- ELSE IF( LDA.LT.MAX( 1, M ) ) THEN
- INFO = -4
- END IF
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'DGEQPF', -INFO )
- RETURN
- END IF
-*
- MN = MIN( M, N )
- TOL3Z = SQRT(DLAMCH('Epsilon'))
-*
-* Move initial columns up front
-*
- ITEMP = 1
- DO 10 I = 1, N
- IF( JPVT( I ).NE.0 ) THEN
- IF( I.NE.ITEMP ) THEN
- CALL DSWAP( M, A( 1, I ), 1, A( 1, ITEMP ), 1 )
- JPVT( I ) = JPVT( ITEMP )
- JPVT( ITEMP ) = I
- ELSE
- JPVT( I ) = I
- END IF
- ITEMP = ITEMP + 1
- ELSE
- JPVT( I ) = I
- END IF
- 10 CONTINUE
- ITEMP = ITEMP - 1
-*
-* Compute the QR factorization and update remaining columns
-*
- IF( ITEMP.GT.0 ) THEN
- MA = MIN( ITEMP, M )
- CALL DGEQR2( M, MA, A, LDA, TAU, WORK, INFO )
- IF( MA.LT.N ) THEN
- CALL DORM2R( 'Left', 'Transpose', M, N-MA, MA, A, LDA, TAU,
- $ A( 1, MA+1 ), LDA, WORK, INFO )
- END IF
- END IF
-*
- IF( ITEMP.LT.MN ) THEN
-*
-* Initialize partial column norms. The first n elements of
-* work store the exact column norms.
-*
- DO 20 I = ITEMP + 1, N
- WORK( I ) = DNRM2( M-ITEMP, A( ITEMP+1, I ), 1 )
- WORK( N+I ) = WORK( I )
- 20 CONTINUE
-*
-* Compute factorization
-*
- DO 40 I = ITEMP + 1, MN
-*
-* Determine ith pivot column and swap if necessary
-*
- PVT = ( I-1 ) + IDAMAX( N-I+1, WORK( I ), 1 )
-*
- IF( PVT.NE.I ) THEN
- CALL DSWAP( M, A( 1, PVT ), 1, A( 1, I ), 1 )
- ITEMP = JPVT( PVT )
- JPVT( PVT ) = JPVT( I )
- JPVT( I ) = ITEMP
- WORK( PVT ) = WORK( I )
- WORK( N+PVT ) = WORK( N+I )
- END IF
-*
-* Generate elementary reflector H(i)
-*
- IF( I.LT.M ) THEN
- CALL DLARFG( M-I+1, A( I, I ), A( I+1, I ), 1, TAU( I ) )
- ELSE
- CALL DLARFG( 1, A( M, M ), A( M, M ), 1, TAU( M ) )
- END IF
-*
- IF( I.LT.N ) THEN
-*
-* Apply H(i) to A(i:m,i+1:n) from the left
-*
- AII = A( I, I )
- A( I, I ) = ONE
- CALL DLARF( 'LEFT', M-I+1, N-I, A( I, I ), 1, TAU( I ),
- $ A( I, I+1 ), LDA, WORK( 2*N+1 ) )
- A( I, I ) = AII
- END IF
-*
-* Update partial column norms
-*
- DO 30 J = I + 1, N
- IF( WORK( J ).NE.ZERO ) THEN
-*
-* NOTE: The following 4 lines follow from the analysis in
-* Lapack Working Note 176.
-*
- TEMP = ABS( A( I, J ) ) / WORK( J )
- TEMP = MAX( ZERO, ( ONE+TEMP )*( ONE-TEMP ) )
- TEMP2 = TEMP*( WORK( J ) / WORK( N+J ) )**2
- IF( TEMP2 .LE. TOL3Z ) THEN
- IF( M-I.GT.0 ) THEN
- WORK( J ) = DNRM2( M-I, A( I+1, J ), 1 )
- WORK( N+J ) = WORK( J )
- ELSE
- WORK( J ) = ZERO
- WORK( N+J ) = ZERO
- END IF
- ELSE
- WORK( J ) = WORK( J )*SQRT( TEMP )
- END IF
- END IF
- 30 CONTINUE
-*
- 40 CONTINUE
- END IF
- RETURN
-*
-* End of DGEQPF
-*
- END
diff --git a/src/lib/lapack/dgeqr2.f b/src/lib/lapack/dgeqr2.f
deleted file mode 100644
index 9872a162..00000000
--- a/src/lib/lapack/dgeqr2.f
+++ /dev/null
@@ -1,121 +0,0 @@
- SUBROUTINE DGEQR2( M, N, A, LDA, TAU, WORK, INFO )
-*
-* -- LAPACK routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- INTEGER INFO, LDA, M, N
-* ..
-* .. Array Arguments ..
- DOUBLE PRECISION A( LDA, * ), TAU( * ), WORK( * )
-* ..
-*
-* Purpose
-* =======
-*
-* DGEQR2 computes a QR factorization of a real m by n matrix A:
-* A = Q * R.
-*
-* Arguments
-* =========
-*
-* M (input) INTEGER
-* The number of rows of the matrix A. M >= 0.
-*
-* N (input) INTEGER
-* The number of columns of the matrix A. N >= 0.
-*
-* A (input/output) DOUBLE PRECISION array, dimension (LDA,N)
-* On entry, the m by n matrix A.
-* On exit, the elements on and above the diagonal of the array
-* contain the min(m,n) by n upper trapezoidal matrix R (R is
-* upper triangular if m >= n); the elements below the diagonal,
-* with the array TAU, represent the orthogonal matrix Q as a
-* product of elementary reflectors (see Further Details).
-*
-* LDA (input) INTEGER
-* The leading dimension of the array A. LDA >= max(1,M).
-*
-* TAU (output) DOUBLE PRECISION array, dimension (min(M,N))
-* The scalar factors of the elementary reflectors (see Further
-* Details).
-*
-* WORK (workspace) DOUBLE PRECISION array, dimension (N)
-*
-* INFO (output) INTEGER
-* = 0: successful exit
-* < 0: if INFO = -i, the i-th argument had an illegal value
-*
-* Further Details
-* ===============
-*
-* The matrix Q is represented as a product of elementary reflectors
-*
-* Q = H(1) H(2) . . . H(k), where k = min(m,n).
-*
-* Each H(i) has the form
-*
-* H(i) = I - tau * v * v'
-*
-* where tau is a real scalar, and v is a real vector with
-* v(1:i-1) = 0 and v(i) = 1; v(i+1:m) is stored on exit in A(i+1:m,i),
-* and tau in TAU(i).
-*
-* =====================================================================
-*
-* .. Parameters ..
- DOUBLE PRECISION ONE
- PARAMETER ( ONE = 1.0D+0 )
-* ..
-* .. Local Scalars ..
- INTEGER I, K
- DOUBLE PRECISION AII
-* ..
-* .. External Subroutines ..
- EXTERNAL DLARF, DLARFG, XERBLA
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC MAX, MIN
-* ..
-* .. Executable Statements ..
-*
-* Test the input arguments
-*
- INFO = 0
- IF( M.LT.0 ) THEN
- INFO = -1
- ELSE IF( N.LT.0 ) THEN
- INFO = -2
- ELSE IF( LDA.LT.MAX( 1, M ) ) THEN
- INFO = -4
- END IF
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'DGEQR2', -INFO )
- RETURN
- END IF
-*
- K = MIN( M, N )
-*
- DO 10 I = 1, K
-*
-* Generate elementary reflector H(i) to annihilate A(i+1:m,i)
-*
- CALL DLARFG( M-I+1, A( I, I ), A( MIN( I+1, M ), I ), 1,
- $ TAU( I ) )
- IF( I.LT.N ) THEN
-*
-* Apply H(i) to A(i:m,i+1:n) from the left
-*
- AII = A( I, I )
- A( I, I ) = ONE
- CALL DLARF( 'Left', M-I+1, N-I, A( I, I ), 1, TAU( I ),
- $ A( I, I+1 ), LDA, WORK )
- A( I, I ) = AII
- END IF
- 10 CONTINUE
- RETURN
-*
-* End of DGEQR2
-*
- END
diff --git a/src/lib/lapack/dgeqrf.f b/src/lib/lapack/dgeqrf.f
deleted file mode 100644
index 1e940597..00000000
--- a/src/lib/lapack/dgeqrf.f
+++ /dev/null
@@ -1,196 +0,0 @@
- SUBROUTINE DGEQRF( M, N, A, LDA, TAU, WORK, LWORK, INFO )
-*
-* -- LAPACK routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- INTEGER INFO, LDA, LWORK, M, N
-* ..
-* .. Array Arguments ..
- DOUBLE PRECISION A( LDA, * ), TAU( * ), WORK( * )
-* ..
-*
-* Purpose
-* =======
-*
-* DGEQRF computes a QR factorization of a real M-by-N matrix A:
-* A = Q * R.
-*
-* Arguments
-* =========
-*
-* M (input) INTEGER
-* The number of rows of the matrix A. M >= 0.
-*
-* N (input) INTEGER
-* The number of columns of the matrix A. N >= 0.
-*
-* A (input/output) DOUBLE PRECISION array, dimension (LDA,N)
-* On entry, the M-by-N matrix A.
-* On exit, the elements on and above the diagonal of the array
-* contain the min(M,N)-by-N upper trapezoidal matrix R (R is
-* upper triangular if m >= n); the elements below the diagonal,
-* with the array TAU, represent the orthogonal matrix Q as a
-* product of min(m,n) elementary reflectors (see Further
-* Details).
-*
-* LDA (input) INTEGER
-* The leading dimension of the array A. LDA >= max(1,M).
-*
-* TAU (output) DOUBLE PRECISION array, dimension (min(M,N))
-* The scalar factors of the elementary reflectors (see Further
-* Details).
-*
-* WORK (workspace/output) DOUBLE PRECISION array, dimension (MAX(1,LWORK))
-* On exit, if INFO = 0, WORK(1) returns the optimal LWORK.
-*
-* LWORK (input) INTEGER
-* The dimension of the array WORK. LWORK >= max(1,N).
-* For optimum performance LWORK >= N*NB, where NB is
-* the optimal blocksize.
-*
-* If LWORK = -1, then a workspace query is assumed; the routine
-* only calculates the optimal size of the WORK array, returns
-* this value as the first entry of the WORK array, and no error
-* message related to LWORK is issued by XERBLA.
-*
-* INFO (output) INTEGER
-* = 0: successful exit
-* < 0: if INFO = -i, the i-th argument had an illegal value
-*
-* Further Details
-* ===============
-*
-* The matrix Q is represented as a product of elementary reflectors
-*
-* Q = H(1) H(2) . . . H(k), where k = min(m,n).
-*
-* Each H(i) has the form
-*
-* H(i) = I - tau * v * v'
-*
-* where tau is a real scalar, and v is a real vector with
-* v(1:i-1) = 0 and v(i) = 1; v(i+1:m) is stored on exit in A(i+1:m,i),
-* and tau in TAU(i).
-*
-* =====================================================================
-*
-* .. Local Scalars ..
- LOGICAL LQUERY
- INTEGER I, IB, IINFO, IWS, K, LDWORK, LWKOPT, NB,
- $ NBMIN, NX
-* ..
-* .. External Subroutines ..
- EXTERNAL DGEQR2, DLARFB, DLARFT, XERBLA
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC MAX, MIN
-* ..
-* .. External Functions ..
- INTEGER ILAENV
- EXTERNAL ILAENV
-* ..
-* .. Executable Statements ..
-*
-* Test the input arguments
-*
- INFO = 0
- NB = ILAENV( 1, 'DGEQRF', ' ', M, N, -1, -1 )
- LWKOPT = N*NB
- WORK( 1 ) = LWKOPT
- LQUERY = ( LWORK.EQ.-1 )
- IF( M.LT.0 ) THEN
- INFO = -1
- ELSE IF( N.LT.0 ) THEN
- INFO = -2
- ELSE IF( LDA.LT.MAX( 1, M ) ) THEN
- INFO = -4
- ELSE IF( LWORK.LT.MAX( 1, N ) .AND. .NOT.LQUERY ) THEN
- INFO = -7
- END IF
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'DGEQRF', -INFO )
- RETURN
- ELSE IF( LQUERY ) THEN
- RETURN
- END IF
-*
-* Quick return if possible
-*
- K = MIN( M, N )
- IF( K.EQ.0 ) THEN
- WORK( 1 ) = 1
- RETURN
- END IF
-*
- NBMIN = 2
- NX = 0
- IWS = N
- IF( NB.GT.1 .AND. NB.LT.K ) THEN
-*
-* Determine when to cross over from blocked to unblocked code.
-*
- NX = MAX( 0, ILAENV( 3, 'DGEQRF', ' ', M, N, -1, -1 ) )
- IF( NX.LT.K ) THEN
-*
-* Determine if workspace is large enough for blocked code.
-*
- LDWORK = N
- IWS = LDWORK*NB
- IF( LWORK.LT.IWS ) THEN
-*
-* Not enough workspace to use optimal NB: reduce NB and
-* determine the minimum value of NB.
-*
- NB = LWORK / LDWORK
- NBMIN = MAX( 2, ILAENV( 2, 'DGEQRF', ' ', M, N, -1,
- $ -1 ) )
- END IF
- END IF
- END IF
-*
- IF( NB.GE.NBMIN .AND. NB.LT.K .AND. NX.LT.K ) THEN
-*
-* Use blocked code initially
-*
- DO 10 I = 1, K - NX, NB
- IB = MIN( K-I+1, NB )
-*
-* Compute the QR factorization of the current block
-* A(i:m,i:i+ib-1)
-*
- CALL DGEQR2( M-I+1, IB, A( I, I ), LDA, TAU( I ), WORK,
- $ IINFO )
- IF( I+IB.LE.N ) THEN
-*
-* Form the triangular factor of the block reflector
-* H = H(i) H(i+1) . . . H(i+ib-1)
-*
- CALL DLARFT( 'Forward', 'Columnwise', M-I+1, IB,
- $ A( I, I ), LDA, TAU( I ), WORK, LDWORK )
-*
-* Apply H' to A(i:m,i+ib:n) from the left
-*
- CALL DLARFB( 'Left', 'Transpose', 'Forward',
- $ 'Columnwise', M-I+1, N-I-IB+1, IB,
- $ A( I, I ), LDA, WORK, LDWORK, A( I, I+IB ),
- $ LDA, WORK( IB+1 ), LDWORK )
- END IF
- 10 CONTINUE
- ELSE
- I = 1
- END IF
-*
-* Use unblocked code to factor the last or only block.
-*
- IF( I.LE.K )
- $ CALL DGEQR2( M-I+1, N-I+1, A( I, I ), LDA, TAU( I ), WORK,
- $ IINFO )
-*
- WORK( 1 ) = IWS
- RETURN
-*
-* End of DGEQRF
-*
- END
diff --git a/src/lib/lapack/dgerfs.f b/src/lib/lapack/dgerfs.f
deleted file mode 100644
index bada6e56..00000000
--- a/src/lib/lapack/dgerfs.f
+++ /dev/null
@@ -1,336 +0,0 @@
- SUBROUTINE DGERFS( TRANS, N, NRHS, A, LDA, AF, LDAF, IPIV, B, LDB,
- $ X, LDX, FERR, BERR, WORK, IWORK, INFO )
-*
-* -- LAPACK routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* Modified to call DLACN2 in place of DLACON, 5 Feb 03, SJH.
-*
-* .. Scalar Arguments ..
- CHARACTER TRANS
- INTEGER INFO, LDA, LDAF, LDB, LDX, N, NRHS
-* ..
-* .. Array Arguments ..
- INTEGER IPIV( * ), IWORK( * )
- DOUBLE PRECISION A( LDA, * ), AF( LDAF, * ), B( LDB, * ),
- $ BERR( * ), FERR( * ), WORK( * ), X( LDX, * )
-* ..
-*
-* Purpose
-* =======
-*
-* DGERFS improves the computed solution to a system of linear
-* equations and provides error bounds and backward error estimates for
-* the solution.
-*
-* Arguments
-* =========
-*
-* TRANS (input) CHARACTER*1
-* Specifies the form of the system of equations:
-* = 'N': A * X = B (No transpose)
-* = 'T': A**T * X = B (Transpose)
-* = 'C': A**H * X = B (Conjugate transpose = Transpose)
-*
-* N (input) INTEGER
-* The order of the matrix A. N >= 0.
-*
-* NRHS (input) INTEGER
-* The number of right hand sides, i.e., the number of columns
-* of the matrices B and X. NRHS >= 0.
-*
-* A (input) DOUBLE PRECISION array, dimension (LDA,N)
-* The original N-by-N matrix A.
-*
-* LDA (input) INTEGER
-* The leading dimension of the array A. LDA >= max(1,N).
-*
-* AF (input) DOUBLE PRECISION array, dimension (LDAF,N)
-* The factors L and U from the factorization A = P*L*U
-* as computed by DGETRF.
-*
-* LDAF (input) INTEGER
-* The leading dimension of the array AF. LDAF >= max(1,N).
-*
-* IPIV (input) INTEGER array, dimension (N)
-* The pivot indices from DGETRF; for 1<=i<=N, row i of the
-* matrix was interchanged with row IPIV(i).
-*
-* B (input) DOUBLE PRECISION array, dimension (LDB,NRHS)
-* The right hand side matrix B.
-*
-* LDB (input) INTEGER
-* The leading dimension of the array B. LDB >= max(1,N).
-*
-* X (input/output) DOUBLE PRECISION array, dimension (LDX,NRHS)
-* On entry, the solution matrix X, as computed by DGETRS.
-* On exit, the improved solution matrix X.
-*
-* LDX (input) INTEGER
-* The leading dimension of the array X. LDX >= max(1,N).
-*
-* FERR (output) DOUBLE PRECISION array, dimension (NRHS)
-* The estimated forward error bound for each solution vector
-* X(j) (the j-th column of the solution matrix X).
-* If XTRUE is the true solution corresponding to X(j), FERR(j)
-* is an estimated upper bound for the magnitude of the largest
-* element in (X(j) - XTRUE) divided by the magnitude of the
-* largest element in X(j). The estimate is as reliable as
-* the estimate for RCOND, and is almost always a slight
-* overestimate of the true error.
-*
-* BERR (output) DOUBLE PRECISION array, dimension (NRHS)
-* The componentwise relative backward error of each solution
-* vector X(j) (i.e., the smallest relative change in
-* any element of A or B that makes X(j) an exact solution).
-*
-* WORK (workspace) DOUBLE PRECISION array, dimension (3*N)
-*
-* IWORK (workspace) INTEGER array, dimension (N)
-*
-* INFO (output) INTEGER
-* = 0: successful exit
-* < 0: if INFO = -i, the i-th argument had an illegal value
-*
-* Internal Parameters
-* ===================
-*
-* ITMAX is the maximum number of steps of iterative refinement.
-*
-* =====================================================================
-*
-* .. Parameters ..
- INTEGER ITMAX
- PARAMETER ( ITMAX = 5 )
- DOUBLE PRECISION ZERO
- PARAMETER ( ZERO = 0.0D+0 )
- DOUBLE PRECISION ONE
- PARAMETER ( ONE = 1.0D+0 )
- DOUBLE PRECISION TWO
- PARAMETER ( TWO = 2.0D+0 )
- DOUBLE PRECISION THREE
- PARAMETER ( THREE = 3.0D+0 )
-* ..
-* .. Local Scalars ..
- LOGICAL NOTRAN
- CHARACTER TRANST
- INTEGER COUNT, I, J, K, KASE, NZ
- DOUBLE PRECISION EPS, LSTRES, S, SAFE1, SAFE2, SAFMIN, XK
-* ..
-* .. Local Arrays ..
- INTEGER ISAVE( 3 )
-* ..
-* .. External Subroutines ..
- EXTERNAL DAXPY, DCOPY, DGEMV, DGETRS, DLACN2, XERBLA
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC ABS, MAX
-* ..
-* .. External Functions ..
- LOGICAL LSAME
- DOUBLE PRECISION DLAMCH
- EXTERNAL LSAME, DLAMCH
-* ..
-* .. Executable Statements ..
-*
-* Test the input parameters.
-*
- INFO = 0
- NOTRAN = LSAME( TRANS, 'N' )
- IF( .NOT.NOTRAN .AND. .NOT.LSAME( TRANS, 'T' ) .AND. .NOT.
- $ LSAME( TRANS, 'C' ) ) THEN
- INFO = -1
- ELSE IF( N.LT.0 ) THEN
- INFO = -2
- ELSE IF( NRHS.LT.0 ) THEN
- INFO = -3
- ELSE IF( LDA.LT.MAX( 1, N ) ) THEN
- INFO = -5
- ELSE IF( LDAF.LT.MAX( 1, N ) ) THEN
- INFO = -7
- ELSE IF( LDB.LT.MAX( 1, N ) ) THEN
- INFO = -10
- ELSE IF( LDX.LT.MAX( 1, N ) ) THEN
- INFO = -12
- END IF
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'DGERFS', -INFO )
- RETURN
- END IF
-*
-* Quick return if possible
-*
- IF( N.EQ.0 .OR. NRHS.EQ.0 ) THEN
- DO 10 J = 1, NRHS
- FERR( J ) = ZERO
- BERR( J ) = ZERO
- 10 CONTINUE
- RETURN
- END IF
-*
- IF( NOTRAN ) THEN
- TRANST = 'T'
- ELSE
- TRANST = 'N'
- END IF
-*
-* NZ = maximum number of nonzero elements in each row of A, plus 1
-*
- NZ = N + 1
- EPS = DLAMCH( 'Epsilon' )
- SAFMIN = DLAMCH( 'Safe minimum' )
- SAFE1 = NZ*SAFMIN
- SAFE2 = SAFE1 / EPS
-*
-* Do for each right hand side
-*
- DO 140 J = 1, NRHS
-*
- COUNT = 1
- LSTRES = THREE
- 20 CONTINUE
-*
-* Loop until stopping criterion is satisfied.
-*
-* Compute residual R = B - op(A) * X,
-* where op(A) = A, A**T, or A**H, depending on TRANS.
-*
- CALL DCOPY( N, B( 1, J ), 1, WORK( N+1 ), 1 )
- CALL DGEMV( TRANS, N, N, -ONE, A, LDA, X( 1, J ), 1, ONE,
- $ WORK( N+1 ), 1 )
-*
-* Compute componentwise relative backward error from formula
-*
-* max(i) ( abs(R(i)) / ( abs(op(A))*abs(X) + abs(B) )(i) )
-*
-* where abs(Z) is the componentwise absolute value of the matrix
-* or vector Z. If the i-th component of the denominator is less
-* than SAFE2, then SAFE1 is added to the i-th components of the
-* numerator and denominator before dividing.
-*
- DO 30 I = 1, N
- WORK( I ) = ABS( B( I, J ) )
- 30 CONTINUE
-*
-* Compute abs(op(A))*abs(X) + abs(B).
-*
- IF( NOTRAN ) THEN
- DO 50 K = 1, N
- XK = ABS( X( K, J ) )
- DO 40 I = 1, N
- WORK( I ) = WORK( I ) + ABS( A( I, K ) )*XK
- 40 CONTINUE
- 50 CONTINUE
- ELSE
- DO 70 K = 1, N
- S = ZERO
- DO 60 I = 1, N
- S = S + ABS( A( I, K ) )*ABS( X( I, J ) )
- 60 CONTINUE
- WORK( K ) = WORK( K ) + S
- 70 CONTINUE
- END IF
- S = ZERO
- DO 80 I = 1, N
- IF( WORK( I ).GT.SAFE2 ) THEN
- S = MAX( S, ABS( WORK( N+I ) ) / WORK( I ) )
- ELSE
- S = MAX( S, ( ABS( WORK( N+I ) )+SAFE1 ) /
- $ ( WORK( I )+SAFE1 ) )
- END IF
- 80 CONTINUE
- BERR( J ) = S
-*
-* Test stopping criterion. Continue iterating if
-* 1) The residual BERR(J) is larger than machine epsilon, and
-* 2) BERR(J) decreased by at least a factor of 2 during the
-* last iteration, and
-* 3) At most ITMAX iterations tried.
-*
- IF( BERR( J ).GT.EPS .AND. TWO*BERR( J ).LE.LSTRES .AND.
- $ COUNT.LE.ITMAX ) THEN
-*
-* Update solution and try again.
-*
- CALL DGETRS( TRANS, N, 1, AF, LDAF, IPIV, WORK( N+1 ), N,
- $ INFO )
- CALL DAXPY( N, ONE, WORK( N+1 ), 1, X( 1, J ), 1 )
- LSTRES = BERR( J )
- COUNT = COUNT + 1
- GO TO 20
- END IF
-*
-* Bound error from formula
-*
-* norm(X - XTRUE) / norm(X) .le. FERR =
-* norm( abs(inv(op(A)))*
-* ( abs(R) + NZ*EPS*( abs(op(A))*abs(X)+abs(B) ))) / norm(X)
-*
-* where
-* norm(Z) is the magnitude of the largest component of Z
-* inv(op(A)) is the inverse of op(A)
-* abs(Z) is the componentwise absolute value of the matrix or
-* vector Z
-* NZ is the maximum number of nonzeros in any row of A, plus 1
-* EPS is machine epsilon
-*
-* The i-th component of abs(R)+NZ*EPS*(abs(op(A))*abs(X)+abs(B))
-* is incremented by SAFE1 if the i-th component of
-* abs(op(A))*abs(X) + abs(B) is less than SAFE2.
-*
-* Use DLACN2 to estimate the infinity-norm of the matrix
-* inv(op(A)) * diag(W),
-* where W = abs(R) + NZ*EPS*( abs(op(A))*abs(X)+abs(B) )))
-*
- DO 90 I = 1, N
- IF( WORK( I ).GT.SAFE2 ) THEN
- WORK( I ) = ABS( WORK( N+I ) ) + NZ*EPS*WORK( I )
- ELSE
- WORK( I ) = ABS( WORK( N+I ) ) + NZ*EPS*WORK( I ) + SAFE1
- END IF
- 90 CONTINUE
-*
- KASE = 0
- 100 CONTINUE
- CALL DLACN2( N, WORK( 2*N+1 ), WORK( N+1 ), IWORK, FERR( J ),
- $ KASE, ISAVE )
- IF( KASE.NE.0 ) THEN
- IF( KASE.EQ.1 ) THEN
-*
-* Multiply by diag(W)*inv(op(A)**T).
-*
- CALL DGETRS( TRANST, N, 1, AF, LDAF, IPIV, WORK( N+1 ),
- $ N, INFO )
- DO 110 I = 1, N
- WORK( N+I ) = WORK( I )*WORK( N+I )
- 110 CONTINUE
- ELSE
-*
-* Multiply by inv(op(A))*diag(W).
-*
- DO 120 I = 1, N
- WORK( N+I ) = WORK( I )*WORK( N+I )
- 120 CONTINUE
- CALL DGETRS( TRANS, N, 1, AF, LDAF, IPIV, WORK( N+1 ), N,
- $ INFO )
- END IF
- GO TO 100
- END IF
-*
-* Normalize error.
-*
- LSTRES = ZERO
- DO 130 I = 1, N
- LSTRES = MAX( LSTRES, ABS( X( I, J ) ) )
- 130 CONTINUE
- IF( LSTRES.NE.ZERO )
- $ FERR( J ) = FERR( J ) / LSTRES
-*
- 140 CONTINUE
-*
- RETURN
-*
-* End of DGERFS
-*
- END
diff --git a/src/lib/lapack/dgerq2.f b/src/lib/lapack/dgerq2.f
deleted file mode 100644
index 4dfe8b0f..00000000
--- a/src/lib/lapack/dgerq2.f
+++ /dev/null
@@ -1,122 +0,0 @@
- SUBROUTINE DGERQ2( M, N, A, LDA, TAU, WORK, INFO )
-*
-* -- LAPACK routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- INTEGER INFO, LDA, M, N
-* ..
-* .. Array Arguments ..
- DOUBLE PRECISION A( LDA, * ), TAU( * ), WORK( * )
-* ..
-*
-* Purpose
-* =======
-*
-* DGERQ2 computes an RQ factorization of a real m by n matrix A:
-* A = R * Q.
-*
-* Arguments
-* =========
-*
-* M (input) INTEGER
-* The number of rows of the matrix A. M >= 0.
-*
-* N (input) INTEGER
-* The number of columns of the matrix A. N >= 0.
-*
-* A (input/output) DOUBLE PRECISION array, dimension (LDA,N)
-* On entry, the m by n matrix A.
-* On exit, if m <= n, the upper triangle of the subarray
-* A(1:m,n-m+1:n) contains the m by m upper triangular matrix R;
-* if m >= n, the elements on and above the (m-n)-th subdiagonal
-* contain the m by n upper trapezoidal matrix R; the remaining
-* elements, with the array TAU, represent the orthogonal matrix
-* Q as a product of elementary reflectors (see Further
-* Details).
-*
-* LDA (input) INTEGER
-* The leading dimension of the array A. LDA >= max(1,M).
-*
-* TAU (output) DOUBLE PRECISION array, dimension (min(M,N))
-* The scalar factors of the elementary reflectors (see Further
-* Details).
-*
-* WORK (workspace) DOUBLE PRECISION array, dimension (M)
-*
-* INFO (output) INTEGER
-* = 0: successful exit
-* < 0: if INFO = -i, the i-th argument had an illegal value
-*
-* Further Details
-* ===============
-*
-* The matrix Q is represented as a product of elementary reflectors
-*
-* Q = H(1) H(2) . . . H(k), where k = min(m,n).
-*
-* Each H(i) has the form
-*
-* H(i) = I - tau * v * v'
-*
-* where tau is a real scalar, and v is a real vector with
-* v(n-k+i+1:n) = 0 and v(n-k+i) = 1; v(1:n-k+i-1) is stored on exit in
-* A(m-k+i,1:n-k+i-1), and tau in TAU(i).
-*
-* =====================================================================
-*
-* .. Parameters ..
- DOUBLE PRECISION ONE
- PARAMETER ( ONE = 1.0D+0 )
-* ..
-* .. Local Scalars ..
- INTEGER I, K
- DOUBLE PRECISION AII
-* ..
-* .. External Subroutines ..
- EXTERNAL DLARF, DLARFG, XERBLA
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC MAX, MIN
-* ..
-* .. Executable Statements ..
-*
-* Test the input arguments
-*
- INFO = 0
- IF( M.LT.0 ) THEN
- INFO = -1
- ELSE IF( N.LT.0 ) THEN
- INFO = -2
- ELSE IF( LDA.LT.MAX( 1, M ) ) THEN
- INFO = -4
- END IF
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'DGERQ2', -INFO )
- RETURN
- END IF
-*
- K = MIN( M, N )
-*
- DO 10 I = K, 1, -1
-*
-* Generate elementary reflector H(i) to annihilate
-* A(m-k+i,1:n-k+i-1)
-*
- CALL DLARFG( N-K+I, A( M-K+I, N-K+I ), A( M-K+I, 1 ), LDA,
- $ TAU( I ) )
-*
-* Apply H(i) to A(1:m-k+i-1,1:n-k+i) from the right
-*
- AII = A( M-K+I, N-K+I )
- A( M-K+I, N-K+I ) = ONE
- CALL DLARF( 'Right', M-K+I-1, N-K+I, A( M-K+I, 1 ), LDA,
- $ TAU( I ), A, LDA, WORK )
- A( M-K+I, N-K+I ) = AII
- 10 CONTINUE
- RETURN
-*
-* End of DGERQ2
-*
- END
diff --git a/src/lib/lapack/dgerqf.f b/src/lib/lapack/dgerqf.f
deleted file mode 100644
index 3dc22652..00000000
--- a/src/lib/lapack/dgerqf.f
+++ /dev/null
@@ -1,213 +0,0 @@
- SUBROUTINE DGERQF( M, N, A, LDA, TAU, WORK, LWORK, INFO )
-*
-* -- LAPACK routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- INTEGER INFO, LDA, LWORK, M, N
-* ..
-* .. Array Arguments ..
- DOUBLE PRECISION A( LDA, * ), TAU( * ), WORK( * )
-* ..
-*
-* Purpose
-* =======
-*
-* DGERQF computes an RQ factorization of a real M-by-N matrix A:
-* A = R * Q.
-*
-* Arguments
-* =========
-*
-* M (input) INTEGER
-* The number of rows of the matrix A. M >= 0.
-*
-* N (input) INTEGER
-* The number of columns of the matrix A. N >= 0.
-*
-* A (input/output) DOUBLE PRECISION array, dimension (LDA,N)
-* On entry, the M-by-N matrix A.
-* On exit,
-* if m <= n, the upper triangle of the subarray
-* A(1:m,n-m+1:n) contains the M-by-M upper triangular matrix R;
-* if m >= n, the elements on and above the (m-n)-th subdiagonal
-* contain the M-by-N upper trapezoidal matrix R;
-* the remaining elements, with the array TAU, represent the
-* orthogonal matrix Q as a product of min(m,n) elementary
-* reflectors (see Further Details).
-*
-* LDA (input) INTEGER
-* The leading dimension of the array A. LDA >= max(1,M).
-*
-* TAU (output) DOUBLE PRECISION array, dimension (min(M,N))
-* The scalar factors of the elementary reflectors (see Further
-* Details).
-*
-* WORK (workspace/output) DOUBLE PRECISION array, dimension (MAX(1,LWORK))
-* On exit, if INFO = 0, WORK(1) returns the optimal LWORK.
-*
-* LWORK (input) INTEGER
-* The dimension of the array WORK. LWORK >= max(1,M).
-* For optimum performance LWORK >= M*NB, where NB is
-* the optimal blocksize.
-*
-* If LWORK = -1, then a workspace query is assumed; the routine
-* only calculates the optimal size of the WORK array, returns
-* this value as the first entry of the WORK array, and no error
-* message related to LWORK is issued by XERBLA.
-*
-* INFO (output) INTEGER
-* = 0: successful exit
-* < 0: if INFO = -i, the i-th argument had an illegal value
-*
-* Further Details
-* ===============
-*
-* The matrix Q is represented as a product of elementary reflectors
-*
-* Q = H(1) H(2) . . . H(k), where k = min(m,n).
-*
-* Each H(i) has the form
-*
-* H(i) = I - tau * v * v'
-*
-* where tau is a real scalar, and v is a real vector with
-* v(n-k+i+1:n) = 0 and v(n-k+i) = 1; v(1:n-k+i-1) is stored on exit in
-* A(m-k+i,1:n-k+i-1), and tau in TAU(i).
-*
-* =====================================================================
-*
-* .. Local Scalars ..
- LOGICAL LQUERY
- INTEGER I, IB, IINFO, IWS, K, KI, KK, LDWORK, LWKOPT,
- $ MU, NB, NBMIN, NU, NX
-* ..
-* .. External Subroutines ..
- EXTERNAL DGERQ2, DLARFB, DLARFT, XERBLA
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC MAX, MIN
-* ..
-* .. External Functions ..
- INTEGER ILAENV
- EXTERNAL ILAENV
-* ..
-* .. Executable Statements ..
-*
-* Test the input arguments
-*
- INFO = 0
- LQUERY = ( LWORK.EQ.-1 )
- IF( M.LT.0 ) THEN
- INFO = -1
- ELSE IF( N.LT.0 ) THEN
- INFO = -2
- ELSE IF( LDA.LT.MAX( 1, M ) ) THEN
- INFO = -4
- END IF
-*
- IF( INFO.EQ.0 ) THEN
- K = MIN( M, N )
- IF( K.EQ.0 ) THEN
- LWKOPT = 1
- ELSE
- NB = ILAENV( 1, 'DGERQF', ' ', M, N, -1, -1 )
- LWKOPT = M*NB
- END IF
- WORK( 1 ) = LWKOPT
-*
- IF( LWORK.LT.MAX( 1, M ) .AND. .NOT.LQUERY ) THEN
- INFO = -7
- END IF
- END IF
-*
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'DGERQF', -INFO )
- RETURN
- ELSE IF( LQUERY ) THEN
- RETURN
- END IF
-*
-* Quick return if possible
-*
- IF( K.EQ.0 ) THEN
- RETURN
- END IF
-*
- NBMIN = 2
- NX = 1
- IWS = M
- IF( NB.GT.1 .AND. NB.LT.K ) THEN
-*
-* Determine when to cross over from blocked to unblocked code.
-*
- NX = MAX( 0, ILAENV( 3, 'DGERQF', ' ', M, N, -1, -1 ) )
- IF( NX.LT.K ) THEN
-*
-* Determine if workspace is large enough for blocked code.
-*
- LDWORK = M
- IWS = LDWORK*NB
- IF( LWORK.LT.IWS ) THEN
-*
-* Not enough workspace to use optimal NB: reduce NB and
-* determine the minimum value of NB.
-*
- NB = LWORK / LDWORK
- NBMIN = MAX( 2, ILAENV( 2, 'DGERQF', ' ', M, N, -1,
- $ -1 ) )
- END IF
- END IF
- END IF
-*
- IF( NB.GE.NBMIN .AND. NB.LT.K .AND. NX.LT.K ) THEN
-*
-* Use blocked code initially.
-* The last kk rows are handled by the block method.
-*
- KI = ( ( K-NX-1 ) / NB )*NB
- KK = MIN( K, KI+NB )
-*
- DO 10 I = K - KK + KI + 1, K - KK + 1, -NB
- IB = MIN( K-I+1, NB )
-*
-* Compute the RQ factorization of the current block
-* A(m-k+i:m-k+i+ib-1,1:n-k+i+ib-1)
-*
- CALL DGERQ2( IB, N-K+I+IB-1, A( M-K+I, 1 ), LDA, TAU( I ),
- $ WORK, IINFO )
- IF( M-K+I.GT.1 ) THEN
-*
-* Form the triangular factor of the block reflector
-* H = H(i+ib-1) . . . H(i+1) H(i)
-*
- CALL DLARFT( 'Backward', 'Rowwise', N-K+I+IB-1, IB,
- $ A( M-K+I, 1 ), LDA, TAU( I ), WORK, LDWORK )
-*
-* Apply H to A(1:m-k+i-1,1:n-k+i+ib-1) from the right
-*
- CALL DLARFB( 'Right', 'No transpose', 'Backward',
- $ 'Rowwise', M-K+I-1, N-K+I+IB-1, IB,
- $ A( M-K+I, 1 ), LDA, WORK, LDWORK, A, LDA,
- $ WORK( IB+1 ), LDWORK )
- END IF
- 10 CONTINUE
- MU = M - K + I + NB - 1
- NU = N - K + I + NB - 1
- ELSE
- MU = M
- NU = N
- END IF
-*
-* Use unblocked code to factor the last or only block
-*
- IF( MU.GT.0 .AND. NU.GT.0 )
- $ CALL DGERQ2( MU, NU, A, LDA, TAU, WORK, IINFO )
-*
- WORK( 1 ) = IWS
- RETURN
-*
-* End of DGERQF
-*
- END
diff --git a/src/lib/lapack/dgesc2.f b/src/lib/lapack/dgesc2.f
deleted file mode 100644
index 1b0331f5..00000000
--- a/src/lib/lapack/dgesc2.f
+++ /dev/null
@@ -1,132 +0,0 @@
- SUBROUTINE DGESC2( N, A, LDA, RHS, IPIV, JPIV, SCALE )
-*
-* -- LAPACK auxiliary routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- INTEGER LDA, N
- DOUBLE PRECISION SCALE
-* ..
-* .. Array Arguments ..
- INTEGER IPIV( * ), JPIV( * )
- DOUBLE PRECISION A( LDA, * ), RHS( * )
-* ..
-*
-* Purpose
-* =======
-*
-* DGESC2 solves a system of linear equations
-*
-* A * X = scale* RHS
-*
-* with a general N-by-N matrix A using the LU factorization with
-* complete pivoting computed by DGETC2.
-*
-* Arguments
-* =========
-*
-* N (input) INTEGER
-* The order of the matrix A.
-*
-* A (input) DOUBLE PRECISION array, dimension (LDA,N)
-* On entry, the LU part of the factorization of the n-by-n
-* matrix A computed by DGETC2: A = P * L * U * Q
-*
-* LDA (input) INTEGER
-* The leading dimension of the array A. LDA >= max(1, N).
-*
-* RHS (input/output) DOUBLE PRECISION array, dimension (N).
-* On entry, the right hand side vector b.
-* On exit, the solution vector X.
-*
-* IPIV (input) INTEGER array, dimension (N).
-* The pivot indices; for 1 <= i <= N, row i of the
-* matrix has been interchanged with row IPIV(i).
-*
-* JPIV (input) INTEGER array, dimension (N).
-* The pivot indices; for 1 <= j <= N, column j of the
-* matrix has been interchanged with column JPIV(j).
-*
-* SCALE (output) DOUBLE PRECISION
-* On exit, SCALE contains the scale factor. SCALE is chosen
-* 0 <= SCALE <= 1 to prevent owerflow in the solution.
-*
-* Further Details
-* ===============
-*
-* Based on contributions by
-* Bo Kagstrom and Peter Poromaa, Department of Computing Science,
-* Umea University, S-901 87 Umea, Sweden.
-*
-* =====================================================================
-*
-* .. Parameters ..
- DOUBLE PRECISION ONE, TWO
- PARAMETER ( ONE = 1.0D+0, TWO = 2.0D+0 )
-* ..
-* .. Local Scalars ..
- INTEGER I, J
- DOUBLE PRECISION BIGNUM, EPS, SMLNUM, TEMP
-* ..
-* .. External Subroutines ..
- EXTERNAL DLASWP, DSCAL
-* ..
-* .. External Functions ..
- INTEGER IDAMAX
- DOUBLE PRECISION DLAMCH
- EXTERNAL IDAMAX, DLAMCH
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC ABS
-* ..
-* .. Executable Statements ..
-*
-* Set constant to control owerflow
-*
- EPS = DLAMCH( 'P' )
- SMLNUM = DLAMCH( 'S' ) / EPS
- BIGNUM = ONE / SMLNUM
- CALL DLABAD( SMLNUM, BIGNUM )
-*
-* Apply permutations IPIV to RHS
-*
- CALL DLASWP( 1, RHS, LDA, 1, N-1, IPIV, 1 )
-*
-* Solve for L part
-*
- DO 20 I = 1, N - 1
- DO 10 J = I + 1, N
- RHS( J ) = RHS( J ) - A( J, I )*RHS( I )
- 10 CONTINUE
- 20 CONTINUE
-*
-* Solve for U part
-*
- SCALE = ONE
-*
-* Check for scaling
-*
- I = IDAMAX( N, RHS, 1 )
- IF( TWO*SMLNUM*ABS( RHS( I ) ).GT.ABS( A( N, N ) ) ) THEN
- TEMP = ( ONE / TWO ) / ABS( RHS( I ) )
- CALL DSCAL( N, TEMP, RHS( 1 ), 1 )
- SCALE = SCALE*TEMP
- END IF
-*
- DO 40 I = N, 1, -1
- TEMP = ONE / A( I, I )
- RHS( I ) = RHS( I )*TEMP
- DO 30 J = I + 1, N
- RHS( I ) = RHS( I ) - RHS( J )*( A( I, J )*TEMP )
- 30 CONTINUE
- 40 CONTINUE
-*
-* Apply permutations JPIV to the solution (RHS)
-*
- CALL DLASWP( 1, RHS, LDA, 1, N-1, JPIV, -1 )
- RETURN
-*
-* End of DGESC2
-*
- END
diff --git a/src/lib/lapack/dgesv.f b/src/lib/lapack/dgesv.f
deleted file mode 100644
index 220ef56f..00000000
--- a/src/lib/lapack/dgesv.f
+++ /dev/null
@@ -1,107 +0,0 @@
- SUBROUTINE DGESV( N, NRHS, A, LDA, IPIV, B, LDB, INFO )
-*
-* -- LAPACK driver routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- INTEGER INFO, LDA, LDB, N, NRHS
-* ..
-* .. Array Arguments ..
- INTEGER IPIV( * )
- DOUBLE PRECISION A( LDA, * ), B( LDB, * )
-* ..
-*
-* Purpose
-* =======
-*
-* DGESV computes the solution to a real system of linear equations
-* A * X = B,
-* where A is an N-by-N matrix and X and B are N-by-NRHS matrices.
-*
-* The LU decomposition with partial pivoting and row interchanges is
-* used to factor A as
-* A = P * L * U,
-* where P is a permutation matrix, L is unit lower triangular, and U is
-* upper triangular. The factored form of A is then used to solve the
-* system of equations A * X = B.
-*
-* Arguments
-* =========
-*
-* N (input) INTEGER
-* The number of linear equations, i.e., the order of the
-* matrix A. N >= 0.
-*
-* NRHS (input) INTEGER
-* The number of right hand sides, i.e., the number of columns
-* of the matrix B. NRHS >= 0.
-*
-* A (input/output) DOUBLE PRECISION array, dimension (LDA,N)
-* On entry, the N-by-N coefficient matrix A.
-* On exit, the factors L and U from the factorization
-* A = P*L*U; the unit diagonal elements of L are not stored.
-*
-* LDA (input) INTEGER
-* The leading dimension of the array A. LDA >= max(1,N).
-*
-* IPIV (output) INTEGER array, dimension (N)
-* The pivot indices that define the permutation matrix P;
-* row i of the matrix was interchanged with row IPIV(i).
-*
-* B (input/output) DOUBLE PRECISION array, dimension (LDB,NRHS)
-* On entry, the N-by-NRHS matrix of right hand side matrix B.
-* On exit, if INFO = 0, the N-by-NRHS solution matrix X.
-*
-* LDB (input) INTEGER
-* The leading dimension of the array B. LDB >= max(1,N).
-*
-* INFO (output) INTEGER
-* = 0: successful exit
-* < 0: if INFO = -i, the i-th argument had an illegal value
-* > 0: if INFO = i, U(i,i) is exactly zero. The factorization
-* has been completed, but the factor U is exactly
-* singular, so the solution could not be computed.
-*
-* =====================================================================
-*
-* .. External Subroutines ..
- EXTERNAL DGETRF, DGETRS, XERBLA
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC MAX
-* ..
-* .. Executable Statements ..
-*
-* Test the input parameters.
-*
- INFO = 0
- IF( N.LT.0 ) THEN
- INFO = -1
- ELSE IF( NRHS.LT.0 ) THEN
- INFO = -2
- ELSE IF( LDA.LT.MAX( 1, N ) ) THEN
- INFO = -4
- ELSE IF( LDB.LT.MAX( 1, N ) ) THEN
- INFO = -7
- END IF
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'DGESV ', -INFO )
- RETURN
- END IF
-*
-* Compute the LU factorization of A.
-*
- CALL DGETRF( N, N, A, LDA, IPIV, INFO )
- IF( INFO.EQ.0 ) THEN
-*
-* Solve the system A*X = B, overwriting B with X.
-*
- CALL DGETRS( 'No transpose', N, NRHS, A, LDA, IPIV, B, LDB,
- $ INFO )
- END IF
- RETURN
-*
-* End of DGESV
-*
- END
diff --git a/src/lib/lapack/dgesvd.f b/src/lib/lapack/dgesvd.f
deleted file mode 100644
index 0b62ca10..00000000
--- a/src/lib/lapack/dgesvd.f
+++ /dev/null
@@ -1,3401 +0,0 @@
- SUBROUTINE DGESVD( JOBU, JOBVT, M, N, A, LDA, S, U, LDU, VT, LDVT,
- $ WORK, LWORK, INFO )
-*
-* -- LAPACK driver routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- CHARACTER JOBU, JOBVT
- INTEGER INFO, LDA, LDU, LDVT, LWORK, M, N
-* ..
-* .. Array Arguments ..
- DOUBLE PRECISION A( LDA, * ), S( * ), U( LDU, * ),
- $ VT( LDVT, * ), WORK( * )
-* ..
-*
-* Purpose
-* =======
-*
-* DGESVD computes the singular value decomposition (SVD) of a real
-* M-by-N matrix A, optionally computing the left and/or right singular
-* vectors. The SVD is written
-*
-* A = U * SIGMA * transpose(V)
-*
-* where SIGMA is an M-by-N matrix which is zero except for its
-* min(m,n) diagonal elements, U is an M-by-M orthogonal matrix, and
-* V is an N-by-N orthogonal matrix. The diagonal elements of SIGMA
-* are the singular values of A; they are real and non-negative, and
-* are returned in descending order. The first min(m,n) columns of
-* U and V are the left and right singular vectors of A.
-*
-* Note that the routine returns V**T, not V.
-*
-* Arguments
-* =========
-*
-* JOBU (input) CHARACTER*1
-* Specifies options for computing all or part of the matrix U:
-* = 'A': all M columns of U are returned in array U:
-* = 'S': the first min(m,n) columns of U (the left singular
-* vectors) are returned in the array U;
-* = 'O': the first min(m,n) columns of U (the left singular
-* vectors) are overwritten on the array A;
-* = 'N': no columns of U (no left singular vectors) are
-* computed.
-*
-* JOBVT (input) CHARACTER*1
-* Specifies options for computing all or part of the matrix
-* V**T:
-* = 'A': all N rows of V**T are returned in the array VT;
-* = 'S': the first min(m,n) rows of V**T (the right singular
-* vectors) are returned in the array VT;
-* = 'O': the first min(m,n) rows of V**T (the right singular
-* vectors) are overwritten on the array A;
-* = 'N': no rows of V**T (no right singular vectors) are
-* computed.
-*
-* JOBVT and JOBU cannot both be 'O'.
-*
-* M (input) INTEGER
-* The number of rows of the input matrix A. M >= 0.
-*
-* N (input) INTEGER
-* The number of columns of the input matrix A. N >= 0.
-*
-* A (input/output) DOUBLE PRECISION array, dimension (LDA,N)
-* On entry, the M-by-N matrix A.
-* On exit,
-* if JOBU = 'O', A is overwritten with the first min(m,n)
-* columns of U (the left singular vectors,
-* stored columnwise);
-* if JOBVT = 'O', A is overwritten with the first min(m,n)
-* rows of V**T (the right singular vectors,
-* stored rowwise);
-* if JOBU .ne. 'O' and JOBVT .ne. 'O', the contents of A
-* are destroyed.
-*
-* LDA (input) INTEGER
-* The leading dimension of the array A. LDA >= max(1,M).
-*
-* S (output) DOUBLE PRECISION array, dimension (min(M,N))
-* The singular values of A, sorted so that S(i) >= S(i+1).
-*
-* U (output) DOUBLE PRECISION array, dimension (LDU,UCOL)
-* (LDU,M) if JOBU = 'A' or (LDU,min(M,N)) if JOBU = 'S'.
-* If JOBU = 'A', U contains the M-by-M orthogonal matrix U;
-* if JOBU = 'S', U contains the first min(m,n) columns of U
-* (the left singular vectors, stored columnwise);
-* if JOBU = 'N' or 'O', U is not referenced.
-*
-* LDU (input) INTEGER
-* The leading dimension of the array U. LDU >= 1; if
-* JOBU = 'S' or 'A', LDU >= M.
-*
-* VT (output) DOUBLE PRECISION array, dimension (LDVT,N)
-* If JOBVT = 'A', VT contains the N-by-N orthogonal matrix
-* V**T;
-* if JOBVT = 'S', VT contains the first min(m,n) rows of
-* V**T (the right singular vectors, stored rowwise);
-* if JOBVT = 'N' or 'O', VT is not referenced.
-*
-* LDVT (input) INTEGER
-* The leading dimension of the array VT. LDVT >= 1; if
-* JOBVT = 'A', LDVT >= N; if JOBVT = 'S', LDVT >= min(M,N).
-*
-* WORK (workspace/output) DOUBLE PRECISION array, dimension (MAX(1,LWORK))
-* On exit, if INFO = 0, WORK(1) returns the optimal LWORK;
-* if INFO > 0, WORK(2:MIN(M,N)) contains the unconverged
-* superdiagonal elements of an upper bidiagonal matrix B
-* whose diagonal is in S (not necessarily sorted). B
-* satisfies A = U * B * VT, so it has the same singular values
-* as A, and singular vectors related by U and VT.
-*
-* LWORK (input) INTEGER
-* The dimension of the array WORK.
-* LWORK >= MAX(1,3*MIN(M,N)+MAX(M,N),5*MIN(M,N)).
-* For good performance, LWORK should generally be larger.
-*
-* If LWORK = -1, then a workspace query is assumed; the routine
-* only calculates the optimal size of the WORK array, returns
-* this value as the first entry of the WORK array, and no error
-* message related to LWORK is issued by XERBLA.
-*
-* INFO (output) INTEGER
-* = 0: successful exit.
-* < 0: if INFO = -i, the i-th argument had an illegal value.
-* > 0: if DBDSQR did not converge, INFO specifies how many
-* superdiagonals of an intermediate bidiagonal form B
-* did not converge to zero. See the description of WORK
-* above for details.
-*
-* =====================================================================
-*
-* .. Parameters ..
- DOUBLE PRECISION ZERO, ONE
- PARAMETER ( ZERO = 0.0D0, ONE = 1.0D0 )
-* ..
-* .. Local Scalars ..
- LOGICAL LQUERY, WNTUA, WNTUAS, WNTUN, WNTUO, WNTUS,
- $ WNTVA, WNTVAS, WNTVN, WNTVO, WNTVS
- INTEGER BDSPAC, BLK, CHUNK, I, IE, IERR, IR, ISCL,
- $ ITAU, ITAUP, ITAUQ, IU, IWORK, LDWRKR, LDWRKU,
- $ MAXWRK, MINMN, MINWRK, MNTHR, NCU, NCVT, NRU,
- $ NRVT, WRKBL
- DOUBLE PRECISION ANRM, BIGNUM, EPS, SMLNUM
-* ..
-* .. Local Arrays ..
- DOUBLE PRECISION DUM( 1 )
-* ..
-* .. External Subroutines ..
- EXTERNAL DBDSQR, DGEBRD, DGELQF, DGEMM, DGEQRF, DLACPY,
- $ DLASCL, DLASET, DORGBR, DORGLQ, DORGQR, DORMBR,
- $ XERBLA
-* ..
-* .. External Functions ..
- LOGICAL LSAME
- INTEGER ILAENV
- DOUBLE PRECISION DLAMCH, DLANGE
- EXTERNAL LSAME, ILAENV, DLAMCH, DLANGE
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC MAX, MIN, SQRT
-* ..
-* .. Executable Statements ..
-*
-* Test the input arguments
-*
- INFO = 0
- MINMN = MIN( M, N )
- WNTUA = LSAME( JOBU, 'A' )
- WNTUS = LSAME( JOBU, 'S' )
- WNTUAS = WNTUA .OR. WNTUS
- WNTUO = LSAME( JOBU, 'O' )
- WNTUN = LSAME( JOBU, 'N' )
- WNTVA = LSAME( JOBVT, 'A' )
- WNTVS = LSAME( JOBVT, 'S' )
- WNTVAS = WNTVA .OR. WNTVS
- WNTVO = LSAME( JOBVT, 'O' )
- WNTVN = LSAME( JOBVT, 'N' )
- LQUERY = ( LWORK.EQ.-1 )
-*
- IF( .NOT.( WNTUA .OR. WNTUS .OR. WNTUO .OR. WNTUN ) ) THEN
- INFO = -1
- ELSE IF( .NOT.( WNTVA .OR. WNTVS .OR. WNTVO .OR. WNTVN ) .OR.
- $ ( WNTVO .AND. WNTUO ) ) THEN
- INFO = -2
- ELSE IF( M.LT.0 ) THEN
- INFO = -3
- ELSE IF( N.LT.0 ) THEN
- INFO = -4
- ELSE IF( LDA.LT.MAX( 1, M ) ) THEN
- INFO = -6
- ELSE IF( LDU.LT.1 .OR. ( WNTUAS .AND. LDU.LT.M ) ) THEN
- INFO = -9
- ELSE IF( LDVT.LT.1 .OR. ( WNTVA .AND. LDVT.LT.N ) .OR.
- $ ( WNTVS .AND. LDVT.LT.MINMN ) ) THEN
- INFO = -11
- END IF
-*
-* Compute workspace
-* (Note: Comments in the code beginning "Workspace:" describe the
-* minimal amount of workspace needed at that point in the code,
-* as well as the preferred amount for good performance.
-* NB refers to the optimal block size for the immediately
-* following subroutine, as returned by ILAENV.)
-*
- IF( INFO.EQ.0 ) THEN
- MINWRK = 1
- MAXWRK = 1
- IF( M.GE.N .AND. MINMN.GT.0 ) THEN
-*
-* Compute space needed for DBDSQR
-*
- MNTHR = ILAENV( 6, 'DGESVD', JOBU // JOBVT, M, N, 0, 0 )
- BDSPAC = 5*N
- IF( M.GE.MNTHR ) THEN
- IF( WNTUN ) THEN
-*
-* Path 1 (M much larger than N, JOBU='N')
-*
- MAXWRK = N + N*ILAENV( 1, 'DGEQRF', ' ', M, N, -1,
- $ -1 )
- MAXWRK = MAX( MAXWRK, 3*N+2*N*
- $ ILAENV( 1, 'DGEBRD', ' ', N, N, -1, -1 ) )
- IF( WNTVO .OR. WNTVAS )
- $ MAXWRK = MAX( MAXWRK, 3*N+( N-1 )*
- $ ILAENV( 1, 'DORGBR', 'P', N, N, N, -1 ) )
- MAXWRK = MAX( MAXWRK, BDSPAC )
- MINWRK = MAX( 4*N, BDSPAC )
- ELSE IF( WNTUO .AND. WNTVN ) THEN
-*
-* Path 2 (M much larger than N, JOBU='O', JOBVT='N')
-*
- WRKBL = N + N*ILAENV( 1, 'DGEQRF', ' ', M, N, -1, -1 )
- WRKBL = MAX( WRKBL, N+N*ILAENV( 1, 'DORGQR', ' ', M,
- $ N, N, -1 ) )
- WRKBL = MAX( WRKBL, 3*N+2*N*
- $ ILAENV( 1, 'DGEBRD', ' ', N, N, -1, -1 ) )
- WRKBL = MAX( WRKBL, 3*N+N*
- $ ILAENV( 1, 'DORGBR', 'Q', N, N, N, -1 ) )
- WRKBL = MAX( WRKBL, BDSPAC )
- MAXWRK = MAX( N*N+WRKBL, N*N+M*N+N )
- MINWRK = MAX( 3*N+M, BDSPAC )
- ELSE IF( WNTUO .AND. WNTVAS ) THEN
-*
-* Path 3 (M much larger than N, JOBU='O', JOBVT='S' or
-* 'A')
-*
- WRKBL = N + N*ILAENV( 1, 'DGEQRF', ' ', M, N, -1, -1 )
- WRKBL = MAX( WRKBL, N+N*ILAENV( 1, 'DORGQR', ' ', M,
- $ N, N, -1 ) )
- WRKBL = MAX( WRKBL, 3*N+2*N*
- $ ILAENV( 1, 'DGEBRD', ' ', N, N, -1, -1 ) )
- WRKBL = MAX( WRKBL, 3*N+N*
- $ ILAENV( 1, 'DORGBR', 'Q', N, N, N, -1 ) )
- WRKBL = MAX( WRKBL, 3*N+( N-1 )*
- $ ILAENV( 1, 'DORGBR', 'P', N, N, N, -1 ) )
- WRKBL = MAX( WRKBL, BDSPAC )
- MAXWRK = MAX( N*N+WRKBL, N*N+M*N+N )
- MINWRK = MAX( 3*N+M, BDSPAC )
- ELSE IF( WNTUS .AND. WNTVN ) THEN
-*
-* Path 4 (M much larger than N, JOBU='S', JOBVT='N')
-*
- WRKBL = N + N*ILAENV( 1, 'DGEQRF', ' ', M, N, -1, -1 )
- WRKBL = MAX( WRKBL, N+N*ILAENV( 1, 'DORGQR', ' ', M,
- $ N, N, -1 ) )
- WRKBL = MAX( WRKBL, 3*N+2*N*
- $ ILAENV( 1, 'DGEBRD', ' ', N, N, -1, -1 ) )
- WRKBL = MAX( WRKBL, 3*N+N*
- $ ILAENV( 1, 'DORGBR', 'Q', N, N, N, -1 ) )
- WRKBL = MAX( WRKBL, BDSPAC )
- MAXWRK = N*N + WRKBL
- MINWRK = MAX( 3*N+M, BDSPAC )
- ELSE IF( WNTUS .AND. WNTVO ) THEN
-*
-* Path 5 (M much larger than N, JOBU='S', JOBVT='O')
-*
- WRKBL = N + N*ILAENV( 1, 'DGEQRF', ' ', M, N, -1, -1 )
- WRKBL = MAX( WRKBL, N+N*ILAENV( 1, 'DORGQR', ' ', M,
- $ N, N, -1 ) )
- WRKBL = MAX( WRKBL, 3*N+2*N*
- $ ILAENV( 1, 'DGEBRD', ' ', N, N, -1, -1 ) )
- WRKBL = MAX( WRKBL, 3*N+N*
- $ ILAENV( 1, 'DORGBR', 'Q', N, N, N, -1 ) )
- WRKBL = MAX( WRKBL, 3*N+( N-1 )*
- $ ILAENV( 1, 'DORGBR', 'P', N, N, N, -1 ) )
- WRKBL = MAX( WRKBL, BDSPAC )
- MAXWRK = 2*N*N + WRKBL
- MINWRK = MAX( 3*N+M, BDSPAC )
- ELSE IF( WNTUS .AND. WNTVAS ) THEN
-*
-* Path 6 (M much larger than N, JOBU='S', JOBVT='S' or
-* 'A')
-*
- WRKBL = N + N*ILAENV( 1, 'DGEQRF', ' ', M, N, -1, -1 )
- WRKBL = MAX( WRKBL, N+N*ILAENV( 1, 'DORGQR', ' ', M,
- $ N, N, -1 ) )
- WRKBL = MAX( WRKBL, 3*N+2*N*
- $ ILAENV( 1, 'DGEBRD', ' ', N, N, -1, -1 ) )
- WRKBL = MAX( WRKBL, 3*N+N*
- $ ILAENV( 1, 'DORGBR', 'Q', N, N, N, -1 ) )
- WRKBL = MAX( WRKBL, 3*N+( N-1 )*
- $ ILAENV( 1, 'DORGBR', 'P', N, N, N, -1 ) )
- WRKBL = MAX( WRKBL, BDSPAC )
- MAXWRK = N*N + WRKBL
- MINWRK = MAX( 3*N+M, BDSPAC )
- ELSE IF( WNTUA .AND. WNTVN ) THEN
-*
-* Path 7 (M much larger than N, JOBU='A', JOBVT='N')
-*
- WRKBL = N + N*ILAENV( 1, 'DGEQRF', ' ', M, N, -1, -1 )
- WRKBL = MAX( WRKBL, N+M*ILAENV( 1, 'DORGQR', ' ', M,
- $ M, N, -1 ) )
- WRKBL = MAX( WRKBL, 3*N+2*N*
- $ ILAENV( 1, 'DGEBRD', ' ', N, N, -1, -1 ) )
- WRKBL = MAX( WRKBL, 3*N+N*
- $ ILAENV( 1, 'DORGBR', 'Q', N, N, N, -1 ) )
- WRKBL = MAX( WRKBL, BDSPAC )
- MAXWRK = N*N + WRKBL
- MINWRK = MAX( 3*N+M, BDSPAC )
- ELSE IF( WNTUA .AND. WNTVO ) THEN
-*
-* Path 8 (M much larger than N, JOBU='A', JOBVT='O')
-*
- WRKBL = N + N*ILAENV( 1, 'DGEQRF', ' ', M, N, -1, -1 )
- WRKBL = MAX( WRKBL, N+M*ILAENV( 1, 'DORGQR', ' ', M,
- $ M, N, -1 ) )
- WRKBL = MAX( WRKBL, 3*N+2*N*
- $ ILAENV( 1, 'DGEBRD', ' ', N, N, -1, -1 ) )
- WRKBL = MAX( WRKBL, 3*N+N*
- $ ILAENV( 1, 'DORGBR', 'Q', N, N, N, -1 ) )
- WRKBL = MAX( WRKBL, 3*N+( N-1 )*
- $ ILAENV( 1, 'DORGBR', 'P', N, N, N, -1 ) )
- WRKBL = MAX( WRKBL, BDSPAC )
- MAXWRK = 2*N*N + WRKBL
- MINWRK = MAX( 3*N+M, BDSPAC )
- ELSE IF( WNTUA .AND. WNTVAS ) THEN
-*
-* Path 9 (M much larger than N, JOBU='A', JOBVT='S' or
-* 'A')
-*
- WRKBL = N + N*ILAENV( 1, 'DGEQRF', ' ', M, N, -1, -1 )
- WRKBL = MAX( WRKBL, N+M*ILAENV( 1, 'DORGQR', ' ', M,
- $ M, N, -1 ) )
- WRKBL = MAX( WRKBL, 3*N+2*N*
- $ ILAENV( 1, 'DGEBRD', ' ', N, N, -1, -1 ) )
- WRKBL = MAX( WRKBL, 3*N+N*
- $ ILAENV( 1, 'DORGBR', 'Q', N, N, N, -1 ) )
- WRKBL = MAX( WRKBL, 3*N+( N-1 )*
- $ ILAENV( 1, 'DORGBR', 'P', N, N, N, -1 ) )
- WRKBL = MAX( WRKBL, BDSPAC )
- MAXWRK = N*N + WRKBL
- MINWRK = MAX( 3*N+M, BDSPAC )
- END IF
- ELSE
-*
-* Path 10 (M at least N, but not much larger)
-*
- MAXWRK = 3*N + ( M+N )*ILAENV( 1, 'DGEBRD', ' ', M, N,
- $ -1, -1 )
- IF( WNTUS .OR. WNTUO )
- $ MAXWRK = MAX( MAXWRK, 3*N+N*
- $ ILAENV( 1, 'DORGBR', 'Q', M, N, N, -1 ) )
- IF( WNTUA )
- $ MAXWRK = MAX( MAXWRK, 3*N+M*
- $ ILAENV( 1, 'DORGBR', 'Q', M, M, N, -1 ) )
- IF( .NOT.WNTVN )
- $ MAXWRK = MAX( MAXWRK, 3*N+( N-1 )*
- $ ILAENV( 1, 'DORGBR', 'P', N, N, N, -1 ) )
- MAXWRK = MAX( MAXWRK, BDSPAC )
- MINWRK = MAX( 3*N+M, BDSPAC )
- END IF
- ELSE IF( MINMN.GT.0 ) THEN
-*
-* Compute space needed for DBDSQR
-*
- MNTHR = ILAENV( 6, 'DGESVD', JOBU // JOBVT, M, N, 0, 0 )
- BDSPAC = 5*M
- IF( N.GE.MNTHR ) THEN
- IF( WNTVN ) THEN
-*
-* Path 1t(N much larger than M, JOBVT='N')
-*
- MAXWRK = M + M*ILAENV( 1, 'DGELQF', ' ', M, N, -1,
- $ -1 )
- MAXWRK = MAX( MAXWRK, 3*M+2*M*
- $ ILAENV( 1, 'DGEBRD', ' ', M, M, -1, -1 ) )
- IF( WNTUO .OR. WNTUAS )
- $ MAXWRK = MAX( MAXWRK, 3*M+M*
- $ ILAENV( 1, 'DORGBR', 'Q', M, M, M, -1 ) )
- MAXWRK = MAX( MAXWRK, BDSPAC )
- MINWRK = MAX( 4*M, BDSPAC )
- ELSE IF( WNTVO .AND. WNTUN ) THEN
-*
-* Path 2t(N much larger than M, JOBU='N', JOBVT='O')
-*
- WRKBL = M + M*ILAENV( 1, 'DGELQF', ' ', M, N, -1, -1 )
- WRKBL = MAX( WRKBL, M+M*ILAENV( 1, 'DORGLQ', ' ', M,
- $ N, M, -1 ) )
- WRKBL = MAX( WRKBL, 3*M+2*M*
- $ ILAENV( 1, 'DGEBRD', ' ', M, M, -1, -1 ) )
- WRKBL = MAX( WRKBL, 3*M+( M-1 )*
- $ ILAENV( 1, 'DORGBR', 'P', M, M, M, -1 ) )
- WRKBL = MAX( WRKBL, BDSPAC )
- MAXWRK = MAX( M*M+WRKBL, M*M+M*N+M )
- MINWRK = MAX( 3*M+N, BDSPAC )
- ELSE IF( WNTVO .AND. WNTUAS ) THEN
-*
-* Path 3t(N much larger than M, JOBU='S' or 'A',
-* JOBVT='O')
-*
- WRKBL = M + M*ILAENV( 1, 'DGELQF', ' ', M, N, -1, -1 )
- WRKBL = MAX( WRKBL, M+M*ILAENV( 1, 'DORGLQ', ' ', M,
- $ N, M, -1 ) )
- WRKBL = MAX( WRKBL, 3*M+2*M*
- $ ILAENV( 1, 'DGEBRD', ' ', M, M, -1, -1 ) )
- WRKBL = MAX( WRKBL, 3*M+( M-1 )*
- $ ILAENV( 1, 'DORGBR', 'P', M, M, M, -1 ) )
- WRKBL = MAX( WRKBL, 3*M+M*
- $ ILAENV( 1, 'DORGBR', 'Q', M, M, M, -1 ) )
- WRKBL = MAX( WRKBL, BDSPAC )
- MAXWRK = MAX( M*M+WRKBL, M*M+M*N+M )
- MINWRK = MAX( 3*M+N, BDSPAC )
- ELSE IF( WNTVS .AND. WNTUN ) THEN
-*
-* Path 4t(N much larger than M, JOBU='N', JOBVT='S')
-*
- WRKBL = M + M*ILAENV( 1, 'DGELQF', ' ', M, N, -1, -1 )
- WRKBL = MAX( WRKBL, M+M*ILAENV( 1, 'DORGLQ', ' ', M,
- $ N, M, -1 ) )
- WRKBL = MAX( WRKBL, 3*M+2*M*
- $ ILAENV( 1, 'DGEBRD', ' ', M, M, -1, -1 ) )
- WRKBL = MAX( WRKBL, 3*M+( M-1 )*
- $ ILAENV( 1, 'DORGBR', 'P', M, M, M, -1 ) )
- WRKBL = MAX( WRKBL, BDSPAC )
- MAXWRK = M*M + WRKBL
- MINWRK = MAX( 3*M+N, BDSPAC )
- ELSE IF( WNTVS .AND. WNTUO ) THEN
-*
-* Path 5t(N much larger than M, JOBU='O', JOBVT='S')
-*
- WRKBL = M + M*ILAENV( 1, 'DGELQF', ' ', M, N, -1, -1 )
- WRKBL = MAX( WRKBL, M+M*ILAENV( 1, 'DORGLQ', ' ', M,
- $ N, M, -1 ) )
- WRKBL = MAX( WRKBL, 3*M+2*M*
- $ ILAENV( 1, 'DGEBRD', ' ', M, M, -1, -1 ) )
- WRKBL = MAX( WRKBL, 3*M+( M-1 )*
- $ ILAENV( 1, 'DORGBR', 'P', M, M, M, -1 ) )
- WRKBL = MAX( WRKBL, 3*M+M*
- $ ILAENV( 1, 'DORGBR', 'Q', M, M, M, -1 ) )
- WRKBL = MAX( WRKBL, BDSPAC )
- MAXWRK = 2*M*M + WRKBL
- MINWRK = MAX( 3*M+N, BDSPAC )
- ELSE IF( WNTVS .AND. WNTUAS ) THEN
-*
-* Path 6t(N much larger than M, JOBU='S' or 'A',
-* JOBVT='S')
-*
- WRKBL = M + M*ILAENV( 1, 'DGELQF', ' ', M, N, -1, -1 )
- WRKBL = MAX( WRKBL, M+M*ILAENV( 1, 'DORGLQ', ' ', M,
- $ N, M, -1 ) )
- WRKBL = MAX( WRKBL, 3*M+2*M*
- $ ILAENV( 1, 'DGEBRD', ' ', M, M, -1, -1 ) )
- WRKBL = MAX( WRKBL, 3*M+( M-1 )*
- $ ILAENV( 1, 'DORGBR', 'P', M, M, M, -1 ) )
- WRKBL = MAX( WRKBL, 3*M+M*
- $ ILAENV( 1, 'DORGBR', 'Q', M, M, M, -1 ) )
- WRKBL = MAX( WRKBL, BDSPAC )
- MAXWRK = M*M + WRKBL
- MINWRK = MAX( 3*M+N, BDSPAC )
- ELSE IF( WNTVA .AND. WNTUN ) THEN
-*
-* Path 7t(N much larger than M, JOBU='N', JOBVT='A')
-*
- WRKBL = M + M*ILAENV( 1, 'DGELQF', ' ', M, N, -1, -1 )
- WRKBL = MAX( WRKBL, M+N*ILAENV( 1, 'DORGLQ', ' ', N,
- $ N, M, -1 ) )
- WRKBL = MAX( WRKBL, 3*M+2*M*
- $ ILAENV( 1, 'DGEBRD', ' ', M, M, -1, -1 ) )
- WRKBL = MAX( WRKBL, 3*M+( M-1 )*
- $ ILAENV( 1, 'DORGBR', 'P', M, M, M, -1 ) )
- WRKBL = MAX( WRKBL, BDSPAC )
- MAXWRK = M*M + WRKBL
- MINWRK = MAX( 3*M+N, BDSPAC )
- ELSE IF( WNTVA .AND. WNTUO ) THEN
-*
-* Path 8t(N much larger than M, JOBU='O', JOBVT='A')
-*
- WRKBL = M + M*ILAENV( 1, 'DGELQF', ' ', M, N, -1, -1 )
- WRKBL = MAX( WRKBL, M+N*ILAENV( 1, 'DORGLQ', ' ', N,
- $ N, M, -1 ) )
- WRKBL = MAX( WRKBL, 3*M+2*M*
- $ ILAENV( 1, 'DGEBRD', ' ', M, M, -1, -1 ) )
- WRKBL = MAX( WRKBL, 3*M+( M-1 )*
- $ ILAENV( 1, 'DORGBR', 'P', M, M, M, -1 ) )
- WRKBL = MAX( WRKBL, 3*M+M*
- $ ILAENV( 1, 'DORGBR', 'Q', M, M, M, -1 ) )
- WRKBL = MAX( WRKBL, BDSPAC )
- MAXWRK = 2*M*M + WRKBL
- MINWRK = MAX( 3*M+N, BDSPAC )
- ELSE IF( WNTVA .AND. WNTUAS ) THEN
-*
-* Path 9t(N much larger than M, JOBU='S' or 'A',
-* JOBVT='A')
-*
- WRKBL = M + M*ILAENV( 1, 'DGELQF', ' ', M, N, -1, -1 )
- WRKBL = MAX( WRKBL, M+N*ILAENV( 1, 'DORGLQ', ' ', N,
- $ N, M, -1 ) )
- WRKBL = MAX( WRKBL, 3*M+2*M*
- $ ILAENV( 1, 'DGEBRD', ' ', M, M, -1, -1 ) )
- WRKBL = MAX( WRKBL, 3*M+( M-1 )*
- $ ILAENV( 1, 'DORGBR', 'P', M, M, M, -1 ) )
- WRKBL = MAX( WRKBL, 3*M+M*
- $ ILAENV( 1, 'DORGBR', 'Q', M, M, M, -1 ) )
- WRKBL = MAX( WRKBL, BDSPAC )
- MAXWRK = M*M + WRKBL
- MINWRK = MAX( 3*M+N, BDSPAC )
- END IF
- ELSE
-*
-* Path 10t(N greater than M, but not much larger)
-*
- MAXWRK = 3*M + ( M+N )*ILAENV( 1, 'DGEBRD', ' ', M, N,
- $ -1, -1 )
- IF( WNTVS .OR. WNTVO )
- $ MAXWRK = MAX( MAXWRK, 3*M+M*
- $ ILAENV( 1, 'DORGBR', 'P', M, N, M, -1 ) )
- IF( WNTVA )
- $ MAXWRK = MAX( MAXWRK, 3*M+N*
- $ ILAENV( 1, 'DORGBR', 'P', N, N, M, -1 ) )
- IF( .NOT.WNTUN )
- $ MAXWRK = MAX( MAXWRK, 3*M+( M-1 )*
- $ ILAENV( 1, 'DORGBR', 'Q', M, M, M, -1 ) )
- MAXWRK = MAX( MAXWRK, BDSPAC )
- MINWRK = MAX( 3*M+N, BDSPAC )
- END IF
- END IF
- MAXWRK = MAX( MAXWRK, MINWRK )
- WORK( 1 ) = MAXWRK
-*
- IF( LWORK.LT.MINWRK .AND. .NOT.LQUERY ) THEN
- INFO = -13
- END IF
- END IF
-*
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'DGESVD', -INFO )
- RETURN
- ELSE IF( LQUERY ) THEN
- RETURN
- END IF
-*
-* Quick return if possible
-*
- IF( M.EQ.0 .OR. N.EQ.0 ) THEN
- RETURN
- END IF
-*
-* Get machine constants
-*
- EPS = DLAMCH( 'P' )
- SMLNUM = SQRT( DLAMCH( 'S' ) ) / EPS
- BIGNUM = ONE / SMLNUM
-*
-* Scale A if max element outside range [SMLNUM,BIGNUM]
-*
- ANRM = DLANGE( 'M', M, N, A, LDA, DUM )
- ISCL = 0
- IF( ANRM.GT.ZERO .AND. ANRM.LT.SMLNUM ) THEN
- ISCL = 1
- CALL DLASCL( 'G', 0, 0, ANRM, SMLNUM, M, N, A, LDA, IERR )
- ELSE IF( ANRM.GT.BIGNUM ) THEN
- ISCL = 1
- CALL DLASCL( 'G', 0, 0, ANRM, BIGNUM, M, N, A, LDA, IERR )
- END IF
-*
- IF( M.GE.N ) THEN
-*
-* A has at least as many rows as columns. If A has sufficiently
-* more rows than columns, first reduce using the QR
-* decomposition (if sufficient workspace available)
-*
- IF( M.GE.MNTHR ) THEN
-*
- IF( WNTUN ) THEN
-*
-* Path 1 (M much larger than N, JOBU='N')
-* No left singular vectors to be computed
-*
- ITAU = 1
- IWORK = ITAU + N
-*
-* Compute A=Q*R
-* (Workspace: need 2*N, prefer N+N*NB)
-*
- CALL DGEQRF( M, N, A, LDA, WORK( ITAU ), WORK( IWORK ),
- $ LWORK-IWORK+1, IERR )
-*
-* Zero out below R
-*
- CALL DLASET( 'L', N-1, N-1, ZERO, ZERO, A( 2, 1 ), LDA )
- IE = 1
- ITAUQ = IE + N
- ITAUP = ITAUQ + N
- IWORK = ITAUP + N
-*
-* Bidiagonalize R in A
-* (Workspace: need 4*N, prefer 3*N+2*N*NB)
-*
- CALL DGEBRD( N, N, A, LDA, S, WORK( IE ), WORK( ITAUQ ),
- $ WORK( ITAUP ), WORK( IWORK ), LWORK-IWORK+1,
- $ IERR )
- NCVT = 0
- IF( WNTVO .OR. WNTVAS ) THEN
-*
-* If right singular vectors desired, generate P'.
-* (Workspace: need 4*N-1, prefer 3*N+(N-1)*NB)
-*
- CALL DORGBR( 'P', N, N, N, A, LDA, WORK( ITAUP ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
- NCVT = N
- END IF
- IWORK = IE + N
-*
-* Perform bidiagonal QR iteration, computing right
-* singular vectors of A in A if desired
-* (Workspace: need BDSPAC)
-*
- CALL DBDSQR( 'U', N, NCVT, 0, 0, S, WORK( IE ), A, LDA,
- $ DUM, 1, DUM, 1, WORK( IWORK ), INFO )
-*
-* If right singular vectors desired in VT, copy them there
-*
- IF( WNTVAS )
- $ CALL DLACPY( 'F', N, N, A, LDA, VT, LDVT )
-*
- ELSE IF( WNTUO .AND. WNTVN ) THEN
-*
-* Path 2 (M much larger than N, JOBU='O', JOBVT='N')
-* N left singular vectors to be overwritten on A and
-* no right singular vectors to be computed
-*
- IF( LWORK.GE.N*N+MAX( 4*N, BDSPAC ) ) THEN
-*
-* Sufficient workspace for a fast algorithm
-*
- IR = 1
- IF( LWORK.GE.MAX( WRKBL, LDA*N+N )+LDA*N ) THEN
-*
-* WORK(IU) is LDA by N, WORK(IR) is LDA by N
-*
- LDWRKU = LDA
- LDWRKR = LDA
- ELSE IF( LWORK.GE.MAX( WRKBL, LDA*N+N )+N*N ) THEN
-*
-* WORK(IU) is LDA by N, WORK(IR) is N by N
-*
- LDWRKU = LDA
- LDWRKR = N
- ELSE
-*
-* WORK(IU) is LDWRKU by N, WORK(IR) is N by N
-*
- LDWRKU = ( LWORK-N*N-N ) / N
- LDWRKR = N
- END IF
- ITAU = IR + LDWRKR*N
- IWORK = ITAU + N
-*
-* Compute A=Q*R
-* (Workspace: need N*N+2*N, prefer N*N+N+N*NB)
-*
- CALL DGEQRF( M, N, A, LDA, WORK( ITAU ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
-*
-* Copy R to WORK(IR) and zero out below it
-*
- CALL DLACPY( 'U', N, N, A, LDA, WORK( IR ), LDWRKR )
- CALL DLASET( 'L', N-1, N-1, ZERO, ZERO, WORK( IR+1 ),
- $ LDWRKR )
-*
-* Generate Q in A
-* (Workspace: need N*N+2*N, prefer N*N+N+N*NB)
-*
- CALL DORGQR( M, N, N, A, LDA, WORK( ITAU ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
- IE = ITAU
- ITAUQ = IE + N
- ITAUP = ITAUQ + N
- IWORK = ITAUP + N
-*
-* Bidiagonalize R in WORK(IR)
-* (Workspace: need N*N+4*N, prefer N*N+3*N+2*N*NB)
-*
- CALL DGEBRD( N, N, WORK( IR ), LDWRKR, S, WORK( IE ),
- $ WORK( ITAUQ ), WORK( ITAUP ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
-*
-* Generate left vectors bidiagonalizing R
-* (Workspace: need N*N+4*N, prefer N*N+3*N+N*NB)
-*
- CALL DORGBR( 'Q', N, N, N, WORK( IR ), LDWRKR,
- $ WORK( ITAUQ ), WORK( IWORK ),
- $ LWORK-IWORK+1, IERR )
- IWORK = IE + N
-*
-* Perform bidiagonal QR iteration, computing left
-* singular vectors of R in WORK(IR)
-* (Workspace: need N*N+BDSPAC)
-*
- CALL DBDSQR( 'U', N, 0, N, 0, S, WORK( IE ), DUM, 1,
- $ WORK( IR ), LDWRKR, DUM, 1,
- $ WORK( IWORK ), INFO )
- IU = IE + N
-*
-* Multiply Q in A by left singular vectors of R in
-* WORK(IR), storing result in WORK(IU) and copying to A
-* (Workspace: need N*N+2*N, prefer N*N+M*N+N)
-*
- DO 10 I = 1, M, LDWRKU
- CHUNK = MIN( M-I+1, LDWRKU )
- CALL DGEMM( 'N', 'N', CHUNK, N, N, ONE, A( I, 1 ),
- $ LDA, WORK( IR ), LDWRKR, ZERO,
- $ WORK( IU ), LDWRKU )
- CALL DLACPY( 'F', CHUNK, N, WORK( IU ), LDWRKU,
- $ A( I, 1 ), LDA )
- 10 CONTINUE
-*
- ELSE
-*
-* Insufficient workspace for a fast algorithm
-*
- IE = 1
- ITAUQ = IE + N
- ITAUP = ITAUQ + N
- IWORK = ITAUP + N
-*
-* Bidiagonalize A
-* (Workspace: need 3*N+M, prefer 3*N+(M+N)*NB)
-*
- CALL DGEBRD( M, N, A, LDA, S, WORK( IE ),
- $ WORK( ITAUQ ), WORK( ITAUP ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
-*
-* Generate left vectors bidiagonalizing A
-* (Workspace: need 4*N, prefer 3*N+N*NB)
-*
- CALL DORGBR( 'Q', M, N, N, A, LDA, WORK( ITAUQ ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
- IWORK = IE + N
-*
-* Perform bidiagonal QR iteration, computing left
-* singular vectors of A in A
-* (Workspace: need BDSPAC)
-*
- CALL DBDSQR( 'U', N, 0, M, 0, S, WORK( IE ), DUM, 1,
- $ A, LDA, DUM, 1, WORK( IWORK ), INFO )
-*
- END IF
-*
- ELSE IF( WNTUO .AND. WNTVAS ) THEN
-*
-* Path 3 (M much larger than N, JOBU='O', JOBVT='S' or 'A')
-* N left singular vectors to be overwritten on A and
-* N right singular vectors to be computed in VT
-*
- IF( LWORK.GE.N*N+MAX( 4*N, BDSPAC ) ) THEN
-*
-* Sufficient workspace for a fast algorithm
-*
- IR = 1
- IF( LWORK.GE.MAX( WRKBL, LDA*N+N )+LDA*N ) THEN
-*
-* WORK(IU) is LDA by N and WORK(IR) is LDA by N
-*
- LDWRKU = LDA
- LDWRKR = LDA
- ELSE IF( LWORK.GE.MAX( WRKBL, LDA*N+N )+N*N ) THEN
-*
-* WORK(IU) is LDA by N and WORK(IR) is N by N
-*
- LDWRKU = LDA
- LDWRKR = N
- ELSE
-*
-* WORK(IU) is LDWRKU by N and WORK(IR) is N by N
-*
- LDWRKU = ( LWORK-N*N-N ) / N
- LDWRKR = N
- END IF
- ITAU = IR + LDWRKR*N
- IWORK = ITAU + N
-*
-* Compute A=Q*R
-* (Workspace: need N*N+2*N, prefer N*N+N+N*NB)
-*
- CALL DGEQRF( M, N, A, LDA, WORK( ITAU ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
-*
-* Copy R to VT, zeroing out below it
-*
- CALL DLACPY( 'U', N, N, A, LDA, VT, LDVT )
- IF( N.GT.1 )
- $ CALL DLASET( 'L', N-1, N-1, ZERO, ZERO,
- $ VT( 2, 1 ), LDVT )
-*
-* Generate Q in A
-* (Workspace: need N*N+2*N, prefer N*N+N+N*NB)
-*
- CALL DORGQR( M, N, N, A, LDA, WORK( ITAU ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
- IE = ITAU
- ITAUQ = IE + N
- ITAUP = ITAUQ + N
- IWORK = ITAUP + N
-*
-* Bidiagonalize R in VT, copying result to WORK(IR)
-* (Workspace: need N*N+4*N, prefer N*N+3*N+2*N*NB)
-*
- CALL DGEBRD( N, N, VT, LDVT, S, WORK( IE ),
- $ WORK( ITAUQ ), WORK( ITAUP ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
- CALL DLACPY( 'L', N, N, VT, LDVT, WORK( IR ), LDWRKR )
-*
-* Generate left vectors bidiagonalizing R in WORK(IR)
-* (Workspace: need N*N+4*N, prefer N*N+3*N+N*NB)
-*
- CALL DORGBR( 'Q', N, N, N, WORK( IR ), LDWRKR,
- $ WORK( ITAUQ ), WORK( IWORK ),
- $ LWORK-IWORK+1, IERR )
-*
-* Generate right vectors bidiagonalizing R in VT
-* (Workspace: need N*N+4*N-1, prefer N*N+3*N+(N-1)*NB)
-*
- CALL DORGBR( 'P', N, N, N, VT, LDVT, WORK( ITAUP ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
- IWORK = IE + N
-*
-* Perform bidiagonal QR iteration, computing left
-* singular vectors of R in WORK(IR) and computing right
-* singular vectors of R in VT
-* (Workspace: need N*N+BDSPAC)
-*
- CALL DBDSQR( 'U', N, N, N, 0, S, WORK( IE ), VT, LDVT,
- $ WORK( IR ), LDWRKR, DUM, 1,
- $ WORK( IWORK ), INFO )
- IU = IE + N
-*
-* Multiply Q in A by left singular vectors of R in
-* WORK(IR), storing result in WORK(IU) and copying to A
-* (Workspace: need N*N+2*N, prefer N*N+M*N+N)
-*
- DO 20 I = 1, M, LDWRKU
- CHUNK = MIN( M-I+1, LDWRKU )
- CALL DGEMM( 'N', 'N', CHUNK, N, N, ONE, A( I, 1 ),
- $ LDA, WORK( IR ), LDWRKR, ZERO,
- $ WORK( IU ), LDWRKU )
- CALL DLACPY( 'F', CHUNK, N, WORK( IU ), LDWRKU,
- $ A( I, 1 ), LDA )
- 20 CONTINUE
-*
- ELSE
-*
-* Insufficient workspace for a fast algorithm
-*
- ITAU = 1
- IWORK = ITAU + N
-*
-* Compute A=Q*R
-* (Workspace: need 2*N, prefer N+N*NB)
-*
- CALL DGEQRF( M, N, A, LDA, WORK( ITAU ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
-*
-* Copy R to VT, zeroing out below it
-*
- CALL DLACPY( 'U', N, N, A, LDA, VT, LDVT )
- IF( N.GT.1 )
- $ CALL DLASET( 'L', N-1, N-1, ZERO, ZERO,
- $ VT( 2, 1 ), LDVT )
-*
-* Generate Q in A
-* (Workspace: need 2*N, prefer N+N*NB)
-*
- CALL DORGQR( M, N, N, A, LDA, WORK( ITAU ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
- IE = ITAU
- ITAUQ = IE + N
- ITAUP = ITAUQ + N
- IWORK = ITAUP + N
-*
-* Bidiagonalize R in VT
-* (Workspace: need 4*N, prefer 3*N+2*N*NB)
-*
- CALL DGEBRD( N, N, VT, LDVT, S, WORK( IE ),
- $ WORK( ITAUQ ), WORK( ITAUP ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
-*
-* Multiply Q in A by left vectors bidiagonalizing R
-* (Workspace: need 3*N+M, prefer 3*N+M*NB)
-*
- CALL DORMBR( 'Q', 'R', 'N', M, N, N, VT, LDVT,
- $ WORK( ITAUQ ), A, LDA, WORK( IWORK ),
- $ LWORK-IWORK+1, IERR )
-*
-* Generate right vectors bidiagonalizing R in VT
-* (Workspace: need 4*N-1, prefer 3*N+(N-1)*NB)
-*
- CALL DORGBR( 'P', N, N, N, VT, LDVT, WORK( ITAUP ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
- IWORK = IE + N
-*
-* Perform bidiagonal QR iteration, computing left
-* singular vectors of A in A and computing right
-* singular vectors of A in VT
-* (Workspace: need BDSPAC)
-*
- CALL DBDSQR( 'U', N, N, M, 0, S, WORK( IE ), VT, LDVT,
- $ A, LDA, DUM, 1, WORK( IWORK ), INFO )
-*
- END IF
-*
- ELSE IF( WNTUS ) THEN
-*
- IF( WNTVN ) THEN
-*
-* Path 4 (M much larger than N, JOBU='S', JOBVT='N')
-* N left singular vectors to be computed in U and
-* no right singular vectors to be computed
-*
- IF( LWORK.GE.N*N+MAX( 4*N, BDSPAC ) ) THEN
-*
-* Sufficient workspace for a fast algorithm
-*
- IR = 1
- IF( LWORK.GE.WRKBL+LDA*N ) THEN
-*
-* WORK(IR) is LDA by N
-*
- LDWRKR = LDA
- ELSE
-*
-* WORK(IR) is N by N
-*
- LDWRKR = N
- END IF
- ITAU = IR + LDWRKR*N
- IWORK = ITAU + N
-*
-* Compute A=Q*R
-* (Workspace: need N*N+2*N, prefer N*N+N+N*NB)
-*
- CALL DGEQRF( M, N, A, LDA, WORK( ITAU ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
-*
-* Copy R to WORK(IR), zeroing out below it
-*
- CALL DLACPY( 'U', N, N, A, LDA, WORK( IR ),
- $ LDWRKR )
- CALL DLASET( 'L', N-1, N-1, ZERO, ZERO,
- $ WORK( IR+1 ), LDWRKR )
-*
-* Generate Q in A
-* (Workspace: need N*N+2*N, prefer N*N+N+N*NB)
-*
- CALL DORGQR( M, N, N, A, LDA, WORK( ITAU ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
- IE = ITAU
- ITAUQ = IE + N
- ITAUP = ITAUQ + N
- IWORK = ITAUP + N
-*
-* Bidiagonalize R in WORK(IR)
-* (Workspace: need N*N+4*N, prefer N*N+3*N+2*N*NB)
-*
- CALL DGEBRD( N, N, WORK( IR ), LDWRKR, S,
- $ WORK( IE ), WORK( ITAUQ ),
- $ WORK( ITAUP ), WORK( IWORK ),
- $ LWORK-IWORK+1, IERR )
-*
-* Generate left vectors bidiagonalizing R in WORK(IR)
-* (Workspace: need N*N+4*N, prefer N*N+3*N+N*NB)
-*
- CALL DORGBR( 'Q', N, N, N, WORK( IR ), LDWRKR,
- $ WORK( ITAUQ ), WORK( IWORK ),
- $ LWORK-IWORK+1, IERR )
- IWORK = IE + N
-*
-* Perform bidiagonal QR iteration, computing left
-* singular vectors of R in WORK(IR)
-* (Workspace: need N*N+BDSPAC)
-*
- CALL DBDSQR( 'U', N, 0, N, 0, S, WORK( IE ), DUM,
- $ 1, WORK( IR ), LDWRKR, DUM, 1,
- $ WORK( IWORK ), INFO )
-*
-* Multiply Q in A by left singular vectors of R in
-* WORK(IR), storing result in U
-* (Workspace: need N*N)
-*
- CALL DGEMM( 'N', 'N', M, N, N, ONE, A, LDA,
- $ WORK( IR ), LDWRKR, ZERO, U, LDU )
-*
- ELSE
-*
-* Insufficient workspace for a fast algorithm
-*
- ITAU = 1
- IWORK = ITAU + N
-*
-* Compute A=Q*R, copying result to U
-* (Workspace: need 2*N, prefer N+N*NB)
-*
- CALL DGEQRF( M, N, A, LDA, WORK( ITAU ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
- CALL DLACPY( 'L', M, N, A, LDA, U, LDU )
-*
-* Generate Q in U
-* (Workspace: need 2*N, prefer N+N*NB)
-*
- CALL DORGQR( M, N, N, U, LDU, WORK( ITAU ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
- IE = ITAU
- ITAUQ = IE + N
- ITAUP = ITAUQ + N
- IWORK = ITAUP + N
-*
-* Zero out below R in A
-*
- CALL DLASET( 'L', N-1, N-1, ZERO, ZERO, A( 2, 1 ),
- $ LDA )
-*
-* Bidiagonalize R in A
-* (Workspace: need 4*N, prefer 3*N+2*N*NB)
-*
- CALL DGEBRD( N, N, A, LDA, S, WORK( IE ),
- $ WORK( ITAUQ ), WORK( ITAUP ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
-*
-* Multiply Q in U by left vectors bidiagonalizing R
-* (Workspace: need 3*N+M, prefer 3*N+M*NB)
-*
- CALL DORMBR( 'Q', 'R', 'N', M, N, N, A, LDA,
- $ WORK( ITAUQ ), U, LDU, WORK( IWORK ),
- $ LWORK-IWORK+1, IERR )
- IWORK = IE + N
-*
-* Perform bidiagonal QR iteration, computing left
-* singular vectors of A in U
-* (Workspace: need BDSPAC)
-*
- CALL DBDSQR( 'U', N, 0, M, 0, S, WORK( IE ), DUM,
- $ 1, U, LDU, DUM, 1, WORK( IWORK ),
- $ INFO )
-*
- END IF
-*
- ELSE IF( WNTVO ) THEN
-*
-* Path 5 (M much larger than N, JOBU='S', JOBVT='O')
-* N left singular vectors to be computed in U and
-* N right singular vectors to be overwritten on A
-*
- IF( LWORK.GE.2*N*N+MAX( 4*N, BDSPAC ) ) THEN
-*
-* Sufficient workspace for a fast algorithm
-*
- IU = 1
- IF( LWORK.GE.WRKBL+2*LDA*N ) THEN
-*
-* WORK(IU) is LDA by N and WORK(IR) is LDA by N
-*
- LDWRKU = LDA
- IR = IU + LDWRKU*N
- LDWRKR = LDA
- ELSE IF( LWORK.GE.WRKBL+( LDA+N )*N ) THEN
-*
-* WORK(IU) is LDA by N and WORK(IR) is N by N
-*
- LDWRKU = LDA
- IR = IU + LDWRKU*N
- LDWRKR = N
- ELSE
-*
-* WORK(IU) is N by N and WORK(IR) is N by N
-*
- LDWRKU = N
- IR = IU + LDWRKU*N
- LDWRKR = N
- END IF
- ITAU = IR + LDWRKR*N
- IWORK = ITAU + N
-*
-* Compute A=Q*R
-* (Workspace: need 2*N*N+2*N, prefer 2*N*N+N+N*NB)
-*
- CALL DGEQRF( M, N, A, LDA, WORK( ITAU ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
-*
-* Copy R to WORK(IU), zeroing out below it
-*
- CALL DLACPY( 'U', N, N, A, LDA, WORK( IU ),
- $ LDWRKU )
- CALL DLASET( 'L', N-1, N-1, ZERO, ZERO,
- $ WORK( IU+1 ), LDWRKU )
-*
-* Generate Q in A
-* (Workspace: need 2*N*N+2*N, prefer 2*N*N+N+N*NB)
-*
- CALL DORGQR( M, N, N, A, LDA, WORK( ITAU ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
- IE = ITAU
- ITAUQ = IE + N
- ITAUP = ITAUQ + N
- IWORK = ITAUP + N
-*
-* Bidiagonalize R in WORK(IU), copying result to
-* WORK(IR)
-* (Workspace: need 2*N*N+4*N,
-* prefer 2*N*N+3*N+2*N*NB)
-*
- CALL DGEBRD( N, N, WORK( IU ), LDWRKU, S,
- $ WORK( IE ), WORK( ITAUQ ),
- $ WORK( ITAUP ), WORK( IWORK ),
- $ LWORK-IWORK+1, IERR )
- CALL DLACPY( 'U', N, N, WORK( IU ), LDWRKU,
- $ WORK( IR ), LDWRKR )
-*
-* Generate left bidiagonalizing vectors in WORK(IU)
-* (Workspace: need 2*N*N+4*N, prefer 2*N*N+3*N+N*NB)
-*
- CALL DORGBR( 'Q', N, N, N, WORK( IU ), LDWRKU,
- $ WORK( ITAUQ ), WORK( IWORK ),
- $ LWORK-IWORK+1, IERR )
-*
-* Generate right bidiagonalizing vectors in WORK(IR)
-* (Workspace: need 2*N*N+4*N-1,
-* prefer 2*N*N+3*N+(N-1)*NB)
-*
- CALL DORGBR( 'P', N, N, N, WORK( IR ), LDWRKR,
- $ WORK( ITAUP ), WORK( IWORK ),
- $ LWORK-IWORK+1, IERR )
- IWORK = IE + N
-*
-* Perform bidiagonal QR iteration, computing left
-* singular vectors of R in WORK(IU) and computing
-* right singular vectors of R in WORK(IR)
-* (Workspace: need 2*N*N+BDSPAC)
-*
- CALL DBDSQR( 'U', N, N, N, 0, S, WORK( IE ),
- $ WORK( IR ), LDWRKR, WORK( IU ),
- $ LDWRKU, DUM, 1, WORK( IWORK ), INFO )
-*
-* Multiply Q in A by left singular vectors of R in
-* WORK(IU), storing result in U
-* (Workspace: need N*N)
-*
- CALL DGEMM( 'N', 'N', M, N, N, ONE, A, LDA,
- $ WORK( IU ), LDWRKU, ZERO, U, LDU )
-*
-* Copy right singular vectors of R to A
-* (Workspace: need N*N)
-*
- CALL DLACPY( 'F', N, N, WORK( IR ), LDWRKR, A,
- $ LDA )
-*
- ELSE
-*
-* Insufficient workspace for a fast algorithm
-*
- ITAU = 1
- IWORK = ITAU + N
-*
-* Compute A=Q*R, copying result to U
-* (Workspace: need 2*N, prefer N+N*NB)
-*
- CALL DGEQRF( M, N, A, LDA, WORK( ITAU ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
- CALL DLACPY( 'L', M, N, A, LDA, U, LDU )
-*
-* Generate Q in U
-* (Workspace: need 2*N, prefer N+N*NB)
-*
- CALL DORGQR( M, N, N, U, LDU, WORK( ITAU ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
- IE = ITAU
- ITAUQ = IE + N
- ITAUP = ITAUQ + N
- IWORK = ITAUP + N
-*
-* Zero out below R in A
-*
- CALL DLASET( 'L', N-1, N-1, ZERO, ZERO, A( 2, 1 ),
- $ LDA )
-*
-* Bidiagonalize R in A
-* (Workspace: need 4*N, prefer 3*N+2*N*NB)
-*
- CALL DGEBRD( N, N, A, LDA, S, WORK( IE ),
- $ WORK( ITAUQ ), WORK( ITAUP ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
-*
-* Multiply Q in U by left vectors bidiagonalizing R
-* (Workspace: need 3*N+M, prefer 3*N+M*NB)
-*
- CALL DORMBR( 'Q', 'R', 'N', M, N, N, A, LDA,
- $ WORK( ITAUQ ), U, LDU, WORK( IWORK ),
- $ LWORK-IWORK+1, IERR )
-*
-* Generate right vectors bidiagonalizing R in A
-* (Workspace: need 4*N-1, prefer 3*N+(N-1)*NB)
-*
- CALL DORGBR( 'P', N, N, N, A, LDA, WORK( ITAUP ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
- IWORK = IE + N
-*
-* Perform bidiagonal QR iteration, computing left
-* singular vectors of A in U and computing right
-* singular vectors of A in A
-* (Workspace: need BDSPAC)
-*
- CALL DBDSQR( 'U', N, N, M, 0, S, WORK( IE ), A,
- $ LDA, U, LDU, DUM, 1, WORK( IWORK ),
- $ INFO )
-*
- END IF
-*
- ELSE IF( WNTVAS ) THEN
-*
-* Path 6 (M much larger than N, JOBU='S', JOBVT='S'
-* or 'A')
-* N left singular vectors to be computed in U and
-* N right singular vectors to be computed in VT
-*
- IF( LWORK.GE.N*N+MAX( 4*N, BDSPAC ) ) THEN
-*
-* Sufficient workspace for a fast algorithm
-*
- IU = 1
- IF( LWORK.GE.WRKBL+LDA*N ) THEN
-*
-* WORK(IU) is LDA by N
-*
- LDWRKU = LDA
- ELSE
-*
-* WORK(IU) is N by N
-*
- LDWRKU = N
- END IF
- ITAU = IU + LDWRKU*N
- IWORK = ITAU + N
-*
-* Compute A=Q*R
-* (Workspace: need N*N+2*N, prefer N*N+N+N*NB)
-*
- CALL DGEQRF( M, N, A, LDA, WORK( ITAU ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
-*
-* Copy R to WORK(IU), zeroing out below it
-*
- CALL DLACPY( 'U', N, N, A, LDA, WORK( IU ),
- $ LDWRKU )
- CALL DLASET( 'L', N-1, N-1, ZERO, ZERO,
- $ WORK( IU+1 ), LDWRKU )
-*
-* Generate Q in A
-* (Workspace: need N*N+2*N, prefer N*N+N+N*NB)
-*
- CALL DORGQR( M, N, N, A, LDA, WORK( ITAU ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
- IE = ITAU
- ITAUQ = IE + N
- ITAUP = ITAUQ + N
- IWORK = ITAUP + N
-*
-* Bidiagonalize R in WORK(IU), copying result to VT
-* (Workspace: need N*N+4*N, prefer N*N+3*N+2*N*NB)
-*
- CALL DGEBRD( N, N, WORK( IU ), LDWRKU, S,
- $ WORK( IE ), WORK( ITAUQ ),
- $ WORK( ITAUP ), WORK( IWORK ),
- $ LWORK-IWORK+1, IERR )
- CALL DLACPY( 'U', N, N, WORK( IU ), LDWRKU, VT,
- $ LDVT )
-*
-* Generate left bidiagonalizing vectors in WORK(IU)
-* (Workspace: need N*N+4*N, prefer N*N+3*N+N*NB)
-*
- CALL DORGBR( 'Q', N, N, N, WORK( IU ), LDWRKU,
- $ WORK( ITAUQ ), WORK( IWORK ),
- $ LWORK-IWORK+1, IERR )
-*
-* Generate right bidiagonalizing vectors in VT
-* (Workspace: need N*N+4*N-1,
-* prefer N*N+3*N+(N-1)*NB)
-*
- CALL DORGBR( 'P', N, N, N, VT, LDVT, WORK( ITAUP ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
- IWORK = IE + N
-*
-* Perform bidiagonal QR iteration, computing left
-* singular vectors of R in WORK(IU) and computing
-* right singular vectors of R in VT
-* (Workspace: need N*N+BDSPAC)
-*
- CALL DBDSQR( 'U', N, N, N, 0, S, WORK( IE ), VT,
- $ LDVT, WORK( IU ), LDWRKU, DUM, 1,
- $ WORK( IWORK ), INFO )
-*
-* Multiply Q in A by left singular vectors of R in
-* WORK(IU), storing result in U
-* (Workspace: need N*N)
-*
- CALL DGEMM( 'N', 'N', M, N, N, ONE, A, LDA,
- $ WORK( IU ), LDWRKU, ZERO, U, LDU )
-*
- ELSE
-*
-* Insufficient workspace for a fast algorithm
-*
- ITAU = 1
- IWORK = ITAU + N
-*
-* Compute A=Q*R, copying result to U
-* (Workspace: need 2*N, prefer N+N*NB)
-*
- CALL DGEQRF( M, N, A, LDA, WORK( ITAU ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
- CALL DLACPY( 'L', M, N, A, LDA, U, LDU )
-*
-* Generate Q in U
-* (Workspace: need 2*N, prefer N+N*NB)
-*
- CALL DORGQR( M, N, N, U, LDU, WORK( ITAU ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
-*
-* Copy R to VT, zeroing out below it
-*
- CALL DLACPY( 'U', N, N, A, LDA, VT, LDVT )
- IF( N.GT.1 )
- $ CALL DLASET( 'L', N-1, N-1, ZERO, ZERO,
- $ VT( 2, 1 ), LDVT )
- IE = ITAU
- ITAUQ = IE + N
- ITAUP = ITAUQ + N
- IWORK = ITAUP + N
-*
-* Bidiagonalize R in VT
-* (Workspace: need 4*N, prefer 3*N+2*N*NB)
-*
- CALL DGEBRD( N, N, VT, LDVT, S, WORK( IE ),
- $ WORK( ITAUQ ), WORK( ITAUP ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
-*
-* Multiply Q in U by left bidiagonalizing vectors
-* in VT
-* (Workspace: need 3*N+M, prefer 3*N+M*NB)
-*
- CALL DORMBR( 'Q', 'R', 'N', M, N, N, VT, LDVT,
- $ WORK( ITAUQ ), U, LDU, WORK( IWORK ),
- $ LWORK-IWORK+1, IERR )
-*
-* Generate right bidiagonalizing vectors in VT
-* (Workspace: need 4*N-1, prefer 3*N+(N-1)*NB)
-*
- CALL DORGBR( 'P', N, N, N, VT, LDVT, WORK( ITAUP ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
- IWORK = IE + N
-*
-* Perform bidiagonal QR iteration, computing left
-* singular vectors of A in U and computing right
-* singular vectors of A in VT
-* (Workspace: need BDSPAC)
-*
- CALL DBDSQR( 'U', N, N, M, 0, S, WORK( IE ), VT,
- $ LDVT, U, LDU, DUM, 1, WORK( IWORK ),
- $ INFO )
-*
- END IF
-*
- END IF
-*
- ELSE IF( WNTUA ) THEN
-*
- IF( WNTVN ) THEN
-*
-* Path 7 (M much larger than N, JOBU='A', JOBVT='N')
-* M left singular vectors to be computed in U and
-* no right singular vectors to be computed
-*
- IF( LWORK.GE.N*N+MAX( N+M, 4*N, BDSPAC ) ) THEN
-*
-* Sufficient workspace for a fast algorithm
-*
- IR = 1
- IF( LWORK.GE.WRKBL+LDA*N ) THEN
-*
-* WORK(IR) is LDA by N
-*
- LDWRKR = LDA
- ELSE
-*
-* WORK(IR) is N by N
-*
- LDWRKR = N
- END IF
- ITAU = IR + LDWRKR*N
- IWORK = ITAU + N
-*
-* Compute A=Q*R, copying result to U
-* (Workspace: need N*N+2*N, prefer N*N+N+N*NB)
-*
- CALL DGEQRF( M, N, A, LDA, WORK( ITAU ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
- CALL DLACPY( 'L', M, N, A, LDA, U, LDU )
-*
-* Copy R to WORK(IR), zeroing out below it
-*
- CALL DLACPY( 'U', N, N, A, LDA, WORK( IR ),
- $ LDWRKR )
- CALL DLASET( 'L', N-1, N-1, ZERO, ZERO,
- $ WORK( IR+1 ), LDWRKR )
-*
-* Generate Q in U
-* (Workspace: need N*N+N+M, prefer N*N+N+M*NB)
-*
- CALL DORGQR( M, M, N, U, LDU, WORK( ITAU ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
- IE = ITAU
- ITAUQ = IE + N
- ITAUP = ITAUQ + N
- IWORK = ITAUP + N
-*
-* Bidiagonalize R in WORK(IR)
-* (Workspace: need N*N+4*N, prefer N*N+3*N+2*N*NB)
-*
- CALL DGEBRD( N, N, WORK( IR ), LDWRKR, S,
- $ WORK( IE ), WORK( ITAUQ ),
- $ WORK( ITAUP ), WORK( IWORK ),
- $ LWORK-IWORK+1, IERR )
-*
-* Generate left bidiagonalizing vectors in WORK(IR)
-* (Workspace: need N*N+4*N, prefer N*N+3*N+N*NB)
-*
- CALL DORGBR( 'Q', N, N, N, WORK( IR ), LDWRKR,
- $ WORK( ITAUQ ), WORK( IWORK ),
- $ LWORK-IWORK+1, IERR )
- IWORK = IE + N
-*
-* Perform bidiagonal QR iteration, computing left
-* singular vectors of R in WORK(IR)
-* (Workspace: need N*N+BDSPAC)
-*
- CALL DBDSQR( 'U', N, 0, N, 0, S, WORK( IE ), DUM,
- $ 1, WORK( IR ), LDWRKR, DUM, 1,
- $ WORK( IWORK ), INFO )
-*
-* Multiply Q in U by left singular vectors of R in
-* WORK(IR), storing result in A
-* (Workspace: need N*N)
-*
- CALL DGEMM( 'N', 'N', M, N, N, ONE, U, LDU,
- $ WORK( IR ), LDWRKR, ZERO, A, LDA )
-*
-* Copy left singular vectors of A from A to U
-*
- CALL DLACPY( 'F', M, N, A, LDA, U, LDU )
-*
- ELSE
-*
-* Insufficient workspace for a fast algorithm
-*
- ITAU = 1
- IWORK = ITAU + N
-*
-* Compute A=Q*R, copying result to U
-* (Workspace: need 2*N, prefer N+N*NB)
-*
- CALL DGEQRF( M, N, A, LDA, WORK( ITAU ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
- CALL DLACPY( 'L', M, N, A, LDA, U, LDU )
-*
-* Generate Q in U
-* (Workspace: need N+M, prefer N+M*NB)
-*
- CALL DORGQR( M, M, N, U, LDU, WORK( ITAU ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
- IE = ITAU
- ITAUQ = IE + N
- ITAUP = ITAUQ + N
- IWORK = ITAUP + N
-*
-* Zero out below R in A
-*
- CALL DLASET( 'L', N-1, N-1, ZERO, ZERO, A( 2, 1 ),
- $ LDA )
-*
-* Bidiagonalize R in A
-* (Workspace: need 4*N, prefer 3*N+2*N*NB)
-*
- CALL DGEBRD( N, N, A, LDA, S, WORK( IE ),
- $ WORK( ITAUQ ), WORK( ITAUP ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
-*
-* Multiply Q in U by left bidiagonalizing vectors
-* in A
-* (Workspace: need 3*N+M, prefer 3*N+M*NB)
-*
- CALL DORMBR( 'Q', 'R', 'N', M, N, N, A, LDA,
- $ WORK( ITAUQ ), U, LDU, WORK( IWORK ),
- $ LWORK-IWORK+1, IERR )
- IWORK = IE + N
-*
-* Perform bidiagonal QR iteration, computing left
-* singular vectors of A in U
-* (Workspace: need BDSPAC)
-*
- CALL DBDSQR( 'U', N, 0, M, 0, S, WORK( IE ), DUM,
- $ 1, U, LDU, DUM, 1, WORK( IWORK ),
- $ INFO )
-*
- END IF
-*
- ELSE IF( WNTVO ) THEN
-*
-* Path 8 (M much larger than N, JOBU='A', JOBVT='O')
-* M left singular vectors to be computed in U and
-* N right singular vectors to be overwritten on A
-*
- IF( LWORK.GE.2*N*N+MAX( N+M, 4*N, BDSPAC ) ) THEN
-*
-* Sufficient workspace for a fast algorithm
-*
- IU = 1
- IF( LWORK.GE.WRKBL+2*LDA*N ) THEN
-*
-* WORK(IU) is LDA by N and WORK(IR) is LDA by N
-*
- LDWRKU = LDA
- IR = IU + LDWRKU*N
- LDWRKR = LDA
- ELSE IF( LWORK.GE.WRKBL+( LDA+N )*N ) THEN
-*
-* WORK(IU) is LDA by N and WORK(IR) is N by N
-*
- LDWRKU = LDA
- IR = IU + LDWRKU*N
- LDWRKR = N
- ELSE
-*
-* WORK(IU) is N by N and WORK(IR) is N by N
-*
- LDWRKU = N
- IR = IU + LDWRKU*N
- LDWRKR = N
- END IF
- ITAU = IR + LDWRKR*N
- IWORK = ITAU + N
-*
-* Compute A=Q*R, copying result to U
-* (Workspace: need 2*N*N+2*N, prefer 2*N*N+N+N*NB)
-*
- CALL DGEQRF( M, N, A, LDA, WORK( ITAU ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
- CALL DLACPY( 'L', M, N, A, LDA, U, LDU )
-*
-* Generate Q in U
-* (Workspace: need 2*N*N+N+M, prefer 2*N*N+N+M*NB)
-*
- CALL DORGQR( M, M, N, U, LDU, WORK( ITAU ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
-*
-* Copy R to WORK(IU), zeroing out below it
-*
- CALL DLACPY( 'U', N, N, A, LDA, WORK( IU ),
- $ LDWRKU )
- CALL DLASET( 'L', N-1, N-1, ZERO, ZERO,
- $ WORK( IU+1 ), LDWRKU )
- IE = ITAU
- ITAUQ = IE + N
- ITAUP = ITAUQ + N
- IWORK = ITAUP + N
-*
-* Bidiagonalize R in WORK(IU), copying result to
-* WORK(IR)
-* (Workspace: need 2*N*N+4*N,
-* prefer 2*N*N+3*N+2*N*NB)
-*
- CALL DGEBRD( N, N, WORK( IU ), LDWRKU, S,
- $ WORK( IE ), WORK( ITAUQ ),
- $ WORK( ITAUP ), WORK( IWORK ),
- $ LWORK-IWORK+1, IERR )
- CALL DLACPY( 'U', N, N, WORK( IU ), LDWRKU,
- $ WORK( IR ), LDWRKR )
-*
-* Generate left bidiagonalizing vectors in WORK(IU)
-* (Workspace: need 2*N*N+4*N, prefer 2*N*N+3*N+N*NB)
-*
- CALL DORGBR( 'Q', N, N, N, WORK( IU ), LDWRKU,
- $ WORK( ITAUQ ), WORK( IWORK ),
- $ LWORK-IWORK+1, IERR )
-*
-* Generate right bidiagonalizing vectors in WORK(IR)
-* (Workspace: need 2*N*N+4*N-1,
-* prefer 2*N*N+3*N+(N-1)*NB)
-*
- CALL DORGBR( 'P', N, N, N, WORK( IR ), LDWRKR,
- $ WORK( ITAUP ), WORK( IWORK ),
- $ LWORK-IWORK+1, IERR )
- IWORK = IE + N
-*
-* Perform bidiagonal QR iteration, computing left
-* singular vectors of R in WORK(IU) and computing
-* right singular vectors of R in WORK(IR)
-* (Workspace: need 2*N*N+BDSPAC)
-*
- CALL DBDSQR( 'U', N, N, N, 0, S, WORK( IE ),
- $ WORK( IR ), LDWRKR, WORK( IU ),
- $ LDWRKU, DUM, 1, WORK( IWORK ), INFO )
-*
-* Multiply Q in U by left singular vectors of R in
-* WORK(IU), storing result in A
-* (Workspace: need N*N)
-*
- CALL DGEMM( 'N', 'N', M, N, N, ONE, U, LDU,
- $ WORK( IU ), LDWRKU, ZERO, A, LDA )
-*
-* Copy left singular vectors of A from A to U
-*
- CALL DLACPY( 'F', M, N, A, LDA, U, LDU )
-*
-* Copy right singular vectors of R from WORK(IR) to A
-*
- CALL DLACPY( 'F', N, N, WORK( IR ), LDWRKR, A,
- $ LDA )
-*
- ELSE
-*
-* Insufficient workspace for a fast algorithm
-*
- ITAU = 1
- IWORK = ITAU + N
-*
-* Compute A=Q*R, copying result to U
-* (Workspace: need 2*N, prefer N+N*NB)
-*
- CALL DGEQRF( M, N, A, LDA, WORK( ITAU ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
- CALL DLACPY( 'L', M, N, A, LDA, U, LDU )
-*
-* Generate Q in U
-* (Workspace: need N+M, prefer N+M*NB)
-*
- CALL DORGQR( M, M, N, U, LDU, WORK( ITAU ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
- IE = ITAU
- ITAUQ = IE + N
- ITAUP = ITAUQ + N
- IWORK = ITAUP + N
-*
-* Zero out below R in A
-*
- CALL DLASET( 'L', N-1, N-1, ZERO, ZERO, A( 2, 1 ),
- $ LDA )
-*
-* Bidiagonalize R in A
-* (Workspace: need 4*N, prefer 3*N+2*N*NB)
-*
- CALL DGEBRD( N, N, A, LDA, S, WORK( IE ),
- $ WORK( ITAUQ ), WORK( ITAUP ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
-*
-* Multiply Q in U by left bidiagonalizing vectors
-* in A
-* (Workspace: need 3*N+M, prefer 3*N+M*NB)
-*
- CALL DORMBR( 'Q', 'R', 'N', M, N, N, A, LDA,
- $ WORK( ITAUQ ), U, LDU, WORK( IWORK ),
- $ LWORK-IWORK+1, IERR )
-*
-* Generate right bidiagonalizing vectors in A
-* (Workspace: need 4*N-1, prefer 3*N+(N-1)*NB)
-*
- CALL DORGBR( 'P', N, N, N, A, LDA, WORK( ITAUP ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
- IWORK = IE + N
-*
-* Perform bidiagonal QR iteration, computing left
-* singular vectors of A in U and computing right
-* singular vectors of A in A
-* (Workspace: need BDSPAC)
-*
- CALL DBDSQR( 'U', N, N, M, 0, S, WORK( IE ), A,
- $ LDA, U, LDU, DUM, 1, WORK( IWORK ),
- $ INFO )
-*
- END IF
-*
- ELSE IF( WNTVAS ) THEN
-*
-* Path 9 (M much larger than N, JOBU='A', JOBVT='S'
-* or 'A')
-* M left singular vectors to be computed in U and
-* N right singular vectors to be computed in VT
-*
- IF( LWORK.GE.N*N+MAX( N+M, 4*N, BDSPAC ) ) THEN
-*
-* Sufficient workspace for a fast algorithm
-*
- IU = 1
- IF( LWORK.GE.WRKBL+LDA*N ) THEN
-*
-* WORK(IU) is LDA by N
-*
- LDWRKU = LDA
- ELSE
-*
-* WORK(IU) is N by N
-*
- LDWRKU = N
- END IF
- ITAU = IU + LDWRKU*N
- IWORK = ITAU + N
-*
-* Compute A=Q*R, copying result to U
-* (Workspace: need N*N+2*N, prefer N*N+N+N*NB)
-*
- CALL DGEQRF( M, N, A, LDA, WORK( ITAU ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
- CALL DLACPY( 'L', M, N, A, LDA, U, LDU )
-*
-* Generate Q in U
-* (Workspace: need N*N+N+M, prefer N*N+N+M*NB)
-*
- CALL DORGQR( M, M, N, U, LDU, WORK( ITAU ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
-*
-* Copy R to WORK(IU), zeroing out below it
-*
- CALL DLACPY( 'U', N, N, A, LDA, WORK( IU ),
- $ LDWRKU )
- CALL DLASET( 'L', N-1, N-1, ZERO, ZERO,
- $ WORK( IU+1 ), LDWRKU )
- IE = ITAU
- ITAUQ = IE + N
- ITAUP = ITAUQ + N
- IWORK = ITAUP + N
-*
-* Bidiagonalize R in WORK(IU), copying result to VT
-* (Workspace: need N*N+4*N, prefer N*N+3*N+2*N*NB)
-*
- CALL DGEBRD( N, N, WORK( IU ), LDWRKU, S,
- $ WORK( IE ), WORK( ITAUQ ),
- $ WORK( ITAUP ), WORK( IWORK ),
- $ LWORK-IWORK+1, IERR )
- CALL DLACPY( 'U', N, N, WORK( IU ), LDWRKU, VT,
- $ LDVT )
-*
-* Generate left bidiagonalizing vectors in WORK(IU)
-* (Workspace: need N*N+4*N, prefer N*N+3*N+N*NB)
-*
- CALL DORGBR( 'Q', N, N, N, WORK( IU ), LDWRKU,
- $ WORK( ITAUQ ), WORK( IWORK ),
- $ LWORK-IWORK+1, IERR )
-*
-* Generate right bidiagonalizing vectors in VT
-* (Workspace: need N*N+4*N-1,
-* prefer N*N+3*N+(N-1)*NB)
-*
- CALL DORGBR( 'P', N, N, N, VT, LDVT, WORK( ITAUP ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
- IWORK = IE + N
-*
-* Perform bidiagonal QR iteration, computing left
-* singular vectors of R in WORK(IU) and computing
-* right singular vectors of R in VT
-* (Workspace: need N*N+BDSPAC)
-*
- CALL DBDSQR( 'U', N, N, N, 0, S, WORK( IE ), VT,
- $ LDVT, WORK( IU ), LDWRKU, DUM, 1,
- $ WORK( IWORK ), INFO )
-*
-* Multiply Q in U by left singular vectors of R in
-* WORK(IU), storing result in A
-* (Workspace: need N*N)
-*
- CALL DGEMM( 'N', 'N', M, N, N, ONE, U, LDU,
- $ WORK( IU ), LDWRKU, ZERO, A, LDA )
-*
-* Copy left singular vectors of A from A to U
-*
- CALL DLACPY( 'F', M, N, A, LDA, U, LDU )
-*
- ELSE
-*
-* Insufficient workspace for a fast algorithm
-*
- ITAU = 1
- IWORK = ITAU + N
-*
-* Compute A=Q*R, copying result to U
-* (Workspace: need 2*N, prefer N+N*NB)
-*
- CALL DGEQRF( M, N, A, LDA, WORK( ITAU ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
- CALL DLACPY( 'L', M, N, A, LDA, U, LDU )
-*
-* Generate Q in U
-* (Workspace: need N+M, prefer N+M*NB)
-*
- CALL DORGQR( M, M, N, U, LDU, WORK( ITAU ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
-*
-* Copy R from A to VT, zeroing out below it
-*
- CALL DLACPY( 'U', N, N, A, LDA, VT, LDVT )
- IF( N.GT.1 )
- $ CALL DLASET( 'L', N-1, N-1, ZERO, ZERO,
- $ VT( 2, 1 ), LDVT )
- IE = ITAU
- ITAUQ = IE + N
- ITAUP = ITAUQ + N
- IWORK = ITAUP + N
-*
-* Bidiagonalize R in VT
-* (Workspace: need 4*N, prefer 3*N+2*N*NB)
-*
- CALL DGEBRD( N, N, VT, LDVT, S, WORK( IE ),
- $ WORK( ITAUQ ), WORK( ITAUP ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
-*
-* Multiply Q in U by left bidiagonalizing vectors
-* in VT
-* (Workspace: need 3*N+M, prefer 3*N+M*NB)
-*
- CALL DORMBR( 'Q', 'R', 'N', M, N, N, VT, LDVT,
- $ WORK( ITAUQ ), U, LDU, WORK( IWORK ),
- $ LWORK-IWORK+1, IERR )
-*
-* Generate right bidiagonalizing vectors in VT
-* (Workspace: need 4*N-1, prefer 3*N+(N-1)*NB)
-*
- CALL DORGBR( 'P', N, N, N, VT, LDVT, WORK( ITAUP ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
- IWORK = IE + N
-*
-* Perform bidiagonal QR iteration, computing left
-* singular vectors of A in U and computing right
-* singular vectors of A in VT
-* (Workspace: need BDSPAC)
-*
- CALL DBDSQR( 'U', N, N, M, 0, S, WORK( IE ), VT,
- $ LDVT, U, LDU, DUM, 1, WORK( IWORK ),
- $ INFO )
-*
- END IF
-*
- END IF
-*
- END IF
-*
- ELSE
-*
-* M .LT. MNTHR
-*
-* Path 10 (M at least N, but not much larger)
-* Reduce to bidiagonal form without QR decomposition
-*
- IE = 1
- ITAUQ = IE + N
- ITAUP = ITAUQ + N
- IWORK = ITAUP + N
-*
-* Bidiagonalize A
-* (Workspace: need 3*N+M, prefer 3*N+(M+N)*NB)
-*
- CALL DGEBRD( M, N, A, LDA, S, WORK( IE ), WORK( ITAUQ ),
- $ WORK( ITAUP ), WORK( IWORK ), LWORK-IWORK+1,
- $ IERR )
- IF( WNTUAS ) THEN
-*
-* If left singular vectors desired in U, copy result to U
-* and generate left bidiagonalizing vectors in U
-* (Workspace: need 3*N+NCU, prefer 3*N+NCU*NB)
-*
- CALL DLACPY( 'L', M, N, A, LDA, U, LDU )
- IF( WNTUS )
- $ NCU = N
- IF( WNTUA )
- $ NCU = M
- CALL DORGBR( 'Q', M, NCU, N, U, LDU, WORK( ITAUQ ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
- END IF
- IF( WNTVAS ) THEN
-*
-* If right singular vectors desired in VT, copy result to
-* VT and generate right bidiagonalizing vectors in VT
-* (Workspace: need 4*N-1, prefer 3*N+(N-1)*NB)
-*
- CALL DLACPY( 'U', N, N, A, LDA, VT, LDVT )
- CALL DORGBR( 'P', N, N, N, VT, LDVT, WORK( ITAUP ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
- END IF
- IF( WNTUO ) THEN
-*
-* If left singular vectors desired in A, generate left
-* bidiagonalizing vectors in A
-* (Workspace: need 4*N, prefer 3*N+N*NB)
-*
- CALL DORGBR( 'Q', M, N, N, A, LDA, WORK( ITAUQ ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
- END IF
- IF( WNTVO ) THEN
-*
-* If right singular vectors desired in A, generate right
-* bidiagonalizing vectors in A
-* (Workspace: need 4*N-1, prefer 3*N+(N-1)*NB)
-*
- CALL DORGBR( 'P', N, N, N, A, LDA, WORK( ITAUP ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
- END IF
- IWORK = IE + N
- IF( WNTUAS .OR. WNTUO )
- $ NRU = M
- IF( WNTUN )
- $ NRU = 0
- IF( WNTVAS .OR. WNTVO )
- $ NCVT = N
- IF( WNTVN )
- $ NCVT = 0
- IF( ( .NOT.WNTUO ) .AND. ( .NOT.WNTVO ) ) THEN
-*
-* Perform bidiagonal QR iteration, if desired, computing
-* left singular vectors in U and computing right singular
-* vectors in VT
-* (Workspace: need BDSPAC)
-*
- CALL DBDSQR( 'U', N, NCVT, NRU, 0, S, WORK( IE ), VT,
- $ LDVT, U, LDU, DUM, 1, WORK( IWORK ), INFO )
- ELSE IF( ( .NOT.WNTUO ) .AND. WNTVO ) THEN
-*
-* Perform bidiagonal QR iteration, if desired, computing
-* left singular vectors in U and computing right singular
-* vectors in A
-* (Workspace: need BDSPAC)
-*
- CALL DBDSQR( 'U', N, NCVT, NRU, 0, S, WORK( IE ), A, LDA,
- $ U, LDU, DUM, 1, WORK( IWORK ), INFO )
- ELSE
-*
-* Perform bidiagonal QR iteration, if desired, computing
-* left singular vectors in A and computing right singular
-* vectors in VT
-* (Workspace: need BDSPAC)
-*
- CALL DBDSQR( 'U', N, NCVT, NRU, 0, S, WORK( IE ), VT,
- $ LDVT, A, LDA, DUM, 1, WORK( IWORK ), INFO )
- END IF
-*
- END IF
-*
- ELSE
-*
-* A has more columns than rows. If A has sufficiently more
-* columns than rows, first reduce using the LQ decomposition (if
-* sufficient workspace available)
-*
- IF( N.GE.MNTHR ) THEN
-*
- IF( WNTVN ) THEN
-*
-* Path 1t(N much larger than M, JOBVT='N')
-* No right singular vectors to be computed
-*
- ITAU = 1
- IWORK = ITAU + M
-*
-* Compute A=L*Q
-* (Workspace: need 2*M, prefer M+M*NB)
-*
- CALL DGELQF( M, N, A, LDA, WORK( ITAU ), WORK( IWORK ),
- $ LWORK-IWORK+1, IERR )
-*
-* Zero out above L
-*
- CALL DLASET( 'U', M-1, M-1, ZERO, ZERO, A( 1, 2 ), LDA )
- IE = 1
- ITAUQ = IE + M
- ITAUP = ITAUQ + M
- IWORK = ITAUP + M
-*
-* Bidiagonalize L in A
-* (Workspace: need 4*M, prefer 3*M+2*M*NB)
-*
- CALL DGEBRD( M, M, A, LDA, S, WORK( IE ), WORK( ITAUQ ),
- $ WORK( ITAUP ), WORK( IWORK ), LWORK-IWORK+1,
- $ IERR )
- IF( WNTUO .OR. WNTUAS ) THEN
-*
-* If left singular vectors desired, generate Q
-* (Workspace: need 4*M, prefer 3*M+M*NB)
-*
- CALL DORGBR( 'Q', M, M, M, A, LDA, WORK( ITAUQ ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
- END IF
- IWORK = IE + M
- NRU = 0
- IF( WNTUO .OR. WNTUAS )
- $ NRU = M
-*
-* Perform bidiagonal QR iteration, computing left singular
-* vectors of A in A if desired
-* (Workspace: need BDSPAC)
-*
- CALL DBDSQR( 'U', M, 0, NRU, 0, S, WORK( IE ), DUM, 1, A,
- $ LDA, DUM, 1, WORK( IWORK ), INFO )
-*
-* If left singular vectors desired in U, copy them there
-*
- IF( WNTUAS )
- $ CALL DLACPY( 'F', M, M, A, LDA, U, LDU )
-*
- ELSE IF( WNTVO .AND. WNTUN ) THEN
-*
-* Path 2t(N much larger than M, JOBU='N', JOBVT='O')
-* M right singular vectors to be overwritten on A and
-* no left singular vectors to be computed
-*
- IF( LWORK.GE.M*M+MAX( 4*M, BDSPAC ) ) THEN
-*
-* Sufficient workspace for a fast algorithm
-*
- IR = 1
- IF( LWORK.GE.MAX( WRKBL, LDA*N+M )+LDA*M ) THEN
-*
-* WORK(IU) is LDA by N and WORK(IR) is LDA by M
-*
- LDWRKU = LDA
- CHUNK = N
- LDWRKR = LDA
- ELSE IF( LWORK.GE.MAX( WRKBL, LDA*N+M )+M*M ) THEN
-*
-* WORK(IU) is LDA by N and WORK(IR) is M by M
-*
- LDWRKU = LDA
- CHUNK = N
- LDWRKR = M
- ELSE
-*
-* WORK(IU) is M by CHUNK and WORK(IR) is M by M
-*
- LDWRKU = M
- CHUNK = ( LWORK-M*M-M ) / M
- LDWRKR = M
- END IF
- ITAU = IR + LDWRKR*M
- IWORK = ITAU + M
-*
-* Compute A=L*Q
-* (Workspace: need M*M+2*M, prefer M*M+M+M*NB)
-*
- CALL DGELQF( M, N, A, LDA, WORK( ITAU ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
-*
-* Copy L to WORK(IR) and zero out above it
-*
- CALL DLACPY( 'L', M, M, A, LDA, WORK( IR ), LDWRKR )
- CALL DLASET( 'U', M-1, M-1, ZERO, ZERO,
- $ WORK( IR+LDWRKR ), LDWRKR )
-*
-* Generate Q in A
-* (Workspace: need M*M+2*M, prefer M*M+M+M*NB)
-*
- CALL DORGLQ( M, N, M, A, LDA, WORK( ITAU ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
- IE = ITAU
- ITAUQ = IE + M
- ITAUP = ITAUQ + M
- IWORK = ITAUP + M
-*
-* Bidiagonalize L in WORK(IR)
-* (Workspace: need M*M+4*M, prefer M*M+3*M+2*M*NB)
-*
- CALL DGEBRD( M, M, WORK( IR ), LDWRKR, S, WORK( IE ),
- $ WORK( ITAUQ ), WORK( ITAUP ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
-*
-* Generate right vectors bidiagonalizing L
-* (Workspace: need M*M+4*M-1, prefer M*M+3*M+(M-1)*NB)
-*
- CALL DORGBR( 'P', M, M, M, WORK( IR ), LDWRKR,
- $ WORK( ITAUP ), WORK( IWORK ),
- $ LWORK-IWORK+1, IERR )
- IWORK = IE + M
-*
-* Perform bidiagonal QR iteration, computing right
-* singular vectors of L in WORK(IR)
-* (Workspace: need M*M+BDSPAC)
-*
- CALL DBDSQR( 'U', M, M, 0, 0, S, WORK( IE ),
- $ WORK( IR ), LDWRKR, DUM, 1, DUM, 1,
- $ WORK( IWORK ), INFO )
- IU = IE + M
-*
-* Multiply right singular vectors of L in WORK(IR) by Q
-* in A, storing result in WORK(IU) and copying to A
-* (Workspace: need M*M+2*M, prefer M*M+M*N+M)
-*
- DO 30 I = 1, N, CHUNK
- BLK = MIN( N-I+1, CHUNK )
- CALL DGEMM( 'N', 'N', M, BLK, M, ONE, WORK( IR ),
- $ LDWRKR, A( 1, I ), LDA, ZERO,
- $ WORK( IU ), LDWRKU )
- CALL DLACPY( 'F', M, BLK, WORK( IU ), LDWRKU,
- $ A( 1, I ), LDA )
- 30 CONTINUE
-*
- ELSE
-*
-* Insufficient workspace for a fast algorithm
-*
- IE = 1
- ITAUQ = IE + M
- ITAUP = ITAUQ + M
- IWORK = ITAUP + M
-*
-* Bidiagonalize A
-* (Workspace: need 3*M+N, prefer 3*M+(M+N)*NB)
-*
- CALL DGEBRD( M, N, A, LDA, S, WORK( IE ),
- $ WORK( ITAUQ ), WORK( ITAUP ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
-*
-* Generate right vectors bidiagonalizing A
-* (Workspace: need 4*M, prefer 3*M+M*NB)
-*
- CALL DORGBR( 'P', M, N, M, A, LDA, WORK( ITAUP ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
- IWORK = IE + M
-*
-* Perform bidiagonal QR iteration, computing right
-* singular vectors of A in A
-* (Workspace: need BDSPAC)
-*
- CALL DBDSQR( 'L', M, N, 0, 0, S, WORK( IE ), A, LDA,
- $ DUM, 1, DUM, 1, WORK( IWORK ), INFO )
-*
- END IF
-*
- ELSE IF( WNTVO .AND. WNTUAS ) THEN
-*
-* Path 3t(N much larger than M, JOBU='S' or 'A', JOBVT='O')
-* M right singular vectors to be overwritten on A and
-* M left singular vectors to be computed in U
-*
- IF( LWORK.GE.M*M+MAX( 4*M, BDSPAC ) ) THEN
-*
-* Sufficient workspace for a fast algorithm
-*
- IR = 1
- IF( LWORK.GE.MAX( WRKBL, LDA*N+M )+LDA*M ) THEN
-*
-* WORK(IU) is LDA by N and WORK(IR) is LDA by M
-*
- LDWRKU = LDA
- CHUNK = N
- LDWRKR = LDA
- ELSE IF( LWORK.GE.MAX( WRKBL, LDA*N+M )+M*M ) THEN
-*
-* WORK(IU) is LDA by N and WORK(IR) is M by M
-*
- LDWRKU = LDA
- CHUNK = N
- LDWRKR = M
- ELSE
-*
-* WORK(IU) is M by CHUNK and WORK(IR) is M by M
-*
- LDWRKU = M
- CHUNK = ( LWORK-M*M-M ) / M
- LDWRKR = M
- END IF
- ITAU = IR + LDWRKR*M
- IWORK = ITAU + M
-*
-* Compute A=L*Q
-* (Workspace: need M*M+2*M, prefer M*M+M+M*NB)
-*
- CALL DGELQF( M, N, A, LDA, WORK( ITAU ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
-*
-* Copy L to U, zeroing about above it
-*
- CALL DLACPY( 'L', M, M, A, LDA, U, LDU )
- CALL DLASET( 'U', M-1, M-1, ZERO, ZERO, U( 1, 2 ),
- $ LDU )
-*
-* Generate Q in A
-* (Workspace: need M*M+2*M, prefer M*M+M+M*NB)
-*
- CALL DORGLQ( M, N, M, A, LDA, WORK( ITAU ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
- IE = ITAU
- ITAUQ = IE + M
- ITAUP = ITAUQ + M
- IWORK = ITAUP + M
-*
-* Bidiagonalize L in U, copying result to WORK(IR)
-* (Workspace: need M*M+4*M, prefer M*M+3*M+2*M*NB)
-*
- CALL DGEBRD( M, M, U, LDU, S, WORK( IE ),
- $ WORK( ITAUQ ), WORK( ITAUP ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
- CALL DLACPY( 'U', M, M, U, LDU, WORK( IR ), LDWRKR )
-*
-* Generate right vectors bidiagonalizing L in WORK(IR)
-* (Workspace: need M*M+4*M-1, prefer M*M+3*M+(M-1)*NB)
-*
- CALL DORGBR( 'P', M, M, M, WORK( IR ), LDWRKR,
- $ WORK( ITAUP ), WORK( IWORK ),
- $ LWORK-IWORK+1, IERR )
-*
-* Generate left vectors bidiagonalizing L in U
-* (Workspace: need M*M+4*M, prefer M*M+3*M+M*NB)
-*
- CALL DORGBR( 'Q', M, M, M, U, LDU, WORK( ITAUQ ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
- IWORK = IE + M
-*
-* Perform bidiagonal QR iteration, computing left
-* singular vectors of L in U, and computing right
-* singular vectors of L in WORK(IR)
-* (Workspace: need M*M+BDSPAC)
-*
- CALL DBDSQR( 'U', M, M, M, 0, S, WORK( IE ),
- $ WORK( IR ), LDWRKR, U, LDU, DUM, 1,
- $ WORK( IWORK ), INFO )
- IU = IE + M
-*
-* Multiply right singular vectors of L in WORK(IR) by Q
-* in A, storing result in WORK(IU) and copying to A
-* (Workspace: need M*M+2*M, prefer M*M+M*N+M))
-*
- DO 40 I = 1, N, CHUNK
- BLK = MIN( N-I+1, CHUNK )
- CALL DGEMM( 'N', 'N', M, BLK, M, ONE, WORK( IR ),
- $ LDWRKR, A( 1, I ), LDA, ZERO,
- $ WORK( IU ), LDWRKU )
- CALL DLACPY( 'F', M, BLK, WORK( IU ), LDWRKU,
- $ A( 1, I ), LDA )
- 40 CONTINUE
-*
- ELSE
-*
-* Insufficient workspace for a fast algorithm
-*
- ITAU = 1
- IWORK = ITAU + M
-*
-* Compute A=L*Q
-* (Workspace: need 2*M, prefer M+M*NB)
-*
- CALL DGELQF( M, N, A, LDA, WORK( ITAU ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
-*
-* Copy L to U, zeroing out above it
-*
- CALL DLACPY( 'L', M, M, A, LDA, U, LDU )
- CALL DLASET( 'U', M-1, M-1, ZERO, ZERO, U( 1, 2 ),
- $ LDU )
-*
-* Generate Q in A
-* (Workspace: need 2*M, prefer M+M*NB)
-*
- CALL DORGLQ( M, N, M, A, LDA, WORK( ITAU ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
- IE = ITAU
- ITAUQ = IE + M
- ITAUP = ITAUQ + M
- IWORK = ITAUP + M
-*
-* Bidiagonalize L in U
-* (Workspace: need 4*M, prefer 3*M+2*M*NB)
-*
- CALL DGEBRD( M, M, U, LDU, S, WORK( IE ),
- $ WORK( ITAUQ ), WORK( ITAUP ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
-*
-* Multiply right vectors bidiagonalizing L by Q in A
-* (Workspace: need 3*M+N, prefer 3*M+N*NB)
-*
- CALL DORMBR( 'P', 'L', 'T', M, N, M, U, LDU,
- $ WORK( ITAUP ), A, LDA, WORK( IWORK ),
- $ LWORK-IWORK+1, IERR )
-*
-* Generate left vectors bidiagonalizing L in U
-* (Workspace: need 4*M, prefer 3*M+M*NB)
-*
- CALL DORGBR( 'Q', M, M, M, U, LDU, WORK( ITAUQ ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
- IWORK = IE + M
-*
-* Perform bidiagonal QR iteration, computing left
-* singular vectors of A in U and computing right
-* singular vectors of A in A
-* (Workspace: need BDSPAC)
-*
- CALL DBDSQR( 'U', M, N, M, 0, S, WORK( IE ), A, LDA,
- $ U, LDU, DUM, 1, WORK( IWORK ), INFO )
-*
- END IF
-*
- ELSE IF( WNTVS ) THEN
-*
- IF( WNTUN ) THEN
-*
-* Path 4t(N much larger than M, JOBU='N', JOBVT='S')
-* M right singular vectors to be computed in VT and
-* no left singular vectors to be computed
-*
- IF( LWORK.GE.M*M+MAX( 4*M, BDSPAC ) ) THEN
-*
-* Sufficient workspace for a fast algorithm
-*
- IR = 1
- IF( LWORK.GE.WRKBL+LDA*M ) THEN
-*
-* WORK(IR) is LDA by M
-*
- LDWRKR = LDA
- ELSE
-*
-* WORK(IR) is M by M
-*
- LDWRKR = M
- END IF
- ITAU = IR + LDWRKR*M
- IWORK = ITAU + M
-*
-* Compute A=L*Q
-* (Workspace: need M*M+2*M, prefer M*M+M+M*NB)
-*
- CALL DGELQF( M, N, A, LDA, WORK( ITAU ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
-*
-* Copy L to WORK(IR), zeroing out above it
-*
- CALL DLACPY( 'L', M, M, A, LDA, WORK( IR ),
- $ LDWRKR )
- CALL DLASET( 'U', M-1, M-1, ZERO, ZERO,
- $ WORK( IR+LDWRKR ), LDWRKR )
-*
-* Generate Q in A
-* (Workspace: need M*M+2*M, prefer M*M+M+M*NB)
-*
- CALL DORGLQ( M, N, M, A, LDA, WORK( ITAU ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
- IE = ITAU
- ITAUQ = IE + M
- ITAUP = ITAUQ + M
- IWORK = ITAUP + M
-*
-* Bidiagonalize L in WORK(IR)
-* (Workspace: need M*M+4*M, prefer M*M+3*M+2*M*NB)
-*
- CALL DGEBRD( M, M, WORK( IR ), LDWRKR, S,
- $ WORK( IE ), WORK( ITAUQ ),
- $ WORK( ITAUP ), WORK( IWORK ),
- $ LWORK-IWORK+1, IERR )
-*
-* Generate right vectors bidiagonalizing L in
-* WORK(IR)
-* (Workspace: need M*M+4*M, prefer M*M+3*M+(M-1)*NB)
-*
- CALL DORGBR( 'P', M, M, M, WORK( IR ), LDWRKR,
- $ WORK( ITAUP ), WORK( IWORK ),
- $ LWORK-IWORK+1, IERR )
- IWORK = IE + M
-*
-* Perform bidiagonal QR iteration, computing right
-* singular vectors of L in WORK(IR)
-* (Workspace: need M*M+BDSPAC)
-*
- CALL DBDSQR( 'U', M, M, 0, 0, S, WORK( IE ),
- $ WORK( IR ), LDWRKR, DUM, 1, DUM, 1,
- $ WORK( IWORK ), INFO )
-*
-* Multiply right singular vectors of L in WORK(IR) by
-* Q in A, storing result in VT
-* (Workspace: need M*M)
-*
- CALL DGEMM( 'N', 'N', M, N, M, ONE, WORK( IR ),
- $ LDWRKR, A, LDA, ZERO, VT, LDVT )
-*
- ELSE
-*
-* Insufficient workspace for a fast algorithm
-*
- ITAU = 1
- IWORK = ITAU + M
-*
-* Compute A=L*Q
-* (Workspace: need 2*M, prefer M+M*NB)
-*
- CALL DGELQF( M, N, A, LDA, WORK( ITAU ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
-*
-* Copy result to VT
-*
- CALL DLACPY( 'U', M, N, A, LDA, VT, LDVT )
-*
-* Generate Q in VT
-* (Workspace: need 2*M, prefer M+M*NB)
-*
- CALL DORGLQ( M, N, M, VT, LDVT, WORK( ITAU ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
- IE = ITAU
- ITAUQ = IE + M
- ITAUP = ITAUQ + M
- IWORK = ITAUP + M
-*
-* Zero out above L in A
-*
- CALL DLASET( 'U', M-1, M-1, ZERO, ZERO, A( 1, 2 ),
- $ LDA )
-*
-* Bidiagonalize L in A
-* (Workspace: need 4*M, prefer 3*M+2*M*NB)
-*
- CALL DGEBRD( M, M, A, LDA, S, WORK( IE ),
- $ WORK( ITAUQ ), WORK( ITAUP ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
-*
-* Multiply right vectors bidiagonalizing L by Q in VT
-* (Workspace: need 3*M+N, prefer 3*M+N*NB)
-*
- CALL DORMBR( 'P', 'L', 'T', M, N, M, A, LDA,
- $ WORK( ITAUP ), VT, LDVT,
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
- IWORK = IE + M
-*
-* Perform bidiagonal QR iteration, computing right
-* singular vectors of A in VT
-* (Workspace: need BDSPAC)
-*
- CALL DBDSQR( 'U', M, N, 0, 0, S, WORK( IE ), VT,
- $ LDVT, DUM, 1, DUM, 1, WORK( IWORK ),
- $ INFO )
-*
- END IF
-*
- ELSE IF( WNTUO ) THEN
-*
-* Path 5t(N much larger than M, JOBU='O', JOBVT='S')
-* M right singular vectors to be computed in VT and
-* M left singular vectors to be overwritten on A
-*
- IF( LWORK.GE.2*M*M+MAX( 4*M, BDSPAC ) ) THEN
-*
-* Sufficient workspace for a fast algorithm
-*
- IU = 1
- IF( LWORK.GE.WRKBL+2*LDA*M ) THEN
-*
-* WORK(IU) is LDA by M and WORK(IR) is LDA by M
-*
- LDWRKU = LDA
- IR = IU + LDWRKU*M
- LDWRKR = LDA
- ELSE IF( LWORK.GE.WRKBL+( LDA+M )*M ) THEN
-*
-* WORK(IU) is LDA by M and WORK(IR) is M by M
-*
- LDWRKU = LDA
- IR = IU + LDWRKU*M
- LDWRKR = M
- ELSE
-*
-* WORK(IU) is M by M and WORK(IR) is M by M
-*
- LDWRKU = M
- IR = IU + LDWRKU*M
- LDWRKR = M
- END IF
- ITAU = IR + LDWRKR*M
- IWORK = ITAU + M
-*
-* Compute A=L*Q
-* (Workspace: need 2*M*M+2*M, prefer 2*M*M+M+M*NB)
-*
- CALL DGELQF( M, N, A, LDA, WORK( ITAU ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
-*
-* Copy L to WORK(IU), zeroing out below it
-*
- CALL DLACPY( 'L', M, M, A, LDA, WORK( IU ),
- $ LDWRKU )
- CALL DLASET( 'U', M-1, M-1, ZERO, ZERO,
- $ WORK( IU+LDWRKU ), LDWRKU )
-*
-* Generate Q in A
-* (Workspace: need 2*M*M+2*M, prefer 2*M*M+M+M*NB)
-*
- CALL DORGLQ( M, N, M, A, LDA, WORK( ITAU ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
- IE = ITAU
- ITAUQ = IE + M
- ITAUP = ITAUQ + M
- IWORK = ITAUP + M
-*
-* Bidiagonalize L in WORK(IU), copying result to
-* WORK(IR)
-* (Workspace: need 2*M*M+4*M,
-* prefer 2*M*M+3*M+2*M*NB)
-*
- CALL DGEBRD( M, M, WORK( IU ), LDWRKU, S,
- $ WORK( IE ), WORK( ITAUQ ),
- $ WORK( ITAUP ), WORK( IWORK ),
- $ LWORK-IWORK+1, IERR )
- CALL DLACPY( 'L', M, M, WORK( IU ), LDWRKU,
- $ WORK( IR ), LDWRKR )
-*
-* Generate right bidiagonalizing vectors in WORK(IU)
-* (Workspace: need 2*M*M+4*M-1,
-* prefer 2*M*M+3*M+(M-1)*NB)
-*
- CALL DORGBR( 'P', M, M, M, WORK( IU ), LDWRKU,
- $ WORK( ITAUP ), WORK( IWORK ),
- $ LWORK-IWORK+1, IERR )
-*
-* Generate left bidiagonalizing vectors in WORK(IR)
-* (Workspace: need 2*M*M+4*M, prefer 2*M*M+3*M+M*NB)
-*
- CALL DORGBR( 'Q', M, M, M, WORK( IR ), LDWRKR,
- $ WORK( ITAUQ ), WORK( IWORK ),
- $ LWORK-IWORK+1, IERR )
- IWORK = IE + M
-*
-* Perform bidiagonal QR iteration, computing left
-* singular vectors of L in WORK(IR) and computing
-* right singular vectors of L in WORK(IU)
-* (Workspace: need 2*M*M+BDSPAC)
-*
- CALL DBDSQR( 'U', M, M, M, 0, S, WORK( IE ),
- $ WORK( IU ), LDWRKU, WORK( IR ),
- $ LDWRKR, DUM, 1, WORK( IWORK ), INFO )
-*
-* Multiply right singular vectors of L in WORK(IU) by
-* Q in A, storing result in VT
-* (Workspace: need M*M)
-*
- CALL DGEMM( 'N', 'N', M, N, M, ONE, WORK( IU ),
- $ LDWRKU, A, LDA, ZERO, VT, LDVT )
-*
-* Copy left singular vectors of L to A
-* (Workspace: need M*M)
-*
- CALL DLACPY( 'F', M, M, WORK( IR ), LDWRKR, A,
- $ LDA )
-*
- ELSE
-*
-* Insufficient workspace for a fast algorithm
-*
- ITAU = 1
- IWORK = ITAU + M
-*
-* Compute A=L*Q, copying result to VT
-* (Workspace: need 2*M, prefer M+M*NB)
-*
- CALL DGELQF( M, N, A, LDA, WORK( ITAU ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
- CALL DLACPY( 'U', M, N, A, LDA, VT, LDVT )
-*
-* Generate Q in VT
-* (Workspace: need 2*M, prefer M+M*NB)
-*
- CALL DORGLQ( M, N, M, VT, LDVT, WORK( ITAU ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
- IE = ITAU
- ITAUQ = IE + M
- ITAUP = ITAUQ + M
- IWORK = ITAUP + M
-*
-* Zero out above L in A
-*
- CALL DLASET( 'U', M-1, M-1, ZERO, ZERO, A( 1, 2 ),
- $ LDA )
-*
-* Bidiagonalize L in A
-* (Workspace: need 4*M, prefer 3*M+2*M*NB)
-*
- CALL DGEBRD( M, M, A, LDA, S, WORK( IE ),
- $ WORK( ITAUQ ), WORK( ITAUP ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
-*
-* Multiply right vectors bidiagonalizing L by Q in VT
-* (Workspace: need 3*M+N, prefer 3*M+N*NB)
-*
- CALL DORMBR( 'P', 'L', 'T', M, N, M, A, LDA,
- $ WORK( ITAUP ), VT, LDVT,
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
-*
-* Generate left bidiagonalizing vectors of L in A
-* (Workspace: need 4*M, prefer 3*M+M*NB)
-*
- CALL DORGBR( 'Q', M, M, M, A, LDA, WORK( ITAUQ ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
- IWORK = IE + M
-*
-* Perform bidiagonal QR iteration, compute left
-* singular vectors of A in A and compute right
-* singular vectors of A in VT
-* (Workspace: need BDSPAC)
-*
- CALL DBDSQR( 'U', M, N, M, 0, S, WORK( IE ), VT,
- $ LDVT, A, LDA, DUM, 1, WORK( IWORK ),
- $ INFO )
-*
- END IF
-*
- ELSE IF( WNTUAS ) THEN
-*
-* Path 6t(N much larger than M, JOBU='S' or 'A',
-* JOBVT='S')
-* M right singular vectors to be computed in VT and
-* M left singular vectors to be computed in U
-*
- IF( LWORK.GE.M*M+MAX( 4*M, BDSPAC ) ) THEN
-*
-* Sufficient workspace for a fast algorithm
-*
- IU = 1
- IF( LWORK.GE.WRKBL+LDA*M ) THEN
-*
-* WORK(IU) is LDA by N
-*
- LDWRKU = LDA
- ELSE
-*
-* WORK(IU) is LDA by M
-*
- LDWRKU = M
- END IF
- ITAU = IU + LDWRKU*M
- IWORK = ITAU + M
-*
-* Compute A=L*Q
-* (Workspace: need M*M+2*M, prefer M*M+M+M*NB)
-*
- CALL DGELQF( M, N, A, LDA, WORK( ITAU ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
-*
-* Copy L to WORK(IU), zeroing out above it
-*
- CALL DLACPY( 'L', M, M, A, LDA, WORK( IU ),
- $ LDWRKU )
- CALL DLASET( 'U', M-1, M-1, ZERO, ZERO,
- $ WORK( IU+LDWRKU ), LDWRKU )
-*
-* Generate Q in A
-* (Workspace: need M*M+2*M, prefer M*M+M+M*NB)
-*
- CALL DORGLQ( M, N, M, A, LDA, WORK( ITAU ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
- IE = ITAU
- ITAUQ = IE + M
- ITAUP = ITAUQ + M
- IWORK = ITAUP + M
-*
-* Bidiagonalize L in WORK(IU), copying result to U
-* (Workspace: need M*M+4*M, prefer M*M+3*M+2*M*NB)
-*
- CALL DGEBRD( M, M, WORK( IU ), LDWRKU, S,
- $ WORK( IE ), WORK( ITAUQ ),
- $ WORK( ITAUP ), WORK( IWORK ),
- $ LWORK-IWORK+1, IERR )
- CALL DLACPY( 'L', M, M, WORK( IU ), LDWRKU, U,
- $ LDU )
-*
-* Generate right bidiagonalizing vectors in WORK(IU)
-* (Workspace: need M*M+4*M-1,
-* prefer M*M+3*M+(M-1)*NB)
-*
- CALL DORGBR( 'P', M, M, M, WORK( IU ), LDWRKU,
- $ WORK( ITAUP ), WORK( IWORK ),
- $ LWORK-IWORK+1, IERR )
-*
-* Generate left bidiagonalizing vectors in U
-* (Workspace: need M*M+4*M, prefer M*M+3*M+M*NB)
-*
- CALL DORGBR( 'Q', M, M, M, U, LDU, WORK( ITAUQ ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
- IWORK = IE + M
-*
-* Perform bidiagonal QR iteration, computing left
-* singular vectors of L in U and computing right
-* singular vectors of L in WORK(IU)
-* (Workspace: need M*M+BDSPAC)
-*
- CALL DBDSQR( 'U', M, M, M, 0, S, WORK( IE ),
- $ WORK( IU ), LDWRKU, U, LDU, DUM, 1,
- $ WORK( IWORK ), INFO )
-*
-* Multiply right singular vectors of L in WORK(IU) by
-* Q in A, storing result in VT
-* (Workspace: need M*M)
-*
- CALL DGEMM( 'N', 'N', M, N, M, ONE, WORK( IU ),
- $ LDWRKU, A, LDA, ZERO, VT, LDVT )
-*
- ELSE
-*
-* Insufficient workspace for a fast algorithm
-*
- ITAU = 1
- IWORK = ITAU + M
-*
-* Compute A=L*Q, copying result to VT
-* (Workspace: need 2*M, prefer M+M*NB)
-*
- CALL DGELQF( M, N, A, LDA, WORK( ITAU ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
- CALL DLACPY( 'U', M, N, A, LDA, VT, LDVT )
-*
-* Generate Q in VT
-* (Workspace: need 2*M, prefer M+M*NB)
-*
- CALL DORGLQ( M, N, M, VT, LDVT, WORK( ITAU ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
-*
-* Copy L to U, zeroing out above it
-*
- CALL DLACPY( 'L', M, M, A, LDA, U, LDU )
- CALL DLASET( 'U', M-1, M-1, ZERO, ZERO, U( 1, 2 ),
- $ LDU )
- IE = ITAU
- ITAUQ = IE + M
- ITAUP = ITAUQ + M
- IWORK = ITAUP + M
-*
-* Bidiagonalize L in U
-* (Workspace: need 4*M, prefer 3*M+2*M*NB)
-*
- CALL DGEBRD( M, M, U, LDU, S, WORK( IE ),
- $ WORK( ITAUQ ), WORK( ITAUP ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
-*
-* Multiply right bidiagonalizing vectors in U by Q
-* in VT
-* (Workspace: need 3*M+N, prefer 3*M+N*NB)
-*
- CALL DORMBR( 'P', 'L', 'T', M, N, M, U, LDU,
- $ WORK( ITAUP ), VT, LDVT,
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
-*
-* Generate left bidiagonalizing vectors in U
-* (Workspace: need 4*M, prefer 3*M+M*NB)
-*
- CALL DORGBR( 'Q', M, M, M, U, LDU, WORK( ITAUQ ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
- IWORK = IE + M
-*
-* Perform bidiagonal QR iteration, computing left
-* singular vectors of A in U and computing right
-* singular vectors of A in VT
-* (Workspace: need BDSPAC)
-*
- CALL DBDSQR( 'U', M, N, M, 0, S, WORK( IE ), VT,
- $ LDVT, U, LDU, DUM, 1, WORK( IWORK ),
- $ INFO )
-*
- END IF
-*
- END IF
-*
- ELSE IF( WNTVA ) THEN
-*
- IF( WNTUN ) THEN
-*
-* Path 7t(N much larger than M, JOBU='N', JOBVT='A')
-* N right singular vectors to be computed in VT and
-* no left singular vectors to be computed
-*
- IF( LWORK.GE.M*M+MAX( N+M, 4*M, BDSPAC ) ) THEN
-*
-* Sufficient workspace for a fast algorithm
-*
- IR = 1
- IF( LWORK.GE.WRKBL+LDA*M ) THEN
-*
-* WORK(IR) is LDA by M
-*
- LDWRKR = LDA
- ELSE
-*
-* WORK(IR) is M by M
-*
- LDWRKR = M
- END IF
- ITAU = IR + LDWRKR*M
- IWORK = ITAU + M
-*
-* Compute A=L*Q, copying result to VT
-* (Workspace: need M*M+2*M, prefer M*M+M+M*NB)
-*
- CALL DGELQF( M, N, A, LDA, WORK( ITAU ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
- CALL DLACPY( 'U', M, N, A, LDA, VT, LDVT )
-*
-* Copy L to WORK(IR), zeroing out above it
-*
- CALL DLACPY( 'L', M, M, A, LDA, WORK( IR ),
- $ LDWRKR )
- CALL DLASET( 'U', M-1, M-1, ZERO, ZERO,
- $ WORK( IR+LDWRKR ), LDWRKR )
-*
-* Generate Q in VT
-* (Workspace: need M*M+M+N, prefer M*M+M+N*NB)
-*
- CALL DORGLQ( N, N, M, VT, LDVT, WORK( ITAU ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
- IE = ITAU
- ITAUQ = IE + M
- ITAUP = ITAUQ + M
- IWORK = ITAUP + M
-*
-* Bidiagonalize L in WORK(IR)
-* (Workspace: need M*M+4*M, prefer M*M+3*M+2*M*NB)
-*
- CALL DGEBRD( M, M, WORK( IR ), LDWRKR, S,
- $ WORK( IE ), WORK( ITAUQ ),
- $ WORK( ITAUP ), WORK( IWORK ),
- $ LWORK-IWORK+1, IERR )
-*
-* Generate right bidiagonalizing vectors in WORK(IR)
-* (Workspace: need M*M+4*M-1,
-* prefer M*M+3*M+(M-1)*NB)
-*
- CALL DORGBR( 'P', M, M, M, WORK( IR ), LDWRKR,
- $ WORK( ITAUP ), WORK( IWORK ),
- $ LWORK-IWORK+1, IERR )
- IWORK = IE + M
-*
-* Perform bidiagonal QR iteration, computing right
-* singular vectors of L in WORK(IR)
-* (Workspace: need M*M+BDSPAC)
-*
- CALL DBDSQR( 'U', M, M, 0, 0, S, WORK( IE ),
- $ WORK( IR ), LDWRKR, DUM, 1, DUM, 1,
- $ WORK( IWORK ), INFO )
-*
-* Multiply right singular vectors of L in WORK(IR) by
-* Q in VT, storing result in A
-* (Workspace: need M*M)
-*
- CALL DGEMM( 'N', 'N', M, N, M, ONE, WORK( IR ),
- $ LDWRKR, VT, LDVT, ZERO, A, LDA )
-*
-* Copy right singular vectors of A from A to VT
-*
- CALL DLACPY( 'F', M, N, A, LDA, VT, LDVT )
-*
- ELSE
-*
-* Insufficient workspace for a fast algorithm
-*
- ITAU = 1
- IWORK = ITAU + M
-*
-* Compute A=L*Q, copying result to VT
-* (Workspace: need 2*M, prefer M+M*NB)
-*
- CALL DGELQF( M, N, A, LDA, WORK( ITAU ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
- CALL DLACPY( 'U', M, N, A, LDA, VT, LDVT )
-*
-* Generate Q in VT
-* (Workspace: need M+N, prefer M+N*NB)
-*
- CALL DORGLQ( N, N, M, VT, LDVT, WORK( ITAU ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
- IE = ITAU
- ITAUQ = IE + M
- ITAUP = ITAUQ + M
- IWORK = ITAUP + M
-*
-* Zero out above L in A
-*
- CALL DLASET( 'U', M-1, M-1, ZERO, ZERO, A( 1, 2 ),
- $ LDA )
-*
-* Bidiagonalize L in A
-* (Workspace: need 4*M, prefer 3*M+2*M*NB)
-*
- CALL DGEBRD( M, M, A, LDA, S, WORK( IE ),
- $ WORK( ITAUQ ), WORK( ITAUP ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
-*
-* Multiply right bidiagonalizing vectors in A by Q
-* in VT
-* (Workspace: need 3*M+N, prefer 3*M+N*NB)
-*
- CALL DORMBR( 'P', 'L', 'T', M, N, M, A, LDA,
- $ WORK( ITAUP ), VT, LDVT,
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
- IWORK = IE + M
-*
-* Perform bidiagonal QR iteration, computing right
-* singular vectors of A in VT
-* (Workspace: need BDSPAC)
-*
- CALL DBDSQR( 'U', M, N, 0, 0, S, WORK( IE ), VT,
- $ LDVT, DUM, 1, DUM, 1, WORK( IWORK ),
- $ INFO )
-*
- END IF
-*
- ELSE IF( WNTUO ) THEN
-*
-* Path 8t(N much larger than M, JOBU='O', JOBVT='A')
-* N right singular vectors to be computed in VT and
-* M left singular vectors to be overwritten on A
-*
- IF( LWORK.GE.2*M*M+MAX( N+M, 4*M, BDSPAC ) ) THEN
-*
-* Sufficient workspace for a fast algorithm
-*
- IU = 1
- IF( LWORK.GE.WRKBL+2*LDA*M ) THEN
-*
-* WORK(IU) is LDA by M and WORK(IR) is LDA by M
-*
- LDWRKU = LDA
- IR = IU + LDWRKU*M
- LDWRKR = LDA
- ELSE IF( LWORK.GE.WRKBL+( LDA+M )*M ) THEN
-*
-* WORK(IU) is LDA by M and WORK(IR) is M by M
-*
- LDWRKU = LDA
- IR = IU + LDWRKU*M
- LDWRKR = M
- ELSE
-*
-* WORK(IU) is M by M and WORK(IR) is M by M
-*
- LDWRKU = M
- IR = IU + LDWRKU*M
- LDWRKR = M
- END IF
- ITAU = IR + LDWRKR*M
- IWORK = ITAU + M
-*
-* Compute A=L*Q, copying result to VT
-* (Workspace: need 2*M*M+2*M, prefer 2*M*M+M+M*NB)
-*
- CALL DGELQF( M, N, A, LDA, WORK( ITAU ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
- CALL DLACPY( 'U', M, N, A, LDA, VT, LDVT )
-*
-* Generate Q in VT
-* (Workspace: need 2*M*M+M+N, prefer 2*M*M+M+N*NB)
-*
- CALL DORGLQ( N, N, M, VT, LDVT, WORK( ITAU ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
-*
-* Copy L to WORK(IU), zeroing out above it
-*
- CALL DLACPY( 'L', M, M, A, LDA, WORK( IU ),
- $ LDWRKU )
- CALL DLASET( 'U', M-1, M-1, ZERO, ZERO,
- $ WORK( IU+LDWRKU ), LDWRKU )
- IE = ITAU
- ITAUQ = IE + M
- ITAUP = ITAUQ + M
- IWORK = ITAUP + M
-*
-* Bidiagonalize L in WORK(IU), copying result to
-* WORK(IR)
-* (Workspace: need 2*M*M+4*M,
-* prefer 2*M*M+3*M+2*M*NB)
-*
- CALL DGEBRD( M, M, WORK( IU ), LDWRKU, S,
- $ WORK( IE ), WORK( ITAUQ ),
- $ WORK( ITAUP ), WORK( IWORK ),
- $ LWORK-IWORK+1, IERR )
- CALL DLACPY( 'L', M, M, WORK( IU ), LDWRKU,
- $ WORK( IR ), LDWRKR )
-*
-* Generate right bidiagonalizing vectors in WORK(IU)
-* (Workspace: need 2*M*M+4*M-1,
-* prefer 2*M*M+3*M+(M-1)*NB)
-*
- CALL DORGBR( 'P', M, M, M, WORK( IU ), LDWRKU,
- $ WORK( ITAUP ), WORK( IWORK ),
- $ LWORK-IWORK+1, IERR )
-*
-* Generate left bidiagonalizing vectors in WORK(IR)
-* (Workspace: need 2*M*M+4*M, prefer 2*M*M+3*M+M*NB)
-*
- CALL DORGBR( 'Q', M, M, M, WORK( IR ), LDWRKR,
- $ WORK( ITAUQ ), WORK( IWORK ),
- $ LWORK-IWORK+1, IERR )
- IWORK = IE + M
-*
-* Perform bidiagonal QR iteration, computing left
-* singular vectors of L in WORK(IR) and computing
-* right singular vectors of L in WORK(IU)
-* (Workspace: need 2*M*M+BDSPAC)
-*
- CALL DBDSQR( 'U', M, M, M, 0, S, WORK( IE ),
- $ WORK( IU ), LDWRKU, WORK( IR ),
- $ LDWRKR, DUM, 1, WORK( IWORK ), INFO )
-*
-* Multiply right singular vectors of L in WORK(IU) by
-* Q in VT, storing result in A
-* (Workspace: need M*M)
-*
- CALL DGEMM( 'N', 'N', M, N, M, ONE, WORK( IU ),
- $ LDWRKU, VT, LDVT, ZERO, A, LDA )
-*
-* Copy right singular vectors of A from A to VT
-*
- CALL DLACPY( 'F', M, N, A, LDA, VT, LDVT )
-*
-* Copy left singular vectors of A from WORK(IR) to A
-*
- CALL DLACPY( 'F', M, M, WORK( IR ), LDWRKR, A,
- $ LDA )
-*
- ELSE
-*
-* Insufficient workspace for a fast algorithm
-*
- ITAU = 1
- IWORK = ITAU + M
-*
-* Compute A=L*Q, copying result to VT
-* (Workspace: need 2*M, prefer M+M*NB)
-*
- CALL DGELQF( M, N, A, LDA, WORK( ITAU ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
- CALL DLACPY( 'U', M, N, A, LDA, VT, LDVT )
-*
-* Generate Q in VT
-* (Workspace: need M+N, prefer M+N*NB)
-*
- CALL DORGLQ( N, N, M, VT, LDVT, WORK( ITAU ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
- IE = ITAU
- ITAUQ = IE + M
- ITAUP = ITAUQ + M
- IWORK = ITAUP + M
-*
-* Zero out above L in A
-*
- CALL DLASET( 'U', M-1, M-1, ZERO, ZERO, A( 1, 2 ),
- $ LDA )
-*
-* Bidiagonalize L in A
-* (Workspace: need 4*M, prefer 3*M+2*M*NB)
-*
- CALL DGEBRD( M, M, A, LDA, S, WORK( IE ),
- $ WORK( ITAUQ ), WORK( ITAUP ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
-*
-* Multiply right bidiagonalizing vectors in A by Q
-* in VT
-* (Workspace: need 3*M+N, prefer 3*M+N*NB)
-*
- CALL DORMBR( 'P', 'L', 'T', M, N, M, A, LDA,
- $ WORK( ITAUP ), VT, LDVT,
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
-*
-* Generate left bidiagonalizing vectors in A
-* (Workspace: need 4*M, prefer 3*M+M*NB)
-*
- CALL DORGBR( 'Q', M, M, M, A, LDA, WORK( ITAUQ ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
- IWORK = IE + M
-*
-* Perform bidiagonal QR iteration, computing left
-* singular vectors of A in A and computing right
-* singular vectors of A in VT
-* (Workspace: need BDSPAC)
-*
- CALL DBDSQR( 'U', M, N, M, 0, S, WORK( IE ), VT,
- $ LDVT, A, LDA, DUM, 1, WORK( IWORK ),
- $ INFO )
-*
- END IF
-*
- ELSE IF( WNTUAS ) THEN
-*
-* Path 9t(N much larger than M, JOBU='S' or 'A',
-* JOBVT='A')
-* N right singular vectors to be computed in VT and
-* M left singular vectors to be computed in U
-*
- IF( LWORK.GE.M*M+MAX( N+M, 4*M, BDSPAC ) ) THEN
-*
-* Sufficient workspace for a fast algorithm
-*
- IU = 1
- IF( LWORK.GE.WRKBL+LDA*M ) THEN
-*
-* WORK(IU) is LDA by M
-*
- LDWRKU = LDA
- ELSE
-*
-* WORK(IU) is M by M
-*
- LDWRKU = M
- END IF
- ITAU = IU + LDWRKU*M
- IWORK = ITAU + M
-*
-* Compute A=L*Q, copying result to VT
-* (Workspace: need M*M+2*M, prefer M*M+M+M*NB)
-*
- CALL DGELQF( M, N, A, LDA, WORK( ITAU ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
- CALL DLACPY( 'U', M, N, A, LDA, VT, LDVT )
-*
-* Generate Q in VT
-* (Workspace: need M*M+M+N, prefer M*M+M+N*NB)
-*
- CALL DORGLQ( N, N, M, VT, LDVT, WORK( ITAU ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
-*
-* Copy L to WORK(IU), zeroing out above it
-*
- CALL DLACPY( 'L', M, M, A, LDA, WORK( IU ),
- $ LDWRKU )
- CALL DLASET( 'U', M-1, M-1, ZERO, ZERO,
- $ WORK( IU+LDWRKU ), LDWRKU )
- IE = ITAU
- ITAUQ = IE + M
- ITAUP = ITAUQ + M
- IWORK = ITAUP + M
-*
-* Bidiagonalize L in WORK(IU), copying result to U
-* (Workspace: need M*M+4*M, prefer M*M+3*M+2*M*NB)
-*
- CALL DGEBRD( M, M, WORK( IU ), LDWRKU, S,
- $ WORK( IE ), WORK( ITAUQ ),
- $ WORK( ITAUP ), WORK( IWORK ),
- $ LWORK-IWORK+1, IERR )
- CALL DLACPY( 'L', M, M, WORK( IU ), LDWRKU, U,
- $ LDU )
-*
-* Generate right bidiagonalizing vectors in WORK(IU)
-* (Workspace: need M*M+4*M, prefer M*M+3*M+(M-1)*NB)
-*
- CALL DORGBR( 'P', M, M, M, WORK( IU ), LDWRKU,
- $ WORK( ITAUP ), WORK( IWORK ),
- $ LWORK-IWORK+1, IERR )
-*
-* Generate left bidiagonalizing vectors in U
-* (Workspace: need M*M+4*M, prefer M*M+3*M+M*NB)
-*
- CALL DORGBR( 'Q', M, M, M, U, LDU, WORK( ITAUQ ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
- IWORK = IE + M
-*
-* Perform bidiagonal QR iteration, computing left
-* singular vectors of L in U and computing right
-* singular vectors of L in WORK(IU)
-* (Workspace: need M*M+BDSPAC)
-*
- CALL DBDSQR( 'U', M, M, M, 0, S, WORK( IE ),
- $ WORK( IU ), LDWRKU, U, LDU, DUM, 1,
- $ WORK( IWORK ), INFO )
-*
-* Multiply right singular vectors of L in WORK(IU) by
-* Q in VT, storing result in A
-* (Workspace: need M*M)
-*
- CALL DGEMM( 'N', 'N', M, N, M, ONE, WORK( IU ),
- $ LDWRKU, VT, LDVT, ZERO, A, LDA )
-*
-* Copy right singular vectors of A from A to VT
-*
- CALL DLACPY( 'F', M, N, A, LDA, VT, LDVT )
-*
- ELSE
-*
-* Insufficient workspace for a fast algorithm
-*
- ITAU = 1
- IWORK = ITAU + M
-*
-* Compute A=L*Q, copying result to VT
-* (Workspace: need 2*M, prefer M+M*NB)
-*
- CALL DGELQF( M, N, A, LDA, WORK( ITAU ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
- CALL DLACPY( 'U', M, N, A, LDA, VT, LDVT )
-*
-* Generate Q in VT
-* (Workspace: need M+N, prefer M+N*NB)
-*
- CALL DORGLQ( N, N, M, VT, LDVT, WORK( ITAU ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
-*
-* Copy L to U, zeroing out above it
-*
- CALL DLACPY( 'L', M, M, A, LDA, U, LDU )
- CALL DLASET( 'U', M-1, M-1, ZERO, ZERO, U( 1, 2 ),
- $ LDU )
- IE = ITAU
- ITAUQ = IE + M
- ITAUP = ITAUQ + M
- IWORK = ITAUP + M
-*
-* Bidiagonalize L in U
-* (Workspace: need 4*M, prefer 3*M+2*M*NB)
-*
- CALL DGEBRD( M, M, U, LDU, S, WORK( IE ),
- $ WORK( ITAUQ ), WORK( ITAUP ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
-*
-* Multiply right bidiagonalizing vectors in U by Q
-* in VT
-* (Workspace: need 3*M+N, prefer 3*M+N*NB)
-*
- CALL DORMBR( 'P', 'L', 'T', M, N, M, U, LDU,
- $ WORK( ITAUP ), VT, LDVT,
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
-*
-* Generate left bidiagonalizing vectors in U
-* (Workspace: need 4*M, prefer 3*M+M*NB)
-*
- CALL DORGBR( 'Q', M, M, M, U, LDU, WORK( ITAUQ ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
- IWORK = IE + M
-*
-* Perform bidiagonal QR iteration, computing left
-* singular vectors of A in U and computing right
-* singular vectors of A in VT
-* (Workspace: need BDSPAC)
-*
- CALL DBDSQR( 'U', M, N, M, 0, S, WORK( IE ), VT,
- $ LDVT, U, LDU, DUM, 1, WORK( IWORK ),
- $ INFO )
-*
- END IF
-*
- END IF
-*
- END IF
-*
- ELSE
-*
-* N .LT. MNTHR
-*
-* Path 10t(N greater than M, but not much larger)
-* Reduce to bidiagonal form without LQ decomposition
-*
- IE = 1
- ITAUQ = IE + M
- ITAUP = ITAUQ + M
- IWORK = ITAUP + M
-*
-* Bidiagonalize A
-* (Workspace: need 3*M+N, prefer 3*M+(M+N)*NB)
-*
- CALL DGEBRD( M, N, A, LDA, S, WORK( IE ), WORK( ITAUQ ),
- $ WORK( ITAUP ), WORK( IWORK ), LWORK-IWORK+1,
- $ IERR )
- IF( WNTUAS ) THEN
-*
-* If left singular vectors desired in U, copy result to U
-* and generate left bidiagonalizing vectors in U
-* (Workspace: need 4*M-1, prefer 3*M+(M-1)*NB)
-*
- CALL DLACPY( 'L', M, M, A, LDA, U, LDU )
- CALL DORGBR( 'Q', M, M, N, U, LDU, WORK( ITAUQ ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
- END IF
- IF( WNTVAS ) THEN
-*
-* If right singular vectors desired in VT, copy result to
-* VT and generate right bidiagonalizing vectors in VT
-* (Workspace: need 3*M+NRVT, prefer 3*M+NRVT*NB)
-*
- CALL DLACPY( 'U', M, N, A, LDA, VT, LDVT )
- IF( WNTVA )
- $ NRVT = N
- IF( WNTVS )
- $ NRVT = M
- CALL DORGBR( 'P', NRVT, N, M, VT, LDVT, WORK( ITAUP ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
- END IF
- IF( WNTUO ) THEN
-*
-* If left singular vectors desired in A, generate left
-* bidiagonalizing vectors in A
-* (Workspace: need 4*M-1, prefer 3*M+(M-1)*NB)
-*
- CALL DORGBR( 'Q', M, M, N, A, LDA, WORK( ITAUQ ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
- END IF
- IF( WNTVO ) THEN
-*
-* If right singular vectors desired in A, generate right
-* bidiagonalizing vectors in A
-* (Workspace: need 4*M, prefer 3*M+M*NB)
-*
- CALL DORGBR( 'P', M, N, M, A, LDA, WORK( ITAUP ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
- END IF
- IWORK = IE + M
- IF( WNTUAS .OR. WNTUO )
- $ NRU = M
- IF( WNTUN )
- $ NRU = 0
- IF( WNTVAS .OR. WNTVO )
- $ NCVT = N
- IF( WNTVN )
- $ NCVT = 0
- IF( ( .NOT.WNTUO ) .AND. ( .NOT.WNTVO ) ) THEN
-*
-* Perform bidiagonal QR iteration, if desired, computing
-* left singular vectors in U and computing right singular
-* vectors in VT
-* (Workspace: need BDSPAC)
-*
- CALL DBDSQR( 'L', M, NCVT, NRU, 0, S, WORK( IE ), VT,
- $ LDVT, U, LDU, DUM, 1, WORK( IWORK ), INFO )
- ELSE IF( ( .NOT.WNTUO ) .AND. WNTVO ) THEN
-*
-* Perform bidiagonal QR iteration, if desired, computing
-* left singular vectors in U and computing right singular
-* vectors in A
-* (Workspace: need BDSPAC)
-*
- CALL DBDSQR( 'L', M, NCVT, NRU, 0, S, WORK( IE ), A, LDA,
- $ U, LDU, DUM, 1, WORK( IWORK ), INFO )
- ELSE
-*
-* Perform bidiagonal QR iteration, if desired, computing
-* left singular vectors in A and computing right singular
-* vectors in VT
-* (Workspace: need BDSPAC)
-*
- CALL DBDSQR( 'L', M, NCVT, NRU, 0, S, WORK( IE ), VT,
- $ LDVT, A, LDA, DUM, 1, WORK( IWORK ), INFO )
- END IF
-*
- END IF
-*
- END IF
-*
-* If DBDSQR failed to converge, copy unconverged superdiagonals
-* to WORK( 2:MINMN )
-*
- IF( INFO.NE.0 ) THEN
- IF( IE.GT.2 ) THEN
- DO 50 I = 1, MINMN - 1
- WORK( I+1 ) = WORK( I+IE-1 )
- 50 CONTINUE
- END IF
- IF( IE.LT.2 ) THEN
- DO 60 I = MINMN - 1, 1, -1
- WORK( I+1 ) = WORK( I+IE-1 )
- 60 CONTINUE
- END IF
- END IF
-*
-* Undo scaling if necessary
-*
- IF( ISCL.EQ.1 ) THEN
- IF( ANRM.GT.BIGNUM )
- $ CALL DLASCL( 'G', 0, 0, BIGNUM, ANRM, MINMN, 1, S, MINMN,
- $ IERR )
- IF( INFO.NE.0 .AND. ANRM.GT.BIGNUM )
- $ CALL DLASCL( 'G', 0, 0, BIGNUM, ANRM, MINMN-1, 1, WORK( 2 ),
- $ MINMN, IERR )
- IF( ANRM.LT.SMLNUM )
- $ CALL DLASCL( 'G', 0, 0, SMLNUM, ANRM, MINMN, 1, S, MINMN,
- $ IERR )
- IF( INFO.NE.0 .AND. ANRM.LT.SMLNUM )
- $ CALL DLASCL( 'G', 0, 0, SMLNUM, ANRM, MINMN-1, 1, WORK( 2 ),
- $ MINMN, IERR )
- END IF
-*
-* Return optimal workspace in WORK(1)
-*
- WORK( 1 ) = MAXWRK
-*
- RETURN
-*
-* End of DGESVD
-*
- END
diff --git a/src/lib/lapack/dgesvx.f b/src/lib/lapack/dgesvx.f
deleted file mode 100644
index 0645a20c..00000000
--- a/src/lib/lapack/dgesvx.f
+++ /dev/null
@@ -1,479 +0,0 @@
- SUBROUTINE DGESVX( FACT, TRANS, N, NRHS, A, LDA, AF, LDAF, IPIV,
- $ EQUED, R, C, B, LDB, X, LDX, RCOND, FERR, BERR,
- $ WORK, IWORK, INFO )
-*
-* -- LAPACK driver routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- CHARACTER EQUED, FACT, TRANS
- INTEGER INFO, LDA, LDAF, LDB, LDX, N, NRHS
- DOUBLE PRECISION RCOND
-* ..
-* .. Array Arguments ..
- INTEGER IPIV( * ), IWORK( * )
- DOUBLE PRECISION A( LDA, * ), AF( LDAF, * ), B( LDB, * ),
- $ BERR( * ), C( * ), FERR( * ), R( * ),
- $ WORK( * ), X( LDX, * )
-* ..
-*
-* Purpose
-* =======
-*
-* DGESVX uses the LU factorization to compute the solution to a real
-* system of linear equations
-* A * X = B,
-* where A is an N-by-N matrix and X and B are N-by-NRHS matrices.
-*
-* Error bounds on the solution and a condition estimate are also
-* provided.
-*
-* Description
-* ===========
-*
-* The following steps are performed:
-*
-* 1. If FACT = 'E', real scaling factors are computed to equilibrate
-* the system:
-* TRANS = 'N': diag(R)*A*diag(C) *inv(diag(C))*X = diag(R)*B
-* TRANS = 'T': (diag(R)*A*diag(C))**T *inv(diag(R))*X = diag(C)*B
-* TRANS = 'C': (diag(R)*A*diag(C))**H *inv(diag(R))*X = diag(C)*B
-* Whether or not the system will be equilibrated depends on the
-* scaling of the matrix A, but if equilibration is used, A is
-* overwritten by diag(R)*A*diag(C) and B by diag(R)*B (if TRANS='N')
-* or diag(C)*B (if TRANS = 'T' or 'C').
-*
-* 2. If FACT = 'N' or 'E', the LU decomposition is used to factor the
-* matrix A (after equilibration if FACT = 'E') as
-* A = P * L * U,
-* where P is a permutation matrix, L is a unit lower triangular
-* matrix, and U is upper triangular.
-*
-* 3. If some U(i,i)=0, so that U is exactly singular, then the routine
-* returns with INFO = i. Otherwise, the factored form of A is used
-* to estimate the condition number of the matrix A. If the
-* reciprocal of the condition number is less than machine precision,
-* INFO = N+1 is returned as a warning, but the routine still goes on
-* to solve for X and compute error bounds as described below.
-*
-* 4. The system of equations is solved for X using the factored form
-* of A.
-*
-* 5. Iterative refinement is applied to improve the computed solution
-* matrix and calculate error bounds and backward error estimates
-* for it.
-*
-* 6. If equilibration was used, the matrix X is premultiplied by
-* diag(C) (if TRANS = 'N') or diag(R) (if TRANS = 'T' or 'C') so
-* that it solves the original system before equilibration.
-*
-* Arguments
-* =========
-*
-* FACT (input) CHARACTER*1
-* Specifies whether or not the factored form of the matrix A is
-* supplied on entry, and if not, whether the matrix A should be
-* equilibrated before it is factored.
-* = 'F': On entry, AF and IPIV contain the factored form of A.
-* If EQUED is not 'N', the matrix A has been
-* equilibrated with scaling factors given by R and C.
-* A, AF, and IPIV are not modified.
-* = 'N': The matrix A will be copied to AF and factored.
-* = 'E': The matrix A will be equilibrated if necessary, then
-* copied to AF and factored.
-*
-* TRANS (input) CHARACTER*1
-* Specifies the form of the system of equations:
-* = 'N': A * X = B (No transpose)
-* = 'T': A**T * X = B (Transpose)
-* = 'C': A**H * X = B (Transpose)
-*
-* N (input) INTEGER
-* The number of linear equations, i.e., the order of the
-* matrix A. N >= 0.
-*
-* NRHS (input) INTEGER
-* The number of right hand sides, i.e., the number of columns
-* of the matrices B and X. NRHS >= 0.
-*
-* A (input/output) DOUBLE PRECISION array, dimension (LDA,N)
-* On entry, the N-by-N matrix A. If FACT = 'F' and EQUED is
-* not 'N', then A must have been equilibrated by the scaling
-* factors in R and/or C. A is not modified if FACT = 'F' or
-* 'N', or if FACT = 'E' and EQUED = 'N' on exit.
-*
-* On exit, if EQUED .ne. 'N', A is scaled as follows:
-* EQUED = 'R': A := diag(R) * A
-* EQUED = 'C': A := A * diag(C)
-* EQUED = 'B': A := diag(R) * A * diag(C).
-*
-* LDA (input) INTEGER
-* The leading dimension of the array A. LDA >= max(1,N).
-*
-* AF (input or output) DOUBLE PRECISION array, dimension (LDAF,N)
-* If FACT = 'F', then AF is an input argument and on entry
-* contains the factors L and U from the factorization
-* A = P*L*U as computed by DGETRF. If EQUED .ne. 'N', then
-* AF is the factored form of the equilibrated matrix A.
-*
-* If FACT = 'N', then AF is an output argument and on exit
-* returns the factors L and U from the factorization A = P*L*U
-* of the original matrix A.
-*
-* If FACT = 'E', then AF is an output argument and on exit
-* returns the factors L and U from the factorization A = P*L*U
-* of the equilibrated matrix A (see the description of A for
-* the form of the equilibrated matrix).
-*
-* LDAF (input) INTEGER
-* The leading dimension of the array AF. LDAF >= max(1,N).
-*
-* IPIV (input or output) INTEGER array, dimension (N)
-* If FACT = 'F', then IPIV is an input argument and on entry
-* contains the pivot indices from the factorization A = P*L*U
-* as computed by DGETRF; row i of the matrix was interchanged
-* with row IPIV(i).
-*
-* If FACT = 'N', then IPIV is an output argument and on exit
-* contains the pivot indices from the factorization A = P*L*U
-* of the original matrix A.
-*
-* If FACT = 'E', then IPIV is an output argument and on exit
-* contains the pivot indices from the factorization A = P*L*U
-* of the equilibrated matrix A.
-*
-* EQUED (input or output) CHARACTER*1
-* Specifies the form of equilibration that was done.
-* = 'N': No equilibration (always true if FACT = 'N').
-* = 'R': Row equilibration, i.e., A has been premultiplied by
-* diag(R).
-* = 'C': Column equilibration, i.e., A has been postmultiplied
-* by diag(C).
-* = 'B': Both row and column equilibration, i.e., A has been
-* replaced by diag(R) * A * diag(C).
-* EQUED is an input argument if FACT = 'F'; otherwise, it is an
-* output argument.
-*
-* R (input or output) DOUBLE PRECISION array, dimension (N)
-* The row scale factors for A. If EQUED = 'R' or 'B', A is
-* multiplied on the left by diag(R); if EQUED = 'N' or 'C', R
-* is not accessed. R is an input argument if FACT = 'F';
-* otherwise, R is an output argument. If FACT = 'F' and
-* EQUED = 'R' or 'B', each element of R must be positive.
-*
-* C (input or output) DOUBLE PRECISION array, dimension (N)
-* The column scale factors for A. If EQUED = 'C' or 'B', A is
-* multiplied on the right by diag(C); if EQUED = 'N' or 'R', C
-* is not accessed. C is an input argument if FACT = 'F';
-* otherwise, C is an output argument. If FACT = 'F' and
-* EQUED = 'C' or 'B', each element of C must be positive.
-*
-* B (input/output) DOUBLE PRECISION array, dimension (LDB,NRHS)
-* On entry, the N-by-NRHS right hand side matrix B.
-* On exit,
-* if EQUED = 'N', B is not modified;
-* if TRANS = 'N' and EQUED = 'R' or 'B', B is overwritten by
-* diag(R)*B;
-* if TRANS = 'T' or 'C' and EQUED = 'C' or 'B', B is
-* overwritten by diag(C)*B.
-*
-* LDB (input) INTEGER
-* The leading dimension of the array B. LDB >= max(1,N).
-*
-* X (output) DOUBLE PRECISION array, dimension (LDX,NRHS)
-* If INFO = 0 or INFO = N+1, the N-by-NRHS solution matrix X
-* to the original system of equations. Note that A and B are
-* modified on exit if EQUED .ne. 'N', and the solution to the
-* equilibrated system is inv(diag(C))*X if TRANS = 'N' and
-* EQUED = 'C' or 'B', or inv(diag(R))*X if TRANS = 'T' or 'C'
-* and EQUED = 'R' or 'B'.
-*
-* LDX (input) INTEGER
-* The leading dimension of the array X. LDX >= max(1,N).
-*
-* RCOND (output) DOUBLE PRECISION
-* The estimate of the reciprocal condition number of the matrix
-* A after equilibration (if done). If RCOND is less than the
-* machine precision (in particular, if RCOND = 0), the matrix
-* is singular to working precision. This condition is
-* indicated by a return code of INFO > 0.
-*
-* FERR (output) DOUBLE PRECISION array, dimension (NRHS)
-* The estimated forward error bound for each solution vector
-* X(j) (the j-th column of the solution matrix X).
-* If XTRUE is the true solution corresponding to X(j), FERR(j)
-* is an estimated upper bound for the magnitude of the largest
-* element in (X(j) - XTRUE) divided by the magnitude of the
-* largest element in X(j). The estimate is as reliable as
-* the estimate for RCOND, and is almost always a slight
-* overestimate of the true error.
-*
-* BERR (output) DOUBLE PRECISION array, dimension (NRHS)
-* The componentwise relative backward error of each solution
-* vector X(j) (i.e., the smallest relative change in
-* any element of A or B that makes X(j) an exact solution).
-*
-* WORK (workspace/output) DOUBLE PRECISION array, dimension (4*N)
-* On exit, WORK(1) contains the reciprocal pivot growth
-* factor norm(A)/norm(U). The "max absolute element" norm is
-* used. If WORK(1) is much less than 1, then the stability
-* of the LU factorization of the (equilibrated) matrix A
-* could be poor. This also means that the solution X, condition
-* estimator RCOND, and forward error bound FERR could be
-* unreliable. If factorization fails with 0<INFO<=N, then
-* WORK(1) contains the reciprocal pivot growth factor for the
-* leading INFO columns of A.
-*
-* IWORK (workspace) INTEGER array, dimension (N)
-*
-* INFO (output) INTEGER
-* = 0: successful exit
-* < 0: if INFO = -i, the i-th argument had an illegal value
-* > 0: if INFO = i, and i is
-* <= N: U(i,i) is exactly zero. The factorization has
-* been completed, but the factor U is exactly
-* singular, so the solution and error bounds
-* could not be computed. RCOND = 0 is returned.
-* = N+1: U is nonsingular, but RCOND is less than machine
-* precision, meaning that the matrix is singular
-* to working precision. Nevertheless, the
-* solution and error bounds are computed because
-* there are a number of situations where the
-* computed solution can be more accurate than the
-* value of RCOND would suggest.
-*
-* =====================================================================
-*
-* .. Parameters ..
- DOUBLE PRECISION ZERO, ONE
- PARAMETER ( ZERO = 0.0D+0, ONE = 1.0D+0 )
-* ..
-* .. Local Scalars ..
- LOGICAL COLEQU, EQUIL, NOFACT, NOTRAN, ROWEQU
- CHARACTER NORM
- INTEGER I, INFEQU, J
- DOUBLE PRECISION AMAX, ANORM, BIGNUM, COLCND, RCMAX, RCMIN,
- $ ROWCND, RPVGRW, SMLNUM
-* ..
-* .. External Functions ..
- LOGICAL LSAME
- DOUBLE PRECISION DLAMCH, DLANGE, DLANTR
- EXTERNAL LSAME, DLAMCH, DLANGE, DLANTR
-* ..
-* .. External Subroutines ..
- EXTERNAL DGECON, DGEEQU, DGERFS, DGETRF, DGETRS, DLACPY,
- $ DLAQGE, XERBLA
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC MAX, MIN
-* ..
-* .. Executable Statements ..
-*
- INFO = 0
- NOFACT = LSAME( FACT, 'N' )
- EQUIL = LSAME( FACT, 'E' )
- NOTRAN = LSAME( TRANS, 'N' )
- IF( NOFACT .OR. EQUIL ) THEN
- EQUED = 'N'
- ROWEQU = .FALSE.
- COLEQU = .FALSE.
- ELSE
- ROWEQU = LSAME( EQUED, 'R' ) .OR. LSAME( EQUED, 'B' )
- COLEQU = LSAME( EQUED, 'C' ) .OR. LSAME( EQUED, 'B' )
- SMLNUM = DLAMCH( 'Safe minimum' )
- BIGNUM = ONE / SMLNUM
- END IF
-*
-* Test the input parameters.
-*
- IF( .NOT.NOFACT .AND. .NOT.EQUIL .AND. .NOT.LSAME( FACT, 'F' ) )
- $ THEN
- INFO = -1
- ELSE IF( .NOT.NOTRAN .AND. .NOT.LSAME( TRANS, 'T' ) .AND. .NOT.
- $ LSAME( TRANS, 'C' ) ) THEN
- INFO = -2
- ELSE IF( N.LT.0 ) THEN
- INFO = -3
- ELSE IF( NRHS.LT.0 ) THEN
- INFO = -4
- ELSE IF( LDA.LT.MAX( 1, N ) ) THEN
- INFO = -6
- ELSE IF( LDAF.LT.MAX( 1, N ) ) THEN
- INFO = -8
- ELSE IF( LSAME( FACT, 'F' ) .AND. .NOT.
- $ ( ROWEQU .OR. COLEQU .OR. LSAME( EQUED, 'N' ) ) ) THEN
- INFO = -10
- ELSE
- IF( ROWEQU ) THEN
- RCMIN = BIGNUM
- RCMAX = ZERO
- DO 10 J = 1, N
- RCMIN = MIN( RCMIN, R( J ) )
- RCMAX = MAX( RCMAX, R( J ) )
- 10 CONTINUE
- IF( RCMIN.LE.ZERO ) THEN
- INFO = -11
- ELSE IF( N.GT.0 ) THEN
- ROWCND = MAX( RCMIN, SMLNUM ) / MIN( RCMAX, BIGNUM )
- ELSE
- ROWCND = ONE
- END IF
- END IF
- IF( COLEQU .AND. INFO.EQ.0 ) THEN
- RCMIN = BIGNUM
- RCMAX = ZERO
- DO 20 J = 1, N
- RCMIN = MIN( RCMIN, C( J ) )
- RCMAX = MAX( RCMAX, C( J ) )
- 20 CONTINUE
- IF( RCMIN.LE.ZERO ) THEN
- INFO = -12
- ELSE IF( N.GT.0 ) THEN
- COLCND = MAX( RCMIN, SMLNUM ) / MIN( RCMAX, BIGNUM )
- ELSE
- COLCND = ONE
- END IF
- END IF
- IF( INFO.EQ.0 ) THEN
- IF( LDB.LT.MAX( 1, N ) ) THEN
- INFO = -14
- ELSE IF( LDX.LT.MAX( 1, N ) ) THEN
- INFO = -16
- END IF
- END IF
- END IF
-*
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'DGESVX', -INFO )
- RETURN
- END IF
-*
- IF( EQUIL ) THEN
-*
-* Compute row and column scalings to equilibrate the matrix A.
-*
- CALL DGEEQU( N, N, A, LDA, R, C, ROWCND, COLCND, AMAX, INFEQU )
- IF( INFEQU.EQ.0 ) THEN
-*
-* Equilibrate the matrix.
-*
- CALL DLAQGE( N, N, A, LDA, R, C, ROWCND, COLCND, AMAX,
- $ EQUED )
- ROWEQU = LSAME( EQUED, 'R' ) .OR. LSAME( EQUED, 'B' )
- COLEQU = LSAME( EQUED, 'C' ) .OR. LSAME( EQUED, 'B' )
- END IF
- END IF
-*
-* Scale the right hand side.
-*
- IF( NOTRAN ) THEN
- IF( ROWEQU ) THEN
- DO 40 J = 1, NRHS
- DO 30 I = 1, N
- B( I, J ) = R( I )*B( I, J )
- 30 CONTINUE
- 40 CONTINUE
- END IF
- ELSE IF( COLEQU ) THEN
- DO 60 J = 1, NRHS
- DO 50 I = 1, N
- B( I, J ) = C( I )*B( I, J )
- 50 CONTINUE
- 60 CONTINUE
- END IF
-*
- IF( NOFACT .OR. EQUIL ) THEN
-*
-* Compute the LU factorization of A.
-*
- CALL DLACPY( 'Full', N, N, A, LDA, AF, LDAF )
- CALL DGETRF( N, N, AF, LDAF, IPIV, INFO )
-*
-* Return if INFO is non-zero.
-*
- IF( INFO.GT.0 ) THEN
-*
-* Compute the reciprocal pivot growth factor of the
-* leading rank-deficient INFO columns of A.
-*
- RPVGRW = DLANTR( 'M', 'U', 'N', INFO, INFO, AF, LDAF,
- $ WORK )
- IF( RPVGRW.EQ.ZERO ) THEN
- RPVGRW = ONE
- ELSE
- RPVGRW = DLANGE( 'M', N, INFO, A, LDA, WORK ) / RPVGRW
- END IF
- WORK( 1 ) = RPVGRW
- RCOND = ZERO
- RETURN
- END IF
- END IF
-*
-* Compute the norm of the matrix A and the
-* reciprocal pivot growth factor RPVGRW.
-*
- IF( NOTRAN ) THEN
- NORM = '1'
- ELSE
- NORM = 'I'
- END IF
- ANORM = DLANGE( NORM, N, N, A, LDA, WORK )
- RPVGRW = DLANTR( 'M', 'U', 'N', N, N, AF, LDAF, WORK )
- IF( RPVGRW.EQ.ZERO ) THEN
- RPVGRW = ONE
- ELSE
- RPVGRW = DLANGE( 'M', N, N, A, LDA, WORK ) / RPVGRW
- END IF
-*
-* Compute the reciprocal of the condition number of A.
-*
- CALL DGECON( NORM, N, AF, LDAF, ANORM, RCOND, WORK, IWORK, INFO )
-*
-* Compute the solution matrix X.
-*
- CALL DLACPY( 'Full', N, NRHS, B, LDB, X, LDX )
- CALL DGETRS( TRANS, N, NRHS, AF, LDAF, IPIV, X, LDX, INFO )
-*
-* Use iterative refinement to improve the computed solution and
-* compute error bounds and backward error estimates for it.
-*
- CALL DGERFS( TRANS, N, NRHS, A, LDA, AF, LDAF, IPIV, B, LDB, X,
- $ LDX, FERR, BERR, WORK, IWORK, INFO )
-*
-* Transform the solution matrix X to a solution of the original
-* system.
-*
- IF( NOTRAN ) THEN
- IF( COLEQU ) THEN
- DO 80 J = 1, NRHS
- DO 70 I = 1, N
- X( I, J ) = C( I )*X( I, J )
- 70 CONTINUE
- 80 CONTINUE
- DO 90 J = 1, NRHS
- FERR( J ) = FERR( J ) / COLCND
- 90 CONTINUE
- END IF
- ELSE IF( ROWEQU ) THEN
- DO 110 J = 1, NRHS
- DO 100 I = 1, N
- X( I, J ) = R( I )*X( I, J )
- 100 CONTINUE
- 110 CONTINUE
- DO 120 J = 1, NRHS
- FERR( J ) = FERR( J ) / ROWCND
- 120 CONTINUE
- END IF
-*
- WORK( 1 ) = RPVGRW
-*
-* Set INFO = N+1 if the matrix is singular to working precision.
-*
- IF( RCOND.LT.DLAMCH( 'Epsilon' ) )
- $ INFO = N + 1
- RETURN
-*
-* End of DGESVX
-*
- END
diff --git a/src/lib/lapack/dgetc2.f b/src/lib/lapack/dgetc2.f
deleted file mode 100644
index 5842b213..00000000
--- a/src/lib/lapack/dgetc2.f
+++ /dev/null
@@ -1,146 +0,0 @@
- SUBROUTINE DGETC2( N, A, LDA, IPIV, JPIV, INFO )
-*
-* -- LAPACK auxiliary routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- INTEGER INFO, LDA, N
-* ..
-* .. Array Arguments ..
- INTEGER IPIV( * ), JPIV( * )
- DOUBLE PRECISION A( LDA, * )
-* ..
-*
-* Purpose
-* =======
-*
-* DGETC2 computes an LU factorization with complete pivoting of the
-* n-by-n matrix A. The factorization has the form A = P * L * U * Q,
-* where P and Q are permutation matrices, L is lower triangular with
-* unit diagonal elements and U is upper triangular.
-*
-* This is the Level 2 BLAS algorithm.
-*
-* Arguments
-* =========
-*
-* N (input) INTEGER
-* The order of the matrix A. N >= 0.
-*
-* A (input/output) DOUBLE PRECISION array, dimension (LDA, N)
-* On entry, the n-by-n matrix A to be factored.
-* On exit, the factors L and U from the factorization
-* A = P*L*U*Q; the unit diagonal elements of L are not stored.
-* If U(k, k) appears to be less than SMIN, U(k, k) is given the
-* value of SMIN, i.e., giving a nonsingular perturbed system.
-*
-* LDA (input) INTEGER
-* The leading dimension of the array A. LDA >= max(1,N).
-*
-* IPIV (output) INTEGER array, dimension(N).
-* The pivot indices; for 1 <= i <= N, row i of the
-* matrix has been interchanged with row IPIV(i).
-*
-* JPIV (output) INTEGER array, dimension(N).
-* The pivot indices; for 1 <= j <= N, column j of the
-* matrix has been interchanged with column JPIV(j).
-*
-* INFO (output) INTEGER
-* = 0: successful exit
-* > 0: if INFO = k, U(k, k) is likely to produce owerflow if
-* we try to solve for x in Ax = b. So U is perturbed to
-* avoid the overflow.
-*
-* Further Details
-* ===============
-*
-* Based on contributions by
-* Bo Kagstrom and Peter Poromaa, Department of Computing Science,
-* Umea University, S-901 87 Umea, Sweden.
-*
-* =====================================================================
-*
-* .. Parameters ..
- DOUBLE PRECISION ZERO, ONE
- PARAMETER ( ZERO = 0.0D+0, ONE = 1.0D+0 )
-* ..
-* .. Local Scalars ..
- INTEGER I, IP, IPV, J, JP, JPV
- DOUBLE PRECISION BIGNUM, EPS, SMIN, SMLNUM, XMAX
-* ..
-* .. External Subroutines ..
- EXTERNAL DGER, DSWAP
-* ..
-* .. External Functions ..
- DOUBLE PRECISION DLAMCH
- EXTERNAL DLAMCH
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC ABS, MAX
-* ..
-* .. Executable Statements ..
-*
-* Set constants to control overflow
-*
- INFO = 0
- EPS = DLAMCH( 'P' )
- SMLNUM = DLAMCH( 'S' ) / EPS
- BIGNUM = ONE / SMLNUM
- CALL DLABAD( SMLNUM, BIGNUM )
-*
-* Factorize A using complete pivoting.
-* Set pivots less than SMIN to SMIN.
-*
- DO 40 I = 1, N - 1
-*
-* Find max element in matrix A
-*
- XMAX = ZERO
- DO 20 IP = I, N
- DO 10 JP = I, N
- IF( ABS( A( IP, JP ) ).GE.XMAX ) THEN
- XMAX = ABS( A( IP, JP ) )
- IPV = IP
- JPV = JP
- END IF
- 10 CONTINUE
- 20 CONTINUE
- IF( I.EQ.1 )
- $ SMIN = MAX( EPS*XMAX, SMLNUM )
-*
-* Swap rows
-*
- IF( IPV.NE.I )
- $ CALL DSWAP( N, A( IPV, 1 ), LDA, A( I, 1 ), LDA )
- IPIV( I ) = IPV
-*
-* Swap columns
-*
- IF( JPV.NE.I )
- $ CALL DSWAP( N, A( 1, JPV ), 1, A( 1, I ), 1 )
- JPIV( I ) = JPV
-*
-* Check for singularity
-*
- IF( ABS( A( I, I ) ).LT.SMIN ) THEN
- INFO = I
- A( I, I ) = SMIN
- END IF
- DO 30 J = I + 1, N
- A( J, I ) = A( J, I ) / A( I, I )
- 30 CONTINUE
- CALL DGER( N-I, N-I, -ONE, A( I+1, I ), 1, A( I, I+1 ), LDA,
- $ A( I+1, I+1 ), LDA )
- 40 CONTINUE
-*
- IF( ABS( A( N, N ) ).LT.SMIN ) THEN
- INFO = N
- A( N, N ) = SMIN
- END IF
-*
- RETURN
-*
-* End of DGETC2
-*
- END
diff --git a/src/lib/lapack/dgetf2.f b/src/lib/lapack/dgetf2.f
deleted file mode 100644
index 573b1408..00000000
--- a/src/lib/lapack/dgetf2.f
+++ /dev/null
@@ -1,147 +0,0 @@
- SUBROUTINE DGETF2( M, N, A, LDA, IPIV, INFO )
-*
-* -- LAPACK routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- INTEGER INFO, LDA, M, N
-* ..
-* .. Array Arguments ..
- INTEGER IPIV( * )
- DOUBLE PRECISION A( LDA, * )
-* ..
-*
-* Purpose
-* =======
-*
-* DGETF2 computes an LU factorization of a general m-by-n matrix A
-* using partial pivoting with row interchanges.
-*
-* The factorization has the form
-* A = P * L * U
-* where P is a permutation matrix, L is lower triangular with unit
-* diagonal elements (lower trapezoidal if m > n), and U is upper
-* triangular (upper trapezoidal if m < n).
-*
-* This is the right-looking Level 2 BLAS version of the algorithm.
-*
-* Arguments
-* =========
-*
-* M (input) INTEGER
-* The number of rows of the matrix A. M >= 0.
-*
-* N (input) INTEGER
-* The number of columns of the matrix A. N >= 0.
-*
-* A (input/output) DOUBLE PRECISION array, dimension (LDA,N)
-* On entry, the m by n matrix to be factored.
-* On exit, the factors L and U from the factorization
-* A = P*L*U; the unit diagonal elements of L are not stored.
-*
-* LDA (input) INTEGER
-* The leading dimension of the array A. LDA >= max(1,M).
-*
-* IPIV (output) INTEGER array, dimension (min(M,N))
-* The pivot indices; for 1 <= i <= min(M,N), row i of the
-* matrix was interchanged with row IPIV(i).
-*
-* INFO (output) INTEGER
-* = 0: successful exit
-* < 0: if INFO = -k, the k-th argument had an illegal value
-* > 0: if INFO = k, U(k,k) is exactly zero. The factorization
-* has been completed, but the factor U is exactly
-* singular, and division by zero will occur if it is used
-* to solve a system of equations.
-*
-* =====================================================================
-*
-* .. Parameters ..
- DOUBLE PRECISION ONE, ZERO
- PARAMETER ( ONE = 1.0D+0, ZERO = 0.0D+0 )
-* ..
-* .. Local Scalars ..
- DOUBLE PRECISION SFMIN
- INTEGER I, J, JP
-* ..
-* .. External Functions ..
- DOUBLE PRECISION DLAMCH
- INTEGER IDAMAX
- EXTERNAL DLAMCH, IDAMAX
-* ..
-* .. External Subroutines ..
- EXTERNAL DGER, DSCAL, DSWAP, XERBLA
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC MAX, MIN
-* ..
-* .. Executable Statements ..
-*
-* Test the input parameters.
-*
- INFO = 0
- IF( M.LT.0 ) THEN
- INFO = -1
- ELSE IF( N.LT.0 ) THEN
- INFO = -2
- ELSE IF( LDA.LT.MAX( 1, M ) ) THEN
- INFO = -4
- END IF
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'DGETF2', -INFO )
- RETURN
- END IF
-*
-* Quick return if possible
-*
- IF( M.EQ.0 .OR. N.EQ.0 )
- $ RETURN
-*
-* Compute machine safe minimum
-*
- SFMIN = DLAMCH('S')
-*
- DO 10 J = 1, MIN( M, N )
-*
-* Find pivot and test for singularity.
-*
- JP = J - 1 + IDAMAX( M-J+1, A( J, J ), 1 )
- IPIV( J ) = JP
- IF( A( JP, J ).NE.ZERO ) THEN
-*
-* Apply the interchange to columns 1:N.
-*
- IF( JP.NE.J )
- $ CALL DSWAP( N, A( J, 1 ), LDA, A( JP, 1 ), LDA )
-*
-* Compute elements J+1:M of J-th column.
-*
- IF( J.LT.M ) THEN
- IF( ABS(A( J, J )) .GE. SFMIN ) THEN
- CALL DSCAL( M-J, ONE / A( J, J ), A( J+1, J ), 1 )
- ELSE
- DO 20 I = 1, M-J
- A( J+I, J ) = A( J+I, J ) / A( J, J )
- 20 CONTINUE
- END IF
- END IF
-*
- ELSE IF( INFO.EQ.0 ) THEN
-*
- INFO = J
- END IF
-*
- IF( J.LT.MIN( M, N ) ) THEN
-*
-* Update trailing submatrix.
-*
- CALL DGER( M-J, N-J, -ONE, A( J+1, J ), 1, A( J, J+1 ), LDA,
- $ A( J+1, J+1 ), LDA )
- END IF
- 10 CONTINUE
- RETURN
-*
-* End of DGETF2
-*
- END
diff --git a/src/lib/lapack/dgetrf.f b/src/lib/lapack/dgetrf.f
deleted file mode 100644
index c5b9df33..00000000
--- a/src/lib/lapack/dgetrf.f
+++ /dev/null
@@ -1,159 +0,0 @@
- SUBROUTINE DGETRF( M, N, A, LDA, IPIV, INFO )
-*
-* -- LAPACK routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- INTEGER INFO, LDA, M, N
-* ..
-* .. Array Arguments ..
- INTEGER IPIV( * )
- DOUBLE PRECISION A( LDA, * )
-* ..
-*
-* Purpose
-* =======
-*
-* DGETRF computes an LU factorization of a general M-by-N matrix A
-* using partial pivoting with row interchanges.
-*
-* The factorization has the form
-* A = P * L * U
-* where P is a permutation matrix, L is lower triangular with unit
-* diagonal elements (lower trapezoidal if m > n), and U is upper
-* triangular (upper trapezoidal if m < n).
-*
-* This is the right-looking Level 3 BLAS version of the algorithm.
-*
-* Arguments
-* =========
-*
-* M (input) INTEGER
-* The number of rows of the matrix A. M >= 0.
-*
-* N (input) INTEGER
-* The number of columns of the matrix A. N >= 0.
-*
-* A (input/output) DOUBLE PRECISION array, dimension (LDA,N)
-* On entry, the M-by-N matrix to be factored.
-* On exit, the factors L and U from the factorization
-* A = P*L*U; the unit diagonal elements of L are not stored.
-*
-* LDA (input) INTEGER
-* The leading dimension of the array A. LDA >= max(1,M).
-*
-* IPIV (output) INTEGER array, dimension (min(M,N))
-* The pivot indices; for 1 <= i <= min(M,N), row i of the
-* matrix was interchanged with row IPIV(i).
-*
-* INFO (output) INTEGER
-* = 0: successful exit
-* < 0: if INFO = -i, the i-th argument had an illegal value
-* > 0: if INFO = i, U(i,i) is exactly zero. The factorization
-* has been completed, but the factor U is exactly
-* singular, and division by zero will occur if it is used
-* to solve a system of equations.
-*
-* =====================================================================
-*
-* .. Parameters ..
- DOUBLE PRECISION ONE
- PARAMETER ( ONE = 1.0D+0 )
-* ..
-* .. Local Scalars ..
- INTEGER I, IINFO, J, JB, NB
-* ..
-* .. External Subroutines ..
- EXTERNAL DGEMM, DGETF2, DLASWP, DTRSM, XERBLA
-* ..
-* .. External Functions ..
- INTEGER ILAENV
- EXTERNAL ILAENV
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC MAX, MIN
-* ..
-* .. Executable Statements ..
-*
-* Test the input parameters.
-*
- INFO = 0
- IF( M.LT.0 ) THEN
- INFO = -1
- ELSE IF( N.LT.0 ) THEN
- INFO = -2
- ELSE IF( LDA.LT.MAX( 1, M ) ) THEN
- INFO = -4
- END IF
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'DGETRF', -INFO )
- RETURN
- END IF
-*
-* Quick return if possible
-*
- IF( M.EQ.0 .OR. N.EQ.0 )
- $ RETURN
-*
-* Determine the block size for this environment.
-*
- NB = ILAENV( 1, 'DGETRF', ' ', M, N, -1, -1 )
- IF( NB.LE.1 .OR. NB.GE.MIN( M, N ) ) THEN
-*
-* Use unblocked code.
-*
- CALL DGETF2( M, N, A, LDA, IPIV, INFO )
- ELSE
-*
-* Use blocked code.
-*
- DO 20 J = 1, MIN( M, N ), NB
- JB = MIN( MIN( M, N )-J+1, NB )
-*
-* Factor diagonal and subdiagonal blocks and test for exact
-* singularity.
-*
- CALL DGETF2( M-J+1, JB, A( J, J ), LDA, IPIV( J ), IINFO )
-*
-* Adjust INFO and the pivot indices.
-*
- IF( INFO.EQ.0 .AND. IINFO.GT.0 )
- $ INFO = IINFO + J - 1
- DO 10 I = J, MIN( M, J+JB-1 )
- IPIV( I ) = J - 1 + IPIV( I )
- 10 CONTINUE
-*
-* Apply interchanges to columns 1:J-1.
-*
- CALL DLASWP( J-1, A, LDA, J, J+JB-1, IPIV, 1 )
-*
- IF( J+JB.LE.N ) THEN
-*
-* Apply interchanges to columns J+JB:N.
-*
- CALL DLASWP( N-J-JB+1, A( 1, J+JB ), LDA, J, J+JB-1,
- $ IPIV, 1 )
-*
-* Compute block row of U.
-*
- CALL DTRSM( 'Left', 'Lower', 'No transpose', 'Unit', JB,
- $ N-J-JB+1, ONE, A( J, J ), LDA, A( J, J+JB ),
- $ LDA )
- IF( J+JB.LE.M ) THEN
-*
-* Update trailing submatrix.
-*
- CALL DGEMM( 'No transpose', 'No transpose', M-J-JB+1,
- $ N-J-JB+1, JB, -ONE, A( J+JB, J ), LDA,
- $ A( J, J+JB ), LDA, ONE, A( J+JB, J+JB ),
- $ LDA )
- END IF
- END IF
- 20 CONTINUE
- END IF
- RETURN
-*
-* End of DGETRF
-*
- END
diff --git a/src/lib/lapack/dgetri.f b/src/lib/lapack/dgetri.f
deleted file mode 100644
index 9f1c1182..00000000
--- a/src/lib/lapack/dgetri.f
+++ /dev/null
@@ -1,192 +0,0 @@
- SUBROUTINE DGETRI( N, A, LDA, IPIV, WORK, LWORK, INFO )
-*
-* -- LAPACK routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- INTEGER INFO, LDA, LWORK, N
-* ..
-* .. Array Arguments ..
- INTEGER IPIV( * )
- DOUBLE PRECISION A( LDA, * ), WORK( * )
-* ..
-*
-* Purpose
-* =======
-*
-* DGETRI computes the inverse of a matrix using the LU factorization
-* computed by DGETRF.
-*
-* This method inverts U and then computes inv(A) by solving the system
-* inv(A)*L = inv(U) for inv(A).
-*
-* Arguments
-* =========
-*
-* N (input) INTEGER
-* The order of the matrix A. N >= 0.
-*
-* A (input/output) DOUBLE PRECISION array, dimension (LDA,N)
-* On entry, the factors L and U from the factorization
-* A = P*L*U as computed by DGETRF.
-* On exit, if INFO = 0, the inverse of the original matrix A.
-*
-* LDA (input) INTEGER
-* The leading dimension of the array A. LDA >= max(1,N).
-*
-* IPIV (input) INTEGER array, dimension (N)
-* The pivot indices from DGETRF; for 1<=i<=N, row i of the
-* matrix was interchanged with row IPIV(i).
-*
-* WORK (workspace/output) DOUBLE PRECISION array, dimension (MAX(1,LWORK))
-* On exit, if INFO=0, then WORK(1) returns the optimal LWORK.
-*
-* LWORK (input) INTEGER
-* The dimension of the array WORK. LWORK >= max(1,N).
-* For optimal performance LWORK >= N*NB, where NB is
-* the optimal blocksize returned by ILAENV.
-*
-* If LWORK = -1, then a workspace query is assumed; the routine
-* only calculates the optimal size of the WORK array, returns
-* this value as the first entry of the WORK array, and no error
-* message related to LWORK is issued by XERBLA.
-*
-* INFO (output) INTEGER
-* = 0: successful exit
-* < 0: if INFO = -i, the i-th argument had an illegal value
-* > 0: if INFO = i, U(i,i) is exactly zero; the matrix is
-* singular and its inverse could not be computed.
-*
-* =====================================================================
-*
-* .. Parameters ..
- DOUBLE PRECISION ZERO, ONE
- PARAMETER ( ZERO = 0.0D+0, ONE = 1.0D+0 )
-* ..
-* .. Local Scalars ..
- LOGICAL LQUERY
- INTEGER I, IWS, J, JB, JJ, JP, LDWORK, LWKOPT, NB,
- $ NBMIN, NN
-* ..
-* .. External Functions ..
- INTEGER ILAENV
- EXTERNAL ILAENV
-* ..
-* .. External Subroutines ..
- EXTERNAL DGEMM, DGEMV, DSWAP, DTRSM, DTRTRI, XERBLA
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC MAX, MIN
-* ..
-* .. Executable Statements ..
-*
-* Test the input parameters.
-*
- INFO = 0
- NB = ILAENV( 1, 'DGETRI', ' ', N, -1, -1, -1 )
- LWKOPT = N*NB
- WORK( 1 ) = LWKOPT
- LQUERY = ( LWORK.EQ.-1 )
- IF( N.LT.0 ) THEN
- INFO = -1
- ELSE IF( LDA.LT.MAX( 1, N ) ) THEN
- INFO = -3
- ELSE IF( LWORK.LT.MAX( 1, N ) .AND. .NOT.LQUERY ) THEN
- INFO = -6
- END IF
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'DGETRI', -INFO )
- RETURN
- ELSE IF( LQUERY ) THEN
- RETURN
- END IF
-*
-* Quick return if possible
-*
- IF( N.EQ.0 )
- $ RETURN
-*
-* Form inv(U). If INFO > 0 from DTRTRI, then U is singular,
-* and the inverse is not computed.
-*
- CALL DTRTRI( 'Upper', 'Non-unit', N, A, LDA, INFO )
- IF( INFO.GT.0 )
- $ RETURN
-*
- NBMIN = 2
- LDWORK = N
- IF( NB.GT.1 .AND. NB.LT.N ) THEN
- IWS = MAX( LDWORK*NB, 1 )
- IF( LWORK.LT.IWS ) THEN
- NB = LWORK / LDWORK
- NBMIN = MAX( 2, ILAENV( 2, 'DGETRI', ' ', N, -1, -1, -1 ) )
- END IF
- ELSE
- IWS = N
- END IF
-*
-* Solve the equation inv(A)*L = inv(U) for inv(A).
-*
- IF( NB.LT.NBMIN .OR. NB.GE.N ) THEN
-*
-* Use unblocked code.
-*
- DO 20 J = N, 1, -1
-*
-* Copy current column of L to WORK and replace with zeros.
-*
- DO 10 I = J + 1, N
- WORK( I ) = A( I, J )
- A( I, J ) = ZERO
- 10 CONTINUE
-*
-* Compute current column of inv(A).
-*
- IF( J.LT.N )
- $ CALL DGEMV( 'No transpose', N, N-J, -ONE, A( 1, J+1 ),
- $ LDA, WORK( J+1 ), 1, ONE, A( 1, J ), 1 )
- 20 CONTINUE
- ELSE
-*
-* Use blocked code.
-*
- NN = ( ( N-1 ) / NB )*NB + 1
- DO 50 J = NN, 1, -NB
- JB = MIN( NB, N-J+1 )
-*
-* Copy current block column of L to WORK and replace with
-* zeros.
-*
- DO 40 JJ = J, J + JB - 1
- DO 30 I = JJ + 1, N
- WORK( I+( JJ-J )*LDWORK ) = A( I, JJ )
- A( I, JJ ) = ZERO
- 30 CONTINUE
- 40 CONTINUE
-*
-* Compute current block column of inv(A).
-*
- IF( J+JB.LE.N )
- $ CALL DGEMM( 'No transpose', 'No transpose', N, JB,
- $ N-J-JB+1, -ONE, A( 1, J+JB ), LDA,
- $ WORK( J+JB ), LDWORK, ONE, A( 1, J ), LDA )
- CALL DTRSM( 'Right', 'Lower', 'No transpose', 'Unit', N, JB,
- $ ONE, WORK( J ), LDWORK, A( 1, J ), LDA )
- 50 CONTINUE
- END IF
-*
-* Apply column interchanges.
-*
- DO 60 J = N - 1, 1, -1
- JP = IPIV( J )
- IF( JP.NE.J )
- $ CALL DSWAP( N, A( 1, J ), 1, A( 1, JP ), 1 )
- 60 CONTINUE
-*
- WORK( 1 ) = IWS
- RETURN
-*
-* End of DGETRI
-*
- END
diff --git a/src/lib/lapack/dgetrs.f b/src/lib/lapack/dgetrs.f
deleted file mode 100644
index b7d17b0a..00000000
--- a/src/lib/lapack/dgetrs.f
+++ /dev/null
@@ -1,149 +0,0 @@
- SUBROUTINE DGETRS( TRANS, N, NRHS, A, LDA, IPIV, B, LDB, INFO )
-*
-* -- LAPACK routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- CHARACTER TRANS
- INTEGER INFO, LDA, LDB, N, NRHS
-* ..
-* .. Array Arguments ..
- INTEGER IPIV( * )
- DOUBLE PRECISION A( LDA, * ), B( LDB, * )
-* ..
-*
-* Purpose
-* =======
-*
-* DGETRS solves a system of linear equations
-* A * X = B or A' * X = B
-* with a general N-by-N matrix A using the LU factorization computed
-* by DGETRF.
-*
-* Arguments
-* =========
-*
-* TRANS (input) CHARACTER*1
-* Specifies the form of the system of equations:
-* = 'N': A * X = B (No transpose)
-* = 'T': A'* X = B (Transpose)
-* = 'C': A'* X = B (Conjugate transpose = Transpose)
-*
-* N (input) INTEGER
-* The order of the matrix A. N >= 0.
-*
-* NRHS (input) INTEGER
-* The number of right hand sides, i.e., the number of columns
-* of the matrix B. NRHS >= 0.
-*
-* A (input) DOUBLE PRECISION array, dimension (LDA,N)
-* The factors L and U from the factorization A = P*L*U
-* as computed by DGETRF.
-*
-* LDA (input) INTEGER
-* The leading dimension of the array A. LDA >= max(1,N).
-*
-* IPIV (input) INTEGER array, dimension (N)
-* The pivot indices from DGETRF; for 1<=i<=N, row i of the
-* matrix was interchanged with row IPIV(i).
-*
-* B (input/output) DOUBLE PRECISION array, dimension (LDB,NRHS)
-* On entry, the right hand side matrix B.
-* On exit, the solution matrix X.
-*
-* LDB (input) INTEGER
-* The leading dimension of the array B. LDB >= max(1,N).
-*
-* INFO (output) INTEGER
-* = 0: successful exit
-* < 0: if INFO = -i, the i-th argument had an illegal value
-*
-* =====================================================================
-*
-* .. Parameters ..
- DOUBLE PRECISION ONE
- PARAMETER ( ONE = 1.0D+0 )
-* ..
-* .. Local Scalars ..
- LOGICAL NOTRAN
-* ..
-* .. External Functions ..
- LOGICAL LSAME
- EXTERNAL LSAME
-* ..
-* .. External Subroutines ..
- EXTERNAL DLASWP, DTRSM, XERBLA
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC MAX
-* ..
-* .. Executable Statements ..
-*
-* Test the input parameters.
-*
- INFO = 0
- NOTRAN = LSAME( TRANS, 'N' )
- IF( .NOT.NOTRAN .AND. .NOT.LSAME( TRANS, 'T' ) .AND. .NOT.
- $ LSAME( TRANS, 'C' ) ) THEN
- INFO = -1
- ELSE IF( N.LT.0 ) THEN
- INFO = -2
- ELSE IF( NRHS.LT.0 ) THEN
- INFO = -3
- ELSE IF( LDA.LT.MAX( 1, N ) ) THEN
- INFO = -5
- ELSE IF( LDB.LT.MAX( 1, N ) ) THEN
- INFO = -8
- END IF
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'DGETRS', -INFO )
- RETURN
- END IF
-*
-* Quick return if possible
-*
- IF( N.EQ.0 .OR. NRHS.EQ.0 )
- $ RETURN
-*
- IF( NOTRAN ) THEN
-*
-* Solve A * X = B.
-*
-* Apply row interchanges to the right hand sides.
-*
- CALL DLASWP( NRHS, B, LDB, 1, N, IPIV, 1 )
-*
-* Solve L*X = B, overwriting B with X.
-*
- CALL DTRSM( 'Left', 'Lower', 'No transpose', 'Unit', N, NRHS,
- $ ONE, A, LDA, B, LDB )
-*
-* Solve U*X = B, overwriting B with X.
-*
- CALL DTRSM( 'Left', 'Upper', 'No transpose', 'Non-unit', N,
- $ NRHS, ONE, A, LDA, B, LDB )
- ELSE
-*
-* Solve A' * X = B.
-*
-* Solve U'*X = B, overwriting B with X.
-*
- CALL DTRSM( 'Left', 'Upper', 'Transpose', 'Non-unit', N, NRHS,
- $ ONE, A, LDA, B, LDB )
-*
-* Solve L'*X = B, overwriting B with X.
-*
- CALL DTRSM( 'Left', 'Lower', 'Transpose', 'Unit', N, NRHS, ONE,
- $ A, LDA, B, LDB )
-*
-* Apply row interchanges to the solution vectors.
-*
- CALL DLASWP( NRHS, B, LDB, 1, N, IPIV, -1 )
- END IF
-*
- RETURN
-*
-* End of DGETRS
-*
- END
diff --git a/src/lib/lapack/dggbak.f b/src/lib/lapack/dggbak.f
deleted file mode 100644
index 8ed9fbd4..00000000
--- a/src/lib/lapack/dggbak.f
+++ /dev/null
@@ -1,220 +0,0 @@
- SUBROUTINE DGGBAK( JOB, SIDE, N, ILO, IHI, LSCALE, RSCALE, M, V,
- $ LDV, INFO )
-*
-* -- LAPACK routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- CHARACTER JOB, SIDE
- INTEGER IHI, ILO, INFO, LDV, M, N
-* ..
-* .. Array Arguments ..
- DOUBLE PRECISION LSCALE( * ), RSCALE( * ), V( LDV, * )
-* ..
-*
-* Purpose
-* =======
-*
-* DGGBAK forms the right or left eigenvectors of a real generalized
-* eigenvalue problem A*x = lambda*B*x, by backward transformation on
-* the computed eigenvectors of the balanced pair of matrices output by
-* DGGBAL.
-*
-* Arguments
-* =========
-*
-* JOB (input) CHARACTER*1
-* Specifies the type of backward transformation required:
-* = 'N': do nothing, return immediately;
-* = 'P': do backward transformation for permutation only;
-* = 'S': do backward transformation for scaling only;
-* = 'B': do backward transformations for both permutation and
-* scaling.
-* JOB must be the same as the argument JOB supplied to DGGBAL.
-*
-* SIDE (input) CHARACTER*1
-* = 'R': V contains right eigenvectors;
-* = 'L': V contains left eigenvectors.
-*
-* N (input) INTEGER
-* The number of rows of the matrix V. N >= 0.
-*
-* ILO (input) INTEGER
-* IHI (input) INTEGER
-* The integers ILO and IHI determined by DGGBAL.
-* 1 <= ILO <= IHI <= N, if N > 0; ILO=1 and IHI=0, if N=0.
-*
-* LSCALE (input) DOUBLE PRECISION array, dimension (N)
-* Details of the permutations and/or scaling factors applied
-* to the left side of A and B, as returned by DGGBAL.
-*
-* RSCALE (input) DOUBLE PRECISION array, dimension (N)
-* Details of the permutations and/or scaling factors applied
-* to the right side of A and B, as returned by DGGBAL.
-*
-* M (input) INTEGER
-* The number of columns of the matrix V. M >= 0.
-*
-* V (input/output) DOUBLE PRECISION array, dimension (LDV,M)
-* On entry, the matrix of right or left eigenvectors to be
-* transformed, as returned by DTGEVC.
-* On exit, V is overwritten by the transformed eigenvectors.
-*
-* LDV (input) INTEGER
-* The leading dimension of the matrix V. LDV >= max(1,N).
-*
-* INFO (output) INTEGER
-* = 0: successful exit.
-* < 0: if INFO = -i, the i-th argument had an illegal value.
-*
-* Further Details
-* ===============
-*
-* See R.C. Ward, Balancing the generalized eigenvalue problem,
-* SIAM J. Sci. Stat. Comp. 2 (1981), 141-152.
-*
-* =====================================================================
-*
-* .. Local Scalars ..
- LOGICAL LEFTV, RIGHTV
- INTEGER I, K
-* ..
-* .. External Functions ..
- LOGICAL LSAME
- EXTERNAL LSAME
-* ..
-* .. External Subroutines ..
- EXTERNAL DSCAL, DSWAP, XERBLA
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC MAX
-* ..
-* .. Executable Statements ..
-*
-* Test the input parameters
-*
- RIGHTV = LSAME( SIDE, 'R' )
- LEFTV = LSAME( SIDE, 'L' )
-*
- INFO = 0
- IF( .NOT.LSAME( JOB, 'N' ) .AND. .NOT.LSAME( JOB, 'P' ) .AND.
- $ .NOT.LSAME( JOB, 'S' ) .AND. .NOT.LSAME( JOB, 'B' ) ) THEN
- INFO = -1
- ELSE IF( .NOT.RIGHTV .AND. .NOT.LEFTV ) THEN
- INFO = -2
- ELSE IF( N.LT.0 ) THEN
- INFO = -3
- ELSE IF( ILO.LT.1 ) THEN
- INFO = -4
- ELSE IF( N.EQ.0 .AND. IHI.EQ.0 .AND. ILO.NE.1 ) THEN
- INFO = -4
- ELSE IF( N.GT.0 .AND. ( IHI.LT.ILO .OR. IHI.GT.MAX( 1, N ) ) )
- $ THEN
- INFO = -5
- ELSE IF( N.EQ.0 .AND. ILO.EQ.1 .AND. IHI.NE.0 ) THEN
- INFO = -5
- ELSE IF( M.LT.0 ) THEN
- INFO = -8
- ELSE IF( LDV.LT.MAX( 1, N ) ) THEN
- INFO = -10
- END IF
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'DGGBAK', -INFO )
- RETURN
- END IF
-*
-* Quick return if possible
-*
- IF( N.EQ.0 )
- $ RETURN
- IF( M.EQ.0 )
- $ RETURN
- IF( LSAME( JOB, 'N' ) )
- $ RETURN
-*
- IF( ILO.EQ.IHI )
- $ GO TO 30
-*
-* Backward balance
-*
- IF( LSAME( JOB, 'S' ) .OR. LSAME( JOB, 'B' ) ) THEN
-*
-* Backward transformation on right eigenvectors
-*
- IF( RIGHTV ) THEN
- DO 10 I = ILO, IHI
- CALL DSCAL( M, RSCALE( I ), V( I, 1 ), LDV )
- 10 CONTINUE
- END IF
-*
-* Backward transformation on left eigenvectors
-*
- IF( LEFTV ) THEN
- DO 20 I = ILO, IHI
- CALL DSCAL( M, LSCALE( I ), V( I, 1 ), LDV )
- 20 CONTINUE
- END IF
- END IF
-*
-* Backward permutation
-*
- 30 CONTINUE
- IF( LSAME( JOB, 'P' ) .OR. LSAME( JOB, 'B' ) ) THEN
-*
-* Backward permutation on right eigenvectors
-*
- IF( RIGHTV ) THEN
- IF( ILO.EQ.1 )
- $ GO TO 50
-*
- DO 40 I = ILO - 1, 1, -1
- K = RSCALE( I )
- IF( K.EQ.I )
- $ GO TO 40
- CALL DSWAP( M, V( I, 1 ), LDV, V( K, 1 ), LDV )
- 40 CONTINUE
-*
- 50 CONTINUE
- IF( IHI.EQ.N )
- $ GO TO 70
- DO 60 I = IHI + 1, N
- K = RSCALE( I )
- IF( K.EQ.I )
- $ GO TO 60
- CALL DSWAP( M, V( I, 1 ), LDV, V( K, 1 ), LDV )
- 60 CONTINUE
- END IF
-*
-* Backward permutation on left eigenvectors
-*
- 70 CONTINUE
- IF( LEFTV ) THEN
- IF( ILO.EQ.1 )
- $ GO TO 90
- DO 80 I = ILO - 1, 1, -1
- K = LSCALE( I )
- IF( K.EQ.I )
- $ GO TO 80
- CALL DSWAP( M, V( I, 1 ), LDV, V( K, 1 ), LDV )
- 80 CONTINUE
-*
- 90 CONTINUE
- IF( IHI.EQ.N )
- $ GO TO 110
- DO 100 I = IHI + 1, N
- K = LSCALE( I )
- IF( K.EQ.I )
- $ GO TO 100
- CALL DSWAP( M, V( I, 1 ), LDV, V( K, 1 ), LDV )
- 100 CONTINUE
- END IF
- END IF
-*
- 110 CONTINUE
-*
- RETURN
-*
-* End of DGGBAK
-*
- END
diff --git a/src/lib/lapack/dggbal.f b/src/lib/lapack/dggbal.f
deleted file mode 100644
index 2034880a..00000000
--- a/src/lib/lapack/dggbal.f
+++ /dev/null
@@ -1,469 +0,0 @@
- SUBROUTINE DGGBAL( JOB, N, A, LDA, B, LDB, ILO, IHI, LSCALE,
- $ RSCALE, WORK, INFO )
-*
-* -- LAPACK routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- CHARACTER JOB
- INTEGER IHI, ILO, INFO, LDA, LDB, N
-* ..
-* .. Array Arguments ..
- DOUBLE PRECISION A( LDA, * ), B( LDB, * ), LSCALE( * ),
- $ RSCALE( * ), WORK( * )
-* ..
-*
-* Purpose
-* =======
-*
-* DGGBAL balances a pair of general real matrices (A,B). This
-* involves, first, permuting A and B by similarity transformations to
-* isolate eigenvalues in the first 1 to ILO$-$1 and last IHI+1 to N
-* elements on the diagonal; and second, applying a diagonal similarity
-* transformation to rows and columns ILO to IHI to make the rows
-* and columns as close in norm as possible. Both steps are optional.
-*
-* Balancing may reduce the 1-norm of the matrices, and improve the
-* accuracy of the computed eigenvalues and/or eigenvectors in the
-* generalized eigenvalue problem A*x = lambda*B*x.
-*
-* Arguments
-* =========
-*
-* JOB (input) CHARACTER*1
-* Specifies the operations to be performed on A and B:
-* = 'N': none: simply set ILO = 1, IHI = N, LSCALE(I) = 1.0
-* and RSCALE(I) = 1.0 for i = 1,...,N.
-* = 'P': permute only;
-* = 'S': scale only;
-* = 'B': both permute and scale.
-*
-* N (input) INTEGER
-* The order of the matrices A and B. N >= 0.
-*
-* A (input/output) DOUBLE PRECISION array, dimension (LDA,N)
-* On entry, the input matrix A.
-* On exit, A is overwritten by the balanced matrix.
-* If JOB = 'N', A is not referenced.
-*
-* LDA (input) INTEGER
-* The leading dimension of the array A. LDA >= max(1,N).
-*
-* B (input/output) DOUBLE PRECISION array, dimension (LDB,N)
-* On entry, the input matrix B.
-* On exit, B is overwritten by the balanced matrix.
-* If JOB = 'N', B is not referenced.
-*
-* LDB (input) INTEGER
-* The leading dimension of the array B. LDB >= max(1,N).
-*
-* ILO (output) INTEGER
-* IHI (output) INTEGER
-* ILO and IHI are set to integers such that on exit
-* A(i,j) = 0 and B(i,j) = 0 if i > j and
-* j = 1,...,ILO-1 or i = IHI+1,...,N.
-* If JOB = 'N' or 'S', ILO = 1 and IHI = N.
-*
-* LSCALE (output) DOUBLE PRECISION array, dimension (N)
-* Details of the permutations and scaling factors applied
-* to the left side of A and B. If P(j) is the index of the
-* row interchanged with row j, and D(j)
-* is the scaling factor applied to row j, then
-* LSCALE(j) = P(j) for J = 1,...,ILO-1
-* = D(j) for J = ILO,...,IHI
-* = P(j) for J = IHI+1,...,N.
-* The order in which the interchanges are made is N to IHI+1,
-* then 1 to ILO-1.
-*
-* RSCALE (output) DOUBLE PRECISION array, dimension (N)
-* Details of the permutations and scaling factors applied
-* to the right side of A and B. If P(j) is the index of the
-* column interchanged with column j, and D(j)
-* is the scaling factor applied to column j, then
-* LSCALE(j) = P(j) for J = 1,...,ILO-1
-* = D(j) for J = ILO,...,IHI
-* = P(j) for J = IHI+1,...,N.
-* The order in which the interchanges are made is N to IHI+1,
-* then 1 to ILO-1.
-*
-* WORK (workspace) REAL array, dimension (lwork)
-* lwork must be at least max(1,6*N) when JOB = 'S' or 'B', and
-* at least 1 when JOB = 'N' or 'P'.
-*
-* INFO (output) INTEGER
-* = 0: successful exit
-* < 0: if INFO = -i, the i-th argument had an illegal value.
-*
-* Further Details
-* ===============
-*
-* See R.C. WARD, Balancing the generalized eigenvalue problem,
-* SIAM J. Sci. Stat. Comp. 2 (1981), 141-152.
-*
-* =====================================================================
-*
-* .. Parameters ..
- DOUBLE PRECISION ZERO, HALF, ONE
- PARAMETER ( ZERO = 0.0D+0, HALF = 0.5D+0, ONE = 1.0D+0 )
- DOUBLE PRECISION THREE, SCLFAC
- PARAMETER ( THREE = 3.0D+0, SCLFAC = 1.0D+1 )
-* ..
-* .. Local Scalars ..
- INTEGER I, ICAB, IFLOW, IP1, IR, IRAB, IT, J, JC, JP1,
- $ K, KOUNT, L, LCAB, LM1, LRAB, LSFMAX, LSFMIN,
- $ M, NR, NRP2
- DOUBLE PRECISION ALPHA, BASL, BETA, CAB, CMAX, COEF, COEF2,
- $ COEF5, COR, EW, EWC, GAMMA, PGAMMA, RAB, SFMAX,
- $ SFMIN, SUM, T, TA, TB, TC
-* ..
-* .. External Functions ..
- LOGICAL LSAME
- INTEGER IDAMAX
- DOUBLE PRECISION DDOT, DLAMCH
- EXTERNAL LSAME, IDAMAX, DDOT, DLAMCH
-* ..
-* .. External Subroutines ..
- EXTERNAL DAXPY, DSCAL, DSWAP, XERBLA
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC ABS, DBLE, INT, LOG10, MAX, MIN, SIGN
-* ..
-* .. Executable Statements ..
-*
-* Test the input parameters
-*
- INFO = 0
- IF( .NOT.LSAME( JOB, 'N' ) .AND. .NOT.LSAME( JOB, 'P' ) .AND.
- $ .NOT.LSAME( JOB, 'S' ) .AND. .NOT.LSAME( JOB, 'B' ) ) THEN
- INFO = -1
- ELSE IF( N.LT.0 ) THEN
- INFO = -2
- ELSE IF( LDA.LT.MAX( 1, N ) ) THEN
- INFO = -4
- ELSE IF( LDB.LT.MAX( 1, N ) ) THEN
- INFO = -6
- END IF
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'DGGBAL', -INFO )
- RETURN
- END IF
-*
-* Quick return if possible
-*
- IF( N.EQ.0 ) THEN
- ILO = 1
- IHI = N
- RETURN
- END IF
-*
- IF( N.EQ.1 ) THEN
- ILO = 1
- IHI = N
- LSCALE( 1 ) = ONE
- RSCALE( 1 ) = ONE
- RETURN
- END IF
-*
- IF( LSAME( JOB, 'N' ) ) THEN
- ILO = 1
- IHI = N
- DO 10 I = 1, N
- LSCALE( I ) = ONE
- RSCALE( I ) = ONE
- 10 CONTINUE
- RETURN
- END IF
-*
- K = 1
- L = N
- IF( LSAME( JOB, 'S' ) )
- $ GO TO 190
-*
- GO TO 30
-*
-* Permute the matrices A and B to isolate the eigenvalues.
-*
-* Find row with one nonzero in columns 1 through L
-*
- 20 CONTINUE
- L = LM1
- IF( L.NE.1 )
- $ GO TO 30
-*
- RSCALE( 1 ) = ONE
- LSCALE( 1 ) = ONE
- GO TO 190
-*
- 30 CONTINUE
- LM1 = L - 1
- DO 80 I = L, 1, -1
- DO 40 J = 1, LM1
- JP1 = J + 1
- IF( A( I, J ).NE.ZERO .OR. B( I, J ).NE.ZERO )
- $ GO TO 50
- 40 CONTINUE
- J = L
- GO TO 70
-*
- 50 CONTINUE
- DO 60 J = JP1, L
- IF( A( I, J ).NE.ZERO .OR. B( I, J ).NE.ZERO )
- $ GO TO 80
- 60 CONTINUE
- J = JP1 - 1
-*
- 70 CONTINUE
- M = L
- IFLOW = 1
- GO TO 160
- 80 CONTINUE
- GO TO 100
-*
-* Find column with one nonzero in rows K through N
-*
- 90 CONTINUE
- K = K + 1
-*
- 100 CONTINUE
- DO 150 J = K, L
- DO 110 I = K, LM1
- IP1 = I + 1
- IF( A( I, J ).NE.ZERO .OR. B( I, J ).NE.ZERO )
- $ GO TO 120
- 110 CONTINUE
- I = L
- GO TO 140
- 120 CONTINUE
- DO 130 I = IP1, L
- IF( A( I, J ).NE.ZERO .OR. B( I, J ).NE.ZERO )
- $ GO TO 150
- 130 CONTINUE
- I = IP1 - 1
- 140 CONTINUE
- M = K
- IFLOW = 2
- GO TO 160
- 150 CONTINUE
- GO TO 190
-*
-* Permute rows M and I
-*
- 160 CONTINUE
- LSCALE( M ) = I
- IF( I.EQ.M )
- $ GO TO 170
- CALL DSWAP( N-K+1, A( I, K ), LDA, A( M, K ), LDA )
- CALL DSWAP( N-K+1, B( I, K ), LDB, B( M, K ), LDB )
-*
-* Permute columns M and J
-*
- 170 CONTINUE
- RSCALE( M ) = J
- IF( J.EQ.M )
- $ GO TO 180
- CALL DSWAP( L, A( 1, J ), 1, A( 1, M ), 1 )
- CALL DSWAP( L, B( 1, J ), 1, B( 1, M ), 1 )
-*
- 180 CONTINUE
- GO TO ( 20, 90 )IFLOW
-*
- 190 CONTINUE
- ILO = K
- IHI = L
-*
- IF( LSAME( JOB, 'P' ) ) THEN
- DO 195 I = ILO, IHI
- LSCALE( I ) = ONE
- RSCALE( I ) = ONE
- 195 CONTINUE
- RETURN
- END IF
-*
- IF( ILO.EQ.IHI )
- $ RETURN
-*
-* Balance the submatrix in rows ILO to IHI.
-*
- NR = IHI - ILO + 1
- DO 200 I = ILO, IHI
- RSCALE( I ) = ZERO
- LSCALE( I ) = ZERO
-*
- WORK( I ) = ZERO
- WORK( I+N ) = ZERO
- WORK( I+2*N ) = ZERO
- WORK( I+3*N ) = ZERO
- WORK( I+4*N ) = ZERO
- WORK( I+5*N ) = ZERO
- 200 CONTINUE
-*
-* Compute right side vector in resulting linear equations
-*
- BASL = LOG10( SCLFAC )
- DO 240 I = ILO, IHI
- DO 230 J = ILO, IHI
- TB = B( I, J )
- TA = A( I, J )
- IF( TA.EQ.ZERO )
- $ GO TO 210
- TA = LOG10( ABS( TA ) ) / BASL
- 210 CONTINUE
- IF( TB.EQ.ZERO )
- $ GO TO 220
- TB = LOG10( ABS( TB ) ) / BASL
- 220 CONTINUE
- WORK( I+4*N ) = WORK( I+4*N ) - TA - TB
- WORK( J+5*N ) = WORK( J+5*N ) - TA - TB
- 230 CONTINUE
- 240 CONTINUE
-*
- COEF = ONE / DBLE( 2*NR )
- COEF2 = COEF*COEF
- COEF5 = HALF*COEF2
- NRP2 = NR + 2
- BETA = ZERO
- IT = 1
-*
-* Start generalized conjugate gradient iteration
-*
- 250 CONTINUE
-*
- GAMMA = DDOT( NR, WORK( ILO+4*N ), 1, WORK( ILO+4*N ), 1 ) +
- $ DDOT( NR, WORK( ILO+5*N ), 1, WORK( ILO+5*N ), 1 )
-*
- EW = ZERO
- EWC = ZERO
- DO 260 I = ILO, IHI
- EW = EW + WORK( I+4*N )
- EWC = EWC + WORK( I+5*N )
- 260 CONTINUE
-*
- GAMMA = COEF*GAMMA - COEF2*( EW**2+EWC**2 ) - COEF5*( EW-EWC )**2
- IF( GAMMA.EQ.ZERO )
- $ GO TO 350
- IF( IT.NE.1 )
- $ BETA = GAMMA / PGAMMA
- T = COEF5*( EWC-THREE*EW )
- TC = COEF5*( EW-THREE*EWC )
-*
- CALL DSCAL( NR, BETA, WORK( ILO ), 1 )
- CALL DSCAL( NR, BETA, WORK( ILO+N ), 1 )
-*
- CALL DAXPY( NR, COEF, WORK( ILO+4*N ), 1, WORK( ILO+N ), 1 )
- CALL DAXPY( NR, COEF, WORK( ILO+5*N ), 1, WORK( ILO ), 1 )
-*
- DO 270 I = ILO, IHI
- WORK( I ) = WORK( I ) + TC
- WORK( I+N ) = WORK( I+N ) + T
- 270 CONTINUE
-*
-* Apply matrix to vector
-*
- DO 300 I = ILO, IHI
- KOUNT = 0
- SUM = ZERO
- DO 290 J = ILO, IHI
- IF( A( I, J ).EQ.ZERO )
- $ GO TO 280
- KOUNT = KOUNT + 1
- SUM = SUM + WORK( J )
- 280 CONTINUE
- IF( B( I, J ).EQ.ZERO )
- $ GO TO 290
- KOUNT = KOUNT + 1
- SUM = SUM + WORK( J )
- 290 CONTINUE
- WORK( I+2*N ) = DBLE( KOUNT )*WORK( I+N ) + SUM
- 300 CONTINUE
-*
- DO 330 J = ILO, IHI
- KOUNT = 0
- SUM = ZERO
- DO 320 I = ILO, IHI
- IF( A( I, J ).EQ.ZERO )
- $ GO TO 310
- KOUNT = KOUNT + 1
- SUM = SUM + WORK( I+N )
- 310 CONTINUE
- IF( B( I, J ).EQ.ZERO )
- $ GO TO 320
- KOUNT = KOUNT + 1
- SUM = SUM + WORK( I+N )
- 320 CONTINUE
- WORK( J+3*N ) = DBLE( KOUNT )*WORK( J ) + SUM
- 330 CONTINUE
-*
- SUM = DDOT( NR, WORK( ILO+N ), 1, WORK( ILO+2*N ), 1 ) +
- $ DDOT( NR, WORK( ILO ), 1, WORK( ILO+3*N ), 1 )
- ALPHA = GAMMA / SUM
-*
-* Determine correction to current iteration
-*
- CMAX = ZERO
- DO 340 I = ILO, IHI
- COR = ALPHA*WORK( I+N )
- IF( ABS( COR ).GT.CMAX )
- $ CMAX = ABS( COR )
- LSCALE( I ) = LSCALE( I ) + COR
- COR = ALPHA*WORK( I )
- IF( ABS( COR ).GT.CMAX )
- $ CMAX = ABS( COR )
- RSCALE( I ) = RSCALE( I ) + COR
- 340 CONTINUE
- IF( CMAX.LT.HALF )
- $ GO TO 350
-*
- CALL DAXPY( NR, -ALPHA, WORK( ILO+2*N ), 1, WORK( ILO+4*N ), 1 )
- CALL DAXPY( NR, -ALPHA, WORK( ILO+3*N ), 1, WORK( ILO+5*N ), 1 )
-*
- PGAMMA = GAMMA
- IT = IT + 1
- IF( IT.LE.NRP2 )
- $ GO TO 250
-*
-* End generalized conjugate gradient iteration
-*
- 350 CONTINUE
- SFMIN = DLAMCH( 'S' )
- SFMAX = ONE / SFMIN
- LSFMIN = INT( LOG10( SFMIN ) / BASL+ONE )
- LSFMAX = INT( LOG10( SFMAX ) / BASL )
- DO 360 I = ILO, IHI
- IRAB = IDAMAX( N-ILO+1, A( I, ILO ), LDA )
- RAB = ABS( A( I, IRAB+ILO-1 ) )
- IRAB = IDAMAX( N-ILO+1, B( I, ILO ), LDB )
- RAB = MAX( RAB, ABS( B( I, IRAB+ILO-1 ) ) )
- LRAB = INT( LOG10( RAB+SFMIN ) / BASL+ONE )
- IR = LSCALE( I ) + SIGN( HALF, LSCALE( I ) )
- IR = MIN( MAX( IR, LSFMIN ), LSFMAX, LSFMAX-LRAB )
- LSCALE( I ) = SCLFAC**IR
- ICAB = IDAMAX( IHI, A( 1, I ), 1 )
- CAB = ABS( A( ICAB, I ) )
- ICAB = IDAMAX( IHI, B( 1, I ), 1 )
- CAB = MAX( CAB, ABS( B( ICAB, I ) ) )
- LCAB = INT( LOG10( CAB+SFMIN ) / BASL+ONE )
- JC = RSCALE( I ) + SIGN( HALF, RSCALE( I ) )
- JC = MIN( MAX( JC, LSFMIN ), LSFMAX, LSFMAX-LCAB )
- RSCALE( I ) = SCLFAC**JC
- 360 CONTINUE
-*
-* Row scaling of matrices A and B
-*
- DO 370 I = ILO, IHI
- CALL DSCAL( N-ILO+1, LSCALE( I ), A( I, ILO ), LDA )
- CALL DSCAL( N-ILO+1, LSCALE( I ), B( I, ILO ), LDB )
- 370 CONTINUE
-*
-* Column scaling of matrices A and B
-*
- DO 380 J = ILO, IHI
- CALL DSCAL( IHI, RSCALE( J ), A( 1, J ), 1 )
- CALL DSCAL( IHI, RSCALE( J ), B( 1, J ), 1 )
- 380 CONTINUE
-*
- RETURN
-*
-* End of DGGBAL
-*
- END
diff --git a/src/lib/lapack/dgges.f b/src/lib/lapack/dgges.f
deleted file mode 100644
index ce29aa52..00000000
--- a/src/lib/lapack/dgges.f
+++ /dev/null
@@ -1,550 +0,0 @@
- SUBROUTINE DGGES( JOBVSL, JOBVSR, SORT, DELCTG, N, A, LDA, B, LDB,
- $ SDIM, ALPHAR, ALPHAI, BETA, VSL, LDVSL, VSR,
- $ LDVSR, WORK, LWORK, BWORK, INFO )
-*
-* -- LAPACK driver routine (version 3.0) --
-* Univ. of Tennessee, Univ. of California Berkeley, NAG Ltd.,
-* Courant Institute, Argonne National Lab, and Rice University
-* June 30, 1999
-*
-* .. Scalar Arguments ..
- CHARACTER JOBVSL, JOBVSR, SORT
- INTEGER INFO, LDA, LDB, LDVSL, LDVSR, LWORK, N, SDIM
-* ..
-* .. Array Arguments ..
- LOGICAL BWORK( * )
- DOUBLE PRECISION A( LDA, * ), ALPHAI( * ), ALPHAR( * ),
- $ B( LDB, * ), BETA( * ), VSL( LDVSL, * ),
- $ VSR( LDVSR, * ), WORK( * )
-* ..
-* .. Function Arguments ..
- LOGICAL DELCTG
- EXTERNAL DELCTG
-* ..
-*
-* Purpose
-* =======
-*
-* DGGES computes for a pair of N-by-N real nonsymmetric matrices (A,B),
-* the generalized eigenvalues, the generalized real Schur form (S,T),
-* optionally, the left and/or right matrices of Schur vectors (VSL and
-* VSR). This gives the generalized Schur factorization
-*
-* (A,B) = ( (VSL)*S*(VSR)**T, (VSL)*T*(VSR)**T )
-*
-* Optionally, it also orders the eigenvalues so that a selected cluster
-* of eigenvalues appears in the leading diagonal blocks of the upper
-* quasi-triangular matrix S and the upper triangular matrix T.The
-* leading columns of VSL and VSR then form an orthonormal basis for the
-* corresponding left and right eigenspaces (deflating subspaces).
-*
-* (If only the generalized eigenvalues are needed, use the driver
-* DGGEV instead, which is faster.)
-*
-* A generalized eigenvalue for a pair of matrices (A,B) is a scalar w
-* or a ratio alpha/beta = w, such that A - w*B is singular. It is
-* usually represented as the pair (alpha,beta), as there is a
-* reasonable interpretation for beta=0 or both being zero.
-*
-* A pair of matrices (S,T) is in generalized real Schur form if T is
-* upper triangular with non-negative diagonal and S is block upper
-* triangular with 1-by-1 and 2-by-2 blocks. 1-by-1 blocks correspond
-* to real generalized eigenvalues, while 2-by-2 blocks of S will be
-* "standardized" by making the corresponding elements of T have the
-* form:
-* [ a 0 ]
-* [ 0 b ]
-*
-* and the pair of corresponding 2-by-2 blocks in S and T will have a
-* complex conjugate pair of generalized eigenvalues.
-*
-*
-* Arguments
-* =========
-*
-* JOBVSL (input) CHARACTER*1
-* = 'N': do not compute the left Schur vectors;
-* = 'V': compute the left Schur vectors.
-*
-* JOBVSR (input) CHARACTER*1
-* = 'N': do not compute the right Schur vectors;
-* = 'V': compute the right Schur vectors.
-*
-* SORT (input) CHARACTER*1
-* Specifies whether or not to order the eigenvalues on the
-* diagonal of the generalized Schur form.
-* = 'N': Eigenvalues are not ordered;
-* = 'S': Eigenvalues are ordered (see DELZTG);
-*
-* DELZTG (input) LOGICAL FUNCTION of three DOUBLE PRECISION arguments
-* DELZTG must be declared EXTERNAL in the calling subroutine.
-* If SORT = 'N', DELZTG is not referenced.
-* If SORT = 'S', DELZTG is used to select eigenvalues to sort
-* to the top left of the Schur form.
-* An eigenvalue (ALPHAR(j)+ALPHAI(j))/BETA(j) is selected if
-* DELZTG(ALPHAR(j),ALPHAI(j),BETA(j)) is true; i.e. if either
-* one of a complex conjugate pair of eigenvalues is selected,
-* then both complex eigenvalues are selected.
-*
-* Note that in the ill-conditioned case, a selected complex
-* eigenvalue may no longer satisfy DELZTG(ALPHAR(j),ALPHAI(j),
-* BETA(j)) = .TRUE. after ordering. INFO is to be set to N+2
-* in this case.
-*
-* N (input) INTEGER
-* The order of the matrices A, B, VSL, and VSR. N >= 0.
-*
-* A (input/output) DOUBLE PRECISION array, dimension (LDA, N)
-* On entry, the first of the pair of matrices.
-* On exit, A has been overwritten by its generalized Schur
-* form S.
-*
-* LDA (input) INTEGER
-* The leading dimension of A. LDA >= max(1,N).
-*
-* B (input/output) DOUBLE PRECISION array, dimension (LDB, N)
-* On entry, the second of the pair of matrices.
-* On exit, B has been overwritten by its generalized Schur
-* form T.
-*
-* LDB (input) INTEGER
-* The leading dimension of B. LDB >= max(1,N).
-*
-* SDIM (output) INTEGER
-* If SORT = 'N', SDIM = 0.
-* If SORT = 'S', SDIM = number of eigenvalues (after sorting)
-* for which DELZTG is true. (Complex conjugate pairs for which
-* DELZTG is true for either eigenvalue count as 2.)
-*
-* ALPHAR (output) DOUBLE PRECISION array, dimension (N)
-* ALPHAI (output) DOUBLE PRECISION array, dimension (N)
-* BETA (output) DOUBLE PRECISION array, dimension (N)
-* On exit, (ALPHAR(j) + ALPHAI(j)*i)/BETA(j), j=1,...,N, will
-* be the generalized eigenvalues. ALPHAR(j) + ALPHAI(j)*i,
-* and BETA(j),j=1,...,N are the diagonals of the complex Schur
-* form (S,T) that would result if the 2-by-2 diagonal blocks of
-* the real Schur form of (A,B) were further reduced to
-* triangular form using 2-by-2 complex unitary transformations.
-* If ALPHAI(j) is zero, then the j-th eigenvalue is real; if
-* positive, then the j-th and (j+1)-st eigenvalues are a
-* complex conjugate pair, with ALPHAI(j+1) negative.
-*
-* Note: the quotients ALPHAR(j)/BETA(j) and ALPHAI(j)/BETA(j)
-* may easily over- or underflow, and BETA(j) may even be zero.
-* Thus, the user should avoid naively computing the ratio.
-* However, ALPHAR and ALPHAI will be always less than and
-* usually comparable with norm(A) in magnitude, and BETA always
-* less than and usually comparable with norm(B).
-*
-* VSL (output) DOUBLE PRECISION array, dimension (LDVSL,N)
-* If JOBVSL = 'V', VSL will contain the left Schur vectors.
-* Not referenced if JOBVSL = 'N'.
-*
-* LDVSL (input) INTEGER
-* The leading dimension of the matrix VSL. LDVSL >=1, and
-* if JOBVSL = 'V', LDVSL >= N.
-*
-* VSR (output) DOUBLE PRECISION array, dimension (LDVSR,N)
-* If JOBVSR = 'V', VSR will contain the right Schur vectors.
-* Not referenced if JOBVSR = 'N'.
-*
-* LDVSR (input) INTEGER
-* The leading dimension of the matrix VSR. LDVSR >= 1, and
-* if JOBVSR = 'V', LDVSR >= N.
-*
-* WORK (workspace/output) DOUBLE PRECISION array, dimension (LWORK)
-* On exit, if INFO = 0, WORK(1) returns the optimal LWORK.
-*
-* LWORK (input) INTEGER
-* The dimension of the array WORK. LWORK >= 8*N+16.
-*
-* If LWORK = -1, then a workspace query is assumed; the routine
-* only calculates the optimal size of the WORK array, returns
-* this value as the first entry of the WORK array, and no error
-* message related to LWORK is issued by XERBLA.
-*
-* BWORK (workspace) LOGICAL array, dimension (N)
-* Not referenced if SORT = 'N'.
-*
-* INFO (output) INTEGER
-* = 0: successful exit
-* < 0: if INFO = -i, the i-th argument had an illegal value.
-* = 1,...,N:
-* The QZ iteration failed. (A,B) are not in Schur
-* form, but ALPHAR(j), ALPHAI(j), and BETA(j) should
-* be correct for j=INFO+1,...,N.
-* > N: =N+1: other than QZ iteration failed in DHGEQZ.
-* =N+2: after reordering, roundoff changed values of
-* some complex eigenvalues so that leading
-* eigenvalues in the Generalized Schur form no
-* longer satisfy DELZTG=.TRUE. This could also
-* be caused due to scaling.
-* =N+3: reordering failed in DTGSEN.
-*
-* =====================================================================
-*
-* .. Parameters ..
- DOUBLE PRECISION ZERO, ONE
- PARAMETER ( ZERO = 0.0D+0, ONE = 1.0D+0 )
-* ..
-* .. Local Scalars ..
- LOGICAL CURSL, ILASCL, ILBSCL, ILVSL, ILVSR, LASTSL,
- $ LQUERY, LST2SL, WANTST
- INTEGER I, ICOLS, IERR, IHI, IJOBVL, IJOBVR, ILEFT,
- $ ILO, IP, IRIGHT, IROWS, ITAU, IWRK, MAXWRK,
- $ MINWRK
- DOUBLE PRECISION ANRM, ANRMTO, BIGNUM, BNRM, BNRMTO, EPS, PVSL,
- $ PVSR, SAFMAX, SAFMIN, SMLNUM
-* ..
-* .. Local Arrays ..
- INTEGER IDUM( 1 )
- DOUBLE PRECISION DIF( 2 )
-* ..
-* .. External Subroutines ..
- EXTERNAL DGEQRF, DGGBAK, DGGBAL, DGGHRD, DHGEQZ, DLABAD,
- $ DLACPY, DLASCL, DLASET, DORGQR, DORMQR, DTGSEN,
- $ XERBLA
-* ..
-* .. External Functions ..
- LOGICAL LSAME
- INTEGER ILAENV
- DOUBLE PRECISION DLAMCH, DLANGE
- EXTERNAL LSAME, ILAENV, DLAMCH, DLANGE
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC ABS, MAX, SQRT
-* ..
-* .. Executable Statements ..
-*
-* Decode the input arguments
-*
- IF( LSAME( JOBVSL, 'N' ) ) THEN
- IJOBVL = 1
- ILVSL = .FALSE.
- ELSE IF( LSAME( JOBVSL, 'V' ) ) THEN
- IJOBVL = 2
- ILVSL = .TRUE.
- ELSE
- IJOBVL = -1
- ILVSL = .FALSE.
- END IF
-*
- IF( LSAME( JOBVSR, 'N' ) ) THEN
- IJOBVR = 1
- ILVSR = .FALSE.
- ELSE IF( LSAME( JOBVSR, 'V' ) ) THEN
- IJOBVR = 2
- ILVSR = .TRUE.
- ELSE
- IJOBVR = -1
- ILVSR = .FALSE.
- END IF
-*
- WANTST = LSAME( SORT, 'S' )
-*
-* Test the input arguments
-*
- INFO = 0
- LQUERY = ( LWORK.EQ.-1 )
- IF( IJOBVL.LE.0 ) THEN
- INFO = -1
- ELSE IF( IJOBVR.LE.0 ) THEN
- INFO = -2
- ELSE IF( ( .NOT.WANTST ) .AND. ( .NOT.LSAME( SORT, 'N' ) ) ) THEN
- INFO = -3
- ELSE IF( N.LT.0 ) THEN
- INFO = -5
- ELSE IF( LDA.LT.MAX( 1, N ) ) THEN
- INFO = -7
- ELSE IF( LDB.LT.MAX( 1, N ) ) THEN
- INFO = -9
- ELSE IF( LDVSL.LT.1 .OR. ( ILVSL .AND. LDVSL.LT.N ) ) THEN
- INFO = -15
- ELSE IF( LDVSR.LT.1 .OR. ( ILVSR .AND. LDVSR.LT.N ) ) THEN
- INFO = -17
- END IF
-*
-* Compute workspace
-* (Note: Comments in the code beginning "Workspace:" describe the
-* minimal amount of workspace needed at that point in the code,
-* as well as the preferred amount for good performance.
-* NB refers to the optimal block size for the immediately
-* following subroutine, as returned by ILAENV.)
-*
- MINWRK = 1
- IF( INFO.EQ.0 .AND. ( LWORK.GE.1 .OR. LQUERY ) ) THEN
- MINWRK = 7*( N+1 ) + 16
- MAXWRK = 7*( N+1 ) + N*ILAENV( 1, 'DGEQRF', ' ', N, 1, N, 0 ) +
- $ 16
- IF( ILVSL ) THEN
- MAXWRK = MAX( MAXWRK, 7*( N+1 )+N*
- $ ILAENV( 1, 'DORGQR', ' ', N, 1, N, -1 ) )
- END IF
- WORK( 1 ) = MAXWRK
- END IF
-*
- IF( LWORK.LT.MINWRK .AND. .NOT.LQUERY )
- $ INFO = -19
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'DGGES ', -INFO )
- RETURN
- ELSE IF( LQUERY ) THEN
- RETURN
- END IF
-*
-* Quick return if possible
-*
- IF( N.EQ.0 ) THEN
- SDIM = 0
- RETURN
- END IF
-*
-* Get machine constants
-*
- EPS = DLAMCH( 'P' )
- SAFMIN = DLAMCH( 'S' )
- SAFMAX = ONE / SAFMIN
- CALL DLABAD( SAFMIN, SAFMAX )
- SMLNUM = SQRT( SAFMIN ) / EPS
- BIGNUM = ONE / SMLNUM
-*
-* Scale A if max element outside range [SMLNUM,BIGNUM]
-*
- ANRM = DLANGE( 'M', N, N, A, LDA, WORK )
- ILASCL = .FALSE.
- IF( ANRM.GT.ZERO .AND. ANRM.LT.SMLNUM ) THEN
- ANRMTO = SMLNUM
- ILASCL = .TRUE.
- ELSE IF( ANRM.GT.BIGNUM ) THEN
- ANRMTO = BIGNUM
- ILASCL = .TRUE.
- END IF
- IF( ILASCL )
- $ CALL DLASCL( 'G', 0, 0, ANRM, ANRMTO, N, N, A, LDA, IERR )
-*
-* Scale B if max element outside range [SMLNUM,BIGNUM]
-*
- BNRM = DLANGE( 'M', N, N, B, LDB, WORK )
- ILBSCL = .FALSE.
- IF( BNRM.GT.ZERO .AND. BNRM.LT.SMLNUM ) THEN
- BNRMTO = SMLNUM
- ILBSCL = .TRUE.
- ELSE IF( BNRM.GT.BIGNUM ) THEN
- BNRMTO = BIGNUM
- ILBSCL = .TRUE.
- END IF
- IF( ILBSCL )
- $ CALL DLASCL( 'G', 0, 0, BNRM, BNRMTO, N, N, B, LDB, IERR )
-*
-* Permute the matrix to make it more nearly triangular
-* (Workspace: need 6*N + 2*N space for storing balancing factors)
-*
- ILEFT = 1
- IRIGHT = N + 1
- IWRK = IRIGHT + N
- CALL DGGBAL( 'P', N, A, LDA, B, LDB, ILO, IHI, WORK( ILEFT ),
- $ WORK( IRIGHT ), WORK( IWRK ), IERR )
-*
-* Reduce B to triangular form (QR decomposition of B)
-* (Workspace: need N, prefer N*NB)
-*
- IROWS = IHI + 1 - ILO
- ICOLS = N + 1 - ILO
- ITAU = IWRK
- IWRK = ITAU + IROWS
- CALL DGEQRF( IROWS, ICOLS, B( ILO, ILO ), LDB, WORK( ITAU ),
- $ WORK( IWRK ), LWORK+1-IWRK, IERR )
-*
-* Apply the orthogonal transformation to matrix A
-* (Workspace: need N, prefer N*NB)
-*
- CALL DORMQR( 'L', 'T', IROWS, ICOLS, IROWS, B( ILO, ILO ), LDB,
- $ WORK( ITAU ), A( ILO, ILO ), LDA, WORK( IWRK ),
- $ LWORK+1-IWRK, IERR )
-*
-* Initialize VSL
-* (Workspace: need N, prefer N*NB)
-*
- IF( ILVSL ) THEN
- CALL DLASET( 'Full', N, N, ZERO, ONE, VSL, LDVSL )
- CALL DLACPY( 'L', IROWS-1, IROWS-1, B( ILO+1, ILO ), LDB,
- $ VSL( ILO+1, ILO ), LDVSL )
- CALL DORGQR( IROWS, IROWS, IROWS, VSL( ILO, ILO ), LDVSL,
- $ WORK( ITAU ), WORK( IWRK ), LWORK+1-IWRK, IERR )
- END IF
-*
-* Initialize VSR
-*
- IF( ILVSR )
- $ CALL DLASET( 'Full', N, N, ZERO, ONE, VSR, LDVSR )
-*
-* Reduce to generalized Hessenberg form
-* (Workspace: none needed)
-*
- CALL DGGHRD( JOBVSL, JOBVSR, N, ILO, IHI, A, LDA, B, LDB, VSL,
- $ LDVSL, VSR, LDVSR, IERR )
-*
-* Perform QZ algorithm, computing Schur vectors if desired
-* (Workspace: need N)
-*
- IWRK = ITAU
- CALL DHGEQZ( 'S', JOBVSL, JOBVSR, N, ILO, IHI, A, LDA, B, LDB,
- $ ALPHAR, ALPHAI, BETA, VSL, LDVSL, VSR, LDVSR,
- $ WORK( IWRK ), LWORK+1-IWRK, IERR )
- IF( IERR.NE.0 ) THEN
- IF( IERR.GT.0 .AND. IERR.LE.N ) THEN
- INFO = IERR
- ELSE IF( IERR.GT.N .AND. IERR.LE.2*N ) THEN
- INFO = IERR - N
- ELSE
- INFO = N + 1
- END IF
- GO TO 50
- END IF
-*
-* Sort eigenvalues ALPHA/BETA if desired
-* (Workspace: need 4*N+16 )
-*
- SDIM = 0
- IF( WANTST ) THEN
-*
-* Undo scaling on eigenvalues before DELZTGing
-*
- IF( ILASCL ) THEN
- CALL DLASCL( 'G', 0, 0, ANRMTO, ANRM, N, 1, ALPHAR, N,
- $ IERR )
- CALL DLASCL( 'G', 0, 0, ANRMTO, ANRM, N, 1, ALPHAI, N,
- $ IERR )
- END IF
- IF( ILBSCL )
- $ CALL DLASCL( 'G', 0, 0, BNRMTO, BNRM, N, 1, BETA, N, IERR )
-*
-* Select eigenvalues
-*
- DO 10 I = 1, N
- BWORK( I ) = DELCTG( ALPHAR( I ), ALPHAI( I ), BETA( I ) )
- 10 CONTINUE
-*
- CALL DTGSEN( 0, ILVSL, ILVSR, BWORK, N, A, LDA, B, LDB, ALPHAR,
- $ ALPHAI, BETA, VSL, LDVSL, VSR, LDVSR, SDIM, PVSL,
- $ PVSR, DIF, WORK( IWRK ), LWORK-IWRK+1, IDUM, 1,
- $ IERR )
- IF( IERR.EQ.1 )
- $ INFO = N + 3
-*
- END IF
-*
-* Apply back-permutation to VSL and VSR
-* (Workspace: none needed)
-*
- IF( ILVSL )
- $ CALL DGGBAK( 'P', 'L', N, ILO, IHI, WORK( ILEFT ),
- $ WORK( IRIGHT ), N, VSL, LDVSL, IERR )
-*
- IF( ILVSR )
- $ CALL DGGBAK( 'P', 'R', N, ILO, IHI, WORK( ILEFT ),
- $ WORK( IRIGHT ), N, VSR, LDVSR, IERR )
-*
-* Check if unscaling would cause over/underflow, if so, rescale
-* (ALPHAR(I),ALPHAI(I),BETA(I)) so BETA(I) is on the order of
-* B(I,I) and ALPHAR(I) and ALPHAI(I) are on the order of A(I,I)
-*
- IF( ILASCL ) THEN
- DO 20 I = 1, N
- IF( ALPHAI( I ).NE.ZERO ) THEN
- IF( ( ALPHAR( I ) / SAFMAX ).GT.( ANRMTO / ANRM ) .OR.
- $ ( SAFMIN / ALPHAR( I ) ).GT.( ANRM / ANRMTO ) ) THEN
- WORK( 1 ) = ABS( A( I, I ) / ALPHAR( I ) )
- BETA( I ) = BETA( I )*WORK( 1 )
- ALPHAR( I ) = ALPHAR( I )*WORK( 1 )
- ALPHAI( I ) = ALPHAI( I )*WORK( 1 )
- ELSE IF( ( ALPHAI( I ) / SAFMAX ).GT.
- $ ( ANRMTO / ANRM ) .OR.
- $ ( SAFMIN / ALPHAI( I ) ).GT.( ANRM / ANRMTO ) )
- $ THEN
- WORK( 1 ) = ABS( A( I, I+1 ) / ALPHAI( I ) )
- BETA( I ) = BETA( I )*WORK( 1 )
- ALPHAR( I ) = ALPHAR( I )*WORK( 1 )
- ALPHAI( I ) = ALPHAI( I )*WORK( 1 )
- END IF
- END IF
- 20 CONTINUE
- END IF
-*
- IF( ILBSCL ) THEN
- DO 30 I = 1, N
- IF( ALPHAI( I ).NE.ZERO ) THEN
- IF( ( BETA( I ) / SAFMAX ).GT.( BNRMTO / BNRM ) .OR.
- $ ( SAFMIN / BETA( I ) ).GT.( BNRM / BNRMTO ) ) THEN
- WORK( 1 ) = ABS( B( I, I ) / BETA( I ) )
- BETA( I ) = BETA( I )*WORK( 1 )
- ALPHAR( I ) = ALPHAR( I )*WORK( 1 )
- ALPHAI( I ) = ALPHAI( I )*WORK( 1 )
- END IF
- END IF
- 30 CONTINUE
- END IF
-*
-* Undo scaling
-*
- IF( ILASCL ) THEN
- CALL DLASCL( 'H', 0, 0, ANRMTO, ANRM, N, N, A, LDA, IERR )
- CALL DLASCL( 'G', 0, 0, ANRMTO, ANRM, N, 1, ALPHAR, N, IERR )
- CALL DLASCL( 'G', 0, 0, ANRMTO, ANRM, N, 1, ALPHAI, N, IERR )
- END IF
-*
- IF( ILBSCL ) THEN
- CALL DLASCL( 'U', 0, 0, BNRMTO, BNRM, N, N, B, LDB, IERR )
- CALL DLASCL( 'G', 0, 0, BNRMTO, BNRM, N, 1, BETA, N, IERR )
- END IF
-*
- IF( WANTST ) THEN
-*
-* Check if reordering is correct
-*
- LASTSL = .TRUE.
- LST2SL = .TRUE.
- SDIM = 0
- IP = 0
- DO 40 I = 1, N
- CURSL = DELCTG( ALPHAR( I ), ALPHAI( I ), BETA( I ) )
- IF( ALPHAI( I ).EQ.ZERO ) THEN
- IF( CURSL )
- $ SDIM = SDIM + 1
- IP = 0
- IF( CURSL .AND. .NOT.LASTSL )
- $ INFO = N + 2
- ELSE
- IF( IP.EQ.1 ) THEN
-*
-* Last eigenvalue of conjugate pair
-*
- CURSL = CURSL .OR. LASTSL
- LASTSL = CURSL
- IF( CURSL )
- $ SDIM = SDIM + 2
- IP = -1
- IF( CURSL .AND. .NOT.LST2SL )
- $ INFO = N + 2
- ELSE
-*
-* First eigenvalue of conjugate pair
-*
- IP = 1
- END IF
- END IF
- LST2SL = LASTSL
- LASTSL = CURSL
- 40 CONTINUE
-*
- END IF
-*
- 50 CONTINUE
-*
- WORK( 1 ) = MAXWRK
-*
- RETURN
-*
-* End of DGGES
-*
- END
diff --git a/src/lib/lapack/dggev.f b/src/lib/lapack/dggev.f
deleted file mode 100644
index 4a204c33..00000000
--- a/src/lib/lapack/dggev.f
+++ /dev/null
@@ -1,489 +0,0 @@
- SUBROUTINE DGGEV( JOBVL, JOBVR, N, A, LDA, B, LDB, ALPHAR, ALPHAI,
- $ BETA, VL, LDVL, VR, LDVR, WORK, LWORK, INFO )
-*
-* -- LAPACK driver routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- CHARACTER JOBVL, JOBVR
- INTEGER INFO, LDA, LDB, LDVL, LDVR, LWORK, N
-* ..
-* .. Array Arguments ..
- DOUBLE PRECISION A( LDA, * ), ALPHAI( * ), ALPHAR( * ),
- $ B( LDB, * ), BETA( * ), VL( LDVL, * ),
- $ VR( LDVR, * ), WORK( * )
-* ..
-*
-* Purpose
-* =======
-*
-* DGGEV computes for a pair of N-by-N real nonsymmetric matrices (A,B)
-* the generalized eigenvalues, and optionally, the left and/or right
-* generalized eigenvectors.
-*
-* A generalized eigenvalue for a pair of matrices (A,B) is a scalar
-* lambda or a ratio alpha/beta = lambda, such that A - lambda*B is
-* singular. It is usually represented as the pair (alpha,beta), as
-* there is a reasonable interpretation for beta=0, and even for both
-* being zero.
-*
-* The right eigenvector v(j) corresponding to the eigenvalue lambda(j)
-* of (A,B) satisfies
-*
-* A * v(j) = lambda(j) * B * v(j).
-*
-* The left eigenvector u(j) corresponding to the eigenvalue lambda(j)
-* of (A,B) satisfies
-*
-* u(j)**H * A = lambda(j) * u(j)**H * B .
-*
-* where u(j)**H is the conjugate-transpose of u(j).
-*
-*
-* Arguments
-* =========
-*
-* JOBVL (input) CHARACTER*1
-* = 'N': do not compute the left generalized eigenvectors;
-* = 'V': compute the left generalized eigenvectors.
-*
-* JOBVR (input) CHARACTER*1
-* = 'N': do not compute the right generalized eigenvectors;
-* = 'V': compute the right generalized eigenvectors.
-*
-* N (input) INTEGER
-* The order of the matrices A, B, VL, and VR. N >= 0.
-*
-* A (input/output) DOUBLE PRECISION array, dimension (LDA, N)
-* On entry, the matrix A in the pair (A,B).
-* On exit, A has been overwritten.
-*
-* LDA (input) INTEGER
-* The leading dimension of A. LDA >= max(1,N).
-*
-* B (input/output) DOUBLE PRECISION array, dimension (LDB, N)
-* On entry, the matrix B in the pair (A,B).
-* On exit, B has been overwritten.
-*
-* LDB (input) INTEGER
-* The leading dimension of B. LDB >= max(1,N).
-*
-* ALPHAR (output) DOUBLE PRECISION array, dimension (N)
-* ALPHAI (output) DOUBLE PRECISION array, dimension (N)
-* BETA (output) DOUBLE PRECISION array, dimension (N)
-* On exit, (ALPHAR(j) + ALPHAI(j)*i)/BETA(j), j=1,...,N, will
-* be the generalized eigenvalues. If ALPHAI(j) is zero, then
-* the j-th eigenvalue is real; if positive, then the j-th and
-* (j+1)-st eigenvalues are a complex conjugate pair, with
-* ALPHAI(j+1) negative.
-*
-* Note: the quotients ALPHAR(j)/BETA(j) and ALPHAI(j)/BETA(j)
-* may easily over- or underflow, and BETA(j) may even be zero.
-* Thus, the user should avoid naively computing the ratio
-* alpha/beta. However, ALPHAR and ALPHAI will be always less
-* than and usually comparable with norm(A) in magnitude, and
-* BETA always less than and usually comparable with norm(B).
-*
-* VL (output) DOUBLE PRECISION array, dimension (LDVL,N)
-* If JOBVL = 'V', the left eigenvectors u(j) are stored one
-* after another in the columns of VL, in the same order as
-* their eigenvalues. If the j-th eigenvalue is real, then
-* u(j) = VL(:,j), the j-th column of VL. If the j-th and
-* (j+1)-th eigenvalues form a complex conjugate pair, then
-* u(j) = VL(:,j)+i*VL(:,j+1) and u(j+1) = VL(:,j)-i*VL(:,j+1).
-* Each eigenvector is scaled so the largest component has
-* abs(real part)+abs(imag. part)=1.
-* Not referenced if JOBVL = 'N'.
-*
-* LDVL (input) INTEGER
-* The leading dimension of the matrix VL. LDVL >= 1, and
-* if JOBVL = 'V', LDVL >= N.
-*
-* VR (output) DOUBLE PRECISION array, dimension (LDVR,N)
-* If JOBVR = 'V', the right eigenvectors v(j) are stored one
-* after another in the columns of VR, in the same order as
-* their eigenvalues. If the j-th eigenvalue is real, then
-* v(j) = VR(:,j), the j-th column of VR. If the j-th and
-* (j+1)-th eigenvalues form a complex conjugate pair, then
-* v(j) = VR(:,j)+i*VR(:,j+1) and v(j+1) = VR(:,j)-i*VR(:,j+1).
-* Each eigenvector is scaled so the largest component has
-* abs(real part)+abs(imag. part)=1.
-* Not referenced if JOBVR = 'N'.
-*
-* LDVR (input) INTEGER
-* The leading dimension of the matrix VR. LDVR >= 1, and
-* if JOBVR = 'V', LDVR >= N.
-*
-* WORK (workspace/output) DOUBLE PRECISION array, dimension (MAX(1,LWORK))
-* On exit, if INFO = 0, WORK(1) returns the optimal LWORK.
-*
-* LWORK (input) INTEGER
-* The dimension of the array WORK. LWORK >= max(1,8*N).
-* For good performance, LWORK must generally be larger.
-*
-* If LWORK = -1, then a workspace query is assumed; the routine
-* only calculates the optimal size of the WORK array, returns
-* this value as the first entry of the WORK array, and no error
-* message related to LWORK is issued by XERBLA.
-*
-* INFO (output) INTEGER
-* = 0: successful exit
-* < 0: if INFO = -i, the i-th argument had an illegal value.
-* = 1,...,N:
-* The QZ iteration failed. No eigenvectors have been
-* calculated, but ALPHAR(j), ALPHAI(j), and BETA(j)
-* should be correct for j=INFO+1,...,N.
-* > N: =N+1: other than QZ iteration failed in DHGEQZ.
-* =N+2: error return from DTGEVC.
-*
-* =====================================================================
-*
-* .. Parameters ..
- DOUBLE PRECISION ZERO, ONE
- PARAMETER ( ZERO = 0.0D+0, ONE = 1.0D+0 )
-* ..
-* .. Local Scalars ..
- LOGICAL ILASCL, ILBSCL, ILV, ILVL, ILVR, LQUERY
- CHARACTER CHTEMP
- INTEGER ICOLS, IERR, IHI, IJOBVL, IJOBVR, ILEFT, ILO,
- $ IN, IRIGHT, IROWS, ITAU, IWRK, JC, JR, MAXWRK,
- $ MINWRK
- DOUBLE PRECISION ANRM, ANRMTO, BIGNUM, BNRM, BNRMTO, EPS,
- $ SMLNUM, TEMP
-* ..
-* .. Local Arrays ..
- LOGICAL LDUMMA( 1 )
-* ..
-* .. External Subroutines ..
- EXTERNAL DGEQRF, DGGBAK, DGGBAL, DGGHRD, DHGEQZ, DLABAD,
- $ DLACPY,DLASCL, DLASET, DORGQR, DORMQR, DTGEVC,
- $ XERBLA
-* ..
-* .. External Functions ..
- LOGICAL LSAME
- INTEGER ILAENV
- DOUBLE PRECISION DLAMCH, DLANGE
- EXTERNAL LSAME, ILAENV, DLAMCH, DLANGE
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC ABS, MAX, SQRT
-* ..
-* .. Executable Statements ..
-*
-* Decode the input arguments
-*
- IF( LSAME( JOBVL, 'N' ) ) THEN
- IJOBVL = 1
- ILVL = .FALSE.
- ELSE IF( LSAME( JOBVL, 'V' ) ) THEN
- IJOBVL = 2
- ILVL = .TRUE.
- ELSE
- IJOBVL = -1
- ILVL = .FALSE.
- END IF
-*
- IF( LSAME( JOBVR, 'N' ) ) THEN
- IJOBVR = 1
- ILVR = .FALSE.
- ELSE IF( LSAME( JOBVR, 'V' ) ) THEN
- IJOBVR = 2
- ILVR = .TRUE.
- ELSE
- IJOBVR = -1
- ILVR = .FALSE.
- END IF
- ILV = ILVL .OR. ILVR
-*
-* Test the input arguments
-*
- INFO = 0
- LQUERY = ( LWORK.EQ.-1 )
- IF( IJOBVL.LE.0 ) THEN
- INFO = -1
- ELSE IF( IJOBVR.LE.0 ) THEN
- INFO = -2
- ELSE IF( N.LT.0 ) THEN
- INFO = -3
- ELSE IF( LDA.LT.MAX( 1, N ) ) THEN
- INFO = -5
- ELSE IF( LDB.LT.MAX( 1, N ) ) THEN
- INFO = -7
- ELSE IF( LDVL.LT.1 .OR. ( ILVL .AND. LDVL.LT.N ) ) THEN
- INFO = -12
- ELSE IF( LDVR.LT.1 .OR. ( ILVR .AND. LDVR.LT.N ) ) THEN
- INFO = -14
- END IF
-*
-* Compute workspace
-* (Note: Comments in the code beginning "Workspace:" describe the
-* minimal amount of workspace needed at that point in the code,
-* as well as the preferred amount for good performance.
-* NB refers to the optimal block size for the immediately
-* following subroutine, as returned by ILAENV. The workspace is
-* computed assuming ILO = 1 and IHI = N, the worst case.)
-*
- IF( INFO.EQ.0 ) THEN
- MINWRK = MAX( 1, 8*N )
- MAXWRK = MAX( 1, N*( 7 +
- $ ILAENV( 1, 'DGEQRF', ' ', N, 1, N, 0 ) ) )
- MAXWRK = MAX( MAXWRK, N*( 7 +
- $ ILAENV( 1, 'DORMQR', ' ', N, 1, N, 0 ) ) )
- IF( ILVL ) THEN
- MAXWRK = MAX( MAXWRK, N*( 7 +
- $ ILAENV( 1, 'DORGQR', ' ', N, 1, N, -1 ) ) )
- END IF
- WORK( 1 ) = MAXWRK
-*
- IF( LWORK.LT.MINWRK .AND. .NOT.LQUERY )
- $ INFO = -16
- END IF
-*
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'DGGEV ', -INFO )
- RETURN
- ELSE IF( LQUERY ) THEN
- RETURN
- END IF
-*
-* Quick return if possible
-*
- IF( N.EQ.0 )
- $ RETURN
-*
-* Get machine constants
-*
- EPS = DLAMCH( 'P' )
- SMLNUM = DLAMCH( 'S' )
- BIGNUM = ONE / SMLNUM
- CALL DLABAD( SMLNUM, BIGNUM )
- SMLNUM = SQRT( SMLNUM ) / EPS
- BIGNUM = ONE / SMLNUM
-*
-* Scale A if max element outside range [SMLNUM,BIGNUM]
-*
- ANRM = DLANGE( 'M', N, N, A, LDA, WORK )
- ILASCL = .FALSE.
- IF( ANRM.GT.ZERO .AND. ANRM.LT.SMLNUM ) THEN
- ANRMTO = SMLNUM
- ILASCL = .TRUE.
- ELSE IF( ANRM.GT.BIGNUM ) THEN
- ANRMTO = BIGNUM
- ILASCL = .TRUE.
- END IF
- IF( ILASCL )
- $ CALL DLASCL( 'G', 0, 0, ANRM, ANRMTO, N, N, A, LDA, IERR )
-*
-* Scale B if max element outside range [SMLNUM,BIGNUM]
-*
- BNRM = DLANGE( 'M', N, N, B, LDB, WORK )
- ILBSCL = .FALSE.
- IF( BNRM.GT.ZERO .AND. BNRM.LT.SMLNUM ) THEN
- BNRMTO = SMLNUM
- ILBSCL = .TRUE.
- ELSE IF( BNRM.GT.BIGNUM ) THEN
- BNRMTO = BIGNUM
- ILBSCL = .TRUE.
- END IF
- IF( ILBSCL )
- $ CALL DLASCL( 'G', 0, 0, BNRM, BNRMTO, N, N, B, LDB, IERR )
-*
-* Permute the matrices A, B to isolate eigenvalues if possible
-* (Workspace: need 6*N)
-*
- ILEFT = 1
- IRIGHT = N + 1
- IWRK = IRIGHT + N
- CALL DGGBAL( 'P', N, A, LDA, B, LDB, ILO, IHI, WORK( ILEFT ),
- $ WORK( IRIGHT ), WORK( IWRK ), IERR )
-*
-* Reduce B to triangular form (QR decomposition of B)
-* (Workspace: need N, prefer N*NB)
-*
- IROWS = IHI + 1 - ILO
- IF( ILV ) THEN
- ICOLS = N + 1 - ILO
- ELSE
- ICOLS = IROWS
- END IF
- ITAU = IWRK
- IWRK = ITAU + IROWS
- CALL DGEQRF( IROWS, ICOLS, B( ILO, ILO ), LDB, WORK( ITAU ),
- $ WORK( IWRK ), LWORK+1-IWRK, IERR )
-*
-* Apply the orthogonal transformation to matrix A
-* (Workspace: need N, prefer N*NB)
-*
- CALL DORMQR( 'L', 'T', IROWS, ICOLS, IROWS, B( ILO, ILO ), LDB,
- $ WORK( ITAU ), A( ILO, ILO ), LDA, WORK( IWRK ),
- $ LWORK+1-IWRK, IERR )
-*
-* Initialize VL
-* (Workspace: need N, prefer N*NB)
-*
- IF( ILVL ) THEN
- CALL DLASET( 'Full', N, N, ZERO, ONE, VL, LDVL )
- IF( IROWS.GT.1 ) THEN
- CALL DLACPY( 'L', IROWS-1, IROWS-1, B( ILO+1, ILO ), LDB,
- $ VL( ILO+1, ILO ), LDVL )
- END IF
- CALL DORGQR( IROWS, IROWS, IROWS, VL( ILO, ILO ), LDVL,
- $ WORK( ITAU ), WORK( IWRK ), LWORK+1-IWRK, IERR )
- END IF
-*
-* Initialize VR
-*
- IF( ILVR )
- $ CALL DLASET( 'Full', N, N, ZERO, ONE, VR, LDVR )
-*
-* Reduce to generalized Hessenberg form
-* (Workspace: none needed)
-*
- IF( ILV ) THEN
-*
-* Eigenvectors requested -- work on whole matrix.
-*
- CALL DGGHRD( JOBVL, JOBVR, N, ILO, IHI, A, LDA, B, LDB, VL,
- $ LDVL, VR, LDVR, IERR )
- ELSE
- CALL DGGHRD( 'N', 'N', IROWS, 1, IROWS, A( ILO, ILO ), LDA,
- $ B( ILO, ILO ), LDB, VL, LDVL, VR, LDVR, IERR )
- END IF
-*
-* Perform QZ algorithm (Compute eigenvalues, and optionally, the
-* Schur forms and Schur vectors)
-* (Workspace: need N)
-*
- IWRK = ITAU
- IF( ILV ) THEN
- CHTEMP = 'S'
- ELSE
- CHTEMP = 'E'
- END IF
- CALL DHGEQZ( CHTEMP, JOBVL, JOBVR, N, ILO, IHI, A, LDA, B, LDB,
- $ ALPHAR, ALPHAI, BETA, VL, LDVL, VR, LDVR,
- $ WORK( IWRK ), LWORK+1-IWRK, IERR )
- IF( IERR.NE.0 ) THEN
- IF( IERR.GT.0 .AND. IERR.LE.N ) THEN
- INFO = IERR
- ELSE IF( IERR.GT.N .AND. IERR.LE.2*N ) THEN
- INFO = IERR - N
- ELSE
- INFO = N + 1
- END IF
- GO TO 110
- END IF
-*
-* Compute Eigenvectors
-* (Workspace: need 6*N)
-*
- IF( ILV ) THEN
- IF( ILVL ) THEN
- IF( ILVR ) THEN
- CHTEMP = 'B'
- ELSE
- CHTEMP = 'L'
- END IF
- ELSE
- CHTEMP = 'R'
- END IF
- CALL DTGEVC( CHTEMP, 'B', LDUMMA, N, A, LDA, B, LDB, VL, LDVL,
- $ VR, LDVR, N, IN, WORK( IWRK ), IERR )
- IF( IERR.NE.0 ) THEN
- INFO = N + 2
- GO TO 110
- END IF
-*
-* Undo balancing on VL and VR and normalization
-* (Workspace: none needed)
-*
- IF( ILVL ) THEN
- CALL DGGBAK( 'P', 'L', N, ILO, IHI, WORK( ILEFT ),
- $ WORK( IRIGHT ), N, VL, LDVL, IERR )
- DO 50 JC = 1, N
- IF( ALPHAI( JC ).LT.ZERO )
- $ GO TO 50
- TEMP = ZERO
- IF( ALPHAI( JC ).EQ.ZERO ) THEN
- DO 10 JR = 1, N
- TEMP = MAX( TEMP, ABS( VL( JR, JC ) ) )
- 10 CONTINUE
- ELSE
- DO 20 JR = 1, N
- TEMP = MAX( TEMP, ABS( VL( JR, JC ) )+
- $ ABS( VL( JR, JC+1 ) ) )
- 20 CONTINUE
- END IF
- IF( TEMP.LT.SMLNUM )
- $ GO TO 50
- TEMP = ONE / TEMP
- IF( ALPHAI( JC ).EQ.ZERO ) THEN
- DO 30 JR = 1, N
- VL( JR, JC ) = VL( JR, JC )*TEMP
- 30 CONTINUE
- ELSE
- DO 40 JR = 1, N
- VL( JR, JC ) = VL( JR, JC )*TEMP
- VL( JR, JC+1 ) = VL( JR, JC+1 )*TEMP
- 40 CONTINUE
- END IF
- 50 CONTINUE
- END IF
- IF( ILVR ) THEN
- CALL DGGBAK( 'P', 'R', N, ILO, IHI, WORK( ILEFT ),
- $ WORK( IRIGHT ), N, VR, LDVR, IERR )
- DO 100 JC = 1, N
- IF( ALPHAI( JC ).LT.ZERO )
- $ GO TO 100
- TEMP = ZERO
- IF( ALPHAI( JC ).EQ.ZERO ) THEN
- DO 60 JR = 1, N
- TEMP = MAX( TEMP, ABS( VR( JR, JC ) ) )
- 60 CONTINUE
- ELSE
- DO 70 JR = 1, N
- TEMP = MAX( TEMP, ABS( VR( JR, JC ) )+
- $ ABS( VR( JR, JC+1 ) ) )
- 70 CONTINUE
- END IF
- IF( TEMP.LT.SMLNUM )
- $ GO TO 100
- TEMP = ONE / TEMP
- IF( ALPHAI( JC ).EQ.ZERO ) THEN
- DO 80 JR = 1, N
- VR( JR, JC ) = VR( JR, JC )*TEMP
- 80 CONTINUE
- ELSE
- DO 90 JR = 1, N
- VR( JR, JC ) = VR( JR, JC )*TEMP
- VR( JR, JC+1 ) = VR( JR, JC+1 )*TEMP
- 90 CONTINUE
- END IF
- 100 CONTINUE
- END IF
-*
-* End of eigenvector calculation
-*
- END IF
-*
-* Undo scaling if necessary
-*
- IF( ILASCL ) THEN
- CALL DLASCL( 'G', 0, 0, ANRMTO, ANRM, N, 1, ALPHAR, N, IERR )
- CALL DLASCL( 'G', 0, 0, ANRMTO, ANRM, N, 1, ALPHAI, N, IERR )
- END IF
-*
- IF( ILBSCL ) THEN
- CALL DLASCL( 'G', 0, 0, BNRMTO, BNRM, N, 1, BETA, N, IERR )
- END IF
-*
- 110 CONTINUE
-*
- WORK( 1 ) = MAXWRK
-*
- RETURN
-*
-* End of DGGEV
-*
- END
diff --git a/src/lib/lapack/dgghrd.f b/src/lib/lapack/dgghrd.f
deleted file mode 100644
index 6b8bbb08..00000000
--- a/src/lib/lapack/dgghrd.f
+++ /dev/null
@@ -1,264 +0,0 @@
- SUBROUTINE DGGHRD( COMPQ, COMPZ, N, ILO, IHI, A, LDA, B, LDB, Q,
- $ LDQ, Z, LDZ, INFO )
-*
-* -- LAPACK routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- CHARACTER COMPQ, COMPZ
- INTEGER IHI, ILO, INFO, LDA, LDB, LDQ, LDZ, N
-* ..
-* .. Array Arguments ..
- DOUBLE PRECISION A( LDA, * ), B( LDB, * ), Q( LDQ, * ),
- $ Z( LDZ, * )
-* ..
-*
-* Purpose
-* =======
-*
-* DGGHRD reduces a pair of real matrices (A,B) to generalized upper
-* Hessenberg form using orthogonal transformations, where A is a
-* general matrix and B is upper triangular. The form of the
-* generalized eigenvalue problem is
-* A*x = lambda*B*x,
-* and B is typically made upper triangular by computing its QR
-* factorization and moving the orthogonal matrix Q to the left side
-* of the equation.
-*
-* This subroutine simultaneously reduces A to a Hessenberg matrix H:
-* Q**T*A*Z = H
-* and transforms B to another upper triangular matrix T:
-* Q**T*B*Z = T
-* in order to reduce the problem to its standard form
-* H*y = lambda*T*y
-* where y = Z**T*x.
-*
-* The orthogonal matrices Q and Z are determined as products of Givens
-* rotations. They may either be formed explicitly, or they may be
-* postmultiplied into input matrices Q1 and Z1, so that
-*
-* Q1 * A * Z1**T = (Q1*Q) * H * (Z1*Z)**T
-*
-* Q1 * B * Z1**T = (Q1*Q) * T * (Z1*Z)**T
-*
-* If Q1 is the orthogonal matrix from the QR factorization of B in the
-* original equation A*x = lambda*B*x, then DGGHRD reduces the original
-* problem to generalized Hessenberg form.
-*
-* Arguments
-* =========
-*
-* COMPQ (input) CHARACTER*1
-* = 'N': do not compute Q;
-* = 'I': Q is initialized to the unit matrix, and the
-* orthogonal matrix Q is returned;
-* = 'V': Q must contain an orthogonal matrix Q1 on entry,
-* and the product Q1*Q is returned.
-*
-* COMPZ (input) CHARACTER*1
-* = 'N': do not compute Z;
-* = 'I': Z is initialized to the unit matrix, and the
-* orthogonal matrix Z is returned;
-* = 'V': Z must contain an orthogonal matrix Z1 on entry,
-* and the product Z1*Z is returned.
-*
-* N (input) INTEGER
-* The order of the matrices A and B. N >= 0.
-*
-* ILO (input) INTEGER
-* IHI (input) INTEGER
-* ILO and IHI mark the rows and columns of A which are to be
-* reduced. It is assumed that A is already upper triangular
-* in rows and columns 1:ILO-1 and IHI+1:N. ILO and IHI are
-* normally set by a previous call to SGGBAL; otherwise they
-* should be set to 1 and N respectively.
-* 1 <= ILO <= IHI <= N, if N > 0; ILO=1 and IHI=0, if N=0.
-*
-* A (input/output) DOUBLE PRECISION array, dimension (LDA, N)
-* On entry, the N-by-N general matrix to be reduced.
-* On exit, the upper triangle and the first subdiagonal of A
-* are overwritten with the upper Hessenberg matrix H, and the
-* rest is set to zero.
-*
-* LDA (input) INTEGER
-* The leading dimension of the array A. LDA >= max(1,N).
-*
-* B (input/output) DOUBLE PRECISION array, dimension (LDB, N)
-* On entry, the N-by-N upper triangular matrix B.
-* On exit, the upper triangular matrix T = Q**T B Z. The
-* elements below the diagonal are set to zero.
-*
-* LDB (input) INTEGER
-* The leading dimension of the array B. LDB >= max(1,N).
-*
-* Q (input/output) DOUBLE PRECISION array, dimension (LDQ, N)
-* On entry, if COMPQ = 'V', the orthogonal matrix Q1,
-* typically from the QR factorization of B.
-* On exit, if COMPQ='I', the orthogonal matrix Q, and if
-* COMPQ = 'V', the product Q1*Q.
-* Not referenced if COMPQ='N'.
-*
-* LDQ (input) INTEGER
-* The leading dimension of the array Q.
-* LDQ >= N if COMPQ='V' or 'I'; LDQ >= 1 otherwise.
-*
-* Z (input/output) DOUBLE PRECISION array, dimension (LDZ, N)
-* On entry, if COMPZ = 'V', the orthogonal matrix Z1.
-* On exit, if COMPZ='I', the orthogonal matrix Z, and if
-* COMPZ = 'V', the product Z1*Z.
-* Not referenced if COMPZ='N'.
-*
-* LDZ (input) INTEGER
-* The leading dimension of the array Z.
-* LDZ >= N if COMPZ='V' or 'I'; LDZ >= 1 otherwise.
-*
-* INFO (output) INTEGER
-* = 0: successful exit.
-* < 0: if INFO = -i, the i-th argument had an illegal value.
-*
-* Further Details
-* ===============
-*
-* This routine reduces A to Hessenberg and B to triangular form by
-* an unblocked reduction, as described in _Matrix_Computations_,
-* by Golub and Van Loan (Johns Hopkins Press.)
-*
-* =====================================================================
-*
-* .. Parameters ..
- DOUBLE PRECISION ONE, ZERO
- PARAMETER ( ONE = 1.0D+0, ZERO = 0.0D+0 )
-* ..
-* .. Local Scalars ..
- LOGICAL ILQ, ILZ
- INTEGER ICOMPQ, ICOMPZ, JCOL, JROW
- DOUBLE PRECISION C, S, TEMP
-* ..
-* .. External Functions ..
- LOGICAL LSAME
- EXTERNAL LSAME
-* ..
-* .. External Subroutines ..
- EXTERNAL DLARTG, DLASET, DROT, XERBLA
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC MAX
-* ..
-* .. Executable Statements ..
-*
-* Decode COMPQ
-*
- IF( LSAME( COMPQ, 'N' ) ) THEN
- ILQ = .FALSE.
- ICOMPQ = 1
- ELSE IF( LSAME( COMPQ, 'V' ) ) THEN
- ILQ = .TRUE.
- ICOMPQ = 2
- ELSE IF( LSAME( COMPQ, 'I' ) ) THEN
- ILQ = .TRUE.
- ICOMPQ = 3
- ELSE
- ICOMPQ = 0
- END IF
-*
-* Decode COMPZ
-*
- IF( LSAME( COMPZ, 'N' ) ) THEN
- ILZ = .FALSE.
- ICOMPZ = 1
- ELSE IF( LSAME( COMPZ, 'V' ) ) THEN
- ILZ = .TRUE.
- ICOMPZ = 2
- ELSE IF( LSAME( COMPZ, 'I' ) ) THEN
- ILZ = .TRUE.
- ICOMPZ = 3
- ELSE
- ICOMPZ = 0
- END IF
-*
-* Test the input parameters.
-*
- INFO = 0
- IF( ICOMPQ.LE.0 ) THEN
- INFO = -1
- ELSE IF( ICOMPZ.LE.0 ) THEN
- INFO = -2
- ELSE IF( N.LT.0 ) THEN
- INFO = -3
- ELSE IF( ILO.LT.1 ) THEN
- INFO = -4
- ELSE IF( IHI.GT.N .OR. IHI.LT.ILO-1 ) THEN
- INFO = -5
- ELSE IF( LDA.LT.MAX( 1, N ) ) THEN
- INFO = -7
- ELSE IF( LDB.LT.MAX( 1, N ) ) THEN
- INFO = -9
- ELSE IF( ( ILQ .AND. LDQ.LT.N ) .OR. LDQ.LT.1 ) THEN
- INFO = -11
- ELSE IF( ( ILZ .AND. LDZ.LT.N ) .OR. LDZ.LT.1 ) THEN
- INFO = -13
- END IF
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'DGGHRD', -INFO )
- RETURN
- END IF
-*
-* Initialize Q and Z if desired.
-*
- IF( ICOMPQ.EQ.3 )
- $ CALL DLASET( 'Full', N, N, ZERO, ONE, Q, LDQ )
- IF( ICOMPZ.EQ.3 )
- $ CALL DLASET( 'Full', N, N, ZERO, ONE, Z, LDZ )
-*
-* Quick return if possible
-*
- IF( N.LE.1 )
- $ RETURN
-*
-* Zero out lower triangle of B
-*
- DO 20 JCOL = 1, N - 1
- DO 10 JROW = JCOL + 1, N
- B( JROW, JCOL ) = ZERO
- 10 CONTINUE
- 20 CONTINUE
-*
-* Reduce A and B
-*
- DO 40 JCOL = ILO, IHI - 2
-*
- DO 30 JROW = IHI, JCOL + 2, -1
-*
-* Step 1: rotate rows JROW-1, JROW to kill A(JROW,JCOL)
-*
- TEMP = A( JROW-1, JCOL )
- CALL DLARTG( TEMP, A( JROW, JCOL ), C, S,
- $ A( JROW-1, JCOL ) )
- A( JROW, JCOL ) = ZERO
- CALL DROT( N-JCOL, A( JROW-1, JCOL+1 ), LDA,
- $ A( JROW, JCOL+1 ), LDA, C, S )
- CALL DROT( N+2-JROW, B( JROW-1, JROW-1 ), LDB,
- $ B( JROW, JROW-1 ), LDB, C, S )
- IF( ILQ )
- $ CALL DROT( N, Q( 1, JROW-1 ), 1, Q( 1, JROW ), 1, C, S )
-*
-* Step 2: rotate columns JROW, JROW-1 to kill B(JROW,JROW-1)
-*
- TEMP = B( JROW, JROW )
- CALL DLARTG( TEMP, B( JROW, JROW-1 ), C, S,
- $ B( JROW, JROW ) )
- B( JROW, JROW-1 ) = ZERO
- CALL DROT( IHI, A( 1, JROW ), 1, A( 1, JROW-1 ), 1, C, S )
- CALL DROT( JROW-1, B( 1, JROW ), 1, B( 1, JROW-1 ), 1, C,
- $ S )
- IF( ILZ )
- $ CALL DROT( N, Z( 1, JROW ), 1, Z( 1, JROW-1 ), 1, C, S )
- 30 CONTINUE
- 40 CONTINUE
-*
- RETURN
-*
-* End of DGGHRD
-*
- END
diff --git a/src/lib/lapack/dhgeqz.f b/src/lib/lapack/dhgeqz.f
deleted file mode 100644
index de137dc1..00000000
--- a/src/lib/lapack/dhgeqz.f
+++ /dev/null
@@ -1,1243 +0,0 @@
- SUBROUTINE DHGEQZ( JOB, COMPQ, COMPZ, N, ILO, IHI, H, LDH, T, LDT,
- $ ALPHAR, ALPHAI, BETA, Q, LDQ, Z, LDZ, WORK,
- $ LWORK, INFO )
-*
-* -- LAPACK routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- CHARACTER COMPQ, COMPZ, JOB
- INTEGER IHI, ILO, INFO, LDH, LDQ, LDT, LDZ, LWORK, N
-* ..
-* .. Array Arguments ..
- DOUBLE PRECISION ALPHAI( * ), ALPHAR( * ), BETA( * ),
- $ H( LDH, * ), Q( LDQ, * ), T( LDT, * ),
- $ WORK( * ), Z( LDZ, * )
-* ..
-*
-* Purpose
-* =======
-*
-* DHGEQZ computes the eigenvalues of a real matrix pair (H,T),
-* where H is an upper Hessenberg matrix and T is upper triangular,
-* using the double-shift QZ method.
-* Matrix pairs of this type are produced by the reduction to
-* generalized upper Hessenberg form of a real matrix pair (A,B):
-*
-* A = Q1*H*Z1**T, B = Q1*T*Z1**T,
-*
-* as computed by DGGHRD.
-*
-* If JOB='S', then the Hessenberg-triangular pair (H,T) is
-* also reduced to generalized Schur form,
-*
-* H = Q*S*Z**T, T = Q*P*Z**T,
-*
-* where Q and Z are orthogonal matrices, P is an upper triangular
-* matrix, and S is a quasi-triangular matrix with 1-by-1 and 2-by-2
-* diagonal blocks.
-*
-* The 1-by-1 blocks correspond to real eigenvalues of the matrix pair
-* (H,T) and the 2-by-2 blocks correspond to complex conjugate pairs of
-* eigenvalues.
-*
-* Additionally, the 2-by-2 upper triangular diagonal blocks of P
-* corresponding to 2-by-2 blocks of S are reduced to positive diagonal
-* form, i.e., if S(j+1,j) is non-zero, then P(j+1,j) = P(j,j+1) = 0,
-* P(j,j) > 0, and P(j+1,j+1) > 0.
-*
-* Optionally, the orthogonal matrix Q from the generalized Schur
-* factorization may be postmultiplied into an input matrix Q1, and the
-* orthogonal matrix Z may be postmultiplied into an input matrix Z1.
-* If Q1 and Z1 are the orthogonal matrices from DGGHRD that reduced
-* the matrix pair (A,B) to generalized upper Hessenberg form, then the
-* output matrices Q1*Q and Z1*Z are the orthogonal factors from the
-* generalized Schur factorization of (A,B):
-*
-* A = (Q1*Q)*S*(Z1*Z)**T, B = (Q1*Q)*P*(Z1*Z)**T.
-*
-* To avoid overflow, eigenvalues of the matrix pair (H,T) (equivalently,
-* of (A,B)) are computed as a pair of values (alpha,beta), where alpha is
-* complex and beta real.
-* If beta is nonzero, lambda = alpha / beta is an eigenvalue of the
-* generalized nonsymmetric eigenvalue problem (GNEP)
-* A*x = lambda*B*x
-* and if alpha is nonzero, mu = beta / alpha is an eigenvalue of the
-* alternate form of the GNEP
-* mu*A*y = B*y.
-* Real eigenvalues can be read directly from the generalized Schur
-* form:
-* alpha = S(i,i), beta = P(i,i).
-*
-* Ref: C.B. Moler & G.W. Stewart, "An Algorithm for Generalized Matrix
-* Eigenvalue Problems", SIAM J. Numer. Anal., 10(1973),
-* pp. 241--256.
-*
-* Arguments
-* =========
-*
-* JOB (input) CHARACTER*1
-* = 'E': Compute eigenvalues only;
-* = 'S': Compute eigenvalues and the Schur form.
-*
-* COMPQ (input) CHARACTER*1
-* = 'N': Left Schur vectors (Q) are not computed;
-* = 'I': Q is initialized to the unit matrix and the matrix Q
-* of left Schur vectors of (H,T) is returned;
-* = 'V': Q must contain an orthogonal matrix Q1 on entry and
-* the product Q1*Q is returned.
-*
-* COMPZ (input) CHARACTER*1
-* = 'N': Right Schur vectors (Z) are not computed;
-* = 'I': Z is initialized to the unit matrix and the matrix Z
-* of right Schur vectors of (H,T) is returned;
-* = 'V': Z must contain an orthogonal matrix Z1 on entry and
-* the product Z1*Z is returned.
-*
-* N (input) INTEGER
-* The order of the matrices H, T, Q, and Z. N >= 0.
-*
-* ILO (input) INTEGER
-* IHI (input) INTEGER
-* ILO and IHI mark the rows and columns of H which are in
-* Hessenberg form. It is assumed that A is already upper
-* triangular in rows and columns 1:ILO-1 and IHI+1:N.
-* If N > 0, 1 <= ILO <= IHI <= N; if N = 0, ILO=1 and IHI=0.
-*
-* H (input/output) DOUBLE PRECISION array, dimension (LDH, N)
-* On entry, the N-by-N upper Hessenberg matrix H.
-* On exit, if JOB = 'S', H contains the upper quasi-triangular
-* matrix S from the generalized Schur factorization;
-* 2-by-2 diagonal blocks (corresponding to complex conjugate
-* pairs of eigenvalues) are returned in standard form, with
-* H(i,i) = H(i+1,i+1) and H(i+1,i)*H(i,i+1) < 0.
-* If JOB = 'E', the diagonal blocks of H match those of S, but
-* the rest of H is unspecified.
-*
-* LDH (input) INTEGER
-* The leading dimension of the array H. LDH >= max( 1, N ).
-*
-* T (input/output) DOUBLE PRECISION array, dimension (LDT, N)
-* On entry, the N-by-N upper triangular matrix T.
-* On exit, if JOB = 'S', T contains the upper triangular
-* matrix P from the generalized Schur factorization;
-* 2-by-2 diagonal blocks of P corresponding to 2-by-2 blocks of S
-* are reduced to positive diagonal form, i.e., if H(j+1,j) is
-* non-zero, then T(j+1,j) = T(j,j+1) = 0, T(j,j) > 0, and
-* T(j+1,j+1) > 0.
-* If JOB = 'E', the diagonal blocks of T match those of P, but
-* the rest of T is unspecified.
-*
-* LDT (input) INTEGER
-* The leading dimension of the array T. LDT >= max( 1, N ).
-*
-* ALPHAR (output) DOUBLE PRECISION array, dimension (N)
-* The real parts of each scalar alpha defining an eigenvalue
-* of GNEP.
-*
-* ALPHAI (output) DOUBLE PRECISION array, dimension (N)
-* The imaginary parts of each scalar alpha defining an
-* eigenvalue of GNEP.
-* If ALPHAI(j) is zero, then the j-th eigenvalue is real; if
-* positive, then the j-th and (j+1)-st eigenvalues are a
-* complex conjugate pair, with ALPHAI(j+1) = -ALPHAI(j).
-*
-* BETA (output) DOUBLE PRECISION array, dimension (N)
-* The scalars beta that define the eigenvalues of GNEP.
-* Together, the quantities alpha = (ALPHAR(j),ALPHAI(j)) and
-* beta = BETA(j) represent the j-th eigenvalue of the matrix
-* pair (A,B), in one of the forms lambda = alpha/beta or
-* mu = beta/alpha. Since either lambda or mu may overflow,
-* they should not, in general, be computed.
-*
-* Q (input/output) DOUBLE PRECISION array, dimension (LDQ, N)
-* On entry, if COMPZ = 'V', the orthogonal matrix Q1 used in
-* the reduction of (A,B) to generalized Hessenberg form.
-* On exit, if COMPZ = 'I', the orthogonal matrix of left Schur
-* vectors of (H,T), and if COMPZ = 'V', the orthogonal matrix
-* of left Schur vectors of (A,B).
-* Not referenced if COMPZ = 'N'.
-*
-* LDQ (input) INTEGER
-* The leading dimension of the array Q. LDQ >= 1.
-* If COMPQ='V' or 'I', then LDQ >= N.
-*
-* Z (input/output) DOUBLE PRECISION array, dimension (LDZ, N)
-* On entry, if COMPZ = 'V', the orthogonal matrix Z1 used in
-* the reduction of (A,B) to generalized Hessenberg form.
-* On exit, if COMPZ = 'I', the orthogonal matrix of
-* right Schur vectors of (H,T), and if COMPZ = 'V', the
-* orthogonal matrix of right Schur vectors of (A,B).
-* Not referenced if COMPZ = 'N'.
-*
-* LDZ (input) INTEGER
-* The leading dimension of the array Z. LDZ >= 1.
-* If COMPZ='V' or 'I', then LDZ >= N.
-*
-* WORK (workspace/output) DOUBLE PRECISION array, dimension (MAX(1,LWORK))
-* On exit, if INFO >= 0, WORK(1) returns the optimal LWORK.
-*
-* LWORK (input) INTEGER
-* The dimension of the array WORK. LWORK >= max(1,N).
-*
-* If LWORK = -1, then a workspace query is assumed; the routine
-* only calculates the optimal size of the WORK array, returns
-* this value as the first entry of the WORK array, and no error
-* message related to LWORK is issued by XERBLA.
-*
-* INFO (output) INTEGER
-* = 0: successful exit
-* < 0: if INFO = -i, the i-th argument had an illegal value
-* = 1,...,N: the QZ iteration did not converge. (H,T) is not
-* in Schur form, but ALPHAR(i), ALPHAI(i), and
-* BETA(i), i=INFO+1,...,N should be correct.
-* = N+1,...,2*N: the shift calculation failed. (H,T) is not
-* in Schur form, but ALPHAR(i), ALPHAI(i), and
-* BETA(i), i=INFO-N+1,...,N should be correct.
-*
-* Further Details
-* ===============
-*
-* Iteration counters:
-*
-* JITER -- counts iterations.
-* IITER -- counts iterations run since ILAST was last
-* changed. This is therefore reset only when a 1-by-1 or
-* 2-by-2 block deflates off the bottom.
-*
-* =====================================================================
-*
-* .. Parameters ..
-* $ SAFETY = 1.0E+0 )
- DOUBLE PRECISION HALF, ZERO, ONE, SAFETY
- PARAMETER ( HALF = 0.5D+0, ZERO = 0.0D+0, ONE = 1.0D+0,
- $ SAFETY = 1.0D+2 )
-* ..
-* .. Local Scalars ..
- LOGICAL ILAZR2, ILAZRO, ILPIVT, ILQ, ILSCHR, ILZ,
- $ LQUERY
- INTEGER ICOMPQ, ICOMPZ, IFIRST, IFRSTM, IITER, ILAST,
- $ ILASTM, IN, ISCHUR, ISTART, J, JC, JCH, JITER,
- $ JR, MAXIT
- DOUBLE PRECISION A11, A12, A1I, A1R, A21, A22, A2I, A2R, AD11,
- $ AD11L, AD12, AD12L, AD21, AD21L, AD22, AD22L,
- $ AD32L, AN, ANORM, ASCALE, ATOL, B11, B1A, B1I,
- $ B1R, B22, B2A, B2I, B2R, BN, BNORM, BSCALE,
- $ BTOL, C, C11I, C11R, C12, C21, C22I, C22R, CL,
- $ CQ, CR, CZ, ESHIFT, S, S1, S1INV, S2, SAFMAX,
- $ SAFMIN, SCALE, SL, SQI, SQR, SR, SZI, SZR, T1,
- $ TAU, TEMP, TEMP2, TEMPI, TEMPR, U1, U12, U12L,
- $ U2, ULP, VS, W11, W12, W21, W22, WABS, WI, WR,
- $ WR2
-* ..
-* .. Local Arrays ..
- DOUBLE PRECISION V( 3 )
-* ..
-* .. External Functions ..
- LOGICAL LSAME
- DOUBLE PRECISION DLAMCH, DLANHS, DLAPY2, DLAPY3
- EXTERNAL LSAME, DLAMCH, DLANHS, DLAPY2, DLAPY3
-* ..
-* .. External Subroutines ..
- EXTERNAL DLAG2, DLARFG, DLARTG, DLASET, DLASV2, DROT,
- $ XERBLA
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC ABS, DBLE, MAX, MIN, SQRT
-* ..
-* .. Executable Statements ..
-*
-* Decode JOB, COMPQ, COMPZ
-*
- IF( LSAME( JOB, 'E' ) ) THEN
- ILSCHR = .FALSE.
- ISCHUR = 1
- ELSE IF( LSAME( JOB, 'S' ) ) THEN
- ILSCHR = .TRUE.
- ISCHUR = 2
- ELSE
- ISCHUR = 0
- END IF
-*
- IF( LSAME( COMPQ, 'N' ) ) THEN
- ILQ = .FALSE.
- ICOMPQ = 1
- ELSE IF( LSAME( COMPQ, 'V' ) ) THEN
- ILQ = .TRUE.
- ICOMPQ = 2
- ELSE IF( LSAME( COMPQ, 'I' ) ) THEN
- ILQ = .TRUE.
- ICOMPQ = 3
- ELSE
- ICOMPQ = 0
- END IF
-*
- IF( LSAME( COMPZ, 'N' ) ) THEN
- ILZ = .FALSE.
- ICOMPZ = 1
- ELSE IF( LSAME( COMPZ, 'V' ) ) THEN
- ILZ = .TRUE.
- ICOMPZ = 2
- ELSE IF( LSAME( COMPZ, 'I' ) ) THEN
- ILZ = .TRUE.
- ICOMPZ = 3
- ELSE
- ICOMPZ = 0
- END IF
-*
-* Check Argument Values
-*
- INFO = 0
- WORK( 1 ) = MAX( 1, N )
- LQUERY = ( LWORK.EQ.-1 )
- IF( ISCHUR.EQ.0 ) THEN
- INFO = -1
- ELSE IF( ICOMPQ.EQ.0 ) THEN
- INFO = -2
- ELSE IF( ICOMPZ.EQ.0 ) THEN
- INFO = -3
- ELSE IF( N.LT.0 ) THEN
- INFO = -4
- ELSE IF( ILO.LT.1 ) THEN
- INFO = -5
- ELSE IF( IHI.GT.N .OR. IHI.LT.ILO-1 ) THEN
- INFO = -6
- ELSE IF( LDH.LT.N ) THEN
- INFO = -8
- ELSE IF( LDT.LT.N ) THEN
- INFO = -10
- ELSE IF( LDQ.LT.1 .OR. ( ILQ .AND. LDQ.LT.N ) ) THEN
- INFO = -15
- ELSE IF( LDZ.LT.1 .OR. ( ILZ .AND. LDZ.LT.N ) ) THEN
- INFO = -17
- ELSE IF( LWORK.LT.MAX( 1, N ) .AND. .NOT.LQUERY ) THEN
- INFO = -19
- END IF
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'DHGEQZ', -INFO )
- RETURN
- ELSE IF( LQUERY ) THEN
- RETURN
- END IF
-*
-* Quick return if possible
-*
- IF( N.LE.0 ) THEN
- WORK( 1 ) = DBLE( 1 )
- RETURN
- END IF
-*
-* Initialize Q and Z
-*
- IF( ICOMPQ.EQ.3 )
- $ CALL DLASET( 'Full', N, N, ZERO, ONE, Q, LDQ )
- IF( ICOMPZ.EQ.3 )
- $ CALL DLASET( 'Full', N, N, ZERO, ONE, Z, LDZ )
-*
-* Machine Constants
-*
- IN = IHI + 1 - ILO
- SAFMIN = DLAMCH( 'S' )
- SAFMAX = ONE / SAFMIN
- ULP = DLAMCH( 'E' )*DLAMCH( 'B' )
- ANORM = DLANHS( 'F', IN, H( ILO, ILO ), LDH, WORK )
- BNORM = DLANHS( 'F', IN, T( ILO, ILO ), LDT, WORK )
- ATOL = MAX( SAFMIN, ULP*ANORM )
- BTOL = MAX( SAFMIN, ULP*BNORM )
- ASCALE = ONE / MAX( SAFMIN, ANORM )
- BSCALE = ONE / MAX( SAFMIN, BNORM )
-*
-* Set Eigenvalues IHI+1:N
-*
- DO 30 J = IHI + 1, N
- IF( T( J, J ).LT.ZERO ) THEN
- IF( ILSCHR ) THEN
- DO 10 JR = 1, J
- H( JR, J ) = -H( JR, J )
- T( JR, J ) = -T( JR, J )
- 10 CONTINUE
- ELSE
- H( J, J ) = -H( J, J )
- T( J, J ) = -T( J, J )
- END IF
- IF( ILZ ) THEN
- DO 20 JR = 1, N
- Z( JR, J ) = -Z( JR, J )
- 20 CONTINUE
- END IF
- END IF
- ALPHAR( J ) = H( J, J )
- ALPHAI( J ) = ZERO
- BETA( J ) = T( J, J )
- 30 CONTINUE
-*
-* If IHI < ILO, skip QZ steps
-*
- IF( IHI.LT.ILO )
- $ GO TO 380
-*
-* MAIN QZ ITERATION LOOP
-*
-* Initialize dynamic indices
-*
-* Eigenvalues ILAST+1:N have been found.
-* Column operations modify rows IFRSTM:whatever.
-* Row operations modify columns whatever:ILASTM.
-*
-* If only eigenvalues are being computed, then
-* IFRSTM is the row of the last splitting row above row ILAST;
-* this is always at least ILO.
-* IITER counts iterations since the last eigenvalue was found,
-* to tell when to use an extraordinary shift.
-* MAXIT is the maximum number of QZ sweeps allowed.
-*
- ILAST = IHI
- IF( ILSCHR ) THEN
- IFRSTM = 1
- ILASTM = N
- ELSE
- IFRSTM = ILO
- ILASTM = IHI
- END IF
- IITER = 0
- ESHIFT = ZERO
- MAXIT = 30*( IHI-ILO+1 )
-*
- DO 360 JITER = 1, MAXIT
-*
-* Split the matrix if possible.
-*
-* Two tests:
-* 1: H(j,j-1)=0 or j=ILO
-* 2: T(j,j)=0
-*
- IF( ILAST.EQ.ILO ) THEN
-*
-* Special case: j=ILAST
-*
- GO TO 80
- ELSE
- IF( ABS( H( ILAST, ILAST-1 ) ).LE.ATOL ) THEN
- H( ILAST, ILAST-1 ) = ZERO
- GO TO 80
- END IF
- END IF
-*
- IF( ABS( T( ILAST, ILAST ) ).LE.BTOL ) THEN
- T( ILAST, ILAST ) = ZERO
- GO TO 70
- END IF
-*
-* General case: j<ILAST
-*
- DO 60 J = ILAST - 1, ILO, -1
-*
-* Test 1: for H(j,j-1)=0 or j=ILO
-*
- IF( J.EQ.ILO ) THEN
- ILAZRO = .TRUE.
- ELSE
- IF( ABS( H( J, J-1 ) ).LE.ATOL ) THEN
- H( J, J-1 ) = ZERO
- ILAZRO = .TRUE.
- ELSE
- ILAZRO = .FALSE.
- END IF
- END IF
-*
-* Test 2: for T(j,j)=0
-*
- IF( ABS( T( J, J ) ).LT.BTOL ) THEN
- T( J, J ) = ZERO
-*
-* Test 1a: Check for 2 consecutive small subdiagonals in A
-*
- ILAZR2 = .FALSE.
- IF( .NOT.ILAZRO ) THEN
- TEMP = ABS( H( J, J-1 ) )
- TEMP2 = ABS( H( J, J ) )
- TEMPR = MAX( TEMP, TEMP2 )
- IF( TEMPR.LT.ONE .AND. TEMPR.NE.ZERO ) THEN
- TEMP = TEMP / TEMPR
- TEMP2 = TEMP2 / TEMPR
- END IF
- IF( TEMP*( ASCALE*ABS( H( J+1, J ) ) ).LE.TEMP2*
- $ ( ASCALE*ATOL ) )ILAZR2 = .TRUE.
- END IF
-*
-* If both tests pass (1 & 2), i.e., the leading diagonal
-* element of B in the block is zero, split a 1x1 block off
-* at the top. (I.e., at the J-th row/column) The leading
-* diagonal element of the remainder can also be zero, so
-* this may have to be done repeatedly.
-*
- IF( ILAZRO .OR. ILAZR2 ) THEN
- DO 40 JCH = J, ILAST - 1
- TEMP = H( JCH, JCH )
- CALL DLARTG( TEMP, H( JCH+1, JCH ), C, S,
- $ H( JCH, JCH ) )
- H( JCH+1, JCH ) = ZERO
- CALL DROT( ILASTM-JCH, H( JCH, JCH+1 ), LDH,
- $ H( JCH+1, JCH+1 ), LDH, C, S )
- CALL DROT( ILASTM-JCH, T( JCH, JCH+1 ), LDT,
- $ T( JCH+1, JCH+1 ), LDT, C, S )
- IF( ILQ )
- $ CALL DROT( N, Q( 1, JCH ), 1, Q( 1, JCH+1 ), 1,
- $ C, S )
- IF( ILAZR2 )
- $ H( JCH, JCH-1 ) = H( JCH, JCH-1 )*C
- ILAZR2 = .FALSE.
- IF( ABS( T( JCH+1, JCH+1 ) ).GE.BTOL ) THEN
- IF( JCH+1.GE.ILAST ) THEN
- GO TO 80
- ELSE
- IFIRST = JCH + 1
- GO TO 110
- END IF
- END IF
- T( JCH+1, JCH+1 ) = ZERO
- 40 CONTINUE
- GO TO 70
- ELSE
-*
-* Only test 2 passed -- chase the zero to T(ILAST,ILAST)
-* Then process as in the case T(ILAST,ILAST)=0
-*
- DO 50 JCH = J, ILAST - 1
- TEMP = T( JCH, JCH+1 )
- CALL DLARTG( TEMP, T( JCH+1, JCH+1 ), C, S,
- $ T( JCH, JCH+1 ) )
- T( JCH+1, JCH+1 ) = ZERO
- IF( JCH.LT.ILASTM-1 )
- $ CALL DROT( ILASTM-JCH-1, T( JCH, JCH+2 ), LDT,
- $ T( JCH+1, JCH+2 ), LDT, C, S )
- CALL DROT( ILASTM-JCH+2, H( JCH, JCH-1 ), LDH,
- $ H( JCH+1, JCH-1 ), LDH, C, S )
- IF( ILQ )
- $ CALL DROT( N, Q( 1, JCH ), 1, Q( 1, JCH+1 ), 1,
- $ C, S )
- TEMP = H( JCH+1, JCH )
- CALL DLARTG( TEMP, H( JCH+1, JCH-1 ), C, S,
- $ H( JCH+1, JCH ) )
- H( JCH+1, JCH-1 ) = ZERO
- CALL DROT( JCH+1-IFRSTM, H( IFRSTM, JCH ), 1,
- $ H( IFRSTM, JCH-1 ), 1, C, S )
- CALL DROT( JCH-IFRSTM, T( IFRSTM, JCH ), 1,
- $ T( IFRSTM, JCH-1 ), 1, C, S )
- IF( ILZ )
- $ CALL DROT( N, Z( 1, JCH ), 1, Z( 1, JCH-1 ), 1,
- $ C, S )
- 50 CONTINUE
- GO TO 70
- END IF
- ELSE IF( ILAZRO ) THEN
-*
-* Only test 1 passed -- work on J:ILAST
-*
- IFIRST = J
- GO TO 110
- END IF
-*
-* Neither test passed -- try next J
-*
- 60 CONTINUE
-*
-* (Drop-through is "impossible")
-*
- INFO = N + 1
- GO TO 420
-*
-* T(ILAST,ILAST)=0 -- clear H(ILAST,ILAST-1) to split off a
-* 1x1 block.
-*
- 70 CONTINUE
- TEMP = H( ILAST, ILAST )
- CALL DLARTG( TEMP, H( ILAST, ILAST-1 ), C, S,
- $ H( ILAST, ILAST ) )
- H( ILAST, ILAST-1 ) = ZERO
- CALL DROT( ILAST-IFRSTM, H( IFRSTM, ILAST ), 1,
- $ H( IFRSTM, ILAST-1 ), 1, C, S )
- CALL DROT( ILAST-IFRSTM, T( IFRSTM, ILAST ), 1,
- $ T( IFRSTM, ILAST-1 ), 1, C, S )
- IF( ILZ )
- $ CALL DROT( N, Z( 1, ILAST ), 1, Z( 1, ILAST-1 ), 1, C, S )
-*
-* H(ILAST,ILAST-1)=0 -- Standardize B, set ALPHAR, ALPHAI,
-* and BETA
-*
- 80 CONTINUE
- IF( T( ILAST, ILAST ).LT.ZERO ) THEN
- IF( ILSCHR ) THEN
- DO 90 J = IFRSTM, ILAST
- H( J, ILAST ) = -H( J, ILAST )
- T( J, ILAST ) = -T( J, ILAST )
- 90 CONTINUE
- ELSE
- H( ILAST, ILAST ) = -H( ILAST, ILAST )
- T( ILAST, ILAST ) = -T( ILAST, ILAST )
- END IF
- IF( ILZ ) THEN
- DO 100 J = 1, N
- Z( J, ILAST ) = -Z( J, ILAST )
- 100 CONTINUE
- END IF
- END IF
- ALPHAR( ILAST ) = H( ILAST, ILAST )
- ALPHAI( ILAST ) = ZERO
- BETA( ILAST ) = T( ILAST, ILAST )
-*
-* Go to next block -- exit if finished.
-*
- ILAST = ILAST - 1
- IF( ILAST.LT.ILO )
- $ GO TO 380
-*
-* Reset counters
-*
- IITER = 0
- ESHIFT = ZERO
- IF( .NOT.ILSCHR ) THEN
- ILASTM = ILAST
- IF( IFRSTM.GT.ILAST )
- $ IFRSTM = ILO
- END IF
- GO TO 350
-*
-* QZ step
-*
-* This iteration only involves rows/columns IFIRST:ILAST. We
-* assume IFIRST < ILAST, and that the diagonal of B is non-zero.
-*
- 110 CONTINUE
- IITER = IITER + 1
- IF( .NOT.ILSCHR ) THEN
- IFRSTM = IFIRST
- END IF
-*
-* Compute single shifts.
-*
-* At this point, IFIRST < ILAST, and the diagonal elements of
-* T(IFIRST:ILAST,IFIRST,ILAST) are larger than BTOL (in
-* magnitude)
-*
- IF( ( IITER / 10 )*10.EQ.IITER ) THEN
-*
-* Exceptional shift. Chosen for no particularly good reason.
-* (Single shift only.)
-*
- IF( ( DBLE( MAXIT )*SAFMIN )*ABS( H( ILAST-1, ILAST ) ).LT.
- $ ABS( T( ILAST-1, ILAST-1 ) ) ) THEN
- ESHIFT = ESHIFT + H( ILAST-1, ILAST ) /
- $ T( ILAST-1, ILAST-1 )
- ELSE
- ESHIFT = ESHIFT + ONE / ( SAFMIN*DBLE( MAXIT ) )
- END IF
- S1 = ONE
- WR = ESHIFT
-*
- ELSE
-*
-* Shifts based on the generalized eigenvalues of the
-* bottom-right 2x2 block of A and B. The first eigenvalue
-* returned by DLAG2 is the Wilkinson shift (AEP p.512),
-*
- CALL DLAG2( H( ILAST-1, ILAST-1 ), LDH,
- $ T( ILAST-1, ILAST-1 ), LDT, SAFMIN*SAFETY, S1,
- $ S2, WR, WR2, WI )
-*
- TEMP = MAX( S1, SAFMIN*MAX( ONE, ABS( WR ), ABS( WI ) ) )
- IF( WI.NE.ZERO )
- $ GO TO 200
- END IF
-*
-* Fiddle with shift to avoid overflow
-*
- TEMP = MIN( ASCALE, ONE )*( HALF*SAFMAX )
- IF( S1.GT.TEMP ) THEN
- SCALE = TEMP / S1
- ELSE
- SCALE = ONE
- END IF
-*
- TEMP = MIN( BSCALE, ONE )*( HALF*SAFMAX )
- IF( ABS( WR ).GT.TEMP )
- $ SCALE = MIN( SCALE, TEMP / ABS( WR ) )
- S1 = SCALE*S1
- WR = SCALE*WR
-*
-* Now check for two consecutive small subdiagonals.
-*
- DO 120 J = ILAST - 1, IFIRST + 1, -1
- ISTART = J
- TEMP = ABS( S1*H( J, J-1 ) )
- TEMP2 = ABS( S1*H( J, J )-WR*T( J, J ) )
- TEMPR = MAX( TEMP, TEMP2 )
- IF( TEMPR.LT.ONE .AND. TEMPR.NE.ZERO ) THEN
- TEMP = TEMP / TEMPR
- TEMP2 = TEMP2 / TEMPR
- END IF
- IF( ABS( ( ASCALE*H( J+1, J ) )*TEMP ).LE.( ASCALE*ATOL )*
- $ TEMP2 )GO TO 130
- 120 CONTINUE
-*
- ISTART = IFIRST
- 130 CONTINUE
-*
-* Do an implicit single-shift QZ sweep.
-*
-* Initial Q
-*
- TEMP = S1*H( ISTART, ISTART ) - WR*T( ISTART, ISTART )
- TEMP2 = S1*H( ISTART+1, ISTART )
- CALL DLARTG( TEMP, TEMP2, C, S, TEMPR )
-*
-* Sweep
-*
- DO 190 J = ISTART, ILAST - 1
- IF( J.GT.ISTART ) THEN
- TEMP = H( J, J-1 )
- CALL DLARTG( TEMP, H( J+1, J-1 ), C, S, H( J, J-1 ) )
- H( J+1, J-1 ) = ZERO
- END IF
-*
- DO 140 JC = J, ILASTM
- TEMP = C*H( J, JC ) + S*H( J+1, JC )
- H( J+1, JC ) = -S*H( J, JC ) + C*H( J+1, JC )
- H( J, JC ) = TEMP
- TEMP2 = C*T( J, JC ) + S*T( J+1, JC )
- T( J+1, JC ) = -S*T( J, JC ) + C*T( J+1, JC )
- T( J, JC ) = TEMP2
- 140 CONTINUE
- IF( ILQ ) THEN
- DO 150 JR = 1, N
- TEMP = C*Q( JR, J ) + S*Q( JR, J+1 )
- Q( JR, J+1 ) = -S*Q( JR, J ) + C*Q( JR, J+1 )
- Q( JR, J ) = TEMP
- 150 CONTINUE
- END IF
-*
- TEMP = T( J+1, J+1 )
- CALL DLARTG( TEMP, T( J+1, J ), C, S, T( J+1, J+1 ) )
- T( J+1, J ) = ZERO
-*
- DO 160 JR = IFRSTM, MIN( J+2, ILAST )
- TEMP = C*H( JR, J+1 ) + S*H( JR, J )
- H( JR, J ) = -S*H( JR, J+1 ) + C*H( JR, J )
- H( JR, J+1 ) = TEMP
- 160 CONTINUE
- DO 170 JR = IFRSTM, J
- TEMP = C*T( JR, J+1 ) + S*T( JR, J )
- T( JR, J ) = -S*T( JR, J+1 ) + C*T( JR, J )
- T( JR, J+1 ) = TEMP
- 170 CONTINUE
- IF( ILZ ) THEN
- DO 180 JR = 1, N
- TEMP = C*Z( JR, J+1 ) + S*Z( JR, J )
- Z( JR, J ) = -S*Z( JR, J+1 ) + C*Z( JR, J )
- Z( JR, J+1 ) = TEMP
- 180 CONTINUE
- END IF
- 190 CONTINUE
-*
- GO TO 350
-*
-* Use Francis double-shift
-*
-* Note: the Francis double-shift should work with real shifts,
-* but only if the block is at least 3x3.
-* This code may break if this point is reached with
-* a 2x2 block with real eigenvalues.
-*
- 200 CONTINUE
- IF( IFIRST+1.EQ.ILAST ) THEN
-*
-* Special case -- 2x2 block with complex eigenvectors
-*
-* Step 1: Standardize, that is, rotate so that
-*
-* ( B11 0 )
-* B = ( ) with B11 non-negative.
-* ( 0 B22 )
-*
- CALL DLASV2( T( ILAST-1, ILAST-1 ), T( ILAST-1, ILAST ),
- $ T( ILAST, ILAST ), B22, B11, SR, CR, SL, CL )
-*
- IF( B11.LT.ZERO ) THEN
- CR = -CR
- SR = -SR
- B11 = -B11
- B22 = -B22
- END IF
-*
- CALL DROT( ILASTM+1-IFIRST, H( ILAST-1, ILAST-1 ), LDH,
- $ H( ILAST, ILAST-1 ), LDH, CL, SL )
- CALL DROT( ILAST+1-IFRSTM, H( IFRSTM, ILAST-1 ), 1,
- $ H( IFRSTM, ILAST ), 1, CR, SR )
-*
- IF( ILAST.LT.ILASTM )
- $ CALL DROT( ILASTM-ILAST, T( ILAST-1, ILAST+1 ), LDT,
- $ T( ILAST, ILAST+1 ), LDH, CL, SL )
- IF( IFRSTM.LT.ILAST-1 )
- $ CALL DROT( IFIRST-IFRSTM, T( IFRSTM, ILAST-1 ), 1,
- $ T( IFRSTM, ILAST ), 1, CR, SR )
-*
- IF( ILQ )
- $ CALL DROT( N, Q( 1, ILAST-1 ), 1, Q( 1, ILAST ), 1, CL,
- $ SL )
- IF( ILZ )
- $ CALL DROT( N, Z( 1, ILAST-1 ), 1, Z( 1, ILAST ), 1, CR,
- $ SR )
-*
- T( ILAST-1, ILAST-1 ) = B11
- T( ILAST-1, ILAST ) = ZERO
- T( ILAST, ILAST-1 ) = ZERO
- T( ILAST, ILAST ) = B22
-*
-* If B22 is negative, negate column ILAST
-*
- IF( B22.LT.ZERO ) THEN
- DO 210 J = IFRSTM, ILAST
- H( J, ILAST ) = -H( J, ILAST )
- T( J, ILAST ) = -T( J, ILAST )
- 210 CONTINUE
-*
- IF( ILZ ) THEN
- DO 220 J = 1, N
- Z( J, ILAST ) = -Z( J, ILAST )
- 220 CONTINUE
- END IF
- END IF
-*
-* Step 2: Compute ALPHAR, ALPHAI, and BETA (see refs.)
-*
-* Recompute shift
-*
- CALL DLAG2( H( ILAST-1, ILAST-1 ), LDH,
- $ T( ILAST-1, ILAST-1 ), LDT, SAFMIN*SAFETY, S1,
- $ TEMP, WR, TEMP2, WI )
-*
-* If standardization has perturbed the shift onto real line,
-* do another (real single-shift) QR step.
-*
- IF( WI.EQ.ZERO )
- $ GO TO 350
- S1INV = ONE / S1
-*
-* Do EISPACK (QZVAL) computation of alpha and beta
-*
- A11 = H( ILAST-1, ILAST-1 )
- A21 = H( ILAST, ILAST-1 )
- A12 = H( ILAST-1, ILAST )
- A22 = H( ILAST, ILAST )
-*
-* Compute complex Givens rotation on right
-* (Assume some element of C = (sA - wB) > unfl )
-* __
-* (sA - wB) ( CZ -SZ )
-* ( SZ CZ )
-*
- C11R = S1*A11 - WR*B11
- C11I = -WI*B11
- C12 = S1*A12
- C21 = S1*A21
- C22R = S1*A22 - WR*B22
- C22I = -WI*B22
-*
- IF( ABS( C11R )+ABS( C11I )+ABS( C12 ).GT.ABS( C21 )+
- $ ABS( C22R )+ABS( C22I ) ) THEN
- T1 = DLAPY3( C12, C11R, C11I )
- CZ = C12 / T1
- SZR = -C11R / T1
- SZI = -C11I / T1
- ELSE
- CZ = DLAPY2( C22R, C22I )
- IF( CZ.LE.SAFMIN ) THEN
- CZ = ZERO
- SZR = ONE
- SZI = ZERO
- ELSE
- TEMPR = C22R / CZ
- TEMPI = C22I / CZ
- T1 = DLAPY2( CZ, C21 )
- CZ = CZ / T1
- SZR = -C21*TEMPR / T1
- SZI = C21*TEMPI / T1
- END IF
- END IF
-*
-* Compute Givens rotation on left
-*
-* ( CQ SQ )
-* ( __ ) A or B
-* ( -SQ CQ )
-*
- AN = ABS( A11 ) + ABS( A12 ) + ABS( A21 ) + ABS( A22 )
- BN = ABS( B11 ) + ABS( B22 )
- WABS = ABS( WR ) + ABS( WI )
- IF( S1*AN.GT.WABS*BN ) THEN
- CQ = CZ*B11
- SQR = SZR*B22
- SQI = -SZI*B22
- ELSE
- A1R = CZ*A11 + SZR*A12
- A1I = SZI*A12
- A2R = CZ*A21 + SZR*A22
- A2I = SZI*A22
- CQ = DLAPY2( A1R, A1I )
- IF( CQ.LE.SAFMIN ) THEN
- CQ = ZERO
- SQR = ONE
- SQI = ZERO
- ELSE
- TEMPR = A1R / CQ
- TEMPI = A1I / CQ
- SQR = TEMPR*A2R + TEMPI*A2I
- SQI = TEMPI*A2R - TEMPR*A2I
- END IF
- END IF
- T1 = DLAPY3( CQ, SQR, SQI )
- CQ = CQ / T1
- SQR = SQR / T1
- SQI = SQI / T1
-*
-* Compute diagonal elements of QBZ
-*
- TEMPR = SQR*SZR - SQI*SZI
- TEMPI = SQR*SZI + SQI*SZR
- B1R = CQ*CZ*B11 + TEMPR*B22
- B1I = TEMPI*B22
- B1A = DLAPY2( B1R, B1I )
- B2R = CQ*CZ*B22 + TEMPR*B11
- B2I = -TEMPI*B11
- B2A = DLAPY2( B2R, B2I )
-*
-* Normalize so beta > 0, and Im( alpha1 ) > 0
-*
- BETA( ILAST-1 ) = B1A
- BETA( ILAST ) = B2A
- ALPHAR( ILAST-1 ) = ( WR*B1A )*S1INV
- ALPHAI( ILAST-1 ) = ( WI*B1A )*S1INV
- ALPHAR( ILAST ) = ( WR*B2A )*S1INV
- ALPHAI( ILAST ) = -( WI*B2A )*S1INV
-*
-* Step 3: Go to next block -- exit if finished.
-*
- ILAST = IFIRST - 1
- IF( ILAST.LT.ILO )
- $ GO TO 380
-*
-* Reset counters
-*
- IITER = 0
- ESHIFT = ZERO
- IF( .NOT.ILSCHR ) THEN
- ILASTM = ILAST
- IF( IFRSTM.GT.ILAST )
- $ IFRSTM = ILO
- END IF
- GO TO 350
- ELSE
-*
-* Usual case: 3x3 or larger block, using Francis implicit
-* double-shift
-*
-* 2
-* Eigenvalue equation is w - c w + d = 0,
-*
-* -1 2 -1
-* so compute 1st column of (A B ) - c A B + d
-* using the formula in QZIT (from EISPACK)
-*
-* We assume that the block is at least 3x3
-*
- AD11 = ( ASCALE*H( ILAST-1, ILAST-1 ) ) /
- $ ( BSCALE*T( ILAST-1, ILAST-1 ) )
- AD21 = ( ASCALE*H( ILAST, ILAST-1 ) ) /
- $ ( BSCALE*T( ILAST-1, ILAST-1 ) )
- AD12 = ( ASCALE*H( ILAST-1, ILAST ) ) /
- $ ( BSCALE*T( ILAST, ILAST ) )
- AD22 = ( ASCALE*H( ILAST, ILAST ) ) /
- $ ( BSCALE*T( ILAST, ILAST ) )
- U12 = T( ILAST-1, ILAST ) / T( ILAST, ILAST )
- AD11L = ( ASCALE*H( IFIRST, IFIRST ) ) /
- $ ( BSCALE*T( IFIRST, IFIRST ) )
- AD21L = ( ASCALE*H( IFIRST+1, IFIRST ) ) /
- $ ( BSCALE*T( IFIRST, IFIRST ) )
- AD12L = ( ASCALE*H( IFIRST, IFIRST+1 ) ) /
- $ ( BSCALE*T( IFIRST+1, IFIRST+1 ) )
- AD22L = ( ASCALE*H( IFIRST+1, IFIRST+1 ) ) /
- $ ( BSCALE*T( IFIRST+1, IFIRST+1 ) )
- AD32L = ( ASCALE*H( IFIRST+2, IFIRST+1 ) ) /
- $ ( BSCALE*T( IFIRST+1, IFIRST+1 ) )
- U12L = T( IFIRST, IFIRST+1 ) / T( IFIRST+1, IFIRST+1 )
-*
- V( 1 ) = ( AD11-AD11L )*( AD22-AD11L ) - AD12*AD21 +
- $ AD21*U12*AD11L + ( AD12L-AD11L*U12L )*AD21L
- V( 2 ) = ( ( AD22L-AD11L )-AD21L*U12L-( AD11-AD11L )-
- $ ( AD22-AD11L )+AD21*U12 )*AD21L
- V( 3 ) = AD32L*AD21L
-*
- ISTART = IFIRST
-*
- CALL DLARFG( 3, V( 1 ), V( 2 ), 1, TAU )
- V( 1 ) = ONE
-*
-* Sweep
-*
- DO 290 J = ISTART, ILAST - 2
-*
-* All but last elements: use 3x3 Householder transforms.
-*
-* Zero (j-1)st column of A
-*
- IF( J.GT.ISTART ) THEN
- V( 1 ) = H( J, J-1 )
- V( 2 ) = H( J+1, J-1 )
- V( 3 ) = H( J+2, J-1 )
-*
- CALL DLARFG( 3, H( J, J-1 ), V( 2 ), 1, TAU )
- V( 1 ) = ONE
- H( J+1, J-1 ) = ZERO
- H( J+2, J-1 ) = ZERO
- END IF
-*
- DO 230 JC = J, ILASTM
- TEMP = TAU*( H( J, JC )+V( 2 )*H( J+1, JC )+V( 3 )*
- $ H( J+2, JC ) )
- H( J, JC ) = H( J, JC ) - TEMP
- H( J+1, JC ) = H( J+1, JC ) - TEMP*V( 2 )
- H( J+2, JC ) = H( J+2, JC ) - TEMP*V( 3 )
- TEMP2 = TAU*( T( J, JC )+V( 2 )*T( J+1, JC )+V( 3 )*
- $ T( J+2, JC ) )
- T( J, JC ) = T( J, JC ) - TEMP2
- T( J+1, JC ) = T( J+1, JC ) - TEMP2*V( 2 )
- T( J+2, JC ) = T( J+2, JC ) - TEMP2*V( 3 )
- 230 CONTINUE
- IF( ILQ ) THEN
- DO 240 JR = 1, N
- TEMP = TAU*( Q( JR, J )+V( 2 )*Q( JR, J+1 )+V( 3 )*
- $ Q( JR, J+2 ) )
- Q( JR, J ) = Q( JR, J ) - TEMP
- Q( JR, J+1 ) = Q( JR, J+1 ) - TEMP*V( 2 )
- Q( JR, J+2 ) = Q( JR, J+2 ) - TEMP*V( 3 )
- 240 CONTINUE
- END IF
-*
-* Zero j-th column of B (see DLAGBC for details)
-*
-* Swap rows to pivot
-*
- ILPIVT = .FALSE.
- TEMP = MAX( ABS( T( J+1, J+1 ) ), ABS( T( J+1, J+2 ) ) )
- TEMP2 = MAX( ABS( T( J+2, J+1 ) ), ABS( T( J+2, J+2 ) ) )
- IF( MAX( TEMP, TEMP2 ).LT.SAFMIN ) THEN
- SCALE = ZERO
- U1 = ONE
- U2 = ZERO
- GO TO 250
- ELSE IF( TEMP.GE.TEMP2 ) THEN
- W11 = T( J+1, J+1 )
- W21 = T( J+2, J+1 )
- W12 = T( J+1, J+2 )
- W22 = T( J+2, J+2 )
- U1 = T( J+1, J )
- U2 = T( J+2, J )
- ELSE
- W21 = T( J+1, J+1 )
- W11 = T( J+2, J+1 )
- W22 = T( J+1, J+2 )
- W12 = T( J+2, J+2 )
- U2 = T( J+1, J )
- U1 = T( J+2, J )
- END IF
-*
-* Swap columns if nec.
-*
- IF( ABS( W12 ).GT.ABS( W11 ) ) THEN
- ILPIVT = .TRUE.
- TEMP = W12
- TEMP2 = W22
- W12 = W11
- W22 = W21
- W11 = TEMP
- W21 = TEMP2
- END IF
-*
-* LU-factor
-*
- TEMP = W21 / W11
- U2 = U2 - TEMP*U1
- W22 = W22 - TEMP*W12
- W21 = ZERO
-*
-* Compute SCALE
-*
- SCALE = ONE
- IF( ABS( W22 ).LT.SAFMIN ) THEN
- SCALE = ZERO
- U2 = ONE
- U1 = -W12 / W11
- GO TO 250
- END IF
- IF( ABS( W22 ).LT.ABS( U2 ) )
- $ SCALE = ABS( W22 / U2 )
- IF( ABS( W11 ).LT.ABS( U1 ) )
- $ SCALE = MIN( SCALE, ABS( W11 / U1 ) )
-*
-* Solve
-*
- U2 = ( SCALE*U2 ) / W22
- U1 = ( SCALE*U1-W12*U2 ) / W11
-*
- 250 CONTINUE
- IF( ILPIVT ) THEN
- TEMP = U2
- U2 = U1
- U1 = TEMP
- END IF
-*
-* Compute Householder Vector
-*
- T1 = SQRT( SCALE**2+U1**2+U2**2 )
- TAU = ONE + SCALE / T1
- VS = -ONE / ( SCALE+T1 )
- V( 1 ) = ONE
- V( 2 ) = VS*U1
- V( 3 ) = VS*U2
-*
-* Apply transformations from the right.
-*
- DO 260 JR = IFRSTM, MIN( J+3, ILAST )
- TEMP = TAU*( H( JR, J )+V( 2 )*H( JR, J+1 )+V( 3 )*
- $ H( JR, J+2 ) )
- H( JR, J ) = H( JR, J ) - TEMP
- H( JR, J+1 ) = H( JR, J+1 ) - TEMP*V( 2 )
- H( JR, J+2 ) = H( JR, J+2 ) - TEMP*V( 3 )
- 260 CONTINUE
- DO 270 JR = IFRSTM, J + 2
- TEMP = TAU*( T( JR, J )+V( 2 )*T( JR, J+1 )+V( 3 )*
- $ T( JR, J+2 ) )
- T( JR, J ) = T( JR, J ) - TEMP
- T( JR, J+1 ) = T( JR, J+1 ) - TEMP*V( 2 )
- T( JR, J+2 ) = T( JR, J+2 ) - TEMP*V( 3 )
- 270 CONTINUE
- IF( ILZ ) THEN
- DO 280 JR = 1, N
- TEMP = TAU*( Z( JR, J )+V( 2 )*Z( JR, J+1 )+V( 3 )*
- $ Z( JR, J+2 ) )
- Z( JR, J ) = Z( JR, J ) - TEMP
- Z( JR, J+1 ) = Z( JR, J+1 ) - TEMP*V( 2 )
- Z( JR, J+2 ) = Z( JR, J+2 ) - TEMP*V( 3 )
- 280 CONTINUE
- END IF
- T( J+1, J ) = ZERO
- T( J+2, J ) = ZERO
- 290 CONTINUE
-*
-* Last elements: Use Givens rotations
-*
-* Rotations from the left
-*
- J = ILAST - 1
- TEMP = H( J, J-1 )
- CALL DLARTG( TEMP, H( J+1, J-1 ), C, S, H( J, J-1 ) )
- H( J+1, J-1 ) = ZERO
-*
- DO 300 JC = J, ILASTM
- TEMP = C*H( J, JC ) + S*H( J+1, JC )
- H( J+1, JC ) = -S*H( J, JC ) + C*H( J+1, JC )
- H( J, JC ) = TEMP
- TEMP2 = C*T( J, JC ) + S*T( J+1, JC )
- T( J+1, JC ) = -S*T( J, JC ) + C*T( J+1, JC )
- T( J, JC ) = TEMP2
- 300 CONTINUE
- IF( ILQ ) THEN
- DO 310 JR = 1, N
- TEMP = C*Q( JR, J ) + S*Q( JR, J+1 )
- Q( JR, J+1 ) = -S*Q( JR, J ) + C*Q( JR, J+1 )
- Q( JR, J ) = TEMP
- 310 CONTINUE
- END IF
-*
-* Rotations from the right.
-*
- TEMP = T( J+1, J+1 )
- CALL DLARTG( TEMP, T( J+1, J ), C, S, T( J+1, J+1 ) )
- T( J+1, J ) = ZERO
-*
- DO 320 JR = IFRSTM, ILAST
- TEMP = C*H( JR, J+1 ) + S*H( JR, J )
- H( JR, J ) = -S*H( JR, J+1 ) + C*H( JR, J )
- H( JR, J+1 ) = TEMP
- 320 CONTINUE
- DO 330 JR = IFRSTM, ILAST - 1
- TEMP = C*T( JR, J+1 ) + S*T( JR, J )
- T( JR, J ) = -S*T( JR, J+1 ) + C*T( JR, J )
- T( JR, J+1 ) = TEMP
- 330 CONTINUE
- IF( ILZ ) THEN
- DO 340 JR = 1, N
- TEMP = C*Z( JR, J+1 ) + S*Z( JR, J )
- Z( JR, J ) = -S*Z( JR, J+1 ) + C*Z( JR, J )
- Z( JR, J+1 ) = TEMP
- 340 CONTINUE
- END IF
-*
-* End of Double-Shift code
-*
- END IF
-*
- GO TO 350
-*
-* End of iteration loop
-*
- 350 CONTINUE
- 360 CONTINUE
-*
-* Drop-through = non-convergence
-*
- INFO = ILAST
- GO TO 420
-*
-* Successful completion of all QZ steps
-*
- 380 CONTINUE
-*
-* Set Eigenvalues 1:ILO-1
-*
- DO 410 J = 1, ILO - 1
- IF( T( J, J ).LT.ZERO ) THEN
- IF( ILSCHR ) THEN
- DO 390 JR = 1, J
- H( JR, J ) = -H( JR, J )
- T( JR, J ) = -T( JR, J )
- 390 CONTINUE
- ELSE
- H( J, J ) = -H( J, J )
- T( J, J ) = -T( J, J )
- END IF
- IF( ILZ ) THEN
- DO 400 JR = 1, N
- Z( JR, J ) = -Z( JR, J )
- 400 CONTINUE
- END IF
- END IF
- ALPHAR( J ) = H( J, J )
- ALPHAI( J ) = ZERO
- BETA( J ) = T( J, J )
- 410 CONTINUE
-*
-* Normal Termination
-*
- INFO = 0
-*
-* Exit (other than argument error) -- return optimal workspace size
-*
- 420 CONTINUE
- WORK( 1 ) = DBLE( N )
- RETURN
-*
-* End of DHGEQZ
-*
- END
diff --git a/src/lib/lapack/dhseqr.f b/src/lib/lapack/dhseqr.f
deleted file mode 100644
index 5b307fa8..00000000
--- a/src/lib/lapack/dhseqr.f
+++ /dev/null
@@ -1,407 +0,0 @@
- SUBROUTINE DHSEQR( JOB, COMPZ, N, ILO, IHI, H, LDH, WR, WI, Z,
- $ LDZ, WORK, LWORK, INFO )
-*
-* -- LAPACK driver routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- INTEGER IHI, ILO, INFO, LDH, LDZ, LWORK, N
- CHARACTER COMPZ, JOB
-* ..
-* .. Array Arguments ..
- DOUBLE PRECISION H( LDH, * ), WI( * ), WORK( * ), WR( * ),
- $ Z( LDZ, * )
-* ..
-* Purpose
-* =======
-*
-* DHSEQR computes the eigenvalues of a Hessenberg matrix H
-* and, optionally, the matrices T and Z from the Schur decomposition
-* H = Z T Z**T, where T is an upper quasi-triangular matrix (the
-* Schur form), and Z is the orthogonal matrix of Schur vectors.
-*
-* Optionally Z may be postmultiplied into an input orthogonal
-* matrix Q so that this routine can give the Schur factorization
-* of a matrix A which has been reduced to the Hessenberg form H
-* by the orthogonal matrix Q: A = Q*H*Q**T = (QZ)*T*(QZ)**T.
-*
-* Arguments
-* =========
-*
-* JOB (input) CHARACTER*1
-* = 'E': compute eigenvalues only;
-* = 'S': compute eigenvalues and the Schur form T.
-*
-* COMPZ (input) CHARACTER*1
-* = 'N': no Schur vectors are computed;
-* = 'I': Z is initialized to the unit matrix and the matrix Z
-* of Schur vectors of H is returned;
-* = 'V': Z must contain an orthogonal matrix Q on entry, and
-* the product Q*Z is returned.
-*
-* N (input) INTEGER
-* The order of the matrix H. N .GE. 0.
-*
-* ILO (input) INTEGER
-* IHI (input) INTEGER
-* It is assumed that H is already upper triangular in rows
-* and columns 1:ILO-1 and IHI+1:N. ILO and IHI are normally
-* set by a previous call to DGEBAL, and then passed to DGEHRD
-* when the matrix output by DGEBAL is reduced to Hessenberg
-* form. Otherwise ILO and IHI should be set to 1 and N
-* respectively. If N.GT.0, then 1.LE.ILO.LE.IHI.LE.N.
-* If N = 0, then ILO = 1 and IHI = 0.
-*
-* H (input/output) DOUBLE PRECISION array, dimension (LDH,N)
-* On entry, the upper Hessenberg matrix H.
-* On exit, if INFO = 0 and JOB = 'S', then H contains the
-* upper quasi-triangular matrix T from the Schur decomposition
-* (the Schur form); 2-by-2 diagonal blocks (corresponding to
-* complex conjugate pairs of eigenvalues) are returned in
-* standard form, with H(i,i) = H(i+1,i+1) and
-* H(i+1,i)*H(i,i+1).LT.0. If INFO = 0 and JOB = 'E', the
-* contents of H are unspecified on exit. (The output value of
-* H when INFO.GT.0 is given under the description of INFO
-* below.)
-*
-* Unlike earlier versions of DHSEQR, this subroutine may
-* explicitly H(i,j) = 0 for i.GT.j and j = 1, 2, ... ILO-1
-* or j = IHI+1, IHI+2, ... N.
-*
-* LDH (input) INTEGER
-* The leading dimension of the array H. LDH .GE. max(1,N).
-*
-* WR (output) DOUBLE PRECISION array, dimension (N)
-* WI (output) DOUBLE PRECISION array, dimension (N)
-* The real and imaginary parts, respectively, of the computed
-* eigenvalues. If two eigenvalues are computed as a complex
-* conjugate pair, they are stored in consecutive elements of
-* WR and WI, say the i-th and (i+1)th, with WI(i) .GT. 0 and
-* WI(i+1) .LT. 0. If JOB = 'S', the eigenvalues are stored in
-* the same order as on the diagonal of the Schur form returned
-* in H, with WR(i) = H(i,i) and, if H(i:i+1,i:i+1) is a 2-by-2
-* diagonal block, WI(i) = sqrt(-H(i+1,i)*H(i,i+1)) and
-* WI(i+1) = -WI(i).
-*
-* Z (input/output) DOUBLE PRECISION array, dimension (LDZ,N)
-* If COMPZ = 'N', Z is not referenced.
-* If COMPZ = 'I', on entry Z need not be set and on exit,
-* if INFO = 0, Z contains the orthogonal matrix Z of the Schur
-* vectors of H. If COMPZ = 'V', on entry Z must contain an
-* N-by-N matrix Q, which is assumed to be equal to the unit
-* matrix except for the submatrix Z(ILO:IHI,ILO:IHI). On exit,
-* if INFO = 0, Z contains Q*Z.
-* Normally Q is the orthogonal matrix generated by DORGHR
-* after the call to DGEHRD which formed the Hessenberg matrix
-* H. (The output value of Z when INFO.GT.0 is given under
-* the description of INFO below.)
-*
-* LDZ (input) INTEGER
-* The leading dimension of the array Z. if COMPZ = 'I' or
-* COMPZ = 'V', then LDZ.GE.MAX(1,N). Otherwize, LDZ.GE.1.
-*
-* WORK (workspace/output) DOUBLE PRECISION array, dimension (LWORK)
-* On exit, if INFO = 0, WORK(1) returns an estimate of
-* the optimal value for LWORK.
-*
-* LWORK (input) INTEGER
-* The dimension of the array WORK. LWORK .GE. max(1,N)
-* is sufficient, but LWORK typically as large as 6*N may
-* be required for optimal performance. A workspace query
-* to determine the optimal workspace size is recommended.
-*
-* If LWORK = -1, then DHSEQR does a workspace query.
-* In this case, DHSEQR checks the input parameters and
-* estimates the optimal workspace size for the given
-* values of N, ILO and IHI. The estimate is returned
-* in WORK(1). No error message related to LWORK is
-* issued by XERBLA. Neither H nor Z are accessed.
-*
-*
-* INFO (output) INTEGER
-* = 0: successful exit
-* .LT. 0: if INFO = -i, the i-th argument had an illegal
-* value
-* .GT. 0: if INFO = i, DHSEQR failed to compute all of
-* the eigenvalues. Elements 1:ilo-1 and i+1:n of WR
-* and WI contain those eigenvalues which have been
-* successfully computed. (Failures are rare.)
-*
-* If INFO .GT. 0 and JOB = 'E', then on exit, the
-* remaining unconverged eigenvalues are the eigen-
-* values of the upper Hessenberg matrix rows and
-* columns ILO through INFO of the final, output
-* value of H.
-*
-* If INFO .GT. 0 and JOB = 'S', then on exit
-*
-* (*) (initial value of H)*U = U*(final value of H)
-*
-* where U is an orthogonal matrix. The final
-* value of H is upper Hessenberg and quasi-triangular
-* in rows and columns INFO+1 through IHI.
-*
-* If INFO .GT. 0 and COMPZ = 'V', then on exit
-*
-* (final value of Z) = (initial value of Z)*U
-*
-* where U is the orthogonal matrix in (*) (regard-
-* less of the value of JOB.)
-*
-* If INFO .GT. 0 and COMPZ = 'I', then on exit
-* (final value of Z) = U
-* where U is the orthogonal matrix in (*) (regard-
-* less of the value of JOB.)
-*
-* If INFO .GT. 0 and COMPZ = 'N', then Z is not
-* accessed.
-*
-* ================================================================
-* Default values supplied by
-* ILAENV(ISPEC,'DHSEQR',JOB(:1)//COMPZ(:1),N,ILO,IHI,LWORK).
-* It is suggested that these defaults be adjusted in order
-* to attain best performance in each particular
-* computational environment.
-*
-* ISPEC=1: The DLAHQR vs DLAQR0 crossover point.
-* Default: 75. (Must be at least 11.)
-*
-* ISPEC=2: Recommended deflation window size.
-* This depends on ILO, IHI and NS. NS is the
-* number of simultaneous shifts returned
-* by ILAENV(ISPEC=4). (See ISPEC=4 below.)
-* The default for (IHI-ILO+1).LE.500 is NS.
-* The default for (IHI-ILO+1).GT.500 is 3*NS/2.
-*
-* ISPEC=3: Nibble crossover point. (See ILAENV for
-* details.) Default: 14% of deflation window
-* size.
-*
-* ISPEC=4: Number of simultaneous shifts, NS, in
-* a multi-shift QR iteration.
-*
-* If IHI-ILO+1 is ...
-*
-* greater than ...but less ... the
-* or equal to ... than default is
-*
-* 1 30 NS - 2(+)
-* 30 60 NS - 4(+)
-* 60 150 NS = 10(+)
-* 150 590 NS = **
-* 590 3000 NS = 64
-* 3000 6000 NS = 128
-* 6000 infinity NS = 256
-*
-* (+) By default some or all matrices of this order
-* are passed to the implicit double shift routine
-* DLAHQR and NS is ignored. See ISPEC=1 above
-* and comments in IPARM for details.
-*
-* The asterisks (**) indicate an ad-hoc
-* function of N increasing from 10 to 64.
-*
-* ISPEC=5: Select structured matrix multiply.
-* (See ILAENV for details.) Default: 3.
-*
-* ================================================================
-* Based on contributions by
-* Karen Braman and Ralph Byers, Department of Mathematics,
-* University of Kansas, USA
-*
-* ================================================================
-* References:
-* K. Braman, R. Byers and R. Mathias, The Multi-Shift QR
-* Algorithm Part I: Maintaining Well Focused Shifts, and Level 3
-* Performance, SIAM Journal of Matrix Analysis, volume 23, pages
-* 929--947, 2002.
-*
-* K. Braman, R. Byers and R. Mathias, The Multi-Shift QR
-* Algorithm Part II: Aggressive Early Deflation, SIAM Journal
-* of Matrix Analysis, volume 23, pages 948--973, 2002.
-*
-* ================================================================
-* .. Parameters ..
-*
-* ==== Matrices of order NTINY or smaller must be processed by
-* . DLAHQR because of insufficient subdiagonal scratch space.
-* . (This is a hard limit.) ====
-*
-* ==== NL allocates some local workspace to help small matrices
-* . through a rare DLAHQR failure. NL .GT. NTINY = 11 is
-* . required and NL .LE. NMIN = ILAENV(ISPEC=1,...) is recom-
-* . mended. (The default value of NMIN is 75.) Using NL = 49
-* . allows up to six simultaneous shifts and a 16-by-16
-* . deflation window. ====
-*
- INTEGER NTINY
- PARAMETER ( NTINY = 11 )
- INTEGER NL
- PARAMETER ( NL = 49 )
- DOUBLE PRECISION ZERO, ONE
- PARAMETER ( ZERO = 0.0d0, ONE = 1.0d0 )
-* ..
-* .. Local Arrays ..
- DOUBLE PRECISION HL( NL, NL ), WORKL( NL )
-* ..
-* .. Local Scalars ..
- INTEGER I, KBOT, NMIN
- LOGICAL INITZ, LQUERY, WANTT, WANTZ
-* ..
-* .. External Functions ..
- INTEGER ILAENV
- LOGICAL LSAME
- EXTERNAL ILAENV, LSAME
-* ..
-* .. External Subroutines ..
- EXTERNAL DLACPY, DLAHQR, DLAQR0, DLASET, XERBLA
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC DBLE, MAX, MIN
-* ..
-* .. Executable Statements ..
-*
-* ==== Decode and check the input parameters. ====
-*
- WANTT = LSAME( JOB, 'S' )
- INITZ = LSAME( COMPZ, 'I' )
- WANTZ = INITZ .OR. LSAME( COMPZ, 'V' )
- WORK( 1 ) = DBLE( MAX( 1, N ) )
- LQUERY = LWORK.EQ.-1
-*
- INFO = 0
- IF( .NOT.LSAME( JOB, 'E' ) .AND. .NOT.WANTT ) THEN
- INFO = -1
- ELSE IF( .NOT.LSAME( COMPZ, 'N' ) .AND. .NOT.WANTZ ) THEN
- INFO = -2
- ELSE IF( N.LT.0 ) THEN
- INFO = -3
- ELSE IF( ILO.LT.1 .OR. ILO.GT.MAX( 1, N ) ) THEN
- INFO = -4
- ELSE IF( IHI.LT.MIN( ILO, N ) .OR. IHI.GT.N ) THEN
- INFO = -5
- ELSE IF( LDH.LT.MAX( 1, N ) ) THEN
- INFO = -7
- ELSE IF( LDZ.LT.1 .OR. ( WANTZ .AND. LDZ.LT.MAX( 1, N ) ) ) THEN
- INFO = -11
- ELSE IF( LWORK.LT.MAX( 1, N ) .AND. .NOT.LQUERY ) THEN
- INFO = -13
- END IF
-*
- IF( INFO.NE.0 ) THEN
-*
-* ==== Quick return in case of invalid argument. ====
-*
- CALL XERBLA( 'DHSEQR', -INFO )
- RETURN
-*
- ELSE IF( N.EQ.0 ) THEN
-*
-* ==== Quick return in case N = 0; nothing to do. ====
-*
- RETURN
-*
- ELSE IF( LQUERY ) THEN
-*
-* ==== Quick return in case of a workspace query ====
-*
- CALL DLAQR0( WANTT, WANTZ, N, ILO, IHI, H, LDH, WR, WI, ILO,
- $ IHI, Z, LDZ, WORK, LWORK, INFO )
-* ==== Ensure reported workspace size is backward-compatible with
-* . previous LAPACK versions. ====
- WORK( 1 ) = MAX( DBLE( MAX( 1, N ) ), WORK( 1 ) )
- RETURN
-*
- ELSE
-*
-* ==== copy eigenvalues isolated by DGEBAL ====
-*
- DO 10 I = 1, ILO - 1
- WR( I ) = H( I, I )
- WI( I ) = ZERO
- 10 CONTINUE
- DO 20 I = IHI + 1, N
- WR( I ) = H( I, I )
- WI( I ) = ZERO
- 20 CONTINUE
-*
-* ==== Initialize Z, if requested ====
-*
- IF( INITZ )
- $ CALL DLASET( 'A', N, N, ZERO, ONE, Z, LDZ )
-*
-* ==== Quick return if possible ====
-*
- IF( ILO.EQ.IHI ) THEN
- WR( ILO ) = H( ILO, ILO )
- WI( ILO ) = ZERO
- RETURN
- END IF
-*
-* ==== DLAHQR/DLAQR0 crossover point ====
-*
- NMIN = ILAENV( 12, 'DHSEQR', JOB( : 1 ) // COMPZ( : 1 ), N,
- $ ILO, IHI, LWORK )
- NMIN = MAX( NTINY, NMIN )
-*
-* ==== DLAQR0 for big matrices; DLAHQR for small ones ====
-*
- IF( N.GT.NMIN ) THEN
- CALL DLAQR0( WANTT, WANTZ, N, ILO, IHI, H, LDH, WR, WI, ILO,
- $ IHI, Z, LDZ, WORK, LWORK, INFO )
- ELSE
-*
-* ==== Small matrix ====
-*
- CALL DLAHQR( WANTT, WANTZ, N, ILO, IHI, H, LDH, WR, WI, ILO,
- $ IHI, Z, LDZ, INFO )
-*
- IF( INFO.GT.0 ) THEN
-*
-* ==== A rare DLAHQR failure! DLAQR0 sometimes succeeds
-* . when DLAHQR fails. ====
-*
- KBOT = INFO
-*
- IF( N.GE.NL ) THEN
-*
-* ==== Larger matrices have enough subdiagonal scratch
-* . space to call DLAQR0 directly. ====
-*
- CALL DLAQR0( WANTT, WANTZ, N, ILO, KBOT, H, LDH, WR,
- $ WI, ILO, IHI, Z, LDZ, WORK, LWORK, INFO )
-*
- ELSE
-*
-* ==== Tiny matrices don't have enough subdiagonal
-* . scratch space to benefit from DLAQR0. Hence,
-* . tiny matrices must be copied into a larger
-* . array before calling DLAQR0. ====
-*
- CALL DLACPY( 'A', N, N, H, LDH, HL, NL )
- HL( N+1, N ) = ZERO
- CALL DLASET( 'A', NL, NL-N, ZERO, ZERO, HL( 1, N+1 ),
- $ NL )
- CALL DLAQR0( WANTT, WANTZ, NL, ILO, KBOT, HL, NL, WR,
- $ WI, ILO, IHI, Z, LDZ, WORKL, NL, INFO )
- IF( WANTT .OR. INFO.NE.0 )
- $ CALL DLACPY( 'A', N, N, HL, NL, H, LDH )
- END IF
- END IF
- END IF
-*
-* ==== Clear out the trash, if necessary. ====
-*
- IF( ( WANTT .OR. INFO.NE.0 ) .AND. N.GT.2 )
- $ CALL DLASET( 'L', N-2, N-2, ZERO, ZERO, H( 3, 1 ), LDH )
-*
-* ==== Ensure reported workspace size is backward-compatible with
-* . previous LAPACK versions. ====
-*
- WORK( 1 ) = MAX( DBLE( MAX( 1, N ) ), WORK( 1 ) )
- END IF
-*
-* ==== End of DHSEQR ====
-*
- END
diff --git a/src/lib/lapack/disnan.f b/src/lib/lapack/disnan.f
deleted file mode 100644
index 52003561..00000000
--- a/src/lib/lapack/disnan.f
+++ /dev/null
@@ -1,33 +0,0 @@
- LOGICAL FUNCTION DISNAN(DIN)
-*
-* -- LAPACK auxiliary routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- DOUBLE PRECISION DIN
-* ..
-*
-* Purpose
-* =======
-*
-* DISNAN returns .TRUE. if its argument is NaN, and .FALSE.
-* otherwise. To be replaced by the Fortran 2003 intrinsic in the
-* future.
-*
-* Arguments
-* =========
-*
-* DIN (input) DOUBLE PRECISION
-* Input to test for NaN.
-*
-* =====================================================================
-*
-* .. External Functions ..
- LOGICAL DLAISNAN
- EXTERNAL DLAISNAN
-* ..
-* .. Executable Statements ..
- DISNAN = DLAISNAN(DIN,DIN)
- RETURN
- END
diff --git a/src/lib/lapack/dlabad.f b/src/lib/lapack/dlabad.f
deleted file mode 100644
index 05ff5d44..00000000
--- a/src/lib/lapack/dlabad.f
+++ /dev/null
@@ -1,55 +0,0 @@
- SUBROUTINE DLABAD( SMALL, LARGE )
-*
-* -- LAPACK auxiliary routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- DOUBLE PRECISION LARGE, SMALL
-* ..
-*
-* Purpose
-* =======
-*
-* DLABAD takes as input the values computed by DLAMCH for underflow and
-* overflow, and returns the square root of each of these values if the
-* log of LARGE is sufficiently large. This subroutine is intended to
-* identify machines with a large exponent range, such as the Crays, and
-* redefine the underflow and overflow limits to be the square roots of
-* the values computed by DLAMCH. This subroutine is needed because
-* DLAMCH does not compensate for poor arithmetic in the upper half of
-* the exponent range, as is found on a Cray.
-*
-* Arguments
-* =========
-*
-* SMALL (input/output) DOUBLE PRECISION
-* On entry, the underflow threshold as computed by DLAMCH.
-* On exit, if LOG10(LARGE) is sufficiently large, the square
-* root of SMALL, otherwise unchanged.
-*
-* LARGE (input/output) DOUBLE PRECISION
-* On entry, the overflow threshold as computed by DLAMCH.
-* On exit, if LOG10(LARGE) is sufficiently large, the square
-* root of LARGE, otherwise unchanged.
-*
-* =====================================================================
-*
-* .. Intrinsic Functions ..
- INTRINSIC LOG10, SQRT
-* ..
-* .. Executable Statements ..
-*
-* If it looks like we're on a Cray, take the square root of
-* SMALL and LARGE to avoid overflow and underflow problems.
-*
- IF( LOG10( LARGE ).GT.2000.D0 ) THEN
- SMALL = SQRT( SMALL )
- LARGE = SQRT( LARGE )
- END IF
-*
- RETURN
-*
-* End of DLABAD
-*
- END
diff --git a/src/lib/lapack/dlabrd.f b/src/lib/lapack/dlabrd.f
deleted file mode 100644
index 196b130c..00000000
--- a/src/lib/lapack/dlabrd.f
+++ /dev/null
@@ -1,290 +0,0 @@
- SUBROUTINE DLABRD( M, N, NB, A, LDA, D, E, TAUQ, TAUP, X, LDX, Y,
- $ LDY )
-*
-* -- LAPACK auxiliary routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- INTEGER LDA, LDX, LDY, M, N, NB
-* ..
-* .. Array Arguments ..
- DOUBLE PRECISION A( LDA, * ), D( * ), E( * ), TAUP( * ),
- $ TAUQ( * ), X( LDX, * ), Y( LDY, * )
-* ..
-*
-* Purpose
-* =======
-*
-* DLABRD reduces the first NB rows and columns of a real general
-* m by n matrix A to upper or lower bidiagonal form by an orthogonal
-* transformation Q' * A * P, and returns the matrices X and Y which
-* are needed to apply the transformation to the unreduced part of A.
-*
-* If m >= n, A is reduced to upper bidiagonal form; if m < n, to lower
-* bidiagonal form.
-*
-* This is an auxiliary routine called by DGEBRD
-*
-* Arguments
-* =========
-*
-* M (input) INTEGER
-* The number of rows in the matrix A.
-*
-* N (input) INTEGER
-* The number of columns in the matrix A.
-*
-* NB (input) INTEGER
-* The number of leading rows and columns of A to be reduced.
-*
-* A (input/output) DOUBLE PRECISION array, dimension (LDA,N)
-* On entry, the m by n general matrix to be reduced.
-* On exit, the first NB rows and columns of the matrix are
-* overwritten; the rest of the array is unchanged.
-* If m >= n, elements on and below the diagonal in the first NB
-* columns, with the array TAUQ, represent the orthogonal
-* matrix Q as a product of elementary reflectors; and
-* elements above the diagonal in the first NB rows, with the
-* array TAUP, represent the orthogonal matrix P as a product
-* of elementary reflectors.
-* If m < n, elements below the diagonal in the first NB
-* columns, with the array TAUQ, represent the orthogonal
-* matrix Q as a product of elementary reflectors, and
-* elements on and above the diagonal in the first NB rows,
-* with the array TAUP, represent the orthogonal matrix P as
-* a product of elementary reflectors.
-* See Further Details.
-*
-* LDA (input) INTEGER
-* The leading dimension of the array A. LDA >= max(1,M).
-*
-* D (output) DOUBLE PRECISION array, dimension (NB)
-* The diagonal elements of the first NB rows and columns of
-* the reduced matrix. D(i) = A(i,i).
-*
-* E (output) DOUBLE PRECISION array, dimension (NB)
-* The off-diagonal elements of the first NB rows and columns of
-* the reduced matrix.
-*
-* TAUQ (output) DOUBLE PRECISION array dimension (NB)
-* The scalar factors of the elementary reflectors which
-* represent the orthogonal matrix Q. See Further Details.
-*
-* TAUP (output) DOUBLE PRECISION array, dimension (NB)
-* The scalar factors of the elementary reflectors which
-* represent the orthogonal matrix P. See Further Details.
-*
-* X (output) DOUBLE PRECISION array, dimension (LDX,NB)
-* The m-by-nb matrix X required to update the unreduced part
-* of A.
-*
-* LDX (input) INTEGER
-* The leading dimension of the array X. LDX >= M.
-*
-* Y (output) DOUBLE PRECISION array, dimension (LDY,NB)
-* The n-by-nb matrix Y required to update the unreduced part
-* of A.
-*
-* LDY (input) INTEGER
-* The leading dimension of the array Y. LDY >= N.
-*
-* Further Details
-* ===============
-*
-* The matrices Q and P are represented as products of elementary
-* reflectors:
-*
-* Q = H(1) H(2) . . . H(nb) and P = G(1) G(2) . . . G(nb)
-*
-* Each H(i) and G(i) has the form:
-*
-* H(i) = I - tauq * v * v' and G(i) = I - taup * u * u'
-*
-* where tauq and taup are real scalars, and v and u are real vectors.
-*
-* If m >= n, v(1:i-1) = 0, v(i) = 1, and v(i:m) is stored on exit in
-* A(i:m,i); u(1:i) = 0, u(i+1) = 1, and u(i+1:n) is stored on exit in
-* A(i,i+1:n); tauq is stored in TAUQ(i) and taup in TAUP(i).
-*
-* If m < n, v(1:i) = 0, v(i+1) = 1, and v(i+1:m) is stored on exit in
-* A(i+2:m,i); u(1:i-1) = 0, u(i) = 1, and u(i:n) is stored on exit in
-* A(i,i+1:n); tauq is stored in TAUQ(i) and taup in TAUP(i).
-*
-* The elements of the vectors v and u together form the m-by-nb matrix
-* V and the nb-by-n matrix U' which are needed, with X and Y, to apply
-* the transformation to the unreduced part of the matrix, using a block
-* update of the form: A := A - V*Y' - X*U'.
-*
-* The contents of A on exit are illustrated by the following examples
-* with nb = 2:
-*
-* m = 6 and n = 5 (m > n): m = 5 and n = 6 (m < n):
-*
-* ( 1 1 u1 u1 u1 ) ( 1 u1 u1 u1 u1 u1 )
-* ( v1 1 1 u2 u2 ) ( 1 1 u2 u2 u2 u2 )
-* ( v1 v2 a a a ) ( v1 1 a a a a )
-* ( v1 v2 a a a ) ( v1 v2 a a a a )
-* ( v1 v2 a a a ) ( v1 v2 a a a a )
-* ( v1 v2 a a a )
-*
-* where a denotes an element of the original matrix which is unchanged,
-* vi denotes an element of the vector defining H(i), and ui an element
-* of the vector defining G(i).
-*
-* =====================================================================
-*
-* .. Parameters ..
- DOUBLE PRECISION ZERO, ONE
- PARAMETER ( ZERO = 0.0D0, ONE = 1.0D0 )
-* ..
-* .. Local Scalars ..
- INTEGER I
-* ..
-* .. External Subroutines ..
- EXTERNAL DGEMV, DLARFG, DSCAL
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC MIN
-* ..
-* .. Executable Statements ..
-*
-* Quick return if possible
-*
- IF( M.LE.0 .OR. N.LE.0 )
- $ RETURN
-*
- IF( M.GE.N ) THEN
-*
-* Reduce to upper bidiagonal form
-*
- DO 10 I = 1, NB
-*
-* Update A(i:m,i)
-*
- CALL DGEMV( 'No transpose', M-I+1, I-1, -ONE, A( I, 1 ),
- $ LDA, Y( I, 1 ), LDY, ONE, A( I, I ), 1 )
- CALL DGEMV( 'No transpose', M-I+1, I-1, -ONE, X( I, 1 ),
- $ LDX, A( 1, I ), 1, ONE, A( I, I ), 1 )
-*
-* Generate reflection Q(i) to annihilate A(i+1:m,i)
-*
- CALL DLARFG( M-I+1, A( I, I ), A( MIN( I+1, M ), I ), 1,
- $ TAUQ( I ) )
- D( I ) = A( I, I )
- IF( I.LT.N ) THEN
- A( I, I ) = ONE
-*
-* Compute Y(i+1:n,i)
-*
- CALL DGEMV( 'Transpose', M-I+1, N-I, ONE, A( I, I+1 ),
- $ LDA, A( I, I ), 1, ZERO, Y( I+1, I ), 1 )
- CALL DGEMV( 'Transpose', M-I+1, I-1, ONE, A( I, 1 ), LDA,
- $ A( I, I ), 1, ZERO, Y( 1, I ), 1 )
- CALL DGEMV( 'No transpose', N-I, I-1, -ONE, Y( I+1, 1 ),
- $ LDY, Y( 1, I ), 1, ONE, Y( I+1, I ), 1 )
- CALL DGEMV( 'Transpose', M-I+1, I-1, ONE, X( I, 1 ), LDX,
- $ A( I, I ), 1, ZERO, Y( 1, I ), 1 )
- CALL DGEMV( 'Transpose', I-1, N-I, -ONE, A( 1, I+1 ),
- $ LDA, Y( 1, I ), 1, ONE, Y( I+1, I ), 1 )
- CALL DSCAL( N-I, TAUQ( I ), Y( I+1, I ), 1 )
-*
-* Update A(i,i+1:n)
-*
- CALL DGEMV( 'No transpose', N-I, I, -ONE, Y( I+1, 1 ),
- $ LDY, A( I, 1 ), LDA, ONE, A( I, I+1 ), LDA )
- CALL DGEMV( 'Transpose', I-1, N-I, -ONE, A( 1, I+1 ),
- $ LDA, X( I, 1 ), LDX, ONE, A( I, I+1 ), LDA )
-*
-* Generate reflection P(i) to annihilate A(i,i+2:n)
-*
- CALL DLARFG( N-I, A( I, I+1 ), A( I, MIN( I+2, N ) ),
- $ LDA, TAUP( I ) )
- E( I ) = A( I, I+1 )
- A( I, I+1 ) = ONE
-*
-* Compute X(i+1:m,i)
-*
- CALL DGEMV( 'No transpose', M-I, N-I, ONE, A( I+1, I+1 ),
- $ LDA, A( I, I+1 ), LDA, ZERO, X( I+1, I ), 1 )
- CALL DGEMV( 'Transpose', N-I, I, ONE, Y( I+1, 1 ), LDY,
- $ A( I, I+1 ), LDA, ZERO, X( 1, I ), 1 )
- CALL DGEMV( 'No transpose', M-I, I, -ONE, A( I+1, 1 ),
- $ LDA, X( 1, I ), 1, ONE, X( I+1, I ), 1 )
- CALL DGEMV( 'No transpose', I-1, N-I, ONE, A( 1, I+1 ),
- $ LDA, A( I, I+1 ), LDA, ZERO, X( 1, I ), 1 )
- CALL DGEMV( 'No transpose', M-I, I-1, -ONE, X( I+1, 1 ),
- $ LDX, X( 1, I ), 1, ONE, X( I+1, I ), 1 )
- CALL DSCAL( M-I, TAUP( I ), X( I+1, I ), 1 )
- END IF
- 10 CONTINUE
- ELSE
-*
-* Reduce to lower bidiagonal form
-*
- DO 20 I = 1, NB
-*
-* Update A(i,i:n)
-*
- CALL DGEMV( 'No transpose', N-I+1, I-1, -ONE, Y( I, 1 ),
- $ LDY, A( I, 1 ), LDA, ONE, A( I, I ), LDA )
- CALL DGEMV( 'Transpose', I-1, N-I+1, -ONE, A( 1, I ), LDA,
- $ X( I, 1 ), LDX, ONE, A( I, I ), LDA )
-*
-* Generate reflection P(i) to annihilate A(i,i+1:n)
-*
- CALL DLARFG( N-I+1, A( I, I ), A( I, MIN( I+1, N ) ), LDA,
- $ TAUP( I ) )
- D( I ) = A( I, I )
- IF( I.LT.M ) THEN
- A( I, I ) = ONE
-*
-* Compute X(i+1:m,i)
-*
- CALL DGEMV( 'No transpose', M-I, N-I+1, ONE, A( I+1, I ),
- $ LDA, A( I, I ), LDA, ZERO, X( I+1, I ), 1 )
- CALL DGEMV( 'Transpose', N-I+1, I-1, ONE, Y( I, 1 ), LDY,
- $ A( I, I ), LDA, ZERO, X( 1, I ), 1 )
- CALL DGEMV( 'No transpose', M-I, I-1, -ONE, A( I+1, 1 ),
- $ LDA, X( 1, I ), 1, ONE, X( I+1, I ), 1 )
- CALL DGEMV( 'No transpose', I-1, N-I+1, ONE, A( 1, I ),
- $ LDA, A( I, I ), LDA, ZERO, X( 1, I ), 1 )
- CALL DGEMV( 'No transpose', M-I, I-1, -ONE, X( I+1, 1 ),
- $ LDX, X( 1, I ), 1, ONE, X( I+1, I ), 1 )
- CALL DSCAL( M-I, TAUP( I ), X( I+1, I ), 1 )
-*
-* Update A(i+1:m,i)
-*
- CALL DGEMV( 'No transpose', M-I, I-1, -ONE, A( I+1, 1 ),
- $ LDA, Y( I, 1 ), LDY, ONE, A( I+1, I ), 1 )
- CALL DGEMV( 'No transpose', M-I, I, -ONE, X( I+1, 1 ),
- $ LDX, A( 1, I ), 1, ONE, A( I+1, I ), 1 )
-*
-* Generate reflection Q(i) to annihilate A(i+2:m,i)
-*
- CALL DLARFG( M-I, A( I+1, I ), A( MIN( I+2, M ), I ), 1,
- $ TAUQ( I ) )
- E( I ) = A( I+1, I )
- A( I+1, I ) = ONE
-*
-* Compute Y(i+1:n,i)
-*
- CALL DGEMV( 'Transpose', M-I, N-I, ONE, A( I+1, I+1 ),
- $ LDA, A( I+1, I ), 1, ZERO, Y( I+1, I ), 1 )
- CALL DGEMV( 'Transpose', M-I, I-1, ONE, A( I+1, 1 ), LDA,
- $ A( I+1, I ), 1, ZERO, Y( 1, I ), 1 )
- CALL DGEMV( 'No transpose', N-I, I-1, -ONE, Y( I+1, 1 ),
- $ LDY, Y( 1, I ), 1, ONE, Y( I+1, I ), 1 )
- CALL DGEMV( 'Transpose', M-I, I, ONE, X( I+1, 1 ), LDX,
- $ A( I+1, I ), 1, ZERO, Y( 1, I ), 1 )
- CALL DGEMV( 'Transpose', I, N-I, -ONE, A( 1, I+1 ), LDA,
- $ Y( 1, I ), 1, ONE, Y( I+1, I ), 1 )
- CALL DSCAL( N-I, TAUQ( I ), Y( I+1, I ), 1 )
- END IF
- 20 CONTINUE
- END IF
- RETURN
-*
-* End of DLABRD
-*
- END
diff --git a/src/lib/lapack/dlacn2.f b/src/lib/lapack/dlacn2.f
deleted file mode 100644
index 6705d256..00000000
--- a/src/lib/lapack/dlacn2.f
+++ /dev/null
@@ -1,214 +0,0 @@
- SUBROUTINE DLACN2( N, V, X, ISGN, EST, KASE, ISAVE )
-*
-* -- LAPACK auxiliary routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- INTEGER KASE, N
- DOUBLE PRECISION EST
-* ..
-* .. Array Arguments ..
- INTEGER ISGN( * ), ISAVE( 3 )
- DOUBLE PRECISION V( * ), X( * )
-* ..
-*
-* Purpose
-* =======
-*
-* DLACN2 estimates the 1-norm of a square, real matrix A.
-* Reverse communication is used for evaluating matrix-vector products.
-*
-* Arguments
-* =========
-*
-* N (input) INTEGER
-* The order of the matrix. N >= 1.
-*
-* V (workspace) DOUBLE PRECISION array, dimension (N)
-* On the final return, V = A*W, where EST = norm(V)/norm(W)
-* (W is not returned).
-*
-* X (input/output) DOUBLE PRECISION array, dimension (N)
-* On an intermediate return, X should be overwritten by
-* A * X, if KASE=1,
-* A' * X, if KASE=2,
-* and DLACN2 must be re-called with all the other parameters
-* unchanged.
-*
-* ISGN (workspace) INTEGER array, dimension (N)
-*
-* EST (input/output) DOUBLE PRECISION
-* On entry with KASE = 1 or 2 and ISAVE(1) = 3, EST should be
-* unchanged from the previous call to DLACN2.
-* On exit, EST is an estimate (a lower bound) for norm(A).
-*
-* KASE (input/output) INTEGER
-* On the initial call to DLACN2, KASE should be 0.
-* On an intermediate return, KASE will be 1 or 2, indicating
-* whether X should be overwritten by A * X or A' * X.
-* On the final return from DLACN2, KASE will again be 0.
-*
-* ISAVE (input/output) INTEGER array, dimension (3)
-* ISAVE is used to save variables between calls to DLACN2
-*
-* Further Details
-* ======= =======
-*
-* Contributed by Nick Higham, University of Manchester.
-* Originally named SONEST, dated March 16, 1988.
-*
-* Reference: N.J. Higham, "FORTRAN codes for estimating the one-norm of
-* a real or complex matrix, with applications to condition estimation",
-* ACM Trans. Math. Soft., vol. 14, no. 4, pp. 381-396, December 1988.
-*
-* This is a thread safe version of DLACON, which uses the array ISAVE
-* in place of a SAVE statement, as follows:
-*
-* DLACON DLACN2
-* JUMP ISAVE(1)
-* J ISAVE(2)
-* ITER ISAVE(3)
-*
-* =====================================================================
-*
-* .. Parameters ..
- INTEGER ITMAX
- PARAMETER ( ITMAX = 5 )
- DOUBLE PRECISION ZERO, ONE, TWO
- PARAMETER ( ZERO = 0.0D+0, ONE = 1.0D+0, TWO = 2.0D+0 )
-* ..
-* .. Local Scalars ..
- INTEGER I, JLAST
- DOUBLE PRECISION ALTSGN, ESTOLD, TEMP
-* ..
-* .. External Functions ..
- INTEGER IDAMAX
- DOUBLE PRECISION DASUM
- EXTERNAL IDAMAX, DASUM
-* ..
-* .. External Subroutines ..
- EXTERNAL DCOPY
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC ABS, DBLE, NINT, SIGN
-* ..
-* .. Executable Statements ..
-*
- IF( KASE.EQ.0 ) THEN
- DO 10 I = 1, N
- X( I ) = ONE / DBLE( N )
- 10 CONTINUE
- KASE = 1
- ISAVE( 1 ) = 1
- RETURN
- END IF
-*
- GO TO ( 20, 40, 70, 110, 140 )ISAVE( 1 )
-*
-* ................ ENTRY (ISAVE( 1 ) = 1)
-* FIRST ITERATION. X HAS BEEN OVERWRITTEN BY A*X.
-*
- 20 CONTINUE
- IF( N.EQ.1 ) THEN
- V( 1 ) = X( 1 )
- EST = ABS( V( 1 ) )
-* ... QUIT
- GO TO 150
- END IF
- EST = DASUM( N, X, 1 )
-*
- DO 30 I = 1, N
- X( I ) = SIGN( ONE, X( I ) )
- ISGN( I ) = NINT( X( I ) )
- 30 CONTINUE
- KASE = 2
- ISAVE( 1 ) = 2
- RETURN
-*
-* ................ ENTRY (ISAVE( 1 ) = 2)
-* FIRST ITERATION. X HAS BEEN OVERWRITTEN BY TRANSPOSE(A)*X.
-*
- 40 CONTINUE
- ISAVE( 2 ) = IDAMAX( N, X, 1 )
- ISAVE( 3 ) = 2
-*
-* MAIN LOOP - ITERATIONS 2,3,...,ITMAX.
-*
- 50 CONTINUE
- DO 60 I = 1, N
- X( I ) = ZERO
- 60 CONTINUE
- X( ISAVE( 2 ) ) = ONE
- KASE = 1
- ISAVE( 1 ) = 3
- RETURN
-*
-* ................ ENTRY (ISAVE( 1 ) = 3)
-* X HAS BEEN OVERWRITTEN BY A*X.
-*
- 70 CONTINUE
- CALL DCOPY( N, X, 1, V, 1 )
- ESTOLD = EST
- EST = DASUM( N, V, 1 )
- DO 80 I = 1, N
- IF( NINT( SIGN( ONE, X( I ) ) ).NE.ISGN( I ) )
- $ GO TO 90
- 80 CONTINUE
-* REPEATED SIGN VECTOR DETECTED, HENCE ALGORITHM HAS CONVERGED.
- GO TO 120
-*
- 90 CONTINUE
-* TEST FOR CYCLING.
- IF( EST.LE.ESTOLD )
- $ GO TO 120
-*
- DO 100 I = 1, N
- X( I ) = SIGN( ONE, X( I ) )
- ISGN( I ) = NINT( X( I ) )
- 100 CONTINUE
- KASE = 2
- ISAVE( 1 ) = 4
- RETURN
-*
-* ................ ENTRY (ISAVE( 1 ) = 4)
-* X HAS BEEN OVERWRITTEN BY TRANSPOSE(A)*X.
-*
- 110 CONTINUE
- JLAST = ISAVE( 2 )
- ISAVE( 2 ) = IDAMAX( N, X, 1 )
- IF( ( X( JLAST ).NE.ABS( X( ISAVE( 2 ) ) ) ) .AND.
- $ ( ISAVE( 3 ).LT.ITMAX ) ) THEN
- ISAVE( 3 ) = ISAVE( 3 ) + 1
- GO TO 50
- END IF
-*
-* ITERATION COMPLETE. FINAL STAGE.
-*
- 120 CONTINUE
- ALTSGN = ONE
- DO 130 I = 1, N
- X( I ) = ALTSGN*( ONE+DBLE( I-1 ) / DBLE( N-1 ) )
- ALTSGN = -ALTSGN
- 130 CONTINUE
- KASE = 1
- ISAVE( 1 ) = 5
- RETURN
-*
-* ................ ENTRY (ISAVE( 1 ) = 5)
-* X HAS BEEN OVERWRITTEN BY A*X.
-*
- 140 CONTINUE
- TEMP = TWO*( DASUM( N, X, 1 ) / DBLE( 3*N ) )
- IF( TEMP.GT.EST ) THEN
- CALL DCOPY( N, X, 1, V, 1 )
- EST = TEMP
- END IF
-*
- 150 CONTINUE
- KASE = 0
- RETURN
-*
-* End of DLACN2
-*
- END
diff --git a/src/lib/lapack/dlacon.f b/src/lib/lapack/dlacon.f
deleted file mode 100644
index f113b03a..00000000
--- a/src/lib/lapack/dlacon.f
+++ /dev/null
@@ -1,205 +0,0 @@
- SUBROUTINE DLACON( N, V, X, ISGN, EST, KASE )
-*
-* -- LAPACK auxiliary routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- INTEGER KASE, N
- DOUBLE PRECISION EST
-* ..
-* .. Array Arguments ..
- INTEGER ISGN( * )
- DOUBLE PRECISION V( * ), X( * )
-* ..
-*
-* Purpose
-* =======
-*
-* DLACON estimates the 1-norm of a square, real matrix A.
-* Reverse communication is used for evaluating matrix-vector products.
-*
-* Arguments
-* =========
-*
-* N (input) INTEGER
-* The order of the matrix. N >= 1.
-*
-* V (workspace) DOUBLE PRECISION array, dimension (N)
-* On the final return, V = A*W, where EST = norm(V)/norm(W)
-* (W is not returned).
-*
-* X (input/output) DOUBLE PRECISION array, dimension (N)
-* On an intermediate return, X should be overwritten by
-* A * X, if KASE=1,
-* A' * X, if KASE=2,
-* and DLACON must be re-called with all the other parameters
-* unchanged.
-*
-* ISGN (workspace) INTEGER array, dimension (N)
-*
-* EST (input/output) DOUBLE PRECISION
-* On entry with KASE = 1 or 2 and JUMP = 3, EST should be
-* unchanged from the previous call to DLACON.
-* On exit, EST is an estimate (a lower bound) for norm(A).
-*
-* KASE (input/output) INTEGER
-* On the initial call to DLACON, KASE should be 0.
-* On an intermediate return, KASE will be 1 or 2, indicating
-* whether X should be overwritten by A * X or A' * X.
-* On the final return from DLACON, KASE will again be 0.
-*
-* Further Details
-* ======= =======
-*
-* Contributed by Nick Higham, University of Manchester.
-* Originally named SONEST, dated March 16, 1988.
-*
-* Reference: N.J. Higham, "FORTRAN codes for estimating the one-norm of
-* a real or complex matrix, with applications to condition estimation",
-* ACM Trans. Math. Soft., vol. 14, no. 4, pp. 381-396, December 1988.
-*
-* =====================================================================
-*
-* .. Parameters ..
- INTEGER ITMAX
- PARAMETER ( ITMAX = 5 )
- DOUBLE PRECISION ZERO, ONE, TWO
- PARAMETER ( ZERO = 0.0D+0, ONE = 1.0D+0, TWO = 2.0D+0 )
-* ..
-* .. Local Scalars ..
- INTEGER I, ITER, J, JLAST, JUMP
- DOUBLE PRECISION ALTSGN, ESTOLD, TEMP
-* ..
-* .. External Functions ..
- INTEGER IDAMAX
- DOUBLE PRECISION DASUM
- EXTERNAL IDAMAX, DASUM
-* ..
-* .. External Subroutines ..
- EXTERNAL DCOPY
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC ABS, DBLE, NINT, SIGN
-* ..
-* .. Save statement ..
- SAVE
-* ..
-* .. Executable Statements ..
-*
- IF( KASE.EQ.0 ) THEN
- DO 10 I = 1, N
- X( I ) = ONE / DBLE( N )
- 10 CONTINUE
- KASE = 1
- JUMP = 1
- RETURN
- END IF
-*
- GO TO ( 20, 40, 70, 110, 140 )JUMP
-*
-* ................ ENTRY (JUMP = 1)
-* FIRST ITERATION. X HAS BEEN OVERWRITTEN BY A*X.
-*
- 20 CONTINUE
- IF( N.EQ.1 ) THEN
- V( 1 ) = X( 1 )
- EST = ABS( V( 1 ) )
-* ... QUIT
- GO TO 150
- END IF
- EST = DASUM( N, X, 1 )
-*
- DO 30 I = 1, N
- X( I ) = SIGN( ONE, X( I ) )
- ISGN( I ) = NINT( X( I ) )
- 30 CONTINUE
- KASE = 2
- JUMP = 2
- RETURN
-*
-* ................ ENTRY (JUMP = 2)
-* FIRST ITERATION. X HAS BEEN OVERWRITTEN BY TRANSPOSE(A)*X.
-*
- 40 CONTINUE
- J = IDAMAX( N, X, 1 )
- ITER = 2
-*
-* MAIN LOOP - ITERATIONS 2,3,...,ITMAX.
-*
- 50 CONTINUE
- DO 60 I = 1, N
- X( I ) = ZERO
- 60 CONTINUE
- X( J ) = ONE
- KASE = 1
- JUMP = 3
- RETURN
-*
-* ................ ENTRY (JUMP = 3)
-* X HAS BEEN OVERWRITTEN BY A*X.
-*
- 70 CONTINUE
- CALL DCOPY( N, X, 1, V, 1 )
- ESTOLD = EST
- EST = DASUM( N, V, 1 )
- DO 80 I = 1, N
- IF( NINT( SIGN( ONE, X( I ) ) ).NE.ISGN( I ) )
- $ GO TO 90
- 80 CONTINUE
-* REPEATED SIGN VECTOR DETECTED, HENCE ALGORITHM HAS CONVERGED.
- GO TO 120
-*
- 90 CONTINUE
-* TEST FOR CYCLING.
- IF( EST.LE.ESTOLD )
- $ GO TO 120
-*
- DO 100 I = 1, N
- X( I ) = SIGN( ONE, X( I ) )
- ISGN( I ) = NINT( X( I ) )
- 100 CONTINUE
- KASE = 2
- JUMP = 4
- RETURN
-*
-* ................ ENTRY (JUMP = 4)
-* X HAS BEEN OVERWRITTEN BY TRANSPOSE(A)*X.
-*
- 110 CONTINUE
- JLAST = J
- J = IDAMAX( N, X, 1 )
- IF( ( X( JLAST ).NE.ABS( X( J ) ) ) .AND. ( ITER.LT.ITMAX ) ) THEN
- ITER = ITER + 1
- GO TO 50
- END IF
-*
-* ITERATION COMPLETE. FINAL STAGE.
-*
- 120 CONTINUE
- ALTSGN = ONE
- DO 130 I = 1, N
- X( I ) = ALTSGN*( ONE+DBLE( I-1 ) / DBLE( N-1 ) )
- ALTSGN = -ALTSGN
- 130 CONTINUE
- KASE = 1
- JUMP = 5
- RETURN
-*
-* ................ ENTRY (JUMP = 5)
-* X HAS BEEN OVERWRITTEN BY A*X.
-*
- 140 CONTINUE
- TEMP = TWO*( DASUM( N, X, 1 ) / DBLE( 3*N ) )
- IF( TEMP.GT.EST ) THEN
- CALL DCOPY( N, X, 1, V, 1 )
- EST = TEMP
- END IF
-*
- 150 CONTINUE
- KASE = 0
- RETURN
-*
-* End of DLACON
-*
- END
diff --git a/src/lib/lapack/dlacpy.f b/src/lib/lapack/dlacpy.f
deleted file mode 100644
index d72603a5..00000000
--- a/src/lib/lapack/dlacpy.f
+++ /dev/null
@@ -1,87 +0,0 @@
- SUBROUTINE DLACPY( UPLO, M, N, A, LDA, B, LDB )
-*
-* -- LAPACK auxiliary routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- CHARACTER UPLO
- INTEGER LDA, LDB, M, N
-* ..
-* .. Array Arguments ..
- DOUBLE PRECISION A( LDA, * ), B( LDB, * )
-* ..
-*
-* Purpose
-* =======
-*
-* DLACPY copies all or part of a two-dimensional matrix A to another
-* matrix B.
-*
-* Arguments
-* =========
-*
-* UPLO (input) CHARACTER*1
-* Specifies the part of the matrix A to be copied to B.
-* = 'U': Upper triangular part
-* = 'L': Lower triangular part
-* Otherwise: All of the matrix A
-*
-* M (input) INTEGER
-* The number of rows of the matrix A. M >= 0.
-*
-* N (input) INTEGER
-* The number of columns of the matrix A. N >= 0.
-*
-* A (input) DOUBLE PRECISION array, dimension (LDA,N)
-* The m by n matrix A. If UPLO = 'U', only the upper triangle
-* or trapezoid is accessed; if UPLO = 'L', only the lower
-* triangle or trapezoid is accessed.
-*
-* LDA (input) INTEGER
-* The leading dimension of the array A. LDA >= max(1,M).
-*
-* B (output) DOUBLE PRECISION array, dimension (LDB,N)
-* On exit, B = A in the locations specified by UPLO.
-*
-* LDB (input) INTEGER
-* The leading dimension of the array B. LDB >= max(1,M).
-*
-* =====================================================================
-*
-* .. Local Scalars ..
- INTEGER I, J
-* ..
-* .. External Functions ..
- LOGICAL LSAME
- EXTERNAL LSAME
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC MIN
-* ..
-* .. Executable Statements ..
-*
- IF( LSAME( UPLO, 'U' ) ) THEN
- DO 20 J = 1, N
- DO 10 I = 1, MIN( J, M )
- B( I, J ) = A( I, J )
- 10 CONTINUE
- 20 CONTINUE
- ELSE IF( LSAME( UPLO, 'L' ) ) THEN
- DO 40 J = 1, N
- DO 30 I = J, M
- B( I, J ) = A( I, J )
- 30 CONTINUE
- 40 CONTINUE
- ELSE
- DO 60 J = 1, N
- DO 50 I = 1, M
- B( I, J ) = A( I, J )
- 50 CONTINUE
- 60 CONTINUE
- END IF
- RETURN
-*
-* End of DLACPY
-*
- END
diff --git a/src/lib/lapack/dladiv.f b/src/lib/lapack/dladiv.f
deleted file mode 100644
index b6a74d1b..00000000
--- a/src/lib/lapack/dladiv.f
+++ /dev/null
@@ -1,62 +0,0 @@
- SUBROUTINE DLADIV( A, B, C, D, P, Q )
-*
-* -- LAPACK auxiliary routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- DOUBLE PRECISION A, B, C, D, P, Q
-* ..
-*
-* Purpose
-* =======
-*
-* DLADIV performs complex division in real arithmetic
-*
-* a + i*b
-* p + i*q = ---------
-* c + i*d
-*
-* The algorithm is due to Robert L. Smith and can be found
-* in D. Knuth, The art of Computer Programming, Vol.2, p.195
-*
-* Arguments
-* =========
-*
-* A (input) DOUBLE PRECISION
-* B (input) DOUBLE PRECISION
-* C (input) DOUBLE PRECISION
-* D (input) DOUBLE PRECISION
-* The scalars a, b, c, and d in the above expression.
-*
-* P (output) DOUBLE PRECISION
-* Q (output) DOUBLE PRECISION
-* The scalars p and q in the above expression.
-*
-* =====================================================================
-*
-* .. Local Scalars ..
- DOUBLE PRECISION E, F
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC ABS
-* ..
-* .. Executable Statements ..
-*
- IF( ABS( D ).LT.ABS( C ) ) THEN
- E = D / C
- F = C + D*E
- P = ( A+B*E ) / F
- Q = ( B-A*E ) / F
- ELSE
- E = C / D
- F = D + C*E
- P = ( B+A*E ) / F
- Q = ( -A+B*E ) / F
- END IF
-*
- RETURN
-*
-* End of DLADIV
-*
- END
diff --git a/src/lib/lapack/dlae2.f b/src/lib/lapack/dlae2.f
deleted file mode 100644
index 8e81c608..00000000
--- a/src/lib/lapack/dlae2.f
+++ /dev/null
@@ -1,123 +0,0 @@
- SUBROUTINE DLAE2( A, B, C, RT1, RT2 )
-*
-* -- LAPACK auxiliary routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- DOUBLE PRECISION A, B, C, RT1, RT2
-* ..
-*
-* Purpose
-* =======
-*
-* DLAE2 computes the eigenvalues of a 2-by-2 symmetric matrix
-* [ A B ]
-* [ B C ].
-* On return, RT1 is the eigenvalue of larger absolute value, and RT2
-* is the eigenvalue of smaller absolute value.
-*
-* Arguments
-* =========
-*
-* A (input) DOUBLE PRECISION
-* The (1,1) element of the 2-by-2 matrix.
-*
-* B (input) DOUBLE PRECISION
-* The (1,2) and (2,1) elements of the 2-by-2 matrix.
-*
-* C (input) DOUBLE PRECISION
-* The (2,2) element of the 2-by-2 matrix.
-*
-* RT1 (output) DOUBLE PRECISION
-* The eigenvalue of larger absolute value.
-*
-* RT2 (output) DOUBLE PRECISION
-* The eigenvalue of smaller absolute value.
-*
-* Further Details
-* ===============
-*
-* RT1 is accurate to a few ulps barring over/underflow.
-*
-* RT2 may be inaccurate if there is massive cancellation in the
-* determinant A*C-B*B; higher precision or correctly rounded or
-* correctly truncated arithmetic would be needed to compute RT2
-* accurately in all cases.
-*
-* Overflow is possible only if RT1 is within a factor of 5 of overflow.
-* Underflow is harmless if the input data is 0 or exceeds
-* underflow_threshold / macheps.
-*
-* =====================================================================
-*
-* .. Parameters ..
- DOUBLE PRECISION ONE
- PARAMETER ( ONE = 1.0D0 )
- DOUBLE PRECISION TWO
- PARAMETER ( TWO = 2.0D0 )
- DOUBLE PRECISION ZERO
- PARAMETER ( ZERO = 0.0D0 )
- DOUBLE PRECISION HALF
- PARAMETER ( HALF = 0.5D0 )
-* ..
-* .. Local Scalars ..
- DOUBLE PRECISION AB, ACMN, ACMX, ADF, DF, RT, SM, TB
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC ABS, SQRT
-* ..
-* .. Executable Statements ..
-*
-* Compute the eigenvalues
-*
- SM = A + C
- DF = A - C
- ADF = ABS( DF )
- TB = B + B
- AB = ABS( TB )
- IF( ABS( A ).GT.ABS( C ) ) THEN
- ACMX = A
- ACMN = C
- ELSE
- ACMX = C
- ACMN = A
- END IF
- IF( ADF.GT.AB ) THEN
- RT = ADF*SQRT( ONE+( AB / ADF )**2 )
- ELSE IF( ADF.LT.AB ) THEN
- RT = AB*SQRT( ONE+( ADF / AB )**2 )
- ELSE
-*
-* Includes case AB=ADF=0
-*
- RT = AB*SQRT( TWO )
- END IF
- IF( SM.LT.ZERO ) THEN
- RT1 = HALF*( SM-RT )
-*
-* Order of execution important.
-* To get fully accurate smaller eigenvalue,
-* next line needs to be executed in higher precision.
-*
- RT2 = ( ACMX / RT1 )*ACMN - ( B / RT1 )*B
- ELSE IF( SM.GT.ZERO ) THEN
- RT1 = HALF*( SM+RT )
-*
-* Order of execution important.
-* To get fully accurate smaller eigenvalue,
-* next line needs to be executed in higher precision.
-*
- RT2 = ( ACMX / RT1 )*ACMN - ( B / RT1 )*B
- ELSE
-*
-* Includes case RT1 = RT2 = 0
-*
- RT1 = HALF*RT
- RT2 = -HALF*RT
- END IF
- RETURN
-*
-* End of DLAE2
-*
- END
diff --git a/src/lib/lapack/dlaev2.f b/src/lib/lapack/dlaev2.f
deleted file mode 100644
index 49402faa..00000000
--- a/src/lib/lapack/dlaev2.f
+++ /dev/null
@@ -1,169 +0,0 @@
- SUBROUTINE DLAEV2( A, B, C, RT1, RT2, CS1, SN1 )
-*
-* -- LAPACK auxiliary routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- DOUBLE PRECISION A, B, C, CS1, RT1, RT2, SN1
-* ..
-*
-* Purpose
-* =======
-*
-* DLAEV2 computes the eigendecomposition of a 2-by-2 symmetric matrix
-* [ A B ]
-* [ B C ].
-* On return, RT1 is the eigenvalue of larger absolute value, RT2 is the
-* eigenvalue of smaller absolute value, and (CS1,SN1) is the unit right
-* eigenvector for RT1, giving the decomposition
-*
-* [ CS1 SN1 ] [ A B ] [ CS1 -SN1 ] = [ RT1 0 ]
-* [-SN1 CS1 ] [ B C ] [ SN1 CS1 ] [ 0 RT2 ].
-*
-* Arguments
-* =========
-*
-* A (input) DOUBLE PRECISION
-* The (1,1) element of the 2-by-2 matrix.
-*
-* B (input) DOUBLE PRECISION
-* The (1,2) element and the conjugate of the (2,1) element of
-* the 2-by-2 matrix.
-*
-* C (input) DOUBLE PRECISION
-* The (2,2) element of the 2-by-2 matrix.
-*
-* RT1 (output) DOUBLE PRECISION
-* The eigenvalue of larger absolute value.
-*
-* RT2 (output) DOUBLE PRECISION
-* The eigenvalue of smaller absolute value.
-*
-* CS1 (output) DOUBLE PRECISION
-* SN1 (output) DOUBLE PRECISION
-* The vector (CS1, SN1) is a unit right eigenvector for RT1.
-*
-* Further Details
-* ===============
-*
-* RT1 is accurate to a few ulps barring over/underflow.
-*
-* RT2 may be inaccurate if there is massive cancellation in the
-* determinant A*C-B*B; higher precision or correctly rounded or
-* correctly truncated arithmetic would be needed to compute RT2
-* accurately in all cases.
-*
-* CS1 and SN1 are accurate to a few ulps barring over/underflow.
-*
-* Overflow is possible only if RT1 is within a factor of 5 of overflow.
-* Underflow is harmless if the input data is 0 or exceeds
-* underflow_threshold / macheps.
-*
-* =====================================================================
-*
-* .. Parameters ..
- DOUBLE PRECISION ONE
- PARAMETER ( ONE = 1.0D0 )
- DOUBLE PRECISION TWO
- PARAMETER ( TWO = 2.0D0 )
- DOUBLE PRECISION ZERO
- PARAMETER ( ZERO = 0.0D0 )
- DOUBLE PRECISION HALF
- PARAMETER ( HALF = 0.5D0 )
-* ..
-* .. Local Scalars ..
- INTEGER SGN1, SGN2
- DOUBLE PRECISION AB, ACMN, ACMX, ACS, ADF, CS, CT, DF, RT, SM,
- $ TB, TN
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC ABS, SQRT
-* ..
-* .. Executable Statements ..
-*
-* Compute the eigenvalues
-*
- SM = A + C
- DF = A - C
- ADF = ABS( DF )
- TB = B + B
- AB = ABS( TB )
- IF( ABS( A ).GT.ABS( C ) ) THEN
- ACMX = A
- ACMN = C
- ELSE
- ACMX = C
- ACMN = A
- END IF
- IF( ADF.GT.AB ) THEN
- RT = ADF*SQRT( ONE+( AB / ADF )**2 )
- ELSE IF( ADF.LT.AB ) THEN
- RT = AB*SQRT( ONE+( ADF / AB )**2 )
- ELSE
-*
-* Includes case AB=ADF=0
-*
- RT = AB*SQRT( TWO )
- END IF
- IF( SM.LT.ZERO ) THEN
- RT1 = HALF*( SM-RT )
- SGN1 = -1
-*
-* Order of execution important.
-* To get fully accurate smaller eigenvalue,
-* next line needs to be executed in higher precision.
-*
- RT2 = ( ACMX / RT1 )*ACMN - ( B / RT1 )*B
- ELSE IF( SM.GT.ZERO ) THEN
- RT1 = HALF*( SM+RT )
- SGN1 = 1
-*
-* Order of execution important.
-* To get fully accurate smaller eigenvalue,
-* next line needs to be executed in higher precision.
-*
- RT2 = ( ACMX / RT1 )*ACMN - ( B / RT1 )*B
- ELSE
-*
-* Includes case RT1 = RT2 = 0
-*
- RT1 = HALF*RT
- RT2 = -HALF*RT
- SGN1 = 1
- END IF
-*
-* Compute the eigenvector
-*
- IF( DF.GE.ZERO ) THEN
- CS = DF + RT
- SGN2 = 1
- ELSE
- CS = DF - RT
- SGN2 = -1
- END IF
- ACS = ABS( CS )
- IF( ACS.GT.AB ) THEN
- CT = -TB / CS
- SN1 = ONE / SQRT( ONE+CT*CT )
- CS1 = CT*SN1
- ELSE
- IF( AB.EQ.ZERO ) THEN
- CS1 = ONE
- SN1 = ZERO
- ELSE
- TN = -CS / TB
- CS1 = ONE / SQRT( ONE+TN*TN )
- SN1 = TN*CS1
- END IF
- END IF
- IF( SGN1.EQ.SGN2 ) THEN
- TN = CS1
- CS1 = -SN1
- SN1 = TN
- END IF
- RETURN
-*
-* End of DLAEV2
-*
- END
diff --git a/src/lib/lapack/dlaexc.f b/src/lib/lapack/dlaexc.f
deleted file mode 100644
index 18e7d247..00000000
--- a/src/lib/lapack/dlaexc.f
+++ /dev/null
@@ -1,354 +0,0 @@
- SUBROUTINE DLAEXC( WANTQ, N, T, LDT, Q, LDQ, J1, N1, N2, WORK,
- $ INFO )
-*
-* -- LAPACK auxiliary routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- LOGICAL WANTQ
- INTEGER INFO, J1, LDQ, LDT, N, N1, N2
-* ..
-* .. Array Arguments ..
- DOUBLE PRECISION Q( LDQ, * ), T( LDT, * ), WORK( * )
-* ..
-*
-* Purpose
-* =======
-*
-* DLAEXC swaps adjacent diagonal blocks T11 and T22 of order 1 or 2 in
-* an upper quasi-triangular matrix T by an orthogonal similarity
-* transformation.
-*
-* T must be in Schur canonical form, that is, block upper triangular
-* with 1-by-1 and 2-by-2 diagonal blocks; each 2-by-2 diagonal block
-* has its diagonal elemnts equal and its off-diagonal elements of
-* opposite sign.
-*
-* Arguments
-* =========
-*
-* WANTQ (input) LOGICAL
-* = .TRUE. : accumulate the transformation in the matrix Q;
-* = .FALSE.: do not accumulate the transformation.
-*
-* N (input) INTEGER
-* The order of the matrix T. N >= 0.
-*
-* T (input/output) DOUBLE PRECISION array, dimension (LDT,N)
-* On entry, the upper quasi-triangular matrix T, in Schur
-* canonical form.
-* On exit, the updated matrix T, again in Schur canonical form.
-*
-* LDT (input) INTEGER
-* The leading dimension of the array T. LDT >= max(1,N).
-*
-* Q (input/output) DOUBLE PRECISION array, dimension (LDQ,N)
-* On entry, if WANTQ is .TRUE., the orthogonal matrix Q.
-* On exit, if WANTQ is .TRUE., the updated matrix Q.
-* If WANTQ is .FALSE., Q is not referenced.
-*
-* LDQ (input) INTEGER
-* The leading dimension of the array Q.
-* LDQ >= 1; and if WANTQ is .TRUE., LDQ >= N.
-*
-* J1 (input) INTEGER
-* The index of the first row of the first block T11.
-*
-* N1 (input) INTEGER
-* The order of the first block T11. N1 = 0, 1 or 2.
-*
-* N2 (input) INTEGER
-* The order of the second block T22. N2 = 0, 1 or 2.
-*
-* WORK (workspace) DOUBLE PRECISION array, dimension (N)
-*
-* INFO (output) INTEGER
-* = 0: successful exit
-* = 1: the transformed matrix T would be too far from Schur
-* form; the blocks are not swapped and T and Q are
-* unchanged.
-*
-* =====================================================================
-*
-* .. Parameters ..
- DOUBLE PRECISION ZERO, ONE
- PARAMETER ( ZERO = 0.0D+0, ONE = 1.0D+0 )
- DOUBLE PRECISION TEN
- PARAMETER ( TEN = 1.0D+1 )
- INTEGER LDD, LDX
- PARAMETER ( LDD = 4, LDX = 2 )
-* ..
-* .. Local Scalars ..
- INTEGER IERR, J2, J3, J4, K, ND
- DOUBLE PRECISION CS, DNORM, EPS, SCALE, SMLNUM, SN, T11, T22,
- $ T33, TAU, TAU1, TAU2, TEMP, THRESH, WI1, WI2,
- $ WR1, WR2, XNORM
-* ..
-* .. Local Arrays ..
- DOUBLE PRECISION D( LDD, 4 ), U( 3 ), U1( 3 ), U2( 3 ),
- $ X( LDX, 2 )
-* ..
-* .. External Functions ..
- DOUBLE PRECISION DLAMCH, DLANGE
- EXTERNAL DLAMCH, DLANGE
-* ..
-* .. External Subroutines ..
- EXTERNAL DLACPY, DLANV2, DLARFG, DLARFX, DLARTG, DLASY2,
- $ DROT
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC ABS, MAX
-* ..
-* .. Executable Statements ..
-*
- INFO = 0
-*
-* Quick return if possible
-*
- IF( N.EQ.0 .OR. N1.EQ.0 .OR. N2.EQ.0 )
- $ RETURN
- IF( J1+N1.GT.N )
- $ RETURN
-*
- J2 = J1 + 1
- J3 = J1 + 2
- J4 = J1 + 3
-*
- IF( N1.EQ.1 .AND. N2.EQ.1 ) THEN
-*
-* Swap two 1-by-1 blocks.
-*
- T11 = T( J1, J1 )
- T22 = T( J2, J2 )
-*
-* Determine the transformation to perform the interchange.
-*
- CALL DLARTG( T( J1, J2 ), T22-T11, CS, SN, TEMP )
-*
-* Apply transformation to the matrix T.
-*
- IF( J3.LE.N )
- $ CALL DROT( N-J1-1, T( J1, J3 ), LDT, T( J2, J3 ), LDT, CS,
- $ SN )
- CALL DROT( J1-1, T( 1, J1 ), 1, T( 1, J2 ), 1, CS, SN )
-*
- T( J1, J1 ) = T22
- T( J2, J2 ) = T11
-*
- IF( WANTQ ) THEN
-*
-* Accumulate transformation in the matrix Q.
-*
- CALL DROT( N, Q( 1, J1 ), 1, Q( 1, J2 ), 1, CS, SN )
- END IF
-*
- ELSE
-*
-* Swapping involves at least one 2-by-2 block.
-*
-* Copy the diagonal block of order N1+N2 to the local array D
-* and compute its norm.
-*
- ND = N1 + N2
- CALL DLACPY( 'Full', ND, ND, T( J1, J1 ), LDT, D, LDD )
- DNORM = DLANGE( 'Max', ND, ND, D, LDD, WORK )
-*
-* Compute machine-dependent threshold for test for accepting
-* swap.
-*
- EPS = DLAMCH( 'P' )
- SMLNUM = DLAMCH( 'S' ) / EPS
- THRESH = MAX( TEN*EPS*DNORM, SMLNUM )
-*
-* Solve T11*X - X*T22 = scale*T12 for X.
-*
- CALL DLASY2( .FALSE., .FALSE., -1, N1, N2, D, LDD,
- $ D( N1+1, N1+1 ), LDD, D( 1, N1+1 ), LDD, SCALE, X,
- $ LDX, XNORM, IERR )
-*
-* Swap the adjacent diagonal blocks.
-*
- K = N1 + N1 + N2 - 3
- GO TO ( 10, 20, 30 )K
-*
- 10 CONTINUE
-*
-* N1 = 1, N2 = 2: generate elementary reflector H so that:
-*
-* ( scale, X11, X12 ) H = ( 0, 0, * )
-*
- U( 1 ) = SCALE
- U( 2 ) = X( 1, 1 )
- U( 3 ) = X( 1, 2 )
- CALL DLARFG( 3, U( 3 ), U, 1, TAU )
- U( 3 ) = ONE
- T11 = T( J1, J1 )
-*
-* Perform swap provisionally on diagonal block in D.
-*
- CALL DLARFX( 'L', 3, 3, U, TAU, D, LDD, WORK )
- CALL DLARFX( 'R', 3, 3, U, TAU, D, LDD, WORK )
-*
-* Test whether to reject swap.
-*
- IF( MAX( ABS( D( 3, 1 ) ), ABS( D( 3, 2 ) ), ABS( D( 3,
- $ 3 )-T11 ) ).GT.THRESH )GO TO 50
-*
-* Accept swap: apply transformation to the entire matrix T.
-*
- CALL DLARFX( 'L', 3, N-J1+1, U, TAU, T( J1, J1 ), LDT, WORK )
- CALL DLARFX( 'R', J2, 3, U, TAU, T( 1, J1 ), LDT, WORK )
-*
- T( J3, J1 ) = ZERO
- T( J3, J2 ) = ZERO
- T( J3, J3 ) = T11
-*
- IF( WANTQ ) THEN
-*
-* Accumulate transformation in the matrix Q.
-*
- CALL DLARFX( 'R', N, 3, U, TAU, Q( 1, J1 ), LDQ, WORK )
- END IF
- GO TO 40
-*
- 20 CONTINUE
-*
-* N1 = 2, N2 = 1: generate elementary reflector H so that:
-*
-* H ( -X11 ) = ( * )
-* ( -X21 ) = ( 0 )
-* ( scale ) = ( 0 )
-*
- U( 1 ) = -X( 1, 1 )
- U( 2 ) = -X( 2, 1 )
- U( 3 ) = SCALE
- CALL DLARFG( 3, U( 1 ), U( 2 ), 1, TAU )
- U( 1 ) = ONE
- T33 = T( J3, J3 )
-*
-* Perform swap provisionally on diagonal block in D.
-*
- CALL DLARFX( 'L', 3, 3, U, TAU, D, LDD, WORK )
- CALL DLARFX( 'R', 3, 3, U, TAU, D, LDD, WORK )
-*
-* Test whether to reject swap.
-*
- IF( MAX( ABS( D( 2, 1 ) ), ABS( D( 3, 1 ) ), ABS( D( 1,
- $ 1 )-T33 ) ).GT.THRESH )GO TO 50
-*
-* Accept swap: apply transformation to the entire matrix T.
-*
- CALL DLARFX( 'R', J3, 3, U, TAU, T( 1, J1 ), LDT, WORK )
- CALL DLARFX( 'L', 3, N-J1, U, TAU, T( J1, J2 ), LDT, WORK )
-*
- T( J1, J1 ) = T33
- T( J2, J1 ) = ZERO
- T( J3, J1 ) = ZERO
-*
- IF( WANTQ ) THEN
-*
-* Accumulate transformation in the matrix Q.
-*
- CALL DLARFX( 'R', N, 3, U, TAU, Q( 1, J1 ), LDQ, WORK )
- END IF
- GO TO 40
-*
- 30 CONTINUE
-*
-* N1 = 2, N2 = 2: generate elementary reflectors H(1) and H(2) so
-* that:
-*
-* H(2) H(1) ( -X11 -X12 ) = ( * * )
-* ( -X21 -X22 ) ( 0 * )
-* ( scale 0 ) ( 0 0 )
-* ( 0 scale ) ( 0 0 )
-*
- U1( 1 ) = -X( 1, 1 )
- U1( 2 ) = -X( 2, 1 )
- U1( 3 ) = SCALE
- CALL DLARFG( 3, U1( 1 ), U1( 2 ), 1, TAU1 )
- U1( 1 ) = ONE
-*
- TEMP = -TAU1*( X( 1, 2 )+U1( 2 )*X( 2, 2 ) )
- U2( 1 ) = -TEMP*U1( 2 ) - X( 2, 2 )
- U2( 2 ) = -TEMP*U1( 3 )
- U2( 3 ) = SCALE
- CALL DLARFG( 3, U2( 1 ), U2( 2 ), 1, TAU2 )
- U2( 1 ) = ONE
-*
-* Perform swap provisionally on diagonal block in D.
-*
- CALL DLARFX( 'L', 3, 4, U1, TAU1, D, LDD, WORK )
- CALL DLARFX( 'R', 4, 3, U1, TAU1, D, LDD, WORK )
- CALL DLARFX( 'L', 3, 4, U2, TAU2, D( 2, 1 ), LDD, WORK )
- CALL DLARFX( 'R', 4, 3, U2, TAU2, D( 1, 2 ), LDD, WORK )
-*
-* Test whether to reject swap.
-*
- IF( MAX( ABS( D( 3, 1 ) ), ABS( D( 3, 2 ) ), ABS( D( 4, 1 ) ),
- $ ABS( D( 4, 2 ) ) ).GT.THRESH )GO TO 50
-*
-* Accept swap: apply transformation to the entire matrix T.
-*
- CALL DLARFX( 'L', 3, N-J1+1, U1, TAU1, T( J1, J1 ), LDT, WORK )
- CALL DLARFX( 'R', J4, 3, U1, TAU1, T( 1, J1 ), LDT, WORK )
- CALL DLARFX( 'L', 3, N-J1+1, U2, TAU2, T( J2, J1 ), LDT, WORK )
- CALL DLARFX( 'R', J4, 3, U2, TAU2, T( 1, J2 ), LDT, WORK )
-*
- T( J3, J1 ) = ZERO
- T( J3, J2 ) = ZERO
- T( J4, J1 ) = ZERO
- T( J4, J2 ) = ZERO
-*
- IF( WANTQ ) THEN
-*
-* Accumulate transformation in the matrix Q.
-*
- CALL DLARFX( 'R', N, 3, U1, TAU1, Q( 1, J1 ), LDQ, WORK )
- CALL DLARFX( 'R', N, 3, U2, TAU2, Q( 1, J2 ), LDQ, WORK )
- END IF
-*
- 40 CONTINUE
-*
- IF( N2.EQ.2 ) THEN
-*
-* Standardize new 2-by-2 block T11
-*
- CALL DLANV2( T( J1, J1 ), T( J1, J2 ), T( J2, J1 ),
- $ T( J2, J2 ), WR1, WI1, WR2, WI2, CS, SN )
- CALL DROT( N-J1-1, T( J1, J1+2 ), LDT, T( J2, J1+2 ), LDT,
- $ CS, SN )
- CALL DROT( J1-1, T( 1, J1 ), 1, T( 1, J2 ), 1, CS, SN )
- IF( WANTQ )
- $ CALL DROT( N, Q( 1, J1 ), 1, Q( 1, J2 ), 1, CS, SN )
- END IF
-*
- IF( N1.EQ.2 ) THEN
-*
-* Standardize new 2-by-2 block T22
-*
- J3 = J1 + N2
- J4 = J3 + 1
- CALL DLANV2( T( J3, J3 ), T( J3, J4 ), T( J4, J3 ),
- $ T( J4, J4 ), WR1, WI1, WR2, WI2, CS, SN )
- IF( J3+2.LE.N )
- $ CALL DROT( N-J3-1, T( J3, J3+2 ), LDT, T( J4, J3+2 ),
- $ LDT, CS, SN )
- CALL DROT( J3-1, T( 1, J3 ), 1, T( 1, J4 ), 1, CS, SN )
- IF( WANTQ )
- $ CALL DROT( N, Q( 1, J3 ), 1, Q( 1, J4 ), 1, CS, SN )
- END IF
-*
- END IF
- RETURN
-*
-* Exit with INFO = 1 if swap was rejected.
-*
- 50 CONTINUE
- INFO = 1
- RETURN
-*
-* End of DLAEXC
-*
- END
diff --git a/src/lib/lapack/dlag2.f b/src/lib/lapack/dlag2.f
deleted file mode 100644
index e754203b..00000000
--- a/src/lib/lapack/dlag2.f
+++ /dev/null
@@ -1,300 +0,0 @@
- SUBROUTINE DLAG2( A, LDA, B, LDB, SAFMIN, SCALE1, SCALE2, WR1,
- $ WR2, WI )
-*
-* -- LAPACK auxiliary routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- INTEGER LDA, LDB
- DOUBLE PRECISION SAFMIN, SCALE1, SCALE2, WI, WR1, WR2
-* ..
-* .. Array Arguments ..
- DOUBLE PRECISION A( LDA, * ), B( LDB, * )
-* ..
-*
-* Purpose
-* =======
-*
-* DLAG2 computes the eigenvalues of a 2 x 2 generalized eigenvalue
-* problem A - w B, with scaling as necessary to avoid over-/underflow.
-*
-* The scaling factor "s" results in a modified eigenvalue equation
-*
-* s A - w B
-*
-* where s is a non-negative scaling factor chosen so that w, w B,
-* and s A do not overflow and, if possible, do not underflow, either.
-*
-* Arguments
-* =========
-*
-* A (input) DOUBLE PRECISION array, dimension (LDA, 2)
-* On entry, the 2 x 2 matrix A. It is assumed that its 1-norm
-* is less than 1/SAFMIN. Entries less than
-* sqrt(SAFMIN)*norm(A) are subject to being treated as zero.
-*
-* LDA (input) INTEGER
-* The leading dimension of the array A. LDA >= 2.
-*
-* B (input) DOUBLE PRECISION array, dimension (LDB, 2)
-* On entry, the 2 x 2 upper triangular matrix B. It is
-* assumed that the one-norm of B is less than 1/SAFMIN. The
-* diagonals should be at least sqrt(SAFMIN) times the largest
-* element of B (in absolute value); if a diagonal is smaller
-* than that, then +/- sqrt(SAFMIN) will be used instead of
-* that diagonal.
-*
-* LDB (input) INTEGER
-* The leading dimension of the array B. LDB >= 2.
-*
-* SAFMIN (input) DOUBLE PRECISION
-* The smallest positive number s.t. 1/SAFMIN does not
-* overflow. (This should always be DLAMCH('S') -- it is an
-* argument in order to avoid having to call DLAMCH frequently.)
-*
-* SCALE1 (output) DOUBLE PRECISION
-* A scaling factor used to avoid over-/underflow in the
-* eigenvalue equation which defines the first eigenvalue. If
-* the eigenvalues are complex, then the eigenvalues are
-* ( WR1 +/- WI i ) / SCALE1 (which may lie outside the
-* exponent range of the machine), SCALE1=SCALE2, and SCALE1
-* will always be positive. If the eigenvalues are real, then
-* the first (real) eigenvalue is WR1 / SCALE1 , but this may
-* overflow or underflow, and in fact, SCALE1 may be zero or
-* less than the underflow threshhold if the exact eigenvalue
-* is sufficiently large.
-*
-* SCALE2 (output) DOUBLE PRECISION
-* A scaling factor used to avoid over-/underflow in the
-* eigenvalue equation which defines the second eigenvalue. If
-* the eigenvalues are complex, then SCALE2=SCALE1. If the
-* eigenvalues are real, then the second (real) eigenvalue is
-* WR2 / SCALE2 , but this may overflow or underflow, and in
-* fact, SCALE2 may be zero or less than the underflow
-* threshhold if the exact eigenvalue is sufficiently large.
-*
-* WR1 (output) DOUBLE PRECISION
-* If the eigenvalue is real, then WR1 is SCALE1 times the
-* eigenvalue closest to the (2,2) element of A B**(-1). If the
-* eigenvalue is complex, then WR1=WR2 is SCALE1 times the real
-* part of the eigenvalues.
-*
-* WR2 (output) DOUBLE PRECISION
-* If the eigenvalue is real, then WR2 is SCALE2 times the
-* other eigenvalue. If the eigenvalue is complex, then
-* WR1=WR2 is SCALE1 times the real part of the eigenvalues.
-*
-* WI (output) DOUBLE PRECISION
-* If the eigenvalue is real, then WI is zero. If the
-* eigenvalue is complex, then WI is SCALE1 times the imaginary
-* part of the eigenvalues. WI will always be non-negative.
-*
-* =====================================================================
-*
-* .. Parameters ..
- DOUBLE PRECISION ZERO, ONE, TWO
- PARAMETER ( ZERO = 0.0D+0, ONE = 1.0D+0, TWO = 2.0D+0 )
- DOUBLE PRECISION HALF
- PARAMETER ( HALF = ONE / TWO )
- DOUBLE PRECISION FUZZY1
- PARAMETER ( FUZZY1 = ONE+1.0D-5 )
-* ..
-* .. Local Scalars ..
- DOUBLE PRECISION A11, A12, A21, A22, ABI22, ANORM, AS11, AS12,
- $ AS22, ASCALE, B11, B12, B22, BINV11, BINV22,
- $ BMIN, BNORM, BSCALE, BSIZE, C1, C2, C3, C4, C5,
- $ DIFF, DISCR, PP, QQ, R, RTMAX, RTMIN, S1, S2,
- $ SAFMAX, SHIFT, SS, SUM, WABS, WBIG, WDET,
- $ WSCALE, WSIZE, WSMALL
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC ABS, MAX, MIN, SIGN, SQRT
-* ..
-* .. Executable Statements ..
-*
- RTMIN = SQRT( SAFMIN )
- RTMAX = ONE / RTMIN
- SAFMAX = ONE / SAFMIN
-*
-* Scale A
-*
- ANORM = MAX( ABS( A( 1, 1 ) )+ABS( A( 2, 1 ) ),
- $ ABS( A( 1, 2 ) )+ABS( A( 2, 2 ) ), SAFMIN )
- ASCALE = ONE / ANORM
- A11 = ASCALE*A( 1, 1 )
- A21 = ASCALE*A( 2, 1 )
- A12 = ASCALE*A( 1, 2 )
- A22 = ASCALE*A( 2, 2 )
-*
-* Perturb B if necessary to insure non-singularity
-*
- B11 = B( 1, 1 )
- B12 = B( 1, 2 )
- B22 = B( 2, 2 )
- BMIN = RTMIN*MAX( ABS( B11 ), ABS( B12 ), ABS( B22 ), RTMIN )
- IF( ABS( B11 ).LT.BMIN )
- $ B11 = SIGN( BMIN, B11 )
- IF( ABS( B22 ).LT.BMIN )
- $ B22 = SIGN( BMIN, B22 )
-*
-* Scale B
-*
- BNORM = MAX( ABS( B11 ), ABS( B12 )+ABS( B22 ), SAFMIN )
- BSIZE = MAX( ABS( B11 ), ABS( B22 ) )
- BSCALE = ONE / BSIZE
- B11 = B11*BSCALE
- B12 = B12*BSCALE
- B22 = B22*BSCALE
-*
-* Compute larger eigenvalue by method described by C. van Loan
-*
-* ( AS is A shifted by -SHIFT*B )
-*
- BINV11 = ONE / B11
- BINV22 = ONE / B22
- S1 = A11*BINV11
- S2 = A22*BINV22
- IF( ABS( S1 ).LE.ABS( S2 ) ) THEN
- AS12 = A12 - S1*B12
- AS22 = A22 - S1*B22
- SS = A21*( BINV11*BINV22 )
- ABI22 = AS22*BINV22 - SS*B12
- PP = HALF*ABI22
- SHIFT = S1
- ELSE
- AS12 = A12 - S2*B12
- AS11 = A11 - S2*B11
- SS = A21*( BINV11*BINV22 )
- ABI22 = -SS*B12
- PP = HALF*( AS11*BINV11+ABI22 )
- SHIFT = S2
- END IF
- QQ = SS*AS12
- IF( ABS( PP*RTMIN ).GE.ONE ) THEN
- DISCR = ( RTMIN*PP )**2 + QQ*SAFMIN
- R = SQRT( ABS( DISCR ) )*RTMAX
- ELSE
- IF( PP**2+ABS( QQ ).LE.SAFMIN ) THEN
- DISCR = ( RTMAX*PP )**2 + QQ*SAFMAX
- R = SQRT( ABS( DISCR ) )*RTMIN
- ELSE
- DISCR = PP**2 + QQ
- R = SQRT( ABS( DISCR ) )
- END IF
- END IF
-*
-* Note: the test of R in the following IF is to cover the case when
-* DISCR is small and negative and is flushed to zero during
-* the calculation of R. On machines which have a consistent
-* flush-to-zero threshhold and handle numbers above that
-* threshhold correctly, it would not be necessary.
-*
- IF( DISCR.GE.ZERO .OR. R.EQ.ZERO ) THEN
- SUM = PP + SIGN( R, PP )
- DIFF = PP - SIGN( R, PP )
- WBIG = SHIFT + SUM
-*
-* Compute smaller eigenvalue
-*
- WSMALL = SHIFT + DIFF
- IF( HALF*ABS( WBIG ).GT.MAX( ABS( WSMALL ), SAFMIN ) ) THEN
- WDET = ( A11*A22-A12*A21 )*( BINV11*BINV22 )
- WSMALL = WDET / WBIG
- END IF
-*
-* Choose (real) eigenvalue closest to 2,2 element of A*B**(-1)
-* for WR1.
-*
- IF( PP.GT.ABI22 ) THEN
- WR1 = MIN( WBIG, WSMALL )
- WR2 = MAX( WBIG, WSMALL )
- ELSE
- WR1 = MAX( WBIG, WSMALL )
- WR2 = MIN( WBIG, WSMALL )
- END IF
- WI = ZERO
- ELSE
-*
-* Complex eigenvalues
-*
- WR1 = SHIFT + PP
- WR2 = WR1
- WI = R
- END IF
-*
-* Further scaling to avoid underflow and overflow in computing
-* SCALE1 and overflow in computing w*B.
-*
-* This scale factor (WSCALE) is bounded from above using C1 and C2,
-* and from below using C3 and C4.
-* C1 implements the condition s A must never overflow.
-* C2 implements the condition w B must never overflow.
-* C3, with C2,
-* implement the condition that s A - w B must never overflow.
-* C4 implements the condition s should not underflow.
-* C5 implements the condition max(s,|w|) should be at least 2.
-*
- C1 = BSIZE*( SAFMIN*MAX( ONE, ASCALE ) )
- C2 = SAFMIN*MAX( ONE, BNORM )
- C3 = BSIZE*SAFMIN
- IF( ASCALE.LE.ONE .AND. BSIZE.LE.ONE ) THEN
- C4 = MIN( ONE, ( ASCALE / SAFMIN )*BSIZE )
- ELSE
- C4 = ONE
- END IF
- IF( ASCALE.LE.ONE .OR. BSIZE.LE.ONE ) THEN
- C5 = MIN( ONE, ASCALE*BSIZE )
- ELSE
- C5 = ONE
- END IF
-*
-* Scale first eigenvalue
-*
- WABS = ABS( WR1 ) + ABS( WI )
- WSIZE = MAX( SAFMIN, C1, FUZZY1*( WABS*C2+C3 ),
- $ MIN( C4, HALF*MAX( WABS, C5 ) ) )
- IF( WSIZE.NE.ONE ) THEN
- WSCALE = ONE / WSIZE
- IF( WSIZE.GT.ONE ) THEN
- SCALE1 = ( MAX( ASCALE, BSIZE )*WSCALE )*
- $ MIN( ASCALE, BSIZE )
- ELSE
- SCALE1 = ( MIN( ASCALE, BSIZE )*WSCALE )*
- $ MAX( ASCALE, BSIZE )
- END IF
- WR1 = WR1*WSCALE
- IF( WI.NE.ZERO ) THEN
- WI = WI*WSCALE
- WR2 = WR1
- SCALE2 = SCALE1
- END IF
- ELSE
- SCALE1 = ASCALE*BSIZE
- SCALE2 = SCALE1
- END IF
-*
-* Scale second eigenvalue (if real)
-*
- IF( WI.EQ.ZERO ) THEN
- WSIZE = MAX( SAFMIN, C1, FUZZY1*( ABS( WR2 )*C2+C3 ),
- $ MIN( C4, HALF*MAX( ABS( WR2 ), C5 ) ) )
- IF( WSIZE.NE.ONE ) THEN
- WSCALE = ONE / WSIZE
- IF( WSIZE.GT.ONE ) THEN
- SCALE2 = ( MAX( ASCALE, BSIZE )*WSCALE )*
- $ MIN( ASCALE, BSIZE )
- ELSE
- SCALE2 = ( MIN( ASCALE, BSIZE )*WSCALE )*
- $ MAX( ASCALE, BSIZE )
- END IF
- WR2 = WR2*WSCALE
- ELSE
- SCALE2 = ASCALE*BSIZE
- END IF
- END IF
-*
-* End of DLAG2
-*
- RETURN
- END
diff --git a/src/lib/lapack/dlagv2.f b/src/lib/lapack/dlagv2.f
deleted file mode 100644
index 15bcb0b9..00000000
--- a/src/lib/lapack/dlagv2.f
+++ /dev/null
@@ -1,287 +0,0 @@
- SUBROUTINE DLAGV2( A, LDA, B, LDB, ALPHAR, ALPHAI, BETA, CSL, SNL,
- $ CSR, SNR )
-*
-* -- LAPACK auxiliary routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- INTEGER LDA, LDB
- DOUBLE PRECISION CSL, CSR, SNL, SNR
-* ..
-* .. Array Arguments ..
- DOUBLE PRECISION A( LDA, * ), ALPHAI( 2 ), ALPHAR( 2 ),
- $ B( LDB, * ), BETA( 2 )
-* ..
-*
-* Purpose
-* =======
-*
-* DLAGV2 computes the Generalized Schur factorization of a real 2-by-2
-* matrix pencil (A,B) where B is upper triangular. This routine
-* computes orthogonal (rotation) matrices given by CSL, SNL and CSR,
-* SNR such that
-*
-* 1) if the pencil (A,B) has two real eigenvalues (include 0/0 or 1/0
-* types), then
-*
-* [ a11 a12 ] := [ CSL SNL ] [ a11 a12 ] [ CSR -SNR ]
-* [ 0 a22 ] [ -SNL CSL ] [ a21 a22 ] [ SNR CSR ]
-*
-* [ b11 b12 ] := [ CSL SNL ] [ b11 b12 ] [ CSR -SNR ]
-* [ 0 b22 ] [ -SNL CSL ] [ 0 b22 ] [ SNR CSR ],
-*
-* 2) if the pencil (A,B) has a pair of complex conjugate eigenvalues,
-* then
-*
-* [ a11 a12 ] := [ CSL SNL ] [ a11 a12 ] [ CSR -SNR ]
-* [ a21 a22 ] [ -SNL CSL ] [ a21 a22 ] [ SNR CSR ]
-*
-* [ b11 0 ] := [ CSL SNL ] [ b11 b12 ] [ CSR -SNR ]
-* [ 0 b22 ] [ -SNL CSL ] [ 0 b22 ] [ SNR CSR ]
-*
-* where b11 >= b22 > 0.
-*
-*
-* Arguments
-* =========
-*
-* A (input/output) DOUBLE PRECISION array, dimension (LDA, 2)
-* On entry, the 2 x 2 matrix A.
-* On exit, A is overwritten by the ``A-part'' of the
-* generalized Schur form.
-*
-* LDA (input) INTEGER
-* THe leading dimension of the array A. LDA >= 2.
-*
-* B (input/output) DOUBLE PRECISION array, dimension (LDB, 2)
-* On entry, the upper triangular 2 x 2 matrix B.
-* On exit, B is overwritten by the ``B-part'' of the
-* generalized Schur form.
-*
-* LDB (input) INTEGER
-* THe leading dimension of the array B. LDB >= 2.
-*
-* ALPHAR (output) DOUBLE PRECISION array, dimension (2)
-* ALPHAI (output) DOUBLE PRECISION array, dimension (2)
-* BETA (output) DOUBLE PRECISION array, dimension (2)
-* (ALPHAR(k)+i*ALPHAI(k))/BETA(k) are the eigenvalues of the
-* pencil (A,B), k=1,2, i = sqrt(-1). Note that BETA(k) may
-* be zero.
-*
-* CSL (output) DOUBLE PRECISION
-* The cosine of the left rotation matrix.
-*
-* SNL (output) DOUBLE PRECISION
-* The sine of the left rotation matrix.
-*
-* CSR (output) DOUBLE PRECISION
-* The cosine of the right rotation matrix.
-*
-* SNR (output) DOUBLE PRECISION
-* The sine of the right rotation matrix.
-*
-* Further Details
-* ===============
-*
-* Based on contributions by
-* Mark Fahey, Department of Mathematics, Univ. of Kentucky, USA
-*
-* =====================================================================
-*
-* .. Parameters ..
- DOUBLE PRECISION ZERO, ONE
- PARAMETER ( ZERO = 0.0D+0, ONE = 1.0D+0 )
-* ..
-* .. Local Scalars ..
- DOUBLE PRECISION ANORM, ASCALE, BNORM, BSCALE, H1, H2, H3, QQ,
- $ R, RR, SAFMIN, SCALE1, SCALE2, T, ULP, WI, WR1,
- $ WR2
-* ..
-* .. External Subroutines ..
- EXTERNAL DLAG2, DLARTG, DLASV2, DROT
-* ..
-* .. External Functions ..
- DOUBLE PRECISION DLAMCH, DLAPY2
- EXTERNAL DLAMCH, DLAPY2
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC ABS, MAX
-* ..
-* .. Executable Statements ..
-*
- SAFMIN = DLAMCH( 'S' )
- ULP = DLAMCH( 'P' )
-*
-* Scale A
-*
- ANORM = MAX( ABS( A( 1, 1 ) )+ABS( A( 2, 1 ) ),
- $ ABS( A( 1, 2 ) )+ABS( A( 2, 2 ) ), SAFMIN )
- ASCALE = ONE / ANORM
- A( 1, 1 ) = ASCALE*A( 1, 1 )
- A( 1, 2 ) = ASCALE*A( 1, 2 )
- A( 2, 1 ) = ASCALE*A( 2, 1 )
- A( 2, 2 ) = ASCALE*A( 2, 2 )
-*
-* Scale B
-*
- BNORM = MAX( ABS( B( 1, 1 ) ), ABS( B( 1, 2 ) )+ABS( B( 2, 2 ) ),
- $ SAFMIN )
- BSCALE = ONE / BNORM
- B( 1, 1 ) = BSCALE*B( 1, 1 )
- B( 1, 2 ) = BSCALE*B( 1, 2 )
- B( 2, 2 ) = BSCALE*B( 2, 2 )
-*
-* Check if A can be deflated
-*
- IF( ABS( A( 2, 1 ) ).LE.ULP ) THEN
- CSL = ONE
- SNL = ZERO
- CSR = ONE
- SNR = ZERO
- A( 2, 1 ) = ZERO
- B( 2, 1 ) = ZERO
-*
-* Check if B is singular
-*
- ELSE IF( ABS( B( 1, 1 ) ).LE.ULP ) THEN
- CALL DLARTG( A( 1, 1 ), A( 2, 1 ), CSL, SNL, R )
- CSR = ONE
- SNR = ZERO
- CALL DROT( 2, A( 1, 1 ), LDA, A( 2, 1 ), LDA, CSL, SNL )
- CALL DROT( 2, B( 1, 1 ), LDB, B( 2, 1 ), LDB, CSL, SNL )
- A( 2, 1 ) = ZERO
- B( 1, 1 ) = ZERO
- B( 2, 1 ) = ZERO
-*
- ELSE IF( ABS( B( 2, 2 ) ).LE.ULP ) THEN
- CALL DLARTG( A( 2, 2 ), A( 2, 1 ), CSR, SNR, T )
- SNR = -SNR
- CALL DROT( 2, A( 1, 1 ), 1, A( 1, 2 ), 1, CSR, SNR )
- CALL DROT( 2, B( 1, 1 ), 1, B( 1, 2 ), 1, CSR, SNR )
- CSL = ONE
- SNL = ZERO
- A( 2, 1 ) = ZERO
- B( 2, 1 ) = ZERO
- B( 2, 2 ) = ZERO
-*
- ELSE
-*
-* B is nonsingular, first compute the eigenvalues of (A,B)
-*
- CALL DLAG2( A, LDA, B, LDB, SAFMIN, SCALE1, SCALE2, WR1, WR2,
- $ WI )
-*
- IF( WI.EQ.ZERO ) THEN
-*
-* two real eigenvalues, compute s*A-w*B
-*
- H1 = SCALE1*A( 1, 1 ) - WR1*B( 1, 1 )
- H2 = SCALE1*A( 1, 2 ) - WR1*B( 1, 2 )
- H3 = SCALE1*A( 2, 2 ) - WR1*B( 2, 2 )
-*
- RR = DLAPY2( H1, H2 )
- QQ = DLAPY2( SCALE1*A( 2, 1 ), H3 )
-*
- IF( RR.GT.QQ ) THEN
-*
-* find right rotation matrix to zero 1,1 element of
-* (sA - wB)
-*
- CALL DLARTG( H2, H1, CSR, SNR, T )
-*
- ELSE
-*
-* find right rotation matrix to zero 2,1 element of
-* (sA - wB)
-*
- CALL DLARTG( H3, SCALE1*A( 2, 1 ), CSR, SNR, T )
-*
- END IF
-*
- SNR = -SNR
- CALL DROT( 2, A( 1, 1 ), 1, A( 1, 2 ), 1, CSR, SNR )
- CALL DROT( 2, B( 1, 1 ), 1, B( 1, 2 ), 1, CSR, SNR )
-*
-* compute inf norms of A and B
-*
- H1 = MAX( ABS( A( 1, 1 ) )+ABS( A( 1, 2 ) ),
- $ ABS( A( 2, 1 ) )+ABS( A( 2, 2 ) ) )
- H2 = MAX( ABS( B( 1, 1 ) )+ABS( B( 1, 2 ) ),
- $ ABS( B( 2, 1 ) )+ABS( B( 2, 2 ) ) )
-*
- IF( ( SCALE1*H1 ).GE.ABS( WR1 )*H2 ) THEN
-*
-* find left rotation matrix Q to zero out B(2,1)
-*
- CALL DLARTG( B( 1, 1 ), B( 2, 1 ), CSL, SNL, R )
-*
- ELSE
-*
-* find left rotation matrix Q to zero out A(2,1)
-*
- CALL DLARTG( A( 1, 1 ), A( 2, 1 ), CSL, SNL, R )
-*
- END IF
-*
- CALL DROT( 2, A( 1, 1 ), LDA, A( 2, 1 ), LDA, CSL, SNL )
- CALL DROT( 2, B( 1, 1 ), LDB, B( 2, 1 ), LDB, CSL, SNL )
-*
- A( 2, 1 ) = ZERO
- B( 2, 1 ) = ZERO
-*
- ELSE
-*
-* a pair of complex conjugate eigenvalues
-* first compute the SVD of the matrix B
-*
- CALL DLASV2( B( 1, 1 ), B( 1, 2 ), B( 2, 2 ), R, T, SNR,
- $ CSR, SNL, CSL )
-*
-* Form (A,B) := Q(A,B)Z' where Q is left rotation matrix and
-* Z is right rotation matrix computed from DLASV2
-*
- CALL DROT( 2, A( 1, 1 ), LDA, A( 2, 1 ), LDA, CSL, SNL )
- CALL DROT( 2, B( 1, 1 ), LDB, B( 2, 1 ), LDB, CSL, SNL )
- CALL DROT( 2, A( 1, 1 ), 1, A( 1, 2 ), 1, CSR, SNR )
- CALL DROT( 2, B( 1, 1 ), 1, B( 1, 2 ), 1, CSR, SNR )
-*
- B( 2, 1 ) = ZERO
- B( 1, 2 ) = ZERO
-*
- END IF
-*
- END IF
-*
-* Unscaling
-*
- A( 1, 1 ) = ANORM*A( 1, 1 )
- A( 2, 1 ) = ANORM*A( 2, 1 )
- A( 1, 2 ) = ANORM*A( 1, 2 )
- A( 2, 2 ) = ANORM*A( 2, 2 )
- B( 1, 1 ) = BNORM*B( 1, 1 )
- B( 2, 1 ) = BNORM*B( 2, 1 )
- B( 1, 2 ) = BNORM*B( 1, 2 )
- B( 2, 2 ) = BNORM*B( 2, 2 )
-*
- IF( WI.EQ.ZERO ) THEN
- ALPHAR( 1 ) = A( 1, 1 )
- ALPHAR( 2 ) = A( 2, 2 )
- ALPHAI( 1 ) = ZERO
- ALPHAI( 2 ) = ZERO
- BETA( 1 ) = B( 1, 1 )
- BETA( 2 ) = B( 2, 2 )
- ELSE
- ALPHAR( 1 ) = ANORM*WR1 / SCALE1 / BNORM
- ALPHAI( 1 ) = ANORM*WI / SCALE1 / BNORM
- ALPHAR( 2 ) = ALPHAR( 1 )
- ALPHAI( 2 ) = -ALPHAI( 1 )
- BETA( 1 ) = ONE
- BETA( 2 ) = ONE
- END IF
-*
- RETURN
-*
-* End of DLAGV2
-*
- END
diff --git a/src/lib/lapack/dlahqr.f b/src/lib/lapack/dlahqr.f
deleted file mode 100644
index 449a3770..00000000
--- a/src/lib/lapack/dlahqr.f
+++ /dev/null
@@ -1,501 +0,0 @@
- SUBROUTINE DLAHQR( WANTT, WANTZ, N, ILO, IHI, H, LDH, WR, WI,
- $ ILOZ, IHIZ, Z, LDZ, INFO )
-*
-* -- LAPACK auxiliary routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- INTEGER IHI, IHIZ, ILO, ILOZ, INFO, LDH, LDZ, N
- LOGICAL WANTT, WANTZ
-* ..
-* .. Array Arguments ..
- DOUBLE PRECISION H( LDH, * ), WI( * ), WR( * ), Z( LDZ, * )
-* ..
-*
-* Purpose
-* =======
-*
-* DLAHQR is an auxiliary routine called by DHSEQR to update the
-* eigenvalues and Schur decomposition already computed by DHSEQR, by
-* dealing with the Hessenberg submatrix in rows and columns ILO to
-* IHI.
-*
-* Arguments
-* =========
-*
-* WANTT (input) LOGICAL
-* = .TRUE. : the full Schur form T is required;
-* = .FALSE.: only eigenvalues are required.
-*
-* WANTZ (input) LOGICAL
-* = .TRUE. : the matrix of Schur vectors Z is required;
-* = .FALSE.: Schur vectors are not required.
-*
-* N (input) INTEGER
-* The order of the matrix H. N >= 0.
-*
-* ILO (input) INTEGER
-* IHI (input) INTEGER
-* It is assumed that H is already upper quasi-triangular in
-* rows and columns IHI+1:N, and that H(ILO,ILO-1) = 0 (unless
-* ILO = 1). DLAHQR works primarily with the Hessenberg
-* submatrix in rows and columns ILO to IHI, but applies
-* transformations to all of H if WANTT is .TRUE..
-* 1 <= ILO <= max(1,IHI); IHI <= N.
-*
-* H (input/output) DOUBLE PRECISION array, dimension (LDH,N)
-* On entry, the upper Hessenberg matrix H.
-* On exit, if INFO is zero and if WANTT is .TRUE., H is upper
-* quasi-triangular in rows and columns ILO:IHI, with any
-* 2-by-2 diagonal blocks in standard form. If INFO is zero
-* and WANTT is .FALSE., the contents of H are unspecified on
-* exit. The output state of H if INFO is nonzero is given
-* below under the description of INFO.
-*
-* LDH (input) INTEGER
-* The leading dimension of the array H. LDH >= max(1,N).
-*
-* WR (output) DOUBLE PRECISION array, dimension (N)
-* WI (output) DOUBLE PRECISION array, dimension (N)
-* The real and imaginary parts, respectively, of the computed
-* eigenvalues ILO to IHI are stored in the corresponding
-* elements of WR and WI. If two eigenvalues are computed as a
-* complex conjugate pair, they are stored in consecutive
-* elements of WR and WI, say the i-th and (i+1)th, with
-* WI(i) > 0 and WI(i+1) < 0. If WANTT is .TRUE., the
-* eigenvalues are stored in the same order as on the diagonal
-* of the Schur form returned in H, with WR(i) = H(i,i), and, if
-* H(i:i+1,i:i+1) is a 2-by-2 diagonal block,
-* WI(i) = sqrt(H(i+1,i)*H(i,i+1)) and WI(i+1) = -WI(i).
-*
-* ILOZ (input) INTEGER
-* IHIZ (input) INTEGER
-* Specify the rows of Z to which transformations must be
-* applied if WANTZ is .TRUE..
-* 1 <= ILOZ <= ILO; IHI <= IHIZ <= N.
-*
-* Z (input/output) DOUBLE PRECISION array, dimension (LDZ,N)
-* If WANTZ is .TRUE., on entry Z must contain the current
-* matrix Z of transformations accumulated by DHSEQR, and on
-* exit Z has been updated; transformations are applied only to
-* the submatrix Z(ILOZ:IHIZ,ILO:IHI).
-* If WANTZ is .FALSE., Z is not referenced.
-*
-* LDZ (input) INTEGER
-* The leading dimension of the array Z. LDZ >= max(1,N).
-*
-* INFO (output) INTEGER
-* = 0: successful exit
-* .GT. 0: If INFO = i, DLAHQR failed to compute all the
-* eigenvalues ILO to IHI in a total of 30 iterations
-* per eigenvalue; elements i+1:ihi of WR and WI
-* contain those eigenvalues which have been
-* successfully computed.
-*
-* If INFO .GT. 0 and WANTT is .FALSE., then on exit,
-* the remaining unconverged eigenvalues are the
-* eigenvalues of the upper Hessenberg matrix rows
-* and columns ILO thorugh INFO of the final, output
-* value of H.
-*
-* If INFO .GT. 0 and WANTT is .TRUE., then on exit
-* (*) (initial value of H)*U = U*(final value of H)
-* where U is an orthognal matrix. The final
-* value of H is upper Hessenberg and triangular in
-* rows and columns INFO+1 through IHI.
-*
-* If INFO .GT. 0 and WANTZ is .TRUE., then on exit
-* (final value of Z) = (initial value of Z)*U
-* where U is the orthogonal matrix in (*)
-* (regardless of the value of WANTT.)
-*
-* Further Details
-* ===============
-*
-* 02-96 Based on modifications by
-* David Day, Sandia National Laboratory, USA
-*
-* 12-04 Further modifications by
-* Ralph Byers, University of Kansas, USA
-*
-* This is a modified version of DLAHQR from LAPACK version 3.0.
-* It is (1) more robust against overflow and underflow and
-* (2) adopts the more conservative Ahues & Tisseur stopping
-* criterion (LAWN 122, 1997).
-*
-* =========================================================
-*
-* .. Parameters ..
- INTEGER ITMAX
- PARAMETER ( ITMAX = 30 )
- DOUBLE PRECISION ZERO, ONE, TWO
- PARAMETER ( ZERO = 0.0d0, ONE = 1.0d0, TWO = 2.0d0 )
- DOUBLE PRECISION DAT1, DAT2
- PARAMETER ( DAT1 = 3.0d0 / 4.0d0, DAT2 = -0.4375d0 )
-* ..
-* .. Local Scalars ..
- DOUBLE PRECISION AA, AB, BA, BB, CS, DET, H11, H12, H21, H21S,
- $ H22, RT1I, RT1R, RT2I, RT2R, RTDISC, S, SAFMAX,
- $ SAFMIN, SMLNUM, SN, SUM, T1, T2, T3, TR, TST,
- $ ULP, V2, V3
- INTEGER I, I1, I2, ITS, J, K, L, M, NH, NR, NZ
-* ..
-* .. Local Arrays ..
- DOUBLE PRECISION V( 3 )
-* ..
-* .. External Functions ..
- DOUBLE PRECISION DLAMCH
- EXTERNAL DLAMCH
-* ..
-* .. External Subroutines ..
- EXTERNAL DCOPY, DLABAD, DLANV2, DLARFG, DROT
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC ABS, DBLE, MAX, MIN, SQRT
-* ..
-* .. Executable Statements ..
-*
- INFO = 0
-*
-* Quick return if possible
-*
- IF( N.EQ.0 )
- $ RETURN
- IF( ILO.EQ.IHI ) THEN
- WR( ILO ) = H( ILO, ILO )
- WI( ILO ) = ZERO
- RETURN
- END IF
-*
-* ==== clear out the trash ====
- DO 10 J = ILO, IHI - 3
- H( J+2, J ) = ZERO
- H( J+3, J ) = ZERO
- 10 CONTINUE
- IF( ILO.LE.IHI-2 )
- $ H( IHI, IHI-2 ) = ZERO
-*
- NH = IHI - ILO + 1
- NZ = IHIZ - ILOZ + 1
-*
-* Set machine-dependent constants for the stopping criterion.
-*
- SAFMIN = DLAMCH( 'SAFE MINIMUM' )
- SAFMAX = ONE / SAFMIN
- CALL DLABAD( SAFMIN, SAFMAX )
- ULP = DLAMCH( 'PRECISION' )
- SMLNUM = SAFMIN*( DBLE( NH ) / ULP )
-*
-* I1 and I2 are the indices of the first row and last column of H
-* to which transformations must be applied. If eigenvalues only are
-* being computed, I1 and I2 are set inside the main loop.
-*
- IF( WANTT ) THEN
- I1 = 1
- I2 = N
- END IF
-*
-* The main loop begins here. I is the loop index and decreases from
-* IHI to ILO in steps of 1 or 2. Each iteration of the loop works
-* with the active submatrix in rows and columns L to I.
-* Eigenvalues I+1 to IHI have already converged. Either L = ILO or
-* H(L,L-1) is negligible so that the matrix splits.
-*
- I = IHI
- 20 CONTINUE
- L = ILO
- IF( I.LT.ILO )
- $ GO TO 160
-*
-* Perform QR iterations on rows and columns ILO to I until a
-* submatrix of order 1 or 2 splits off at the bottom because a
-* subdiagonal element has become negligible.
-*
- DO 140 ITS = 0, ITMAX
-*
-* Look for a single small subdiagonal element.
-*
- DO 30 K = I, L + 1, -1
- IF( ABS( H( K, K-1 ) ).LE.SMLNUM )
- $ GO TO 40
- TST = ABS( H( K-1, K-1 ) ) + ABS( H( K, K ) )
- IF( TST.EQ.ZERO ) THEN
- IF( K-2.GE.ILO )
- $ TST = TST + ABS( H( K-1, K-2 ) )
- IF( K+1.LE.IHI )
- $ TST = TST + ABS( H( K+1, K ) )
- END IF
-* ==== The following is a conservative small subdiagonal
-* . deflation criterion due to Ahues & Tisseur (LAWN 122,
-* . 1997). It has better mathematical foundation and
-* . improves accuracy in some cases. ====
- IF( ABS( H( K, K-1 ) ).LE.ULP*TST ) THEN
- AB = MAX( ABS( H( K, K-1 ) ), ABS( H( K-1, K ) ) )
- BA = MIN( ABS( H( K, K-1 ) ), ABS( H( K-1, K ) ) )
- AA = MAX( ABS( H( K, K ) ),
- $ ABS( H( K-1, K-1 )-H( K, K ) ) )
- BB = MIN( ABS( H( K, K ) ),
- $ ABS( H( K-1, K-1 )-H( K, K ) ) )
- S = AA + AB
- IF( BA*( AB / S ).LE.MAX( SMLNUM,
- $ ULP*( BB*( AA / S ) ) ) )GO TO 40
- END IF
- 30 CONTINUE
- 40 CONTINUE
- L = K
- IF( L.GT.ILO ) THEN
-*
-* H(L,L-1) is negligible
-*
- H( L, L-1 ) = ZERO
- END IF
-*
-* Exit from loop if a submatrix of order 1 or 2 has split off.
-*
- IF( L.GE.I-1 )
- $ GO TO 150
-*
-* Now the active submatrix is in rows and columns L to I. If
-* eigenvalues only are being computed, only the active submatrix
-* need be transformed.
-*
- IF( .NOT.WANTT ) THEN
- I1 = L
- I2 = I
- END IF
-*
- IF( ITS.EQ.10 .OR. ITS.EQ.20 ) THEN
-*
-* Exceptional shift.
-*
- H11 = DAT1*S + H( I, I )
- H12 = DAT2*S
- H21 = S
- H22 = H11
- ELSE
-*
-* Prepare to use Francis' double shift
-* (i.e. 2nd degree generalized Rayleigh quotient)
-*
- H11 = H( I-1, I-1 )
- H21 = H( I, I-1 )
- H12 = H( I-1, I )
- H22 = H( I, I )
- END IF
- S = ABS( H11 ) + ABS( H12 ) + ABS( H21 ) + ABS( H22 )
- IF( S.EQ.ZERO ) THEN
- RT1R = ZERO
- RT1I = ZERO
- RT2R = ZERO
- RT2I = ZERO
- ELSE
- H11 = H11 / S
- H21 = H21 / S
- H12 = H12 / S
- H22 = H22 / S
- TR = ( H11+H22 ) / TWO
- DET = ( H11-TR )*( H22-TR ) - H12*H21
- RTDISC = SQRT( ABS( DET ) )
- IF( DET.GE.ZERO ) THEN
-*
-* ==== complex conjugate shifts ====
-*
- RT1R = TR*S
- RT2R = RT1R
- RT1I = RTDISC*S
- RT2I = -RT1I
- ELSE
-*
-* ==== real shifts (use only one of them) ====
-*
- RT1R = TR + RTDISC
- RT2R = TR - RTDISC
- IF( ABS( RT1R-H22 ).LE.ABS( RT2R-H22 ) ) THEN
- RT1R = RT1R*S
- RT2R = RT1R
- ELSE
- RT2R = RT2R*S
- RT1R = RT2R
- END IF
- RT1I = ZERO
- RT2I = ZERO
- END IF
- END IF
-*
-* Look for two consecutive small subdiagonal elements.
-*
- DO 50 M = I - 2, L, -1
-* Determine the effect of starting the double-shift QR
-* iteration at row M, and see if this would make H(M,M-1)
-* negligible. (The following uses scaling to avoid
-* overflows and most underflows.)
-*
- H21S = H( M+1, M )
- S = ABS( H( M, M )-RT2R ) + ABS( RT2I ) + ABS( H21S )
- H21S = H( M+1, M ) / S
- V( 1 ) = H21S*H( M, M+1 ) + ( H( M, M )-RT1R )*
- $ ( ( H( M, M )-RT2R ) / S ) - RT1I*( RT2I / S )
- V( 2 ) = H21S*( H( M, M )+H( M+1, M+1 )-RT1R-RT2R )
- V( 3 ) = H21S*H( M+2, M+1 )
- S = ABS( V( 1 ) ) + ABS( V( 2 ) ) + ABS( V( 3 ) )
- V( 1 ) = V( 1 ) / S
- V( 2 ) = V( 2 ) / S
- V( 3 ) = V( 3 ) / S
- IF( M.EQ.L )
- $ GO TO 60
- IF( ABS( H( M, M-1 ) )*( ABS( V( 2 ) )+ABS( V( 3 ) ) ).LE.
- $ ULP*ABS( V( 1 ) )*( ABS( H( M-1, M-1 ) )+ABS( H( M,
- $ M ) )+ABS( H( M+1, M+1 ) ) ) )GO TO 60
- 50 CONTINUE
- 60 CONTINUE
-*
-* Double-shift QR step
-*
- DO 130 K = M, I - 1
-*
-* The first iteration of this loop determines a reflection G
-* from the vector V and applies it from left and right to H,
-* thus creating a nonzero bulge below the subdiagonal.
-*
-* Each subsequent iteration determines a reflection G to
-* restore the Hessenberg form in the (K-1)th column, and thus
-* chases the bulge one step toward the bottom of the active
-* submatrix. NR is the order of G.
-*
- NR = MIN( 3, I-K+1 )
- IF( K.GT.M )
- $ CALL DCOPY( NR, H( K, K-1 ), 1, V, 1 )
- CALL DLARFG( NR, V( 1 ), V( 2 ), 1, T1 )
- IF( K.GT.M ) THEN
- H( K, K-1 ) = V( 1 )
- H( K+1, K-1 ) = ZERO
- IF( K.LT.I-1 )
- $ H( K+2, K-1 ) = ZERO
- ELSE IF( M.GT.L ) THEN
- H( K, K-1 ) = -H( K, K-1 )
- END IF
- V2 = V( 2 )
- T2 = T1*V2
- IF( NR.EQ.3 ) THEN
- V3 = V( 3 )
- T3 = T1*V3
-*
-* Apply G from the left to transform the rows of the matrix
-* in columns K to I2.
-*
- DO 70 J = K, I2
- SUM = H( K, J ) + V2*H( K+1, J ) + V3*H( K+2, J )
- H( K, J ) = H( K, J ) - SUM*T1
- H( K+1, J ) = H( K+1, J ) - SUM*T2
- H( K+2, J ) = H( K+2, J ) - SUM*T3
- 70 CONTINUE
-*
-* Apply G from the right to transform the columns of the
-* matrix in rows I1 to min(K+3,I).
-*
- DO 80 J = I1, MIN( K+3, I )
- SUM = H( J, K ) + V2*H( J, K+1 ) + V3*H( J, K+2 )
- H( J, K ) = H( J, K ) - SUM*T1
- H( J, K+1 ) = H( J, K+1 ) - SUM*T2
- H( J, K+2 ) = H( J, K+2 ) - SUM*T3
- 80 CONTINUE
-*
- IF( WANTZ ) THEN
-*
-* Accumulate transformations in the matrix Z
-*
- DO 90 J = ILOZ, IHIZ
- SUM = Z( J, K ) + V2*Z( J, K+1 ) + V3*Z( J, K+2 )
- Z( J, K ) = Z( J, K ) - SUM*T1
- Z( J, K+1 ) = Z( J, K+1 ) - SUM*T2
- Z( J, K+2 ) = Z( J, K+2 ) - SUM*T3
- 90 CONTINUE
- END IF
- ELSE IF( NR.EQ.2 ) THEN
-*
-* Apply G from the left to transform the rows of the matrix
-* in columns K to I2.
-*
- DO 100 J = K, I2
- SUM = H( K, J ) + V2*H( K+1, J )
- H( K, J ) = H( K, J ) - SUM*T1
- H( K+1, J ) = H( K+1, J ) - SUM*T2
- 100 CONTINUE
-*
-* Apply G from the right to transform the columns of the
-* matrix in rows I1 to min(K+3,I).
-*
- DO 110 J = I1, I
- SUM = H( J, K ) + V2*H( J, K+1 )
- H( J, K ) = H( J, K ) - SUM*T1
- H( J, K+1 ) = H( J, K+1 ) - SUM*T2
- 110 CONTINUE
-*
- IF( WANTZ ) THEN
-*
-* Accumulate transformations in the matrix Z
-*
- DO 120 J = ILOZ, IHIZ
- SUM = Z( J, K ) + V2*Z( J, K+1 )
- Z( J, K ) = Z( J, K ) - SUM*T1
- Z( J, K+1 ) = Z( J, K+1 ) - SUM*T2
- 120 CONTINUE
- END IF
- END IF
- 130 CONTINUE
-*
- 140 CONTINUE
-*
-* Failure to converge in remaining number of iterations
-*
- INFO = I
- RETURN
-*
- 150 CONTINUE
-*
- IF( L.EQ.I ) THEN
-*
-* H(I,I-1) is negligible: one eigenvalue has converged.
-*
- WR( I ) = H( I, I )
- WI( I ) = ZERO
- ELSE IF( L.EQ.I-1 ) THEN
-*
-* H(I-1,I-2) is negligible: a pair of eigenvalues have converged.
-*
-* Transform the 2-by-2 submatrix to standard Schur form,
-* and compute and store the eigenvalues.
-*
- CALL DLANV2( H( I-1, I-1 ), H( I-1, I ), H( I, I-1 ),
- $ H( I, I ), WR( I-1 ), WI( I-1 ), WR( I ), WI( I ),
- $ CS, SN )
-*
- IF( WANTT ) THEN
-*
-* Apply the transformation to the rest of H.
-*
- IF( I2.GT.I )
- $ CALL DROT( I2-I, H( I-1, I+1 ), LDH, H( I, I+1 ), LDH,
- $ CS, SN )
- CALL DROT( I-I1-1, H( I1, I-1 ), 1, H( I1, I ), 1, CS, SN )
- END IF
- IF( WANTZ ) THEN
-*
-* Apply the transformation to Z.
-*
- CALL DROT( NZ, Z( ILOZ, I-1 ), 1, Z( ILOZ, I ), 1, CS, SN )
- END IF
- END IF
-*
-* return to start of the main loop with new value of I.
-*
- I = L - 1
- GO TO 20
-*
- 160 CONTINUE
- RETURN
-*
-* End of DLAHQR
-*
- END
diff --git a/src/lib/lapack/dlahr2.f b/src/lib/lapack/dlahr2.f
deleted file mode 100644
index 6af74977..00000000
--- a/src/lib/lapack/dlahr2.f
+++ /dev/null
@@ -1,238 +0,0 @@
- SUBROUTINE DLAHR2( N, K, NB, A, LDA, TAU, T, LDT, Y, LDY )
-*
-* -- LAPACK auxiliary routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- INTEGER K, LDA, LDT, LDY, N, NB
-* ..
-* .. Array Arguments ..
- DOUBLE PRECISION A( LDA, * ), T( LDT, NB ), TAU( NB ),
- $ Y( LDY, NB )
-* ..
-*
-* Purpose
-* =======
-*
-* DLAHR2 reduces the first NB columns of A real general n-BY-(n-k+1)
-* matrix A so that elements below the k-th subdiagonal are zero. The
-* reduction is performed by an orthogonal similarity transformation
-* Q' * A * Q. The routine returns the matrices V and T which determine
-* Q as a block reflector I - V*T*V', and also the matrix Y = A * V * T.
-*
-* This is an auxiliary routine called by DGEHRD.
-*
-* Arguments
-* =========
-*
-* N (input) INTEGER
-* The order of the matrix A.
-*
-* K (input) INTEGER
-* The offset for the reduction. Elements below the k-th
-* subdiagonal in the first NB columns are reduced to zero.
-* K < N.
-*
-* NB (input) INTEGER
-* The number of columns to be reduced.
-*
-* A (input/output) DOUBLE PRECISION array, dimension (LDA,N-K+1)
-* On entry, the n-by-(n-k+1) general matrix A.
-* On exit, the elements on and above the k-th subdiagonal in
-* the first NB columns are overwritten with the corresponding
-* elements of the reduced matrix; the elements below the k-th
-* subdiagonal, with the array TAU, represent the matrix Q as a
-* product of elementary reflectors. The other columns of A are
-* unchanged. See Further Details.
-*
-* LDA (input) INTEGER
-* The leading dimension of the array A. LDA >= max(1,N).
-*
-* TAU (output) DOUBLE PRECISION array, dimension (NB)
-* The scalar factors of the elementary reflectors. See Further
-* Details.
-*
-* T (output) DOUBLE PRECISION array, dimension (LDT,NB)
-* The upper triangular matrix T.
-*
-* LDT (input) INTEGER
-* The leading dimension of the array T. LDT >= NB.
-*
-* Y (output) DOUBLE PRECISION array, dimension (LDY,NB)
-* The n-by-nb matrix Y.
-*
-* LDY (input) INTEGER
-* The leading dimension of the array Y. LDY >= N.
-*
-* Further Details
-* ===============
-*
-* The matrix Q is represented as a product of nb elementary reflectors
-*
-* Q = H(1) H(2) . . . H(nb).
-*
-* Each H(i) has the form
-*
-* H(i) = I - tau * v * v'
-*
-* where tau is a real scalar, and v is a real vector with
-* v(1:i+k-1) = 0, v(i+k) = 1; v(i+k+1:n) is stored on exit in
-* A(i+k+1:n,i), and tau in TAU(i).
-*
-* The elements of the vectors v together form the (n-k+1)-by-nb matrix
-* V which is needed, with T and Y, to apply the transformation to the
-* unreduced part of the matrix, using an update of the form:
-* A := (I - V*T*V') * (A - Y*V').
-*
-* The contents of A on exit are illustrated by the following example
-* with n = 7, k = 3 and nb = 2:
-*
-* ( a a a a a )
-* ( a a a a a )
-* ( a a a a a )
-* ( h h a a a )
-* ( v1 h a a a )
-* ( v1 v2 a a a )
-* ( v1 v2 a a a )
-*
-* where a denotes an element of the original matrix A, h denotes a
-* modified element of the upper Hessenberg matrix H, and vi denotes an
-* element of the vector defining H(i).
-*
-* This file is a slight modification of LAPACK-3.0's DLAHRD
-* incorporating improvements proposed by Quintana-Orti and Van de
-* Gejin. Note that the entries of A(1:K,2:NB) differ from those
-* returned by the original LAPACK routine. This function is
-* not backward compatible with LAPACK3.0.
-*
-* =====================================================================
-*
-* .. Parameters ..
- DOUBLE PRECISION ZERO, ONE
- PARAMETER ( ZERO = 0.0D+0,
- $ ONE = 1.0D+0 )
-* ..
-* .. Local Scalars ..
- INTEGER I
- DOUBLE PRECISION EI
-* ..
-* .. External Subroutines ..
- EXTERNAL DAXPY, DCOPY, DGEMM, DGEMV, DLACPY,
- $ DLARFG, DSCAL, DTRMM, DTRMV
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC MIN
-* ..
-* .. Executable Statements ..
-*
-* Quick return if possible
-*
- IF( N.LE.1 )
- $ RETURN
-*
- DO 10 I = 1, NB
- IF( I.GT.1 ) THEN
-*
-* Update A(K+1:N,I)
-*
-* Update I-th column of A - Y * V'
-*
- CALL DGEMV( 'NO TRANSPOSE', N-K, I-1, -ONE, Y(K+1,1), LDY,
- $ A( K+I-1, 1 ), LDA, ONE, A( K+1, I ), 1 )
-*
-* Apply I - V * T' * V' to this column (call it b) from the
-* left, using the last column of T as workspace
-*
-* Let V = ( V1 ) and b = ( b1 ) (first I-1 rows)
-* ( V2 ) ( b2 )
-*
-* where V1 is unit lower triangular
-*
-* w := V1' * b1
-*
- CALL DCOPY( I-1, A( K+1, I ), 1, T( 1, NB ), 1 )
- CALL DTRMV( 'Lower', 'Transpose', 'UNIT',
- $ I-1, A( K+1, 1 ),
- $ LDA, T( 1, NB ), 1 )
-*
-* w := w + V2'*b2
-*
- CALL DGEMV( 'Transpose', N-K-I+1, I-1,
- $ ONE, A( K+I, 1 ),
- $ LDA, A( K+I, I ), 1, ONE, T( 1, NB ), 1 )
-*
-* w := T'*w
-*
- CALL DTRMV( 'Upper', 'Transpose', 'NON-UNIT',
- $ I-1, T, LDT,
- $ T( 1, NB ), 1 )
-*
-* b2 := b2 - V2*w
-*
- CALL DGEMV( 'NO TRANSPOSE', N-K-I+1, I-1, -ONE,
- $ A( K+I, 1 ),
- $ LDA, T( 1, NB ), 1, ONE, A( K+I, I ), 1 )
-*
-* b1 := b1 - V1*w
-*
- CALL DTRMV( 'Lower', 'NO TRANSPOSE',
- $ 'UNIT', I-1,
- $ A( K+1, 1 ), LDA, T( 1, NB ), 1 )
- CALL DAXPY( I-1, -ONE, T( 1, NB ), 1, A( K+1, I ), 1 )
-*
- A( K+I-1, I-1 ) = EI
- END IF
-*
-* Generate the elementary reflector H(I) to annihilate
-* A(K+I+1:N,I)
-*
- CALL DLARFG( N-K-I+1, A( K+I, I ), A( MIN( K+I+1, N ), I ), 1,
- $ TAU( I ) )
- EI = A( K+I, I )
- A( K+I, I ) = ONE
-*
-* Compute Y(K+1:N,I)
-*
- CALL DGEMV( 'NO TRANSPOSE', N-K, N-K-I+1,
- $ ONE, A( K+1, I+1 ),
- $ LDA, A( K+I, I ), 1, ZERO, Y( K+1, I ), 1 )
- CALL DGEMV( 'Transpose', N-K-I+1, I-1,
- $ ONE, A( K+I, 1 ), LDA,
- $ A( K+I, I ), 1, ZERO, T( 1, I ), 1 )
- CALL DGEMV( 'NO TRANSPOSE', N-K, I-1, -ONE,
- $ Y( K+1, 1 ), LDY,
- $ T( 1, I ), 1, ONE, Y( K+1, I ), 1 )
- CALL DSCAL( N-K, TAU( I ), Y( K+1, I ), 1 )
-*
-* Compute T(1:I,I)
-*
- CALL DSCAL( I-1, -TAU( I ), T( 1, I ), 1 )
- CALL DTRMV( 'Upper', 'No Transpose', 'NON-UNIT',
- $ I-1, T, LDT,
- $ T( 1, I ), 1 )
- T( I, I ) = TAU( I )
-*
- 10 CONTINUE
- A( K+NB, NB ) = EI
-*
-* Compute Y(1:K,1:NB)
-*
- CALL DLACPY( 'ALL', K, NB, A( 1, 2 ), LDA, Y, LDY )
- CALL DTRMM( 'RIGHT', 'Lower', 'NO TRANSPOSE',
- $ 'UNIT', K, NB,
- $ ONE, A( K+1, 1 ), LDA, Y, LDY )
- IF( N.GT.K+NB )
- $ CALL DGEMM( 'NO TRANSPOSE', 'NO TRANSPOSE', K,
- $ NB, N-K-NB, ONE,
- $ A( 1, 2+NB ), LDA, A( K+1+NB, 1 ), LDA, ONE, Y,
- $ LDY )
- CALL DTRMM( 'RIGHT', 'Upper', 'NO TRANSPOSE',
- $ 'NON-UNIT', K, NB,
- $ ONE, T, LDT, Y, LDY )
-*
- RETURN
-*
-* End of DLAHR2
-*
- END
diff --git a/src/lib/lapack/dlahrd.f b/src/lib/lapack/dlahrd.f
deleted file mode 100644
index a04133d1..00000000
--- a/src/lib/lapack/dlahrd.f
+++ /dev/null
@@ -1,207 +0,0 @@
- SUBROUTINE DLAHRD( N, K, NB, A, LDA, TAU, T, LDT, Y, LDY )
-*
-* -- LAPACK auxiliary routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- INTEGER K, LDA, LDT, LDY, N, NB
-* ..
-* .. Array Arguments ..
- DOUBLE PRECISION A( LDA, * ), T( LDT, NB ), TAU( NB ),
- $ Y( LDY, NB )
-* ..
-*
-* Purpose
-* =======
-*
-* DLAHRD reduces the first NB columns of a real general n-by-(n-k+1)
-* matrix A so that elements below the k-th subdiagonal are zero. The
-* reduction is performed by an orthogonal similarity transformation
-* Q' * A * Q. The routine returns the matrices V and T which determine
-* Q as a block reflector I - V*T*V', and also the matrix Y = A * V * T.
-*
-* This is an OBSOLETE auxiliary routine.
-* This routine will be 'deprecated' in a future release.
-* Please use the new routine DLAHR2 instead.
-*
-* Arguments
-* =========
-*
-* N (input) INTEGER
-* The order of the matrix A.
-*
-* K (input) INTEGER
-* The offset for the reduction. Elements below the k-th
-* subdiagonal in the first NB columns are reduced to zero.
-*
-* NB (input) INTEGER
-* The number of columns to be reduced.
-*
-* A (input/output) DOUBLE PRECISION array, dimension (LDA,N-K+1)
-* On entry, the n-by-(n-k+1) general matrix A.
-* On exit, the elements on and above the k-th subdiagonal in
-* the first NB columns are overwritten with the corresponding
-* elements of the reduced matrix; the elements below the k-th
-* subdiagonal, with the array TAU, represent the matrix Q as a
-* product of elementary reflectors. The other columns of A are
-* unchanged. See Further Details.
-*
-* LDA (input) INTEGER
-* The leading dimension of the array A. LDA >= max(1,N).
-*
-* TAU (output) DOUBLE PRECISION array, dimension (NB)
-* The scalar factors of the elementary reflectors. See Further
-* Details.
-*
-* T (output) DOUBLE PRECISION array, dimension (LDT,NB)
-* The upper triangular matrix T.
-*
-* LDT (input) INTEGER
-* The leading dimension of the array T. LDT >= NB.
-*
-* Y (output) DOUBLE PRECISION array, dimension (LDY,NB)
-* The n-by-nb matrix Y.
-*
-* LDY (input) INTEGER
-* The leading dimension of the array Y. LDY >= N.
-*
-* Further Details
-* ===============
-*
-* The matrix Q is represented as a product of nb elementary reflectors
-*
-* Q = H(1) H(2) . . . H(nb).
-*
-* Each H(i) has the form
-*
-* H(i) = I - tau * v * v'
-*
-* where tau is a real scalar, and v is a real vector with
-* v(1:i+k-1) = 0, v(i+k) = 1; v(i+k+1:n) is stored on exit in
-* A(i+k+1:n,i), and tau in TAU(i).
-*
-* The elements of the vectors v together form the (n-k+1)-by-nb matrix
-* V which is needed, with T and Y, to apply the transformation to the
-* unreduced part of the matrix, using an update of the form:
-* A := (I - V*T*V') * (A - Y*V').
-*
-* The contents of A on exit are illustrated by the following example
-* with n = 7, k = 3 and nb = 2:
-*
-* ( a h a a a )
-* ( a h a a a )
-* ( a h a a a )
-* ( h h a a a )
-* ( v1 h a a a )
-* ( v1 v2 a a a )
-* ( v1 v2 a a a )
-*
-* where a denotes an element of the original matrix A, h denotes a
-* modified element of the upper Hessenberg matrix H, and vi denotes an
-* element of the vector defining H(i).
-*
-* =====================================================================
-*
-* .. Parameters ..
- DOUBLE PRECISION ZERO, ONE
- PARAMETER ( ZERO = 0.0D+0, ONE = 1.0D+0 )
-* ..
-* .. Local Scalars ..
- INTEGER I
- DOUBLE PRECISION EI
-* ..
-* .. External Subroutines ..
- EXTERNAL DAXPY, DCOPY, DGEMV, DLARFG, DSCAL, DTRMV
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC MIN
-* ..
-* .. Executable Statements ..
-*
-* Quick return if possible
-*
- IF( N.LE.1 )
- $ RETURN
-*
- DO 10 I = 1, NB
- IF( I.GT.1 ) THEN
-*
-* Update A(1:n,i)
-*
-* Compute i-th column of A - Y * V'
-*
- CALL DGEMV( 'No transpose', N, I-1, -ONE, Y, LDY,
- $ A( K+I-1, 1 ), LDA, ONE, A( 1, I ), 1 )
-*
-* Apply I - V * T' * V' to this column (call it b) from the
-* left, using the last column of T as workspace
-*
-* Let V = ( V1 ) and b = ( b1 ) (first I-1 rows)
-* ( V2 ) ( b2 )
-*
-* where V1 is unit lower triangular
-*
-* w := V1' * b1
-*
- CALL DCOPY( I-1, A( K+1, I ), 1, T( 1, NB ), 1 )
- CALL DTRMV( 'Lower', 'Transpose', 'Unit', I-1, A( K+1, 1 ),
- $ LDA, T( 1, NB ), 1 )
-*
-* w := w + V2'*b2
-*
- CALL DGEMV( 'Transpose', N-K-I+1, I-1, ONE, A( K+I, 1 ),
- $ LDA, A( K+I, I ), 1, ONE, T( 1, NB ), 1 )
-*
-* w := T'*w
-*
- CALL DTRMV( 'Upper', 'Transpose', 'Non-unit', I-1, T, LDT,
- $ T( 1, NB ), 1 )
-*
-* b2 := b2 - V2*w
-*
- CALL DGEMV( 'No transpose', N-K-I+1, I-1, -ONE, A( K+I, 1 ),
- $ LDA, T( 1, NB ), 1, ONE, A( K+I, I ), 1 )
-*
-* b1 := b1 - V1*w
-*
- CALL DTRMV( 'Lower', 'No transpose', 'Unit', I-1,
- $ A( K+1, 1 ), LDA, T( 1, NB ), 1 )
- CALL DAXPY( I-1, -ONE, T( 1, NB ), 1, A( K+1, I ), 1 )
-*
- A( K+I-1, I-1 ) = EI
- END IF
-*
-* Generate the elementary reflector H(i) to annihilate
-* A(k+i+1:n,i)
-*
- CALL DLARFG( N-K-I+1, A( K+I, I ), A( MIN( K+I+1, N ), I ), 1,
- $ TAU( I ) )
- EI = A( K+I, I )
- A( K+I, I ) = ONE
-*
-* Compute Y(1:n,i)
-*
- CALL DGEMV( 'No transpose', N, N-K-I+1, ONE, A( 1, I+1 ), LDA,
- $ A( K+I, I ), 1, ZERO, Y( 1, I ), 1 )
- CALL DGEMV( 'Transpose', N-K-I+1, I-1, ONE, A( K+I, 1 ), LDA,
- $ A( K+I, I ), 1, ZERO, T( 1, I ), 1 )
- CALL DGEMV( 'No transpose', N, I-1, -ONE, Y, LDY, T( 1, I ), 1,
- $ ONE, Y( 1, I ), 1 )
- CALL DSCAL( N, TAU( I ), Y( 1, I ), 1 )
-*
-* Compute T(1:i,i)
-*
- CALL DSCAL( I-1, -TAU( I ), T( 1, I ), 1 )
- CALL DTRMV( 'Upper', 'No transpose', 'Non-unit', I-1, T, LDT,
- $ T( 1, I ), 1 )
- T( I, I ) = TAU( I )
-*
- 10 CONTINUE
- A( K+NB, NB ) = EI
-*
- RETURN
-*
-* End of DLAHRD
-*
- END
diff --git a/src/lib/lapack/dlaic1.f b/src/lib/lapack/dlaic1.f
deleted file mode 100644
index 44baece1..00000000
--- a/src/lib/lapack/dlaic1.f
+++ /dev/null
@@ -1,292 +0,0 @@
- SUBROUTINE DLAIC1( JOB, J, X, SEST, W, GAMMA, SESTPR, S, C )
-*
-* -- LAPACK auxiliary routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- INTEGER J, JOB
- DOUBLE PRECISION C, GAMMA, S, SEST, SESTPR
-* ..
-* .. Array Arguments ..
- DOUBLE PRECISION W( J ), X( J )
-* ..
-*
-* Purpose
-* =======
-*
-* DLAIC1 applies one step of incremental condition estimation in
-* its simplest version:
-*
-* Let x, twonorm(x) = 1, be an approximate singular vector of an j-by-j
-* lower triangular matrix L, such that
-* twonorm(L*x) = sest
-* Then DLAIC1 computes sestpr, s, c such that
-* the vector
-* [ s*x ]
-* xhat = [ c ]
-* is an approximate singular vector of
-* [ L 0 ]
-* Lhat = [ w' gamma ]
-* in the sense that
-* twonorm(Lhat*xhat) = sestpr.
-*
-* Depending on JOB, an estimate for the largest or smallest singular
-* value is computed.
-*
-* Note that [s c]' and sestpr**2 is an eigenpair of the system
-*
-* diag(sest*sest, 0) + [alpha gamma] * [ alpha ]
-* [ gamma ]
-*
-* where alpha = x'*w.
-*
-* Arguments
-* =========
-*
-* JOB (input) INTEGER
-* = 1: an estimate for the largest singular value is computed.
-* = 2: an estimate for the smallest singular value is computed.
-*
-* J (input) INTEGER
-* Length of X and W
-*
-* X (input) DOUBLE PRECISION array, dimension (J)
-* The j-vector x.
-*
-* SEST (input) DOUBLE PRECISION
-* Estimated singular value of j by j matrix L
-*
-* W (input) DOUBLE PRECISION array, dimension (J)
-* The j-vector w.
-*
-* GAMMA (input) DOUBLE PRECISION
-* The diagonal element gamma.
-*
-* SESTPR (output) DOUBLE PRECISION
-* Estimated singular value of (j+1) by (j+1) matrix Lhat.
-*
-* S (output) DOUBLE PRECISION
-* Sine needed in forming xhat.
-*
-* C (output) DOUBLE PRECISION
-* Cosine needed in forming xhat.
-*
-* =====================================================================
-*
-* .. Parameters ..
- DOUBLE PRECISION ZERO, ONE, TWO
- PARAMETER ( ZERO = 0.0D0, ONE = 1.0D0, TWO = 2.0D0 )
- DOUBLE PRECISION HALF, FOUR
- PARAMETER ( HALF = 0.5D0, FOUR = 4.0D0 )
-* ..
-* .. Local Scalars ..
- DOUBLE PRECISION ABSALP, ABSEST, ABSGAM, ALPHA, B, COSINE, EPS,
- $ NORMA, S1, S2, SINE, T, TEST, TMP, ZETA1, ZETA2
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC ABS, MAX, SIGN, SQRT
-* ..
-* .. External Functions ..
- DOUBLE PRECISION DDOT, DLAMCH
- EXTERNAL DDOT, DLAMCH
-* ..
-* .. Executable Statements ..
-*
- EPS = DLAMCH( 'Epsilon' )
- ALPHA = DDOT( J, X, 1, W, 1 )
-*
- ABSALP = ABS( ALPHA )
- ABSGAM = ABS( GAMMA )
- ABSEST = ABS( SEST )
-*
- IF( JOB.EQ.1 ) THEN
-*
-* Estimating largest singular value
-*
-* special cases
-*
- IF( SEST.EQ.ZERO ) THEN
- S1 = MAX( ABSGAM, ABSALP )
- IF( S1.EQ.ZERO ) THEN
- S = ZERO
- C = ONE
- SESTPR = ZERO
- ELSE
- S = ALPHA / S1
- C = GAMMA / S1
- TMP = SQRT( S*S+C*C )
- S = S / TMP
- C = C / TMP
- SESTPR = S1*TMP
- END IF
- RETURN
- ELSE IF( ABSGAM.LE.EPS*ABSEST ) THEN
- S = ONE
- C = ZERO
- TMP = MAX( ABSEST, ABSALP )
- S1 = ABSEST / TMP
- S2 = ABSALP / TMP
- SESTPR = TMP*SQRT( S1*S1+S2*S2 )
- RETURN
- ELSE IF( ABSALP.LE.EPS*ABSEST ) THEN
- S1 = ABSGAM
- S2 = ABSEST
- IF( S1.LE.S2 ) THEN
- S = ONE
- C = ZERO
- SESTPR = S2
- ELSE
- S = ZERO
- C = ONE
- SESTPR = S1
- END IF
- RETURN
- ELSE IF( ABSEST.LE.EPS*ABSALP .OR. ABSEST.LE.EPS*ABSGAM ) THEN
- S1 = ABSGAM
- S2 = ABSALP
- IF( S1.LE.S2 ) THEN
- TMP = S1 / S2
- S = SQRT( ONE+TMP*TMP )
- SESTPR = S2*S
- C = ( GAMMA / S2 ) / S
- S = SIGN( ONE, ALPHA ) / S
- ELSE
- TMP = S2 / S1
- C = SQRT( ONE+TMP*TMP )
- SESTPR = S1*C
- S = ( ALPHA / S1 ) / C
- C = SIGN( ONE, GAMMA ) / C
- END IF
- RETURN
- ELSE
-*
-* normal case
-*
- ZETA1 = ALPHA / ABSEST
- ZETA2 = GAMMA / ABSEST
-*
- B = ( ONE-ZETA1*ZETA1-ZETA2*ZETA2 )*HALF
- C = ZETA1*ZETA1
- IF( B.GT.ZERO ) THEN
- T = C / ( B+SQRT( B*B+C ) )
- ELSE
- T = SQRT( B*B+C ) - B
- END IF
-*
- SINE = -ZETA1 / T
- COSINE = -ZETA2 / ( ONE+T )
- TMP = SQRT( SINE*SINE+COSINE*COSINE )
- S = SINE / TMP
- C = COSINE / TMP
- SESTPR = SQRT( T+ONE )*ABSEST
- RETURN
- END IF
-*
- ELSE IF( JOB.EQ.2 ) THEN
-*
-* Estimating smallest singular value
-*
-* special cases
-*
- IF( SEST.EQ.ZERO ) THEN
- SESTPR = ZERO
- IF( MAX( ABSGAM, ABSALP ).EQ.ZERO ) THEN
- SINE = ONE
- COSINE = ZERO
- ELSE
- SINE = -GAMMA
- COSINE = ALPHA
- END IF
- S1 = MAX( ABS( SINE ), ABS( COSINE ) )
- S = SINE / S1
- C = COSINE / S1
- TMP = SQRT( S*S+C*C )
- S = S / TMP
- C = C / TMP
- RETURN
- ELSE IF( ABSGAM.LE.EPS*ABSEST ) THEN
- S = ZERO
- C = ONE
- SESTPR = ABSGAM
- RETURN
- ELSE IF( ABSALP.LE.EPS*ABSEST ) THEN
- S1 = ABSGAM
- S2 = ABSEST
- IF( S1.LE.S2 ) THEN
- S = ZERO
- C = ONE
- SESTPR = S1
- ELSE
- S = ONE
- C = ZERO
- SESTPR = S2
- END IF
- RETURN
- ELSE IF( ABSEST.LE.EPS*ABSALP .OR. ABSEST.LE.EPS*ABSGAM ) THEN
- S1 = ABSGAM
- S2 = ABSALP
- IF( S1.LE.S2 ) THEN
- TMP = S1 / S2
- C = SQRT( ONE+TMP*TMP )
- SESTPR = ABSEST*( TMP / C )
- S = -( GAMMA / S2 ) / C
- C = SIGN( ONE, ALPHA ) / C
- ELSE
- TMP = S2 / S1
- S = SQRT( ONE+TMP*TMP )
- SESTPR = ABSEST / S
- C = ( ALPHA / S1 ) / S
- S = -SIGN( ONE, GAMMA ) / S
- END IF
- RETURN
- ELSE
-*
-* normal case
-*
- ZETA1 = ALPHA / ABSEST
- ZETA2 = GAMMA / ABSEST
-*
- NORMA = MAX( ONE+ZETA1*ZETA1+ABS( ZETA1*ZETA2 ),
- $ ABS( ZETA1*ZETA2 )+ZETA2*ZETA2 )
-*
-* See if root is closer to zero or to ONE
-*
- TEST = ONE + TWO*( ZETA1-ZETA2 )*( ZETA1+ZETA2 )
- IF( TEST.GE.ZERO ) THEN
-*
-* root is close to zero, compute directly
-*
- B = ( ZETA1*ZETA1+ZETA2*ZETA2+ONE )*HALF
- C = ZETA2*ZETA2
- T = C / ( B+SQRT( ABS( B*B-C ) ) )
- SINE = ZETA1 / ( ONE-T )
- COSINE = -ZETA2 / T
- SESTPR = SQRT( T+FOUR*EPS*EPS*NORMA )*ABSEST
- ELSE
-*
-* root is closer to ONE, shift by that amount
-*
- B = ( ZETA2*ZETA2+ZETA1*ZETA1-ONE )*HALF
- C = ZETA1*ZETA1
- IF( B.GE.ZERO ) THEN
- T = -C / ( B+SQRT( B*B+C ) )
- ELSE
- T = B - SQRT( B*B+C )
- END IF
- SINE = -ZETA1 / T
- COSINE = -ZETA2 / ( ONE+T )
- SESTPR = SQRT( ONE+T+FOUR*EPS*EPS*NORMA )*ABSEST
- END IF
- TMP = SQRT( SINE*SINE+COSINE*COSINE )
- S = SINE / TMP
- C = COSINE / TMP
- RETURN
-*
- END IF
- END IF
- RETURN
-*
-* End of DLAIC1
-*
- END
diff --git a/src/lib/lapack/dlaisnan.f b/src/lib/lapack/dlaisnan.f
deleted file mode 100644
index 96350a27..00000000
--- a/src/lib/lapack/dlaisnan.f
+++ /dev/null
@@ -1,41 +0,0 @@
- LOGICAL FUNCTION DLAISNAN(DIN1,DIN2)
-*
-* -- LAPACK auxiliary routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- DOUBLE PRECISION DIN1,DIN2
-* ..
-*
-* Purpose
-* =======
-*
-* This routine is not for general use. It exists solely to avoid
-* over-optimization in DISNAN.
-*
-* DLAISNAN checks for NaNs by comparing its two arguments for
-* inequality. NaN is the only floating-point value where NaN != NaN
-* returns .TRUE. To check for NaNs, pass the same variable as both
-* arguments.
-*
-* Strictly speaking, Fortran does not allow aliasing of function
-* arguments. So a compiler must assume that the two arguments are
-* not the same variable, and the test will not be optimized away.
-* Interprocedural or whole-program optimization may delete this
-* test. The ISNAN functions will be replaced by the correct
-* Fortran 03 intrinsic once the intrinsic is widely available.
-*
-* Arguments
-* =========
-*
-* DIN1 (input) DOUBLE PRECISION
-* DIN2 (input) DOUBLE PRECISION
-* Two numbers to compare for inequality.
-*
-* =====================================================================
-*
-* .. Executable Statements ..
- DLAISNAN = (DIN1.NE.DIN2)
- RETURN
- END
diff --git a/src/lib/lapack/dlaln2.f b/src/lib/lapack/dlaln2.f
deleted file mode 100644
index 7c99bdbe..00000000
--- a/src/lib/lapack/dlaln2.f
+++ /dev/null
@@ -1,507 +0,0 @@
- SUBROUTINE DLALN2( LTRANS, NA, NW, SMIN, CA, A, LDA, D1, D2, B,
- $ LDB, WR, WI, X, LDX, SCALE, XNORM, INFO )
-*
-* -- LAPACK auxiliary routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- LOGICAL LTRANS
- INTEGER INFO, LDA, LDB, LDX, NA, NW
- DOUBLE PRECISION CA, D1, D2, SCALE, SMIN, WI, WR, XNORM
-* ..
-* .. Array Arguments ..
- DOUBLE PRECISION A( LDA, * ), B( LDB, * ), X( LDX, * )
-* ..
-*
-* Purpose
-* =======
-*
-* DLALN2 solves a system of the form (ca A - w D ) X = s B
-* or (ca A' - w D) X = s B with possible scaling ("s") and
-* perturbation of A. (A' means A-transpose.)
-*
-* A is an NA x NA real matrix, ca is a real scalar, D is an NA x NA
-* real diagonal matrix, w is a real or complex value, and X and B are
-* NA x 1 matrices -- real if w is real, complex if w is complex. NA
-* may be 1 or 2.
-*
-* If w is complex, X and B are represented as NA x 2 matrices,
-* the first column of each being the real part and the second
-* being the imaginary part.
-*
-* "s" is a scaling factor (.LE. 1), computed by DLALN2, which is
-* so chosen that X can be computed without overflow. X is further
-* scaled if necessary to assure that norm(ca A - w D)*norm(X) is less
-* than overflow.
-*
-* If both singular values of (ca A - w D) are less than SMIN,
-* SMIN*identity will be used instead of (ca A - w D). If only one
-* singular value is less than SMIN, one element of (ca A - w D) will be
-* perturbed enough to make the smallest singular value roughly SMIN.
-* If both singular values are at least SMIN, (ca A - w D) will not be
-* perturbed. In any case, the perturbation will be at most some small
-* multiple of max( SMIN, ulp*norm(ca A - w D) ). The singular values
-* are computed by infinity-norm approximations, and thus will only be
-* correct to a factor of 2 or so.
-*
-* Note: all input quantities are assumed to be smaller than overflow
-* by a reasonable factor. (See BIGNUM.)
-*
-* Arguments
-* ==========
-*
-* LTRANS (input) LOGICAL
-* =.TRUE.: A-transpose will be used.
-* =.FALSE.: A will be used (not transposed.)
-*
-* NA (input) INTEGER
-* The size of the matrix A. It may (only) be 1 or 2.
-*
-* NW (input) INTEGER
-* 1 if "w" is real, 2 if "w" is complex. It may only be 1
-* or 2.
-*
-* SMIN (input) DOUBLE PRECISION
-* The desired lower bound on the singular values of A. This
-* should be a safe distance away from underflow or overflow,
-* say, between (underflow/machine precision) and (machine
-* precision * overflow ). (See BIGNUM and ULP.)
-*
-* CA (input) DOUBLE PRECISION
-* The coefficient c, which A is multiplied by.
-*
-* A (input) DOUBLE PRECISION array, dimension (LDA,NA)
-* The NA x NA matrix A.
-*
-* LDA (input) INTEGER
-* The leading dimension of A. It must be at least NA.
-*
-* D1 (input) DOUBLE PRECISION
-* The 1,1 element in the diagonal matrix D.
-*
-* D2 (input) DOUBLE PRECISION
-* The 2,2 element in the diagonal matrix D. Not used if NW=1.
-*
-* B (input) DOUBLE PRECISION array, dimension (LDB,NW)
-* The NA x NW matrix B (right-hand side). If NW=2 ("w" is
-* complex), column 1 contains the real part of B and column 2
-* contains the imaginary part.
-*
-* LDB (input) INTEGER
-* The leading dimension of B. It must be at least NA.
-*
-* WR (input) DOUBLE PRECISION
-* The real part of the scalar "w".
-*
-* WI (input) DOUBLE PRECISION
-* The imaginary part of the scalar "w". Not used if NW=1.
-*
-* X (output) DOUBLE PRECISION array, dimension (LDX,NW)
-* The NA x NW matrix X (unknowns), as computed by DLALN2.
-* If NW=2 ("w" is complex), on exit, column 1 will contain
-* the real part of X and column 2 will contain the imaginary
-* part.
-*
-* LDX (input) INTEGER
-* The leading dimension of X. It must be at least NA.
-*
-* SCALE (output) DOUBLE PRECISION
-* The scale factor that B must be multiplied by to insure
-* that overflow does not occur when computing X. Thus,
-* (ca A - w D) X will be SCALE*B, not B (ignoring
-* perturbations of A.) It will be at most 1.
-*
-* XNORM (output) DOUBLE PRECISION
-* The infinity-norm of X, when X is regarded as an NA x NW
-* real matrix.
-*
-* INFO (output) INTEGER
-* An error flag. It will be set to zero if no error occurs,
-* a negative number if an argument is in error, or a positive
-* number if ca A - w D had to be perturbed.
-* The possible values are:
-* = 0: No error occurred, and (ca A - w D) did not have to be
-* perturbed.
-* = 1: (ca A - w D) had to be perturbed to make its smallest
-* (or only) singular value greater than SMIN.
-* NOTE: In the interests of speed, this routine does not
-* check the inputs for errors.
-*
-* =====================================================================
-*
-* .. Parameters ..
- DOUBLE PRECISION ZERO, ONE
- PARAMETER ( ZERO = 0.0D0, ONE = 1.0D0 )
- DOUBLE PRECISION TWO
- PARAMETER ( TWO = 2.0D0 )
-* ..
-* .. Local Scalars ..
- INTEGER ICMAX, J
- DOUBLE PRECISION BBND, BI1, BI2, BIGNUM, BNORM, BR1, BR2, CI21,
- $ CI22, CMAX, CNORM, CR21, CR22, CSI, CSR, LI21,
- $ LR21, SMINI, SMLNUM, TEMP, U22ABS, UI11, UI11R,
- $ UI12, UI12S, UI22, UR11, UR11R, UR12, UR12S,
- $ UR22, XI1, XI2, XR1, XR2
-* ..
-* .. Local Arrays ..
- LOGICAL RSWAP( 4 ), ZSWAP( 4 )
- INTEGER IPIVOT( 4, 4 )
- DOUBLE PRECISION CI( 2, 2 ), CIV( 4 ), CR( 2, 2 ), CRV( 4 )
-* ..
-* .. External Functions ..
- DOUBLE PRECISION DLAMCH
- EXTERNAL DLAMCH
-* ..
-* .. External Subroutines ..
- EXTERNAL DLADIV
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC ABS, MAX
-* ..
-* .. Equivalences ..
- EQUIVALENCE ( CI( 1, 1 ), CIV( 1 ) ),
- $ ( CR( 1, 1 ), CRV( 1 ) )
-* ..
-* .. Data statements ..
- DATA ZSWAP / .FALSE., .FALSE., .TRUE., .TRUE. /
- DATA RSWAP / .FALSE., .TRUE., .FALSE., .TRUE. /
- DATA IPIVOT / 1, 2, 3, 4, 2, 1, 4, 3, 3, 4, 1, 2, 4,
- $ 3, 2, 1 /
-* ..
-* .. Executable Statements ..
-*
-* Compute BIGNUM
-*
- SMLNUM = TWO*DLAMCH( 'Safe minimum' )
- BIGNUM = ONE / SMLNUM
- SMINI = MAX( SMIN, SMLNUM )
-*
-* Don't check for input errors
-*
- INFO = 0
-*
-* Standard Initializations
-*
- SCALE = ONE
-*
- IF( NA.EQ.1 ) THEN
-*
-* 1 x 1 (i.e., scalar) system C X = B
-*
- IF( NW.EQ.1 ) THEN
-*
-* Real 1x1 system.
-*
-* C = ca A - w D
-*
- CSR = CA*A( 1, 1 ) - WR*D1
- CNORM = ABS( CSR )
-*
-* If | C | < SMINI, use C = SMINI
-*
- IF( CNORM.LT.SMINI ) THEN
- CSR = SMINI
- CNORM = SMINI
- INFO = 1
- END IF
-*
-* Check scaling for X = B / C
-*
- BNORM = ABS( B( 1, 1 ) )
- IF( CNORM.LT.ONE .AND. BNORM.GT.ONE ) THEN
- IF( BNORM.GT.BIGNUM*CNORM )
- $ SCALE = ONE / BNORM
- END IF
-*
-* Compute X
-*
- X( 1, 1 ) = ( B( 1, 1 )*SCALE ) / CSR
- XNORM = ABS( X( 1, 1 ) )
- ELSE
-*
-* Complex 1x1 system (w is complex)
-*
-* C = ca A - w D
-*
- CSR = CA*A( 1, 1 ) - WR*D1
- CSI = -WI*D1
- CNORM = ABS( CSR ) + ABS( CSI )
-*
-* If | C | < SMINI, use C = SMINI
-*
- IF( CNORM.LT.SMINI ) THEN
- CSR = SMINI
- CSI = ZERO
- CNORM = SMINI
- INFO = 1
- END IF
-*
-* Check scaling for X = B / C
-*
- BNORM = ABS( B( 1, 1 ) ) + ABS( B( 1, 2 ) )
- IF( CNORM.LT.ONE .AND. BNORM.GT.ONE ) THEN
- IF( BNORM.GT.BIGNUM*CNORM )
- $ SCALE = ONE / BNORM
- END IF
-*
-* Compute X
-*
- CALL DLADIV( SCALE*B( 1, 1 ), SCALE*B( 1, 2 ), CSR, CSI,
- $ X( 1, 1 ), X( 1, 2 ) )
- XNORM = ABS( X( 1, 1 ) ) + ABS( X( 1, 2 ) )
- END IF
-*
- ELSE
-*
-* 2x2 System
-*
-* Compute the real part of C = ca A - w D (or ca A' - w D )
-*
- CR( 1, 1 ) = CA*A( 1, 1 ) - WR*D1
- CR( 2, 2 ) = CA*A( 2, 2 ) - WR*D2
- IF( LTRANS ) THEN
- CR( 1, 2 ) = CA*A( 2, 1 )
- CR( 2, 1 ) = CA*A( 1, 2 )
- ELSE
- CR( 2, 1 ) = CA*A( 2, 1 )
- CR( 1, 2 ) = CA*A( 1, 2 )
- END IF
-*
- IF( NW.EQ.1 ) THEN
-*
-* Real 2x2 system (w is real)
-*
-* Find the largest element in C
-*
- CMAX = ZERO
- ICMAX = 0
-*
- DO 10 J = 1, 4
- IF( ABS( CRV( J ) ).GT.CMAX ) THEN
- CMAX = ABS( CRV( J ) )
- ICMAX = J
- END IF
- 10 CONTINUE
-*
-* If norm(C) < SMINI, use SMINI*identity.
-*
- IF( CMAX.LT.SMINI ) THEN
- BNORM = MAX( ABS( B( 1, 1 ) ), ABS( B( 2, 1 ) ) )
- IF( SMINI.LT.ONE .AND. BNORM.GT.ONE ) THEN
- IF( BNORM.GT.BIGNUM*SMINI )
- $ SCALE = ONE / BNORM
- END IF
- TEMP = SCALE / SMINI
- X( 1, 1 ) = TEMP*B( 1, 1 )
- X( 2, 1 ) = TEMP*B( 2, 1 )
- XNORM = TEMP*BNORM
- INFO = 1
- RETURN
- END IF
-*
-* Gaussian elimination with complete pivoting.
-*
- UR11 = CRV( ICMAX )
- CR21 = CRV( IPIVOT( 2, ICMAX ) )
- UR12 = CRV( IPIVOT( 3, ICMAX ) )
- CR22 = CRV( IPIVOT( 4, ICMAX ) )
- UR11R = ONE / UR11
- LR21 = UR11R*CR21
- UR22 = CR22 - UR12*LR21
-*
-* If smaller pivot < SMINI, use SMINI
-*
- IF( ABS( UR22 ).LT.SMINI ) THEN
- UR22 = SMINI
- INFO = 1
- END IF
- IF( RSWAP( ICMAX ) ) THEN
- BR1 = B( 2, 1 )
- BR2 = B( 1, 1 )
- ELSE
- BR1 = B( 1, 1 )
- BR2 = B( 2, 1 )
- END IF
- BR2 = BR2 - LR21*BR1
- BBND = MAX( ABS( BR1*( UR22*UR11R ) ), ABS( BR2 ) )
- IF( BBND.GT.ONE .AND. ABS( UR22 ).LT.ONE ) THEN
- IF( BBND.GE.BIGNUM*ABS( UR22 ) )
- $ SCALE = ONE / BBND
- END IF
-*
- XR2 = ( BR2*SCALE ) / UR22
- XR1 = ( SCALE*BR1 )*UR11R - XR2*( UR11R*UR12 )
- IF( ZSWAP( ICMAX ) ) THEN
- X( 1, 1 ) = XR2
- X( 2, 1 ) = XR1
- ELSE
- X( 1, 1 ) = XR1
- X( 2, 1 ) = XR2
- END IF
- XNORM = MAX( ABS( XR1 ), ABS( XR2 ) )
-*
-* Further scaling if norm(A) norm(X) > overflow
-*
- IF( XNORM.GT.ONE .AND. CMAX.GT.ONE ) THEN
- IF( XNORM.GT.BIGNUM / CMAX ) THEN
- TEMP = CMAX / BIGNUM
- X( 1, 1 ) = TEMP*X( 1, 1 )
- X( 2, 1 ) = TEMP*X( 2, 1 )
- XNORM = TEMP*XNORM
- SCALE = TEMP*SCALE
- END IF
- END IF
- ELSE
-*
-* Complex 2x2 system (w is complex)
-*
-* Find the largest element in C
-*
- CI( 1, 1 ) = -WI*D1
- CI( 2, 1 ) = ZERO
- CI( 1, 2 ) = ZERO
- CI( 2, 2 ) = -WI*D2
- CMAX = ZERO
- ICMAX = 0
-*
- DO 20 J = 1, 4
- IF( ABS( CRV( J ) )+ABS( CIV( J ) ).GT.CMAX ) THEN
- CMAX = ABS( CRV( J ) ) + ABS( CIV( J ) )
- ICMAX = J
- END IF
- 20 CONTINUE
-*
-* If norm(C) < SMINI, use SMINI*identity.
-*
- IF( CMAX.LT.SMINI ) THEN
- BNORM = MAX( ABS( B( 1, 1 ) )+ABS( B( 1, 2 ) ),
- $ ABS( B( 2, 1 ) )+ABS( B( 2, 2 ) ) )
- IF( SMINI.LT.ONE .AND. BNORM.GT.ONE ) THEN
- IF( BNORM.GT.BIGNUM*SMINI )
- $ SCALE = ONE / BNORM
- END IF
- TEMP = SCALE / SMINI
- X( 1, 1 ) = TEMP*B( 1, 1 )
- X( 2, 1 ) = TEMP*B( 2, 1 )
- X( 1, 2 ) = TEMP*B( 1, 2 )
- X( 2, 2 ) = TEMP*B( 2, 2 )
- XNORM = TEMP*BNORM
- INFO = 1
- RETURN
- END IF
-*
-* Gaussian elimination with complete pivoting.
-*
- UR11 = CRV( ICMAX )
- UI11 = CIV( ICMAX )
- CR21 = CRV( IPIVOT( 2, ICMAX ) )
- CI21 = CIV( IPIVOT( 2, ICMAX ) )
- UR12 = CRV( IPIVOT( 3, ICMAX ) )
- UI12 = CIV( IPIVOT( 3, ICMAX ) )
- CR22 = CRV( IPIVOT( 4, ICMAX ) )
- CI22 = CIV( IPIVOT( 4, ICMAX ) )
- IF( ICMAX.EQ.1 .OR. ICMAX.EQ.4 ) THEN
-*
-* Code when off-diagonals of pivoted C are real
-*
- IF( ABS( UR11 ).GT.ABS( UI11 ) ) THEN
- TEMP = UI11 / UR11
- UR11R = ONE / ( UR11*( ONE+TEMP**2 ) )
- UI11R = -TEMP*UR11R
- ELSE
- TEMP = UR11 / UI11
- UI11R = -ONE / ( UI11*( ONE+TEMP**2 ) )
- UR11R = -TEMP*UI11R
- END IF
- LR21 = CR21*UR11R
- LI21 = CR21*UI11R
- UR12S = UR12*UR11R
- UI12S = UR12*UI11R
- UR22 = CR22 - UR12*LR21
- UI22 = CI22 - UR12*LI21
- ELSE
-*
-* Code when diagonals of pivoted C are real
-*
- UR11R = ONE / UR11
- UI11R = ZERO
- LR21 = CR21*UR11R
- LI21 = CI21*UR11R
- UR12S = UR12*UR11R
- UI12S = UI12*UR11R
- UR22 = CR22 - UR12*LR21 + UI12*LI21
- UI22 = -UR12*LI21 - UI12*LR21
- END IF
- U22ABS = ABS( UR22 ) + ABS( UI22 )
-*
-* If smaller pivot < SMINI, use SMINI
-*
- IF( U22ABS.LT.SMINI ) THEN
- UR22 = SMINI
- UI22 = ZERO
- INFO = 1
- END IF
- IF( RSWAP( ICMAX ) ) THEN
- BR2 = B( 1, 1 )
- BR1 = B( 2, 1 )
- BI2 = B( 1, 2 )
- BI1 = B( 2, 2 )
- ELSE
- BR1 = B( 1, 1 )
- BR2 = B( 2, 1 )
- BI1 = B( 1, 2 )
- BI2 = B( 2, 2 )
- END IF
- BR2 = BR2 - LR21*BR1 + LI21*BI1
- BI2 = BI2 - LI21*BR1 - LR21*BI1
- BBND = MAX( ( ABS( BR1 )+ABS( BI1 ) )*
- $ ( U22ABS*( ABS( UR11R )+ABS( UI11R ) ) ),
- $ ABS( BR2 )+ABS( BI2 ) )
- IF( BBND.GT.ONE .AND. U22ABS.LT.ONE ) THEN
- IF( BBND.GE.BIGNUM*U22ABS ) THEN
- SCALE = ONE / BBND
- BR1 = SCALE*BR1
- BI1 = SCALE*BI1
- BR2 = SCALE*BR2
- BI2 = SCALE*BI2
- END IF
- END IF
-*
- CALL DLADIV( BR2, BI2, UR22, UI22, XR2, XI2 )
- XR1 = UR11R*BR1 - UI11R*BI1 - UR12S*XR2 + UI12S*XI2
- XI1 = UI11R*BR1 + UR11R*BI1 - UI12S*XR2 - UR12S*XI2
- IF( ZSWAP( ICMAX ) ) THEN
- X( 1, 1 ) = XR2
- X( 2, 1 ) = XR1
- X( 1, 2 ) = XI2
- X( 2, 2 ) = XI1
- ELSE
- X( 1, 1 ) = XR1
- X( 2, 1 ) = XR2
- X( 1, 2 ) = XI1
- X( 2, 2 ) = XI2
- END IF
- XNORM = MAX( ABS( XR1 )+ABS( XI1 ), ABS( XR2 )+ABS( XI2 ) )
-*
-* Further scaling if norm(A) norm(X) > overflow
-*
- IF( XNORM.GT.ONE .AND. CMAX.GT.ONE ) THEN
- IF( XNORM.GT.BIGNUM / CMAX ) THEN
- TEMP = CMAX / BIGNUM
- X( 1, 1 ) = TEMP*X( 1, 1 )
- X( 2, 1 ) = TEMP*X( 2, 1 )
- X( 1, 2 ) = TEMP*X( 1, 2 )
- X( 2, 2 ) = TEMP*X( 2, 2 )
- XNORM = TEMP*XNORM
- SCALE = TEMP*SCALE
- END IF
- END IF
- END IF
- END IF
-*
- RETURN
-*
-* End of DLALN2
-*
- END
diff --git a/src/lib/lapack/dlamch.f b/src/lib/lapack/dlamch.f
deleted file mode 100644
index 64ac3bec..00000000
--- a/src/lib/lapack/dlamch.f
+++ /dev/null
@@ -1,857 +0,0 @@
- DOUBLE PRECISION FUNCTION DLAMCH( CMACH )
-*
-* -- LAPACK auxiliary routine (version 3.0) --
-* Univ. of Tennessee, Univ. of California Berkeley, NAG Ltd.,
-* Courant Institute, Argonne National Lab, and Rice University
-* October 31, 1992
-*
-* .. Scalar Arguments ..
- CHARACTER CMACH
-* ..
-*
-* Purpose
-* =======
-*
-* DLAMCH determines double precision machine parameters.
-*
-* Arguments
-* =========
-*
-* CMACH (input) CHARACTER*1
-* Specifies the value to be returned by DLAMCH:
-* = 'E' or 'e', DLAMCH := eps
-* = 'S' or 's , DLAMCH := sfmin
-* = 'B' or 'b', DLAMCH := base
-* = 'P' or 'p', DLAMCH := eps*base
-* = 'N' or 'n', DLAMCH := t
-* = 'R' or 'r', DLAMCH := rnd
-* = 'M' or 'm', DLAMCH := emin
-* = 'U' or 'u', DLAMCH := rmin
-* = 'L' or 'l', DLAMCH := emax
-* = 'O' or 'o', DLAMCH := rmax
-*
-* where
-*
-* eps = relative machine precision
-* sfmin = safe minimum, such that 1/sfmin does not overflow
-* base = base of the machine
-* prec = eps*base
-* t = number of (base) digits in the mantissa
-* rnd = 1.0 when rounding occurs in addition, 0.0 otherwise
-* emin = minimum exponent before (gradual) underflow
-* rmin = underflow threshold - base**(emin-1)
-* emax = largest exponent before overflow
-* rmax = overflow threshold - (base**emax)*(1-eps)
-*
-* =====================================================================
-*
-* .. Parameters ..
- DOUBLE PRECISION ONE, ZERO
- PARAMETER ( ONE = 1.0D+0, ZERO = 0.0D+0 )
-* ..
-* .. Local Scalars ..
- LOGICAL FIRST, LRND
- INTEGER BETA, IMAX, IMIN, IT
- DOUBLE PRECISION BASE, EMAX, EMIN, EPS, PREC, RMACH, RMAX, RMIN,
- $ RND, SFMIN, SMALL, T
-* ..
-* .. External Functions ..
- LOGICAL LSAME
- EXTERNAL LSAME
-* ..
-* .. External Subroutines ..
- EXTERNAL DLAMC2
-* ..
-* .. Save statement ..
- SAVE FIRST, EPS, SFMIN, BASE, T, RND, EMIN, RMIN,
- $ EMAX, RMAX, PREC
-* ..
-* .. Data statements ..
- DATA FIRST / .TRUE. /
-* ..
-* .. Executable Statements ..
-*
- IF( FIRST ) THEN
- FIRST = .FALSE.
- CALL DLAMC2( BETA, IT, LRND, EPS, IMIN, RMIN, IMAX, RMAX )
- BASE = BETA
- T = IT
- IF( LRND ) THEN
- RND = ONE
- EPS = ( BASE**( 1-IT ) ) / 2
- ELSE
- RND = ZERO
- EPS = BASE**( 1-IT )
- END IF
- PREC = EPS*BASE
- EMIN = IMIN
- EMAX = IMAX
- SFMIN = RMIN
- SMALL = ONE / RMAX
- IF( SMALL.GE.SFMIN ) THEN
-*
-* Use SMALL plus a bit, to avoid the possibility of rounding
-* causing overflow when computing 1/sfmin.
-*
- SFMIN = SMALL*( ONE+EPS )
- END IF
- END IF
-*
- IF( LSAME( CMACH, 'E' ) ) THEN
- RMACH = EPS
- ELSE IF( LSAME( CMACH, 'S' ) ) THEN
- RMACH = SFMIN
- ELSE IF( LSAME( CMACH, 'B' ) ) THEN
- RMACH = BASE
- ELSE IF( LSAME( CMACH, 'P' ) ) THEN
- RMACH = PREC
- ELSE IF( LSAME( CMACH, 'N' ) ) THEN
- RMACH = T
- ELSE IF( LSAME( CMACH, 'R' ) ) THEN
- RMACH = RND
- ELSE IF( LSAME( CMACH, 'M' ) ) THEN
- RMACH = EMIN
- ELSE IF( LSAME( CMACH, 'U' ) ) THEN
- RMACH = RMIN
- ELSE IF( LSAME( CMACH, 'L' ) ) THEN
- RMACH = EMAX
- ELSE IF( LSAME( CMACH, 'O' ) ) THEN
- RMACH = RMAX
- END IF
-*
- DLAMCH = RMACH
- RETURN
-*
-* End of DLAMCH
-*
- END
-*
-************************************************************************
-*
- SUBROUTINE DLAMC1( BETA, T, RND, IEEE1 )
-*
-* -- LAPACK auxiliary routine (version 3.0) --
-* Univ. of Tennessee, Univ. of California Berkeley, NAG Ltd.,
-* Courant Institute, Argonne National Lab, and Rice University
-* October 31, 1992
-*
-* .. Scalar Arguments ..
- LOGICAL IEEE1, RND
- INTEGER BETA, T
-* ..
-*
-* Purpose
-* =======
-*
-* DLAMC1 determines the machine parameters given by BETA, T, RND, and
-* IEEE1.
-*
-* Arguments
-* =========
-*
-* BETA (output) INTEGER
-* The base of the machine.
-*
-* T (output) INTEGER
-* The number of ( BETA ) digits in the mantissa.
-*
-* RND (output) LOGICAL
-* Specifies whether proper rounding ( RND = .TRUE. ) or
-* chopping ( RND = .FALSE. ) occurs in addition. This may not
-* be a reliable guide to the way in which the machine performs
-* its arithmetic.
-*
-* IEEE1 (output) LOGICAL
-* Specifies whether rounding appears to be done in the IEEE
-* 'round to nearest' style.
-*
-* Further Details
-* ===============
-*
-* The routine is based on the routine ENVRON by Malcolm and
-* incorporates suggestions by Gentleman and Marovich. See
-*
-* Malcolm M. A. (1972) Algorithms to reveal properties of
-* floating-point arithmetic. Comms. of the ACM, 15, 949-951.
-*
-* Gentleman W. M. and Marovich S. B. (1974) More on algorithms
-* that reveal properties of floating point arithmetic units.
-* Comms. of the ACM, 17, 276-277.
-*
-* =====================================================================
-*
-* .. Local Scalars ..
- LOGICAL FIRST, LIEEE1, LRND
- INTEGER LBETA, LT
- DOUBLE PRECISION A, B, C, F, ONE, QTR, SAVEC, T1, T2
-* ..
-* .. External Functions ..
- DOUBLE PRECISION DLAMC3
- EXTERNAL DLAMC3
-* ..
-* .. Save statement ..
- SAVE FIRST, LIEEE1, LBETA, LRND, LT
-* ..
-* .. Data statements ..
- DATA FIRST / .TRUE. /
-* ..
-* .. Executable Statements ..
-*
- IF( FIRST ) THEN
- FIRST = .FALSE.
- ONE = 1
-*
-* LBETA, LIEEE1, LT and LRND are the local values of BETA,
-* IEEE1, T and RND.
-*
-* Throughout this routine we use the function DLAMC3 to ensure
-* that relevant values are stored and not held in registers, or
-* are not affected by optimizers.
-*
-* Compute a = 2.0**m with the smallest positive integer m such
-* that
-*
-* fl( a + 1.0 ) = a.
-*
- A = 1
- C = 1
-*
-*+ WHILE( C.EQ.ONE )LOOP
- 10 CONTINUE
- IF( C.EQ.ONE ) THEN
- A = 2*A
- C = DLAMC3( A, ONE )
- C = DLAMC3( C, -A )
- GO TO 10
- END IF
-*+ END WHILE
-*
-* Now compute b = 2.0**m with the smallest positive integer m
-* such that
-*
-* fl( a + b ) .gt. a.
-*
- B = 1
- C = DLAMC3( A, B )
-*
-*+ WHILE( C.EQ.A )LOOP
- 20 CONTINUE
- IF( C.EQ.A ) THEN
- B = 2*B
- C = DLAMC3( A, B )
- GO TO 20
- END IF
-*+ END WHILE
-*
-* Now compute the base. a and c are neighbouring floating point
-* numbers in the interval ( beta**t, beta**( t + 1 ) ) and so
-* their difference is beta. Adding 0.25 to c is to ensure that it
-* is truncated to beta and not ( beta - 1 ).
-*
- QTR = ONE / 4
- SAVEC = C
- C = DLAMC3( C, -A )
- LBETA = C + QTR
-*
-* Now determine whether rounding or chopping occurs, by adding a
-* bit less than beta/2 and a bit more than beta/2 to a.
-*
- B = LBETA
- F = DLAMC3( B / 2, -B / 100 )
- C = DLAMC3( F, A )
- IF( C.EQ.A ) THEN
- LRND = .TRUE.
- ELSE
- LRND = .FALSE.
- END IF
- F = DLAMC3( B / 2, B / 100 )
- C = DLAMC3( F, A )
- IF( ( LRND ) .AND. ( C.EQ.A ) )
- $ LRND = .FALSE.
-*
-* Try and decide whether rounding is done in the IEEE 'round to
-* nearest' style. B/2 is half a unit in the last place of the two
-* numbers A and SAVEC. Furthermore, A is even, i.e. has last bit
-* zero, and SAVEC is odd. Thus adding B/2 to A should not change
-* A, but adding B/2 to SAVEC should change SAVEC.
-*
- T1 = DLAMC3( B / 2, A )
- T2 = DLAMC3( B / 2, SAVEC )
- LIEEE1 = ( T1.EQ.A ) .AND. ( T2.GT.SAVEC ) .AND. LRND
-*
-* Now find the mantissa, t. It should be the integer part of
-* log to the base beta of a, however it is safer to determine t
-* by powering. So we find t as the smallest positive integer for
-* which
-*
-* fl( beta**t + 1.0 ) = 1.0.
-*
- LT = 0
- A = 1
- C = 1
-*
-*+ WHILE( C.EQ.ONE )LOOP
- 30 CONTINUE
- IF( C.EQ.ONE ) THEN
- LT = LT + 1
- A = A*LBETA
- C = DLAMC3( A, ONE )
- C = DLAMC3( C, -A )
- GO TO 30
- END IF
-*+ END WHILE
-*
- END IF
-*
- BETA = LBETA
- T = LT
- RND = LRND
- IEEE1 = LIEEE1
- RETURN
-*
-* End of DLAMC1
-*
- END
-*
-************************************************************************
-*
- SUBROUTINE DLAMC2( BETA, T, RND, EPS, EMIN, RMIN, EMAX, RMAX )
-*
-* -- LAPACK auxiliary routine (version 3.0) --
-* Univ. of Tennessee, Univ. of California Berkeley, NAG Ltd.,
-* Courant Institute, Argonne National Lab, and Rice University
-* October 31, 1992
-*
-* .. Scalar Arguments ..
- LOGICAL RND
- INTEGER BETA, EMAX, EMIN, T
- DOUBLE PRECISION EPS, RMAX, RMIN
-* ..
-*
-* Purpose
-* =======
-*
-* DLAMC2 determines the machine parameters specified in its argument
-* list.
-*
-* Arguments
-* =========
-*
-* BETA (output) INTEGER
-* The base of the machine.
-*
-* T (output) INTEGER
-* The number of ( BETA ) digits in the mantissa.
-*
-* RND (output) LOGICAL
-* Specifies whether proper rounding ( RND = .TRUE. ) or
-* chopping ( RND = .FALSE. ) occurs in addition. This may not
-* be a reliable guide to the way in which the machine performs
-* its arithmetic.
-*
-* EPS (output) DOUBLE PRECISION
-* The smallest positive number such that
-*
-* fl( 1.0 - EPS ) .LT. 1.0,
-*
-* where fl denotes the computed value.
-*
-* EMIN (output) INTEGER
-* The minimum exponent before (gradual) underflow occurs.
-*
-* RMIN (output) DOUBLE PRECISION
-* The smallest normalized number for the machine, given by
-* BASE**( EMIN - 1 ), where BASE is the floating point value
-* of BETA.
-*
-* EMAX (output) INTEGER
-* The maximum exponent before overflow occurs.
-*
-* RMAX (output) DOUBLE PRECISION
-* The largest positive number for the machine, given by
-* BASE**EMAX * ( 1 - EPS ), where BASE is the floating point
-* value of BETA.
-*
-* Further Details
-* ===============
-*
-* The computation of EPS is based on a routine PARANOIA by
-* W. Kahan of the University of California at Berkeley.
-*
-* =====================================================================
-*
-* .. Local Scalars ..
- LOGICAL FIRST, IEEE, IWARN, LIEEE1, LRND
- INTEGER GNMIN, GPMIN, I, LBETA, LEMAX, LEMIN, LT,
- $ NGNMIN, NGPMIN
- DOUBLE PRECISION A, B, C, HALF, LEPS, LRMAX, LRMIN, ONE, RBASE,
- $ SIXTH, SMALL, THIRD, TWO, ZERO
-* ..
-* .. External Functions ..
- DOUBLE PRECISION DLAMC3
- EXTERNAL DLAMC3
-* ..
-* .. External Subroutines ..
- EXTERNAL DLAMC1, DLAMC4, DLAMC5
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC ABS, MAX, MIN
-* ..
-* .. Save statement ..
- SAVE FIRST, IWARN, LBETA, LEMAX, LEMIN, LEPS, LRMAX,
- $ LRMIN, LT
-* ..
-* .. Data statements ..
- DATA FIRST / .TRUE. / , IWARN / .FALSE. /
-* ..
-* .. Executable Statements ..
-*
- IF( FIRST ) THEN
- FIRST = .FALSE.
- ZERO = 0
- ONE = 1
- TWO = 2
-*
-* LBETA, LT, LRND, LEPS, LEMIN and LRMIN are the local values of
-* BETA, T, RND, EPS, EMIN and RMIN.
-*
-* Throughout this routine we use the function DLAMC3 to ensure
-* that relevant values are stored and not held in registers, or
-* are not affected by optimizers.
-*
-* DLAMC1 returns the parameters LBETA, LT, LRND and LIEEE1.
-*
- CALL DLAMC1( LBETA, LT, LRND, LIEEE1 )
-*
-* Start to find EPS.
-*
- B = LBETA
- A = B**( -LT )
- LEPS = A
-*
-* Try some tricks to see whether or not this is the correct EPS.
-*
- B = TWO / 3
- HALF = ONE / 2
- SIXTH = DLAMC3( B, -HALF )
- THIRD = DLAMC3( SIXTH, SIXTH )
- B = DLAMC3( THIRD, -HALF )
- B = DLAMC3( B, SIXTH )
- B = ABS( B )
- IF( B.LT.LEPS )
- $ B = LEPS
-*
- LEPS = 1
-*
-*+ WHILE( ( LEPS.GT.B ).AND.( B.GT.ZERO ) )LOOP
- 10 CONTINUE
- IF( ( LEPS.GT.B ) .AND. ( B.GT.ZERO ) ) THEN
- LEPS = B
- C = DLAMC3( HALF*LEPS, ( TWO**5 )*( LEPS**2 ) )
- C = DLAMC3( HALF, -C )
- B = DLAMC3( HALF, C )
- C = DLAMC3( HALF, -B )
- B = DLAMC3( HALF, C )
- GO TO 10
- END IF
-*+ END WHILE
-*
- IF( A.LT.LEPS )
- $ LEPS = A
-*
-* Computation of EPS complete.
-*
-* Now find EMIN. Let A = + or - 1, and + or - (1 + BASE**(-3)).
-* Keep dividing A by BETA until (gradual) underflow occurs. This
-* is detected when we cannot recover the previous A.
-*
- RBASE = ONE / LBETA
- SMALL = ONE
- DO 20 I = 1, 3
- SMALL = DLAMC3( SMALL*RBASE, ZERO )
- 20 CONTINUE
- A = DLAMC3( ONE, SMALL )
- CALL DLAMC4( NGPMIN, ONE, LBETA )
- CALL DLAMC4( NGNMIN, -ONE, LBETA )
- CALL DLAMC4( GPMIN, A, LBETA )
- CALL DLAMC4( GNMIN, -A, LBETA )
- IEEE = .FALSE.
-*
- IF( ( NGPMIN.EQ.NGNMIN ) .AND. ( GPMIN.EQ.GNMIN ) ) THEN
- IF( NGPMIN.EQ.GPMIN ) THEN
- LEMIN = NGPMIN
-* ( Non twos-complement machines, no gradual underflow;
-* e.g., VAX )
- ELSE IF( ( GPMIN-NGPMIN ).EQ.3 ) THEN
- LEMIN = NGPMIN - 1 + LT
- IEEE = .TRUE.
-* ( Non twos-complement machines, with gradual underflow;
-* e.g., IEEE standard followers )
- ELSE
- LEMIN = MIN( NGPMIN, GPMIN )
-* ( A guess; no known machine )
- IWARN = .TRUE.
- END IF
-*
- ELSE IF( ( NGPMIN.EQ.GPMIN ) .AND. ( NGNMIN.EQ.GNMIN ) ) THEN
- IF( ABS( NGPMIN-NGNMIN ).EQ.1 ) THEN
- LEMIN = MAX( NGPMIN, NGNMIN )
-* ( Twos-complement machines, no gradual underflow;
-* e.g., CYBER 205 )
- ELSE
- LEMIN = MIN( NGPMIN, NGNMIN )
-* ( A guess; no known machine )
- IWARN = .TRUE.
- END IF
-*
- ELSE IF( ( ABS( NGPMIN-NGNMIN ).EQ.1 ) .AND.
- $ ( GPMIN.EQ.GNMIN ) ) THEN
- IF( ( GPMIN-MIN( NGPMIN, NGNMIN ) ).EQ.3 ) THEN
- LEMIN = MAX( NGPMIN, NGNMIN ) - 1 + LT
-* ( Twos-complement machines with gradual underflow;
-* no known machine )
- ELSE
- LEMIN = MIN( NGPMIN, NGNMIN )
-* ( A guess; no known machine )
- IWARN = .TRUE.
- END IF
-*
- ELSE
- LEMIN = MIN( NGPMIN, NGNMIN, GPMIN, GNMIN )
-* ( A guess; no known machine )
- IWARN = .TRUE.
- END IF
-***
-* Comment out this if block if EMIN is ok
- IF( IWARN ) THEN
- FIRST = .TRUE.
- WRITE( 6, FMT = 9999 )LEMIN
- END IF
-***
-*
-* Assume IEEE arithmetic if we found denormalised numbers above,
-* or if arithmetic seems to round in the IEEE style, determined
-* in routine DLAMC1. A true IEEE machine should have both things
-* true; however, faulty machines may have one or the other.
-*
- IEEE = IEEE .OR. LIEEE1
-*
-* Compute RMIN by successive division by BETA. We could compute
-* RMIN as BASE**( EMIN - 1 ), but some machines underflow during
-* this computation.
-*
- LRMIN = 1
- DO 30 I = 1, 1 - LEMIN
- LRMIN = DLAMC3( LRMIN*RBASE, ZERO )
- 30 CONTINUE
-*
-* Finally, call DLAMC5 to compute EMAX and RMAX.
-*
- CALL DLAMC5( LBETA, LT, LEMIN, IEEE, LEMAX, LRMAX )
- END IF
-*
- BETA = LBETA
- T = LT
- RND = LRND
- EPS = LEPS
- EMIN = LEMIN
- RMIN = LRMIN
- EMAX = LEMAX
- RMAX = LRMAX
-*
- RETURN
-*
- 9999 FORMAT( / / ' WARNING. The value EMIN may be incorrect:-',
- $ ' EMIN = ', I8, /
- $ ' If, after inspection, the value EMIN looks',
- $ ' acceptable please comment out ',
- $ / ' the IF block as marked within the code of routine',
- $ ' DLAMC2,', / ' otherwise supply EMIN explicitly.', / )
-*
-* End of DLAMC2
-*
- END
-*
-************************************************************************
-*
- DOUBLE PRECISION FUNCTION DLAMC3( A, B )
-*
-* -- LAPACK auxiliary routine (version 3.0) --
-* Univ. of Tennessee, Univ. of California Berkeley, NAG Ltd.,
-* Courant Institute, Argonne National Lab, and Rice University
-* October 31, 1992
-*
-* .. Scalar Arguments ..
- DOUBLE PRECISION A, B
-* ..
-*
-* Purpose
-* =======
-*
-* DLAMC3 is intended to force A and B to be stored prior to doing
-* the addition of A and B , for use in situations where optimizers
-* might hold one of these in a register.
-*
-* Arguments
-* =========
-*
-* A, B (input) DOUBLE PRECISION
-* The values A and B.
-*
-* =====================================================================
-*
-* .. Executable Statements ..
-*
- DLAMC3 = A + B
-*
- RETURN
-*
-* End of DLAMC3
-*
- END
-*
-************************************************************************
-*
- SUBROUTINE DLAMC4( EMIN, START, BASE )
-*
-* -- LAPACK auxiliary routine (version 3.0) --
-* Univ. of Tennessee, Univ. of California Berkeley, NAG Ltd.,
-* Courant Institute, Argonne National Lab, and Rice University
-* October 31, 1992
-*
-* .. Scalar Arguments ..
- INTEGER BASE, EMIN
- DOUBLE PRECISION START
-* ..
-*
-* Purpose
-* =======
-*
-* DLAMC4 is a service routine for DLAMC2.
-*
-* Arguments
-* =========
-*
-* EMIN (output) EMIN
-* The minimum exponent before (gradual) underflow, computed by
-* setting A = START and dividing by BASE until the previous A
-* can not be recovered.
-*
-* START (input) DOUBLE PRECISION
-* The starting point for determining EMIN.
-*
-* BASE (input) INTEGER
-* The base of the machine.
-*
-* =====================================================================
-*
-* .. Local Scalars ..
- INTEGER I
- DOUBLE PRECISION A, B1, B2, C1, C2, D1, D2, ONE, RBASE, ZERO
-* ..
-* .. External Functions ..
- DOUBLE PRECISION DLAMC3
- EXTERNAL DLAMC3
-* ..
-* .. Executable Statements ..
-*
- A = START
- ONE = 1
- RBASE = ONE / BASE
- ZERO = 0
- EMIN = 1
- B1 = DLAMC3( A*RBASE, ZERO )
- C1 = A
- C2 = A
- D1 = A
- D2 = A
-*+ WHILE( ( C1.EQ.A ).AND.( C2.EQ.A ).AND.
-* $ ( D1.EQ.A ).AND.( D2.EQ.A ) )LOOP
- 10 CONTINUE
- IF( ( C1.EQ.A ) .AND. ( C2.EQ.A ) .AND. ( D1.EQ.A ) .AND.
- $ ( D2.EQ.A ) ) THEN
- EMIN = EMIN - 1
- A = B1
- B1 = DLAMC3( A / BASE, ZERO )
- C1 = DLAMC3( B1*BASE, ZERO )
- D1 = ZERO
- DO 20 I = 1, BASE
- D1 = D1 + B1
- 20 CONTINUE
- B2 = DLAMC3( A*RBASE, ZERO )
- C2 = DLAMC3( B2 / RBASE, ZERO )
- D2 = ZERO
- DO 30 I = 1, BASE
- D2 = D2 + B2
- 30 CONTINUE
- GO TO 10
- END IF
-*+ END WHILE
-*
- RETURN
-*
-* End of DLAMC4
-*
- END
-*
-************************************************************************
-*
- SUBROUTINE DLAMC5( BETA, P, EMIN, IEEE, EMAX, RMAX )
-*
-* -- LAPACK auxiliary routine (version 3.0) --
-* Univ. of Tennessee, Univ. of California Berkeley, NAG Ltd.,
-* Courant Institute, Argonne National Lab, and Rice University
-* October 31, 1992
-*
-* .. Scalar Arguments ..
- LOGICAL IEEE
- INTEGER BETA, EMAX, EMIN, P
- DOUBLE PRECISION RMAX
-* ..
-*
-* Purpose
-* =======
-*
-* DLAMC5 attempts to compute RMAX, the largest machine floating-point
-* number, without overflow. It assumes that EMAX + abs(EMIN) sum
-* approximately to a power of 2. It will fail on machines where this
-* assumption does not hold, for example, the Cyber 205 (EMIN = -28625,
-* EMAX = 28718). It will also fail if the value supplied for EMIN is
-* too large (i.e. too close to zero), probably with overflow.
-*
-* Arguments
-* =========
-*
-* BETA (input) INTEGER
-* The base of floating-point arithmetic.
-*
-* P (input) INTEGER
-* The number of base BETA digits in the mantissa of a
-* floating-point value.
-*
-* EMIN (input) INTEGER
-* The minimum exponent before (gradual) underflow.
-*
-* IEEE (input) LOGICAL
-* A logical flag specifying whether or not the arithmetic
-* system is thought to comply with the IEEE standard.
-*
-* EMAX (output) INTEGER
-* The largest exponent before overflow
-*
-* RMAX (output) DOUBLE PRECISION
-* The largest machine floating-point number.
-*
-* =====================================================================
-*
-* .. Parameters ..
- DOUBLE PRECISION ZERO, ONE
- PARAMETER ( ZERO = 0.0D0, ONE = 1.0D0 )
-* ..
-* .. Local Scalars ..
- INTEGER EXBITS, EXPSUM, I, LEXP, NBITS, TRY, UEXP
- DOUBLE PRECISION OLDY, RECBAS, Y, Z
-* ..
-* .. External Functions ..
- DOUBLE PRECISION DLAMC3
- EXTERNAL DLAMC3
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC MOD
-* ..
-* .. Executable Statements ..
-*
-* First compute LEXP and UEXP, two powers of 2 that bound
-* abs(EMIN). We then assume that EMAX + abs(EMIN) will sum
-* approximately to the bound that is closest to abs(EMIN).
-* (EMAX is the exponent of the required number RMAX).
-*
- LEXP = 1
- EXBITS = 1
- 10 CONTINUE
- TRY = LEXP*2
- IF( TRY.LE.( -EMIN ) ) THEN
- LEXP = TRY
- EXBITS = EXBITS + 1
- GO TO 10
- END IF
- IF( LEXP.EQ.-EMIN ) THEN
- UEXP = LEXP
- ELSE
- UEXP = TRY
- EXBITS = EXBITS + 1
- END IF
-*
-* Now -LEXP is less than or equal to EMIN, and -UEXP is greater
-* than or equal to EMIN. EXBITS is the number of bits needed to
-* store the exponent.
-*
- IF( ( UEXP+EMIN ).GT.( -LEXP-EMIN ) ) THEN
- EXPSUM = 2*LEXP
- ELSE
- EXPSUM = 2*UEXP
- END IF
-*
-* EXPSUM is the exponent range, approximately equal to
-* EMAX - EMIN + 1 .
-*
- EMAX = EXPSUM + EMIN - 1
- NBITS = 1 + EXBITS + P
-*
-* NBITS is the total number of bits needed to store a
-* floating-point number.
-*
- IF( ( MOD( NBITS, 2 ).EQ.1 ) .AND. ( BETA.EQ.2 ) ) THEN
-*
-* Either there are an odd number of bits used to store a
-* floating-point number, which is unlikely, or some bits are
-* not used in the representation of numbers, which is possible,
-* (e.g. Cray machines) or the mantissa has an implicit bit,
-* (e.g. IEEE machines, Dec Vax machines), which is perhaps the
-* most likely. We have to assume the last alternative.
-* If this is true, then we need to reduce EMAX by one because
-* there must be some way of representing zero in an implicit-bit
-* system. On machines like Cray, we are reducing EMAX by one
-* unnecessarily.
-*
- EMAX = EMAX - 1
- END IF
-*
- IF( IEEE ) THEN
-*
-* Assume we are on an IEEE machine which reserves one exponent
-* for infinity and NaN.
-*
- EMAX = EMAX - 1
- END IF
-*
-* Now create RMAX, the largest machine number, which should
-* be equal to (1.0 - BETA**(-P)) * BETA**EMAX .
-*
-* First compute 1.0 - BETA**(-P), being careful that the
-* result is less than 1.0 .
-*
- RECBAS = ONE / BETA
- Z = BETA - ONE
- Y = ZERO
- DO 20 I = 1, P
- Z = Z*RECBAS
- IF( Y.LT.ONE )
- $ OLDY = Y
- Y = DLAMC3( Y, Z )
- 20 CONTINUE
- IF( Y.GE.ONE )
- $ Y = OLDY
-*
-* Now multiply by BETA**EMAX to get RMAX.
-*
- DO 30 I = 1, EMAX
- Y = DLAMC3( Y*BETA, ZERO )
- 30 CONTINUE
-*
- RMAX = Y
- RETURN
-*
-* End of DLAMC5
-*
- END
diff --git a/src/lib/lapack/dlange.f b/src/lib/lapack/dlange.f
deleted file mode 100644
index fec96ac7..00000000
--- a/src/lib/lapack/dlange.f
+++ /dev/null
@@ -1,144 +0,0 @@
- DOUBLE PRECISION FUNCTION DLANGE( NORM, M, N, A, LDA, WORK )
-*
-* -- LAPACK auxiliary routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- CHARACTER NORM
- INTEGER LDA, M, N
-* ..
-* .. Array Arguments ..
- DOUBLE PRECISION A( LDA, * ), WORK( * )
-* ..
-*
-* Purpose
-* =======
-*
-* DLANGE returns the value of the one norm, or the Frobenius norm, or
-* the infinity norm, or the element of largest absolute value of a
-* real matrix A.
-*
-* Description
-* ===========
-*
-* DLANGE returns the value
-*
-* DLANGE = ( max(abs(A(i,j))), NORM = 'M' or 'm'
-* (
-* ( norm1(A), NORM = '1', 'O' or 'o'
-* (
-* ( normI(A), NORM = 'I' or 'i'
-* (
-* ( normF(A), NORM = 'F', 'f', 'E' or 'e'
-*
-* where norm1 denotes the one norm of a matrix (maximum column sum),
-* normI denotes the infinity norm of a matrix (maximum row sum) and
-* normF denotes the Frobenius norm of a matrix (square root of sum of
-* squares). Note that max(abs(A(i,j))) is not a consistent matrix norm.
-*
-* Arguments
-* =========
-*
-* NORM (input) CHARACTER*1
-* Specifies the value to be returned in DLANGE as described
-* above.
-*
-* M (input) INTEGER
-* The number of rows of the matrix A. M >= 0. When M = 0,
-* DLANGE is set to zero.
-*
-* N (input) INTEGER
-* The number of columns of the matrix A. N >= 0. When N = 0,
-* DLANGE is set to zero.
-*
-* A (input) DOUBLE PRECISION array, dimension (LDA,N)
-* The m by n matrix A.
-*
-* LDA (input) INTEGER
-* The leading dimension of the array A. LDA >= max(M,1).
-*
-* WORK (workspace) DOUBLE PRECISION array, dimension (MAX(1,LWORK)),
-* where LWORK >= M when NORM = 'I'; otherwise, WORK is not
-* referenced.
-*
-* =====================================================================
-*
-* .. Parameters ..
- DOUBLE PRECISION ONE, ZERO
- PARAMETER ( ONE = 1.0D+0, ZERO = 0.0D+0 )
-* ..
-* .. Local Scalars ..
- INTEGER I, J
- DOUBLE PRECISION SCALE, SUM, VALUE
-* ..
-* .. External Subroutines ..
- EXTERNAL DLASSQ
-* ..
-* .. External Functions ..
- LOGICAL LSAME
- EXTERNAL LSAME
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC ABS, MAX, MIN, SQRT
-* ..
-* .. Executable Statements ..
-*
- IF( MIN( M, N ).EQ.0 ) THEN
- VALUE = ZERO
- ELSE IF( LSAME( NORM, 'M' ) ) THEN
-*
-* Find max(abs(A(i,j))).
-*
- VALUE = ZERO
- DO 20 J = 1, N
- DO 10 I = 1, M
- VALUE = MAX( VALUE, ABS( A( I, J ) ) )
- 10 CONTINUE
- 20 CONTINUE
- ELSE IF( ( LSAME( NORM, 'O' ) ) .OR. ( NORM.EQ.'1' ) ) THEN
-*
-* Find norm1(A).
-*
- VALUE = ZERO
- DO 40 J = 1, N
- SUM = ZERO
- DO 30 I = 1, M
- SUM = SUM + ABS( A( I, J ) )
- 30 CONTINUE
- VALUE = MAX( VALUE, SUM )
- 40 CONTINUE
- ELSE IF( LSAME( NORM, 'I' ) ) THEN
-*
-* Find normI(A).
-*
- DO 50 I = 1, M
- WORK( I ) = ZERO
- 50 CONTINUE
- DO 70 J = 1, N
- DO 60 I = 1, M
- WORK( I ) = WORK( I ) + ABS( A( I, J ) )
- 60 CONTINUE
- 70 CONTINUE
- VALUE = ZERO
- DO 80 I = 1, M
- VALUE = MAX( VALUE, WORK( I ) )
- 80 CONTINUE
- ELSE IF( ( LSAME( NORM, 'F' ) ) .OR. ( LSAME( NORM, 'E' ) ) ) THEN
-*
-* Find normF(A).
-*
- SCALE = ZERO
- SUM = ONE
- DO 90 J = 1, N
- CALL DLASSQ( M, A( 1, J ), 1, SCALE, SUM )
- 90 CONTINUE
- VALUE = SCALE*SQRT( SUM )
- END IF
-*
- DLANGE = VALUE
- RETURN
-*
-* End of DLANGE
-*
- END
diff --git a/src/lib/lapack/dlanhs.f b/src/lib/lapack/dlanhs.f
deleted file mode 100644
index 76b87eeb..00000000
--- a/src/lib/lapack/dlanhs.f
+++ /dev/null
@@ -1,141 +0,0 @@
- DOUBLE PRECISION FUNCTION DLANHS( NORM, N, A, LDA, WORK )
-*
-* -- LAPACK auxiliary routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- CHARACTER NORM
- INTEGER LDA, N
-* ..
-* .. Array Arguments ..
- DOUBLE PRECISION A( LDA, * ), WORK( * )
-* ..
-*
-* Purpose
-* =======
-*
-* DLANHS returns the value of the one norm, or the Frobenius norm, or
-* the infinity norm, or the element of largest absolute value of a
-* Hessenberg matrix A.
-*
-* Description
-* ===========
-*
-* DLANHS returns the value
-*
-* DLANHS = ( max(abs(A(i,j))), NORM = 'M' or 'm'
-* (
-* ( norm1(A), NORM = '1', 'O' or 'o'
-* (
-* ( normI(A), NORM = 'I' or 'i'
-* (
-* ( normF(A), NORM = 'F', 'f', 'E' or 'e'
-*
-* where norm1 denotes the one norm of a matrix (maximum column sum),
-* normI denotes the infinity norm of a matrix (maximum row sum) and
-* normF denotes the Frobenius norm of a matrix (square root of sum of
-* squares). Note that max(abs(A(i,j))) is not a consistent matrix norm.
-*
-* Arguments
-* =========
-*
-* NORM (input) CHARACTER*1
-* Specifies the value to be returned in DLANHS as described
-* above.
-*
-* N (input) INTEGER
-* The order of the matrix A. N >= 0. When N = 0, DLANHS is
-* set to zero.
-*
-* A (input) DOUBLE PRECISION array, dimension (LDA,N)
-* The n by n upper Hessenberg matrix A; the part of A below the
-* first sub-diagonal is not referenced.
-*
-* LDA (input) INTEGER
-* The leading dimension of the array A. LDA >= max(N,1).
-*
-* WORK (workspace) DOUBLE PRECISION array, dimension (MAX(1,LWORK)),
-* where LWORK >= N when NORM = 'I'; otherwise, WORK is not
-* referenced.
-*
-* =====================================================================
-*
-* .. Parameters ..
- DOUBLE PRECISION ONE, ZERO
- PARAMETER ( ONE = 1.0D+0, ZERO = 0.0D+0 )
-* ..
-* .. Local Scalars ..
- INTEGER I, J
- DOUBLE PRECISION SCALE, SUM, VALUE
-* ..
-* .. External Subroutines ..
- EXTERNAL DLASSQ
-* ..
-* .. External Functions ..
- LOGICAL LSAME
- EXTERNAL LSAME
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC ABS, MAX, MIN, SQRT
-* ..
-* .. Executable Statements ..
-*
- IF( N.EQ.0 ) THEN
- VALUE = ZERO
- ELSE IF( LSAME( NORM, 'M' ) ) THEN
-*
-* Find max(abs(A(i,j))).
-*
- VALUE = ZERO
- DO 20 J = 1, N
- DO 10 I = 1, MIN( N, J+1 )
- VALUE = MAX( VALUE, ABS( A( I, J ) ) )
- 10 CONTINUE
- 20 CONTINUE
- ELSE IF( ( LSAME( NORM, 'O' ) ) .OR. ( NORM.EQ.'1' ) ) THEN
-*
-* Find norm1(A).
-*
- VALUE = ZERO
- DO 40 J = 1, N
- SUM = ZERO
- DO 30 I = 1, MIN( N, J+1 )
- SUM = SUM + ABS( A( I, J ) )
- 30 CONTINUE
- VALUE = MAX( VALUE, SUM )
- 40 CONTINUE
- ELSE IF( LSAME( NORM, 'I' ) ) THEN
-*
-* Find normI(A).
-*
- DO 50 I = 1, N
- WORK( I ) = ZERO
- 50 CONTINUE
- DO 70 J = 1, N
- DO 60 I = 1, MIN( N, J+1 )
- WORK( I ) = WORK( I ) + ABS( A( I, J ) )
- 60 CONTINUE
- 70 CONTINUE
- VALUE = ZERO
- DO 80 I = 1, N
- VALUE = MAX( VALUE, WORK( I ) )
- 80 CONTINUE
- ELSE IF( ( LSAME( NORM, 'F' ) ) .OR. ( LSAME( NORM, 'E' ) ) ) THEN
-*
-* Find normF(A).
-*
- SCALE = ZERO
- SUM = ONE
- DO 90 J = 1, N
- CALL DLASSQ( MIN( N, J+1 ), A( 1, J ), 1, SCALE, SUM )
- 90 CONTINUE
- VALUE = SCALE*SQRT( SUM )
- END IF
-*
- DLANHS = VALUE
- RETURN
-*
-* End of DLANHS
-*
- END
diff --git a/src/lib/lapack/dlansp.f b/src/lib/lapack/dlansp.f
deleted file mode 100644
index ab221006..00000000
--- a/src/lib/lapack/dlansp.f
+++ /dev/null
@@ -1,196 +0,0 @@
- DOUBLE PRECISION FUNCTION DLANSP( NORM, UPLO, N, AP, WORK )
-*
-* -- LAPACK auxiliary routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- CHARACTER NORM, UPLO
- INTEGER N
-* ..
-* .. Array Arguments ..
- DOUBLE PRECISION AP( * ), WORK( * )
-* ..
-*
-* Purpose
-* =======
-*
-* DLANSP returns the value of the one norm, or the Frobenius norm, or
-* the infinity norm, or the element of largest absolute value of a
-* real symmetric matrix A, supplied in packed form.
-*
-* Description
-* ===========
-*
-* DLANSP returns the value
-*
-* DLANSP = ( max(abs(A(i,j))), NORM = 'M' or 'm'
-* (
-* ( norm1(A), NORM = '1', 'O' or 'o'
-* (
-* ( normI(A), NORM = 'I' or 'i'
-* (
-* ( normF(A), NORM = 'F', 'f', 'E' or 'e'
-*
-* where norm1 denotes the one norm of a matrix (maximum column sum),
-* normI denotes the infinity norm of a matrix (maximum row sum) and
-* normF denotes the Frobenius norm of a matrix (square root of sum of
-* squares). Note that max(abs(A(i,j))) is not a consistent matrix norm.
-*
-* Arguments
-* =========
-*
-* NORM (input) CHARACTER*1
-* Specifies the value to be returned in DLANSP as described
-* above.
-*
-* UPLO (input) CHARACTER*1
-* Specifies whether the upper or lower triangular part of the
-* symmetric matrix A is supplied.
-* = 'U': Upper triangular part of A is supplied
-* = 'L': Lower triangular part of A is supplied
-*
-* N (input) INTEGER
-* The order of the matrix A. N >= 0. When N = 0, DLANSP is
-* set to zero.
-*
-* AP (input) DOUBLE PRECISION array, dimension (N*(N+1)/2)
-* The upper or lower triangle of the symmetric matrix A, packed
-* columnwise in a linear array. The j-th column of A is stored
-* in the array AP as follows:
-* if UPLO = 'U', AP(i + (j-1)*j/2) = A(i,j) for 1<=i<=j;
-* if UPLO = 'L', AP(i + (j-1)*(2n-j)/2) = A(i,j) for j<=i<=n.
-*
-* WORK (workspace) DOUBLE PRECISION array, dimension (MAX(1,LWORK)),
-* where LWORK >= N when NORM = 'I' or '1' or 'O'; otherwise,
-* WORK is not referenced.
-*
-* =====================================================================
-*
-* .. Parameters ..
- DOUBLE PRECISION ONE, ZERO
- PARAMETER ( ONE = 1.0D+0, ZERO = 0.0D+0 )
-* ..
-* .. Local Scalars ..
- INTEGER I, J, K
- DOUBLE PRECISION ABSA, SCALE, SUM, VALUE
-* ..
-* .. External Subroutines ..
- EXTERNAL DLASSQ
-* ..
-* .. External Functions ..
- LOGICAL LSAME
- EXTERNAL LSAME
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC ABS, MAX, SQRT
-* ..
-* .. Executable Statements ..
-*
- IF( N.EQ.0 ) THEN
- VALUE = ZERO
- ELSE IF( LSAME( NORM, 'M' ) ) THEN
-*
-* Find max(abs(A(i,j))).
-*
- VALUE = ZERO
- IF( LSAME( UPLO, 'U' ) ) THEN
- K = 1
- DO 20 J = 1, N
- DO 10 I = K, K + J - 1
- VALUE = MAX( VALUE, ABS( AP( I ) ) )
- 10 CONTINUE
- K = K + J
- 20 CONTINUE
- ELSE
- K = 1
- DO 40 J = 1, N
- DO 30 I = K, K + N - J
- VALUE = MAX( VALUE, ABS( AP( I ) ) )
- 30 CONTINUE
- K = K + N - J + 1
- 40 CONTINUE
- END IF
- ELSE IF( ( LSAME( NORM, 'I' ) ) .OR. ( LSAME( NORM, 'O' ) ) .OR.
- $ ( NORM.EQ.'1' ) ) THEN
-*
-* Find normI(A) ( = norm1(A), since A is symmetric).
-*
- VALUE = ZERO
- K = 1
- IF( LSAME( UPLO, 'U' ) ) THEN
- DO 60 J = 1, N
- SUM = ZERO
- DO 50 I = 1, J - 1
- ABSA = ABS( AP( K ) )
- SUM = SUM + ABSA
- WORK( I ) = WORK( I ) + ABSA
- K = K + 1
- 50 CONTINUE
- WORK( J ) = SUM + ABS( AP( K ) )
- K = K + 1
- 60 CONTINUE
- DO 70 I = 1, N
- VALUE = MAX( VALUE, WORK( I ) )
- 70 CONTINUE
- ELSE
- DO 80 I = 1, N
- WORK( I ) = ZERO
- 80 CONTINUE
- DO 100 J = 1, N
- SUM = WORK( J ) + ABS( AP( K ) )
- K = K + 1
- DO 90 I = J + 1, N
- ABSA = ABS( AP( K ) )
- SUM = SUM + ABSA
- WORK( I ) = WORK( I ) + ABSA
- K = K + 1
- 90 CONTINUE
- VALUE = MAX( VALUE, SUM )
- 100 CONTINUE
- END IF
- ELSE IF( ( LSAME( NORM, 'F' ) ) .OR. ( LSAME( NORM, 'E' ) ) ) THEN
-*
-* Find normF(A).
-*
- SCALE = ZERO
- SUM = ONE
- K = 2
- IF( LSAME( UPLO, 'U' ) ) THEN
- DO 110 J = 2, N
- CALL DLASSQ( J-1, AP( K ), 1, SCALE, SUM )
- K = K + J
- 110 CONTINUE
- ELSE
- DO 120 J = 1, N - 1
- CALL DLASSQ( N-J, AP( K ), 1, SCALE, SUM )
- K = K + N - J + 1
- 120 CONTINUE
- END IF
- SUM = 2*SUM
- K = 1
- DO 130 I = 1, N
- IF( AP( K ).NE.ZERO ) THEN
- ABSA = ABS( AP( K ) )
- IF( SCALE.LT.ABSA ) THEN
- SUM = ONE + SUM*( SCALE / ABSA )**2
- SCALE = ABSA
- ELSE
- SUM = SUM + ( ABSA / SCALE )**2
- END IF
- END IF
- IF( LSAME( UPLO, 'U' ) ) THEN
- K = K + I + 1
- ELSE
- K = K + N - I + 1
- END IF
- 130 CONTINUE
- VALUE = SCALE*SQRT( SUM )
- END IF
-*
- DLANSP = VALUE
- RETURN
-*
-* End of DLANSP
-*
- END
diff --git a/src/lib/lapack/dlanst.f b/src/lib/lapack/dlanst.f
deleted file mode 100644
index 2b12091a..00000000
--- a/src/lib/lapack/dlanst.f
+++ /dev/null
@@ -1,124 +0,0 @@
- DOUBLE PRECISION FUNCTION DLANST( NORM, N, D, E )
-*
-* -- LAPACK auxiliary routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- CHARACTER NORM
- INTEGER N
-* ..
-* .. Array Arguments ..
- DOUBLE PRECISION D( * ), E( * )
-* ..
-*
-* Purpose
-* =======
-*
-* DLANST returns the value of the one norm, or the Frobenius norm, or
-* the infinity norm, or the element of largest absolute value of a
-* real symmetric tridiagonal matrix A.
-*
-* Description
-* ===========
-*
-* DLANST returns the value
-*
-* DLANST = ( max(abs(A(i,j))), NORM = 'M' or 'm'
-* (
-* ( norm1(A), NORM = '1', 'O' or 'o'
-* (
-* ( normI(A), NORM = 'I' or 'i'
-* (
-* ( normF(A), NORM = 'F', 'f', 'E' or 'e'
-*
-* where norm1 denotes the one norm of a matrix (maximum column sum),
-* normI denotes the infinity norm of a matrix (maximum row sum) and
-* normF denotes the Frobenius norm of a matrix (square root of sum of
-* squares). Note that max(abs(A(i,j))) is not a consistent matrix norm.
-*
-* Arguments
-* =========
-*
-* NORM (input) CHARACTER*1
-* Specifies the value to be returned in DLANST as described
-* above.
-*
-* N (input) INTEGER
-* The order of the matrix A. N >= 0. When N = 0, DLANST is
-* set to zero.
-*
-* D (input) DOUBLE PRECISION array, dimension (N)
-* The diagonal elements of A.
-*
-* E (input) DOUBLE PRECISION array, dimension (N-1)
-* The (n-1) sub-diagonal or super-diagonal elements of A.
-*
-* =====================================================================
-*
-* .. Parameters ..
- DOUBLE PRECISION ONE, ZERO
- PARAMETER ( ONE = 1.0D+0, ZERO = 0.0D+0 )
-* ..
-* .. Local Scalars ..
- INTEGER I
- DOUBLE PRECISION ANORM, SCALE, SUM
-* ..
-* .. External Functions ..
- LOGICAL LSAME
- EXTERNAL LSAME
-* ..
-* .. External Subroutines ..
- EXTERNAL DLASSQ
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC ABS, MAX, SQRT
-* ..
-* .. Executable Statements ..
-*
- IF( N.LE.0 ) THEN
- ANORM = ZERO
- ELSE IF( LSAME( NORM, 'M' ) ) THEN
-*
-* Find max(abs(A(i,j))).
-*
- ANORM = ABS( D( N ) )
- DO 10 I = 1, N - 1
- ANORM = MAX( ANORM, ABS( D( I ) ) )
- ANORM = MAX( ANORM, ABS( E( I ) ) )
- 10 CONTINUE
- ELSE IF( LSAME( NORM, 'O' ) .OR. NORM.EQ.'1' .OR.
- $ LSAME( NORM, 'I' ) ) THEN
-*
-* Find norm1(A).
-*
- IF( N.EQ.1 ) THEN
- ANORM = ABS( D( 1 ) )
- ELSE
- ANORM = MAX( ABS( D( 1 ) )+ABS( E( 1 ) ),
- $ ABS( E( N-1 ) )+ABS( D( N ) ) )
- DO 20 I = 2, N - 1
- ANORM = MAX( ANORM, ABS( D( I ) )+ABS( E( I ) )+
- $ ABS( E( I-1 ) ) )
- 20 CONTINUE
- END IF
- ELSE IF( ( LSAME( NORM, 'F' ) ) .OR. ( LSAME( NORM, 'E' ) ) ) THEN
-*
-* Find normF(A).
-*
- SCALE = ZERO
- SUM = ONE
- IF( N.GT.1 ) THEN
- CALL DLASSQ( N-1, E, 1, SCALE, SUM )
- SUM = 2*SUM
- END IF
- CALL DLASSQ( N, D, 1, SCALE, SUM )
- ANORM = SCALE*SQRT( SUM )
- END IF
-*
- DLANST = ANORM
- RETURN
-*
-* End of DLANST
-*
- END
diff --git a/src/lib/lapack/dlansy.f b/src/lib/lapack/dlansy.f
deleted file mode 100644
index b6c727c0..00000000
--- a/src/lib/lapack/dlansy.f
+++ /dev/null
@@ -1,173 +0,0 @@
- DOUBLE PRECISION FUNCTION DLANSY( NORM, UPLO, N, A, LDA, WORK )
-*
-* -- LAPACK auxiliary routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- CHARACTER NORM, UPLO
- INTEGER LDA, N
-* ..
-* .. Array Arguments ..
- DOUBLE PRECISION A( LDA, * ), WORK( * )
-* ..
-*
-* Purpose
-* =======
-*
-* DLANSY returns the value of the one norm, or the Frobenius norm, or
-* the infinity norm, or the element of largest absolute value of a
-* real symmetric matrix A.
-*
-* Description
-* ===========
-*
-* DLANSY returns the value
-*
-* DLANSY = ( max(abs(A(i,j))), NORM = 'M' or 'm'
-* (
-* ( norm1(A), NORM = '1', 'O' or 'o'
-* (
-* ( normI(A), NORM = 'I' or 'i'
-* (
-* ( normF(A), NORM = 'F', 'f', 'E' or 'e'
-*
-* where norm1 denotes the one norm of a matrix (maximum column sum),
-* normI denotes the infinity norm of a matrix (maximum row sum) and
-* normF denotes the Frobenius norm of a matrix (square root of sum of
-* squares). Note that max(abs(A(i,j))) is not a consistent matrix norm.
-*
-* Arguments
-* =========
-*
-* NORM (input) CHARACTER*1
-* Specifies the value to be returned in DLANSY as described
-* above.
-*
-* UPLO (input) CHARACTER*1
-* Specifies whether the upper or lower triangular part of the
-* symmetric matrix A is to be referenced.
-* = 'U': Upper triangular part of A is referenced
-* = 'L': Lower triangular part of A is referenced
-*
-* N (input) INTEGER
-* The order of the matrix A. N >= 0. When N = 0, DLANSY is
-* set to zero.
-*
-* A (input) DOUBLE PRECISION array, dimension (LDA,N)
-* The symmetric matrix A. If UPLO = 'U', the leading n by n
-* upper triangular part of A contains the upper triangular part
-* of the matrix A, and the strictly lower triangular part of A
-* is not referenced. If UPLO = 'L', the leading n by n lower
-* triangular part of A contains the lower triangular part of
-* the matrix A, and the strictly upper triangular part of A is
-* not referenced.
-*
-* LDA (input) INTEGER
-* The leading dimension of the array A. LDA >= max(N,1).
-*
-* WORK (workspace) DOUBLE PRECISION array, dimension (MAX(1,LWORK)),
-* where LWORK >= N when NORM = 'I' or '1' or 'O'; otherwise,
-* WORK is not referenced.
-*
-* =====================================================================
-*
-* .. Parameters ..
- DOUBLE PRECISION ONE, ZERO
- PARAMETER ( ONE = 1.0D+0, ZERO = 0.0D+0 )
-* ..
-* .. Local Scalars ..
- INTEGER I, J
- DOUBLE PRECISION ABSA, SCALE, SUM, VALUE
-* ..
-* .. External Subroutines ..
- EXTERNAL DLASSQ
-* ..
-* .. External Functions ..
- LOGICAL LSAME
- EXTERNAL LSAME
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC ABS, MAX, SQRT
-* ..
-* .. Executable Statements ..
-*
- IF( N.EQ.0 ) THEN
- VALUE = ZERO
- ELSE IF( LSAME( NORM, 'M' ) ) THEN
-*
-* Find max(abs(A(i,j))).
-*
- VALUE = ZERO
- IF( LSAME( UPLO, 'U' ) ) THEN
- DO 20 J = 1, N
- DO 10 I = 1, J
- VALUE = MAX( VALUE, ABS( A( I, J ) ) )
- 10 CONTINUE
- 20 CONTINUE
- ELSE
- DO 40 J = 1, N
- DO 30 I = J, N
- VALUE = MAX( VALUE, ABS( A( I, J ) ) )
- 30 CONTINUE
- 40 CONTINUE
- END IF
- ELSE IF( ( LSAME( NORM, 'I' ) ) .OR. ( LSAME( NORM, 'O' ) ) .OR.
- $ ( NORM.EQ.'1' ) ) THEN
-*
-* Find normI(A) ( = norm1(A), since A is symmetric).
-*
- VALUE = ZERO
- IF( LSAME( UPLO, 'U' ) ) THEN
- DO 60 J = 1, N
- SUM = ZERO
- DO 50 I = 1, J - 1
- ABSA = ABS( A( I, J ) )
- SUM = SUM + ABSA
- WORK( I ) = WORK( I ) + ABSA
- 50 CONTINUE
- WORK( J ) = SUM + ABS( A( J, J ) )
- 60 CONTINUE
- DO 70 I = 1, N
- VALUE = MAX( VALUE, WORK( I ) )
- 70 CONTINUE
- ELSE
- DO 80 I = 1, N
- WORK( I ) = ZERO
- 80 CONTINUE
- DO 100 J = 1, N
- SUM = WORK( J ) + ABS( A( J, J ) )
- DO 90 I = J + 1, N
- ABSA = ABS( A( I, J ) )
- SUM = SUM + ABSA
- WORK( I ) = WORK( I ) + ABSA
- 90 CONTINUE
- VALUE = MAX( VALUE, SUM )
- 100 CONTINUE
- END IF
- ELSE IF( ( LSAME( NORM, 'F' ) ) .OR. ( LSAME( NORM, 'E' ) ) ) THEN
-*
-* Find normF(A).
-*
- SCALE = ZERO
- SUM = ONE
- IF( LSAME( UPLO, 'U' ) ) THEN
- DO 110 J = 2, N
- CALL DLASSQ( J-1, A( 1, J ), 1, SCALE, SUM )
- 110 CONTINUE
- ELSE
- DO 120 J = 1, N - 1
- CALL DLASSQ( N-J, A( J+1, J ), 1, SCALE, SUM )
- 120 CONTINUE
- END IF
- SUM = 2*SUM
- CALL DLASSQ( N, A, LDA+1, SCALE, SUM )
- VALUE = SCALE*SQRT( SUM )
- END IF
-*
- DLANSY = VALUE
- RETURN
-*
-* End of DLANSY
-*
- END
diff --git a/src/lib/lapack/dlantr.f b/src/lib/lapack/dlantr.f
deleted file mode 100644
index 92debd3d..00000000
--- a/src/lib/lapack/dlantr.f
+++ /dev/null
@@ -1,276 +0,0 @@
- DOUBLE PRECISION FUNCTION DLANTR( NORM, UPLO, DIAG, M, N, A, LDA,
- $ WORK )
-*
-* -- LAPACK auxiliary routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- CHARACTER DIAG, NORM, UPLO
- INTEGER LDA, M, N
-* ..
-* .. Array Arguments ..
- DOUBLE PRECISION A( LDA, * ), WORK( * )
-* ..
-*
-* Purpose
-* =======
-*
-* DLANTR returns the value of the one norm, or the Frobenius norm, or
-* the infinity norm, or the element of largest absolute value of a
-* trapezoidal or triangular matrix A.
-*
-* Description
-* ===========
-*
-* DLANTR returns the value
-*
-* DLANTR = ( max(abs(A(i,j))), NORM = 'M' or 'm'
-* (
-* ( norm1(A), NORM = '1', 'O' or 'o'
-* (
-* ( normI(A), NORM = 'I' or 'i'
-* (
-* ( normF(A), NORM = 'F', 'f', 'E' or 'e'
-*
-* where norm1 denotes the one norm of a matrix (maximum column sum),
-* normI denotes the infinity norm of a matrix (maximum row sum) and
-* normF denotes the Frobenius norm of a matrix (square root of sum of
-* squares). Note that max(abs(A(i,j))) is not a consistent matrix norm.
-*
-* Arguments
-* =========
-*
-* NORM (input) CHARACTER*1
-* Specifies the value to be returned in DLANTR as described
-* above.
-*
-* UPLO (input) CHARACTER*1
-* Specifies whether the matrix A is upper or lower trapezoidal.
-* = 'U': Upper trapezoidal
-* = 'L': Lower trapezoidal
-* Note that A is triangular instead of trapezoidal if M = N.
-*
-* DIAG (input) CHARACTER*1
-* Specifies whether or not the matrix A has unit diagonal.
-* = 'N': Non-unit diagonal
-* = 'U': Unit diagonal
-*
-* M (input) INTEGER
-* The number of rows of the matrix A. M >= 0, and if
-* UPLO = 'U', M <= N. When M = 0, DLANTR is set to zero.
-*
-* N (input) INTEGER
-* The number of columns of the matrix A. N >= 0, and if
-* UPLO = 'L', N <= M. When N = 0, DLANTR is set to zero.
-*
-* A (input) DOUBLE PRECISION array, dimension (LDA,N)
-* The trapezoidal matrix A (A is triangular if M = N).
-* If UPLO = 'U', the leading m by n upper trapezoidal part of
-* the array A contains the upper trapezoidal matrix, and the
-* strictly lower triangular part of A is not referenced.
-* If UPLO = 'L', the leading m by n lower trapezoidal part of
-* the array A contains the lower trapezoidal matrix, and the
-* strictly upper triangular part of A is not referenced. Note
-* that when DIAG = 'U', the diagonal elements of A are not
-* referenced and are assumed to be one.
-*
-* LDA (input) INTEGER
-* The leading dimension of the array A. LDA >= max(M,1).
-*
-* WORK (workspace) DOUBLE PRECISION array, dimension (MAX(1,LWORK)),
-* where LWORK >= M when NORM = 'I'; otherwise, WORK is not
-* referenced.
-*
-* =====================================================================
-*
-* .. Parameters ..
- DOUBLE PRECISION ONE, ZERO
- PARAMETER ( ONE = 1.0D+0, ZERO = 0.0D+0 )
-* ..
-* .. Local Scalars ..
- LOGICAL UDIAG
- INTEGER I, J
- DOUBLE PRECISION SCALE, SUM, VALUE
-* ..
-* .. External Subroutines ..
- EXTERNAL DLASSQ
-* ..
-* .. External Functions ..
- LOGICAL LSAME
- EXTERNAL LSAME
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC ABS, MAX, MIN, SQRT
-* ..
-* .. Executable Statements ..
-*
- IF( MIN( M, N ).EQ.0 ) THEN
- VALUE = ZERO
- ELSE IF( LSAME( NORM, 'M' ) ) THEN
-*
-* Find max(abs(A(i,j))).
-*
- IF( LSAME( DIAG, 'U' ) ) THEN
- VALUE = ONE
- IF( LSAME( UPLO, 'U' ) ) THEN
- DO 20 J = 1, N
- DO 10 I = 1, MIN( M, J-1 )
- VALUE = MAX( VALUE, ABS( A( I, J ) ) )
- 10 CONTINUE
- 20 CONTINUE
- ELSE
- DO 40 J = 1, N
- DO 30 I = J + 1, M
- VALUE = MAX( VALUE, ABS( A( I, J ) ) )
- 30 CONTINUE
- 40 CONTINUE
- END IF
- ELSE
- VALUE = ZERO
- IF( LSAME( UPLO, 'U' ) ) THEN
- DO 60 J = 1, N
- DO 50 I = 1, MIN( M, J )
- VALUE = MAX( VALUE, ABS( A( I, J ) ) )
- 50 CONTINUE
- 60 CONTINUE
- ELSE
- DO 80 J = 1, N
- DO 70 I = J, M
- VALUE = MAX( VALUE, ABS( A( I, J ) ) )
- 70 CONTINUE
- 80 CONTINUE
- END IF
- END IF
- ELSE IF( ( LSAME( NORM, 'O' ) ) .OR. ( NORM.EQ.'1' ) ) THEN
-*
-* Find norm1(A).
-*
- VALUE = ZERO
- UDIAG = LSAME( DIAG, 'U' )
- IF( LSAME( UPLO, 'U' ) ) THEN
- DO 110 J = 1, N
- IF( ( UDIAG ) .AND. ( J.LE.M ) ) THEN
- SUM = ONE
- DO 90 I = 1, J - 1
- SUM = SUM + ABS( A( I, J ) )
- 90 CONTINUE
- ELSE
- SUM = ZERO
- DO 100 I = 1, MIN( M, J )
- SUM = SUM + ABS( A( I, J ) )
- 100 CONTINUE
- END IF
- VALUE = MAX( VALUE, SUM )
- 110 CONTINUE
- ELSE
- DO 140 J = 1, N
- IF( UDIAG ) THEN
- SUM = ONE
- DO 120 I = J + 1, M
- SUM = SUM + ABS( A( I, J ) )
- 120 CONTINUE
- ELSE
- SUM = ZERO
- DO 130 I = J, M
- SUM = SUM + ABS( A( I, J ) )
- 130 CONTINUE
- END IF
- VALUE = MAX( VALUE, SUM )
- 140 CONTINUE
- END IF
- ELSE IF( LSAME( NORM, 'I' ) ) THEN
-*
-* Find normI(A).
-*
- IF( LSAME( UPLO, 'U' ) ) THEN
- IF( LSAME( DIAG, 'U' ) ) THEN
- DO 150 I = 1, M
- WORK( I ) = ONE
- 150 CONTINUE
- DO 170 J = 1, N
- DO 160 I = 1, MIN( M, J-1 )
- WORK( I ) = WORK( I ) + ABS( A( I, J ) )
- 160 CONTINUE
- 170 CONTINUE
- ELSE
- DO 180 I = 1, M
- WORK( I ) = ZERO
- 180 CONTINUE
- DO 200 J = 1, N
- DO 190 I = 1, MIN( M, J )
- WORK( I ) = WORK( I ) + ABS( A( I, J ) )
- 190 CONTINUE
- 200 CONTINUE
- END IF
- ELSE
- IF( LSAME( DIAG, 'U' ) ) THEN
- DO 210 I = 1, N
- WORK( I ) = ONE
- 210 CONTINUE
- DO 220 I = N + 1, M
- WORK( I ) = ZERO
- 220 CONTINUE
- DO 240 J = 1, N
- DO 230 I = J + 1, M
- WORK( I ) = WORK( I ) + ABS( A( I, J ) )
- 230 CONTINUE
- 240 CONTINUE
- ELSE
- DO 250 I = 1, M
- WORK( I ) = ZERO
- 250 CONTINUE
- DO 270 J = 1, N
- DO 260 I = J, M
- WORK( I ) = WORK( I ) + ABS( A( I, J ) )
- 260 CONTINUE
- 270 CONTINUE
- END IF
- END IF
- VALUE = ZERO
- DO 280 I = 1, M
- VALUE = MAX( VALUE, WORK( I ) )
- 280 CONTINUE
- ELSE IF( ( LSAME( NORM, 'F' ) ) .OR. ( LSAME( NORM, 'E' ) ) ) THEN
-*
-* Find normF(A).
-*
- IF( LSAME( UPLO, 'U' ) ) THEN
- IF( LSAME( DIAG, 'U' ) ) THEN
- SCALE = ONE
- SUM = MIN( M, N )
- DO 290 J = 2, N
- CALL DLASSQ( MIN( M, J-1 ), A( 1, J ), 1, SCALE, SUM )
- 290 CONTINUE
- ELSE
- SCALE = ZERO
- SUM = ONE
- DO 300 J = 1, N
- CALL DLASSQ( MIN( M, J ), A( 1, J ), 1, SCALE, SUM )
- 300 CONTINUE
- END IF
- ELSE
- IF( LSAME( DIAG, 'U' ) ) THEN
- SCALE = ONE
- SUM = MIN( M, N )
- DO 310 J = 1, N
- CALL DLASSQ( M-J, A( MIN( M, J+1 ), J ), 1, SCALE,
- $ SUM )
- 310 CONTINUE
- ELSE
- SCALE = ZERO
- SUM = ONE
- DO 320 J = 1, N
- CALL DLASSQ( M-J+1, A( J, J ), 1, SCALE, SUM )
- 320 CONTINUE
- END IF
- END IF
- VALUE = SCALE*SQRT( SUM )
- END IF
-*
- DLANTR = VALUE
- RETURN
-*
-* End of DLANTR
-*
- END
diff --git a/src/lib/lapack/dlanv2.f b/src/lib/lapack/dlanv2.f
deleted file mode 100644
index cef3f472..00000000
--- a/src/lib/lapack/dlanv2.f
+++ /dev/null
@@ -1,205 +0,0 @@
- SUBROUTINE DLANV2( A, B, C, D, RT1R, RT1I, RT2R, RT2I, CS, SN )
-*
-* -- LAPACK driver routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- DOUBLE PRECISION A, B, C, CS, D, RT1I, RT1R, RT2I, RT2R, SN
-* ..
-*
-* Purpose
-* =======
-*
-* DLANV2 computes the Schur factorization of a real 2-by-2 nonsymmetric
-* matrix in standard form:
-*
-* [ A B ] = [ CS -SN ] [ AA BB ] [ CS SN ]
-* [ C D ] [ SN CS ] [ CC DD ] [-SN CS ]
-*
-* where either
-* 1) CC = 0 so that AA and DD are real eigenvalues of the matrix, or
-* 2) AA = DD and BB*CC < 0, so that AA + or - sqrt(BB*CC) are complex
-* conjugate eigenvalues.
-*
-* Arguments
-* =========
-*
-* A (input/output) DOUBLE PRECISION
-* B (input/output) DOUBLE PRECISION
-* C (input/output) DOUBLE PRECISION
-* D (input/output) DOUBLE PRECISION
-* On entry, the elements of the input matrix.
-* On exit, they are overwritten by the elements of the
-* standardised Schur form.
-*
-* RT1R (output) DOUBLE PRECISION
-* RT1I (output) DOUBLE PRECISION
-* RT2R (output) DOUBLE PRECISION
-* RT2I (output) DOUBLE PRECISION
-* The real and imaginary parts of the eigenvalues. If the
-* eigenvalues are a complex conjugate pair, RT1I > 0.
-*
-* CS (output) DOUBLE PRECISION
-* SN (output) DOUBLE PRECISION
-* Parameters of the rotation matrix.
-*
-* Further Details
-* ===============
-*
-* Modified by V. Sima, Research Institute for Informatics, Bucharest,
-* Romania, to reduce the risk of cancellation errors,
-* when computing real eigenvalues, and to ensure, if possible, that
-* abs(RT1R) >= abs(RT2R).
-*
-* =====================================================================
-*
-* .. Parameters ..
- DOUBLE PRECISION ZERO, HALF, ONE
- PARAMETER ( ZERO = 0.0D+0, HALF = 0.5D+0, ONE = 1.0D+0 )
- DOUBLE PRECISION MULTPL
- PARAMETER ( MULTPL = 4.0D+0 )
-* ..
-* .. Local Scalars ..
- DOUBLE PRECISION AA, BB, BCMAX, BCMIS, CC, CS1, DD, EPS, P, SAB,
- $ SAC, SCALE, SIGMA, SN1, TAU, TEMP, Z
-* ..
-* .. External Functions ..
- DOUBLE PRECISION DLAMCH, DLAPY2
- EXTERNAL DLAMCH, DLAPY2
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC ABS, MAX, MIN, SIGN, SQRT
-* ..
-* .. Executable Statements ..
-*
- EPS = DLAMCH( 'P' )
- IF( C.EQ.ZERO ) THEN
- CS = ONE
- SN = ZERO
- GO TO 10
-*
- ELSE IF( B.EQ.ZERO ) THEN
-*
-* Swap rows and columns
-*
- CS = ZERO
- SN = ONE
- TEMP = D
- D = A
- A = TEMP
- B = -C
- C = ZERO
- GO TO 10
- ELSE IF( ( A-D ).EQ.ZERO .AND. SIGN( ONE, B ).NE.SIGN( ONE, C ) )
- $ THEN
- CS = ONE
- SN = ZERO
- GO TO 10
- ELSE
-*
- TEMP = A - D
- P = HALF*TEMP
- BCMAX = MAX( ABS( B ), ABS( C ) )
- BCMIS = MIN( ABS( B ), ABS( C ) )*SIGN( ONE, B )*SIGN( ONE, C )
- SCALE = MAX( ABS( P ), BCMAX )
- Z = ( P / SCALE )*P + ( BCMAX / SCALE )*BCMIS
-*
-* If Z is of the order of the machine accuracy, postpone the
-* decision on the nature of eigenvalues
-*
- IF( Z.GE.MULTPL*EPS ) THEN
-*
-* Real eigenvalues. Compute A and D.
-*
- Z = P + SIGN( SQRT( SCALE )*SQRT( Z ), P )
- A = D + Z
- D = D - ( BCMAX / Z )*BCMIS
-*
-* Compute B and the rotation matrix
-*
- TAU = DLAPY2( C, Z )
- CS = Z / TAU
- SN = C / TAU
- B = B - C
- C = ZERO
- ELSE
-*
-* Complex eigenvalues, or real (almost) equal eigenvalues.
-* Make diagonal elements equal.
-*
- SIGMA = B + C
- TAU = DLAPY2( SIGMA, TEMP )
- CS = SQRT( HALF*( ONE+ABS( SIGMA ) / TAU ) )
- SN = -( P / ( TAU*CS ) )*SIGN( ONE, SIGMA )
-*
-* Compute [ AA BB ] = [ A B ] [ CS -SN ]
-* [ CC DD ] [ C D ] [ SN CS ]
-*
- AA = A*CS + B*SN
- BB = -A*SN + B*CS
- CC = C*CS + D*SN
- DD = -C*SN + D*CS
-*
-* Compute [ A B ] = [ CS SN ] [ AA BB ]
-* [ C D ] [-SN CS ] [ CC DD ]
-*
- A = AA*CS + CC*SN
- B = BB*CS + DD*SN
- C = -AA*SN + CC*CS
- D = -BB*SN + DD*CS
-*
- TEMP = HALF*( A+D )
- A = TEMP
- D = TEMP
-*
- IF( C.NE.ZERO ) THEN
- IF( B.NE.ZERO ) THEN
- IF( SIGN( ONE, B ).EQ.SIGN( ONE, C ) ) THEN
-*
-* Real eigenvalues: reduce to upper triangular form
-*
- SAB = SQRT( ABS( B ) )
- SAC = SQRT( ABS( C ) )
- P = SIGN( SAB*SAC, C )
- TAU = ONE / SQRT( ABS( B+C ) )
- A = TEMP + P
- D = TEMP - P
- B = B - C
- C = ZERO
- CS1 = SAB*TAU
- SN1 = SAC*TAU
- TEMP = CS*CS1 - SN*SN1
- SN = CS*SN1 + SN*CS1
- CS = TEMP
- END IF
- ELSE
- B = -C
- C = ZERO
- TEMP = CS
- CS = -SN
- SN = TEMP
- END IF
- END IF
- END IF
-*
- END IF
-*
- 10 CONTINUE
-*
-* Store eigenvalues in (RT1R,RT1I) and (RT2R,RT2I).
-*
- RT1R = A
- RT2R = D
- IF( C.EQ.ZERO ) THEN
- RT1I = ZERO
- RT2I = ZERO
- ELSE
- RT1I = SQRT( ABS( B ) )*SQRT( ABS( C ) )
- RT2I = -RT1I
- END IF
- RETURN
-*
-* End of DLANV2
-*
- END
diff --git a/src/lib/lapack/dlapmt.f b/src/lib/lapack/dlapmt.f
deleted file mode 100644
index 325774c0..00000000
--- a/src/lib/lapack/dlapmt.f
+++ /dev/null
@@ -1,136 +0,0 @@
- SUBROUTINE DLAPMT( FORWRD, M, N, X, LDX, K )
-*
-* -- LAPACK auxiliary routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- LOGICAL FORWRD
- INTEGER LDX, M, N
-* ..
-* .. Array Arguments ..
- INTEGER K( * )
- DOUBLE PRECISION X( LDX, * )
-* ..
-*
-* Purpose
-* =======
-*
-* DLAPMT rearranges the columns of the M by N matrix X as specified
-* by the permutation K(1),K(2),...,K(N) of the integers 1,...,N.
-* If FORWRD = .TRUE., forward permutation:
-*
-* X(*,K(J)) is moved X(*,J) for J = 1,2,...,N.
-*
-* If FORWRD = .FALSE., backward permutation:
-*
-* X(*,J) is moved to X(*,K(J)) for J = 1,2,...,N.
-*
-* Arguments
-* =========
-*
-* FORWRD (input) LOGICAL
-* = .TRUE., forward permutation
-* = .FALSE., backward permutation
-*
-* M (input) INTEGER
-* The number of rows of the matrix X. M >= 0.
-*
-* N (input) INTEGER
-* The number of columns of the matrix X. N >= 0.
-*
-* X (input/output) DOUBLE PRECISION array, dimension (LDX,N)
-* On entry, the M by N matrix X.
-* On exit, X contains the permuted matrix X.
-*
-* LDX (input) INTEGER
-* The leading dimension of the array X, LDX >= MAX(1,M).
-*
-* K (input/output) INTEGER array, dimension (N)
-* On entry, K contains the permutation vector. K is used as
-* internal workspace, but reset to its original value on
-* output.
-*
-* =====================================================================
-*
-* .. Local Scalars ..
- INTEGER I, II, IN, J
- DOUBLE PRECISION TEMP
-* ..
-* .. Executable Statements ..
-*
- IF( N.LE.1 )
- $ RETURN
-*
- DO 10 I = 1, N
- K( I ) = -K( I )
- 10 CONTINUE
-*
- IF( FORWRD ) THEN
-*
-* Forward permutation
-*
- DO 50 I = 1, N
-*
- IF( K( I ).GT.0 )
- $ GO TO 40
-*
- J = I
- K( J ) = -K( J )
- IN = K( J )
-*
- 20 CONTINUE
- IF( K( IN ).GT.0 )
- $ GO TO 40
-*
- DO 30 II = 1, M
- TEMP = X( II, J )
- X( II, J ) = X( II, IN )
- X( II, IN ) = TEMP
- 30 CONTINUE
-*
- K( IN ) = -K( IN )
- J = IN
- IN = K( IN )
- GO TO 20
-*
- 40 CONTINUE
-*
- 50 CONTINUE
-*
- ELSE
-*
-* Backward permutation
-*
- DO 90 I = 1, N
-*
- IF( K( I ).GT.0 )
- $ GO TO 80
-*
- K( I ) = -K( I )
- J = K( I )
- 60 CONTINUE
- IF( J.EQ.I )
- $ GO TO 80
-*
- DO 70 II = 1, M
- TEMP = X( II, I )
- X( II, I ) = X( II, J )
- X( II, J ) = TEMP
- 70 CONTINUE
-*
- K( J ) = -K( J )
- J = K( J )
- GO TO 60
-*
- 80 CONTINUE
-*
- 90 CONTINUE
-*
- END IF
-*
- RETURN
-*
-* End of DLAPMT
-*
- END
diff --git a/src/lib/lapack/dlapy2.f b/src/lib/lapack/dlapy2.f
deleted file mode 100644
index 98ef81b6..00000000
--- a/src/lib/lapack/dlapy2.f
+++ /dev/null
@@ -1,53 +0,0 @@
- DOUBLE PRECISION FUNCTION DLAPY2( X, Y )
-*
-* -- LAPACK auxiliary routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- DOUBLE PRECISION X, Y
-* ..
-*
-* Purpose
-* =======
-*
-* DLAPY2 returns sqrt(x**2+y**2), taking care not to cause unnecessary
-* overflow.
-*
-* Arguments
-* =========
-*
-* X (input) DOUBLE PRECISION
-* Y (input) DOUBLE PRECISION
-* X and Y specify the values x and y.
-*
-* =====================================================================
-*
-* .. Parameters ..
- DOUBLE PRECISION ZERO
- PARAMETER ( ZERO = 0.0D0 )
- DOUBLE PRECISION ONE
- PARAMETER ( ONE = 1.0D0 )
-* ..
-* .. Local Scalars ..
- DOUBLE PRECISION W, XABS, YABS, Z
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC ABS, MAX, MIN, SQRT
-* ..
-* .. Executable Statements ..
-*
- XABS = ABS( X )
- YABS = ABS( Y )
- W = MAX( XABS, YABS )
- Z = MIN( XABS, YABS )
- IF( Z.EQ.ZERO ) THEN
- DLAPY2 = W
- ELSE
- DLAPY2 = W*SQRT( ONE+( Z / W )**2 )
- END IF
- RETURN
-*
-* End of DLAPY2
-*
- END
diff --git a/src/lib/lapack/dlapy3.f b/src/lib/lapack/dlapy3.f
deleted file mode 100644
index 2b47bb47..00000000
--- a/src/lib/lapack/dlapy3.f
+++ /dev/null
@@ -1,56 +0,0 @@
- DOUBLE PRECISION FUNCTION DLAPY3( X, Y, Z )
-*
-* -- LAPACK auxiliary routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- DOUBLE PRECISION X, Y, Z
-* ..
-*
-* Purpose
-* =======
-*
-* DLAPY3 returns sqrt(x**2+y**2+z**2), taking care not to cause
-* unnecessary overflow.
-*
-* Arguments
-* =========
-*
-* X (input) DOUBLE PRECISION
-* Y (input) DOUBLE PRECISION
-* Z (input) DOUBLE PRECISION
-* X, Y and Z specify the values x, y and z.
-*
-* =====================================================================
-*
-* .. Parameters ..
- DOUBLE PRECISION ZERO
- PARAMETER ( ZERO = 0.0D0 )
-* ..
-* .. Local Scalars ..
- DOUBLE PRECISION W, XABS, YABS, ZABS
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC ABS, MAX, SQRT
-* ..
-* .. Executable Statements ..
-*
- XABS = ABS( X )
- YABS = ABS( Y )
- ZABS = ABS( Z )
- W = MAX( XABS, YABS, ZABS )
- IF( W.EQ.ZERO ) THEN
-* W can be zero for max(0,nan,0)
-* adding all three entries together will make sure
-* NaN will not disappear.
- DLAPY3 = XABS + YABS + ZABS
- ELSE
- DLAPY3 = W*SQRT( ( XABS / W )**2+( YABS / W )**2+
- $ ( ZABS / W )**2 )
- END IF
- RETURN
-*
-* End of DLAPY3
-*
- END
diff --git a/src/lib/lapack/dlaqge.f b/src/lib/lapack/dlaqge.f
deleted file mode 100644
index 9feb927c..00000000
--- a/src/lib/lapack/dlaqge.f
+++ /dev/null
@@ -1,154 +0,0 @@
- SUBROUTINE DLAQGE( M, N, A, LDA, R, C, ROWCND, COLCND, AMAX,
- $ EQUED )
-*
-* -- LAPACK auxiliary routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- CHARACTER EQUED
- INTEGER LDA, M, N
- DOUBLE PRECISION AMAX, COLCND, ROWCND
-* ..
-* .. Array Arguments ..
- DOUBLE PRECISION A( LDA, * ), C( * ), R( * )
-* ..
-*
-* Purpose
-* =======
-*
-* DLAQGE equilibrates a general M by N matrix A using the row and
-* column scaling factors in the vectors R and C.
-*
-* Arguments
-* =========
-*
-* M (input) INTEGER
-* The number of rows of the matrix A. M >= 0.
-*
-* N (input) INTEGER
-* The number of columns of the matrix A. N >= 0.
-*
-* A (input/output) DOUBLE PRECISION array, dimension (LDA,N)
-* On entry, the M by N matrix A.
-* On exit, the equilibrated matrix. See EQUED for the form of
-* the equilibrated matrix.
-*
-* LDA (input) INTEGER
-* The leading dimension of the array A. LDA >= max(M,1).
-*
-* R (input) DOUBLE PRECISION array, dimension (M)
-* The row scale factors for A.
-*
-* C (input) DOUBLE PRECISION array, dimension (N)
-* The column scale factors for A.
-*
-* ROWCND (input) DOUBLE PRECISION
-* Ratio of the smallest R(i) to the largest R(i).
-*
-* COLCND (input) DOUBLE PRECISION
-* Ratio of the smallest C(i) to the largest C(i).
-*
-* AMAX (input) DOUBLE PRECISION
-* Absolute value of largest matrix entry.
-*
-* EQUED (output) CHARACTER*1
-* Specifies the form of equilibration that was done.
-* = 'N': No equilibration
-* = 'R': Row equilibration, i.e., A has been premultiplied by
-* diag(R).
-* = 'C': Column equilibration, i.e., A has been postmultiplied
-* by diag(C).
-* = 'B': Both row and column equilibration, i.e., A has been
-* replaced by diag(R) * A * diag(C).
-*
-* Internal Parameters
-* ===================
-*
-* THRESH is a threshold value used to decide if row or column scaling
-* should be done based on the ratio of the row or column scaling
-* factors. If ROWCND < THRESH, row scaling is done, and if
-* COLCND < THRESH, column scaling is done.
-*
-* LARGE and SMALL are threshold values used to decide if row scaling
-* should be done based on the absolute size of the largest matrix
-* element. If AMAX > LARGE or AMAX < SMALL, row scaling is done.
-*
-* =====================================================================
-*
-* .. Parameters ..
- DOUBLE PRECISION ONE, THRESH
- PARAMETER ( ONE = 1.0D+0, THRESH = 0.1D+0 )
-* ..
-* .. Local Scalars ..
- INTEGER I, J
- DOUBLE PRECISION CJ, LARGE, SMALL
-* ..
-* .. External Functions ..
- DOUBLE PRECISION DLAMCH
- EXTERNAL DLAMCH
-* ..
-* .. Executable Statements ..
-*
-* Quick return if possible
-*
- IF( M.LE.0 .OR. N.LE.0 ) THEN
- EQUED = 'N'
- RETURN
- END IF
-*
-* Initialize LARGE and SMALL.
-*
- SMALL = DLAMCH( 'Safe minimum' ) / DLAMCH( 'Precision' )
- LARGE = ONE / SMALL
-*
- IF( ROWCND.GE.THRESH .AND. AMAX.GE.SMALL .AND. AMAX.LE.LARGE )
- $ THEN
-*
-* No row scaling
-*
- IF( COLCND.GE.THRESH ) THEN
-*
-* No column scaling
-*
- EQUED = 'N'
- ELSE
-*
-* Column scaling
-*
- DO 20 J = 1, N
- CJ = C( J )
- DO 10 I = 1, M
- A( I, J ) = CJ*A( I, J )
- 10 CONTINUE
- 20 CONTINUE
- EQUED = 'C'
- END IF
- ELSE IF( COLCND.GE.THRESH ) THEN
-*
-* Row scaling, no column scaling
-*
- DO 40 J = 1, N
- DO 30 I = 1, M
- A( I, J ) = R( I )*A( I, J )
- 30 CONTINUE
- 40 CONTINUE
- EQUED = 'R'
- ELSE
-*
-* Row and column scaling
-*
- DO 60 J = 1, N
- CJ = C( J )
- DO 50 I = 1, M
- A( I, J ) = CJ*R( I )*A( I, J )
- 50 CONTINUE
- 60 CONTINUE
- EQUED = 'B'
- END IF
-*
- RETURN
-*
-* End of DLAQGE
-*
- END
diff --git a/src/lib/lapack/dlaqp2.f b/src/lib/lapack/dlaqp2.f
deleted file mode 100644
index 5ce3b162..00000000
--- a/src/lib/lapack/dlaqp2.f
+++ /dev/null
@@ -1,175 +0,0 @@
- SUBROUTINE DLAQP2( M, N, OFFSET, A, LDA, JPVT, TAU, VN1, VN2,
- $ WORK )
-*
-* -- LAPACK auxiliary routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- INTEGER LDA, M, N, OFFSET
-* ..
-* .. Array Arguments ..
- INTEGER JPVT( * )
- DOUBLE PRECISION A( LDA, * ), TAU( * ), VN1( * ), VN2( * ),
- $ WORK( * )
-* ..
-*
-* Purpose
-* =======
-*
-* DLAQP2 computes a QR factorization with column pivoting of
-* the block A(OFFSET+1:M,1:N).
-* The block A(1:OFFSET,1:N) is accordingly pivoted, but not factorized.
-*
-* Arguments
-* =========
-*
-* M (input) INTEGER
-* The number of rows of the matrix A. M >= 0.
-*
-* N (input) INTEGER
-* The number of columns of the matrix A. N >= 0.
-*
-* OFFSET (input) INTEGER
-* The number of rows of the matrix A that must be pivoted
-* but no factorized. OFFSET >= 0.
-*
-* A (input/output) DOUBLE PRECISION array, dimension (LDA,N)
-* On entry, the M-by-N matrix A.
-* On exit, the upper triangle of block A(OFFSET+1:M,1:N) is
-* the triangular factor obtained; the elements in block
-* A(OFFSET+1:M,1:N) below the diagonal, together with the
-* array TAU, represent the orthogonal matrix Q as a product of
-* elementary reflectors. Block A(1:OFFSET,1:N) has been
-* accordingly pivoted, but no factorized.
-*
-* LDA (input) INTEGER
-* The leading dimension of the array A. LDA >= max(1,M).
-*
-* JPVT (input/output) INTEGER array, dimension (N)
-* On entry, if JPVT(i) .ne. 0, the i-th column of A is permuted
-* to the front of A*P (a leading column); if JPVT(i) = 0,
-* the i-th column of A is a free column.
-* On exit, if JPVT(i) = k, then the i-th column of A*P
-* was the k-th column of A.
-*
-* TAU (output) DOUBLE PRECISION array, dimension (min(M,N))
-* The scalar factors of the elementary reflectors.
-*
-* VN1 (input/output) DOUBLE PRECISION array, dimension (N)
-* The vector with the partial column norms.
-*
-* VN2 (input/output) DOUBLE PRECISION array, dimension (N)
-* The vector with the exact column norms.
-*
-* WORK (workspace) DOUBLE PRECISION array, dimension (N)
-*
-* Further Details
-* ===============
-*
-* Based on contributions by
-* G. Quintana-Orti, Depto. de Informatica, Universidad Jaime I, Spain
-* X. Sun, Computer Science Dept., Duke University, USA
-*
-* Partial column norm updating strategy modified by
-* Z. Drmac and Z. Bujanovic, Dept. of Mathematics,
-* University of Zagreb, Croatia.
-* June 2006.
-* For more details see LAPACK Working Note 176.
-* =====================================================================
-*
-* .. Parameters ..
- DOUBLE PRECISION ZERO, ONE
- PARAMETER ( ZERO = 0.0D+0, ONE = 1.0D+0 )
-* ..
-* .. Local Scalars ..
- INTEGER I, ITEMP, J, MN, OFFPI, PVT
- DOUBLE PRECISION AII, TEMP, TEMP2, TOL3Z
-* ..
-* .. External Subroutines ..
- EXTERNAL DLARF, DLARFG, DSWAP
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC ABS, MAX, MIN, SQRT
-* ..
-* .. External Functions ..
- INTEGER IDAMAX
- DOUBLE PRECISION DLAMCH, DNRM2
- EXTERNAL IDAMAX, DLAMCH, DNRM2
-* ..
-* .. Executable Statements ..
-*
- MN = MIN( M-OFFSET, N )
- TOL3Z = SQRT(DLAMCH('Epsilon'))
-*
-* Compute factorization.
-*
- DO 20 I = 1, MN
-*
- OFFPI = OFFSET + I
-*
-* Determine ith pivot column and swap if necessary.
-*
- PVT = ( I-1 ) + IDAMAX( N-I+1, VN1( I ), 1 )
-*
- IF( PVT.NE.I ) THEN
- CALL DSWAP( M, A( 1, PVT ), 1, A( 1, I ), 1 )
- ITEMP = JPVT( PVT )
- JPVT( PVT ) = JPVT( I )
- JPVT( I ) = ITEMP
- VN1( PVT ) = VN1( I )
- VN2( PVT ) = VN2( I )
- END IF
-*
-* Generate elementary reflector H(i).
-*
- IF( OFFPI.LT.M ) THEN
- CALL DLARFG( M-OFFPI+1, A( OFFPI, I ), A( OFFPI+1, I ), 1,
- $ TAU( I ) )
- ELSE
- CALL DLARFG( 1, A( M, I ), A( M, I ), 1, TAU( I ) )
- END IF
-*
- IF( I.LT.N ) THEN
-*
-* Apply H(i)' to A(offset+i:m,i+1:n) from the left.
-*
- AII = A( OFFPI, I )
- A( OFFPI, I ) = ONE
- CALL DLARF( 'Left', M-OFFPI+1, N-I, A( OFFPI, I ), 1,
- $ TAU( I ), A( OFFPI, I+1 ), LDA, WORK( 1 ) )
- A( OFFPI, I ) = AII
- END IF
-*
-* Update partial column norms.
-*
- DO 10 J = I + 1, N
- IF( VN1( J ).NE.ZERO ) THEN
-*
-* NOTE: The following 4 lines follow from the analysis in
-* Lapack Working Note 176.
-*
- TEMP = ONE - ( ABS( A( OFFPI, J ) ) / VN1( J ) )**2
- TEMP = MAX( TEMP, ZERO )
- TEMP2 = TEMP*( VN1( J ) / VN2( J ) )**2
- IF( TEMP2 .LE. TOL3Z ) THEN
- IF( OFFPI.LT.M ) THEN
- VN1( J ) = DNRM2( M-OFFPI, A( OFFPI+1, J ), 1 )
- VN2( J ) = VN1( J )
- ELSE
- VN1( J ) = ZERO
- VN2( J ) = ZERO
- END IF
- ELSE
- VN1( J ) = VN1( J )*SQRT( TEMP )
- END IF
- END IF
- 10 CONTINUE
-*
- 20 CONTINUE
-*
- RETURN
-*
-* End of DLAQP2
-*
- END
diff --git a/src/lib/lapack/dlaqps.f b/src/lib/lapack/dlaqps.f
deleted file mode 100644
index 94658d27..00000000
--- a/src/lib/lapack/dlaqps.f
+++ /dev/null
@@ -1,259 +0,0 @@
- SUBROUTINE DLAQPS( M, N, OFFSET, NB, KB, A, LDA, JPVT, TAU, VN1,
- $ VN2, AUXV, F, LDF )
-*
-* -- LAPACK auxiliary routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- INTEGER KB, LDA, LDF, M, N, NB, OFFSET
-* ..
-* .. Array Arguments ..
- INTEGER JPVT( * )
- DOUBLE PRECISION A( LDA, * ), AUXV( * ), F( LDF, * ), TAU( * ),
- $ VN1( * ), VN2( * )
-* ..
-*
-* Purpose
-* =======
-*
-* DLAQPS computes a step of QR factorization with column pivoting
-* of a real M-by-N matrix A by using Blas-3. It tries to factorize
-* NB columns from A starting from the row OFFSET+1, and updates all
-* of the matrix with Blas-3 xGEMM.
-*
-* In some cases, due to catastrophic cancellations, it cannot
-* factorize NB columns. Hence, the actual number of factorized
-* columns is returned in KB.
-*
-* Block A(1:OFFSET,1:N) is accordingly pivoted, but not factorized.
-*
-* Arguments
-* =========
-*
-* M (input) INTEGER
-* The number of rows of the matrix A. M >= 0.
-*
-* N (input) INTEGER
-* The number of columns of the matrix A. N >= 0
-*
-* OFFSET (input) INTEGER
-* The number of rows of A that have been factorized in
-* previous steps.
-*
-* NB (input) INTEGER
-* The number of columns to factorize.
-*
-* KB (output) INTEGER
-* The number of columns actually factorized.
-*
-* A (input/output) DOUBLE PRECISION array, dimension (LDA,N)
-* On entry, the M-by-N matrix A.
-* On exit, block A(OFFSET+1:M,1:KB) is the triangular
-* factor obtained and block A(1:OFFSET,1:N) has been
-* accordingly pivoted, but no factorized.
-* The rest of the matrix, block A(OFFSET+1:M,KB+1:N) has
-* been updated.
-*
-* LDA (input) INTEGER
-* The leading dimension of the array A. LDA >= max(1,M).
-*
-* JPVT (input/output) INTEGER array, dimension (N)
-* JPVT(I) = K <==> Column K of the full matrix A has been
-* permuted into position I in AP.
-*
-* TAU (output) DOUBLE PRECISION array, dimension (KB)
-* The scalar factors of the elementary reflectors.
-*
-* VN1 (input/output) DOUBLE PRECISION array, dimension (N)
-* The vector with the partial column norms.
-*
-* VN2 (input/output) DOUBLE PRECISION array, dimension (N)
-* The vector with the exact column norms.
-*
-* AUXV (input/output) DOUBLE PRECISION array, dimension (NB)
-* Auxiliar vector.
-*
-* F (input/output) DOUBLE PRECISION array, dimension (LDF,NB)
-* Matrix F' = L*Y'*A.
-*
-* LDF (input) INTEGER
-* The leading dimension of the array F. LDF >= max(1,N).
-*
-* Further Details
-* ===============
-*
-* Based on contributions by
-* G. Quintana-Orti, Depto. de Informatica, Universidad Jaime I, Spain
-* X. Sun, Computer Science Dept., Duke University, USA
-*
-* Partial column norm updating strategy modified by
-* Z. Drmac and Z. Bujanovic, Dept. of Mathematics,
-* University of Zagreb, Croatia.
-* June 2006.
-* For more details see LAPACK Working Note 176.
-* =====================================================================
-*
-* .. Parameters ..
- DOUBLE PRECISION ZERO, ONE
- PARAMETER ( ZERO = 0.0D+0, ONE = 1.0D+0 )
-* ..
-* .. Local Scalars ..
- INTEGER ITEMP, J, K, LASTRK, LSTICC, PVT, RK
- DOUBLE PRECISION AKK, TEMP, TEMP2, TOL3Z
-* ..
-* .. External Subroutines ..
- EXTERNAL DGEMM, DGEMV, DLARFG, DSWAP
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC ABS, DBLE, MAX, MIN, NINT, SQRT
-* ..
-* .. External Functions ..
- INTEGER IDAMAX
- DOUBLE PRECISION DLAMCH, DNRM2
- EXTERNAL IDAMAX, DLAMCH, DNRM2
-* ..
-* .. Executable Statements ..
-*
- LASTRK = MIN( M, N+OFFSET )
- LSTICC = 0
- K = 0
- TOL3Z = SQRT(DLAMCH('Epsilon'))
-*
-* Beginning of while loop.
-*
- 10 CONTINUE
- IF( ( K.LT.NB ) .AND. ( LSTICC.EQ.0 ) ) THEN
- K = K + 1
- RK = OFFSET + K
-*
-* Determine ith pivot column and swap if necessary
-*
- PVT = ( K-1 ) + IDAMAX( N-K+1, VN1( K ), 1 )
- IF( PVT.NE.K ) THEN
- CALL DSWAP( M, A( 1, PVT ), 1, A( 1, K ), 1 )
- CALL DSWAP( K-1, F( PVT, 1 ), LDF, F( K, 1 ), LDF )
- ITEMP = JPVT( PVT )
- JPVT( PVT ) = JPVT( K )
- JPVT( K ) = ITEMP
- VN1( PVT ) = VN1( K )
- VN2( PVT ) = VN2( K )
- END IF
-*
-* Apply previous Householder reflectors to column K:
-* A(RK:M,K) := A(RK:M,K) - A(RK:M,1:K-1)*F(K,1:K-1)'.
-*
- IF( K.GT.1 ) THEN
- CALL DGEMV( 'No transpose', M-RK+1, K-1, -ONE, A( RK, 1 ),
- $ LDA, F( K, 1 ), LDF, ONE, A( RK, K ), 1 )
- END IF
-*
-* Generate elementary reflector H(k).
-*
- IF( RK.LT.M ) THEN
- CALL DLARFG( M-RK+1, A( RK, K ), A( RK+1, K ), 1, TAU( K ) )
- ELSE
- CALL DLARFG( 1, A( RK, K ), A( RK, K ), 1, TAU( K ) )
- END IF
-*
- AKK = A( RK, K )
- A( RK, K ) = ONE
-*
-* Compute Kth column of F:
-*
-* Compute F(K+1:N,K) := tau(K)*A(RK:M,K+1:N)'*A(RK:M,K).
-*
- IF( K.LT.N ) THEN
- CALL DGEMV( 'Transpose', M-RK+1, N-K, TAU( K ),
- $ A( RK, K+1 ), LDA, A( RK, K ), 1, ZERO,
- $ F( K+1, K ), 1 )
- END IF
-*
-* Padding F(1:K,K) with zeros.
-*
- DO 20 J = 1, K
- F( J, K ) = ZERO
- 20 CONTINUE
-*
-* Incremental updating of F:
-* F(1:N,K) := F(1:N,K) - tau(K)*F(1:N,1:K-1)*A(RK:M,1:K-1)'
-* *A(RK:M,K).
-*
- IF( K.GT.1 ) THEN
- CALL DGEMV( 'Transpose', M-RK+1, K-1, -TAU( K ), A( RK, 1 ),
- $ LDA, A( RK, K ), 1, ZERO, AUXV( 1 ), 1 )
-*
- CALL DGEMV( 'No transpose', N, K-1, ONE, F( 1, 1 ), LDF,
- $ AUXV( 1 ), 1, ONE, F( 1, K ), 1 )
- END IF
-*
-* Update the current row of A:
-* A(RK,K+1:N) := A(RK,K+1:N) - A(RK,1:K)*F(K+1:N,1:K)'.
-*
- IF( K.LT.N ) THEN
- CALL DGEMV( 'No transpose', N-K, K, -ONE, F( K+1, 1 ), LDF,
- $ A( RK, 1 ), LDA, ONE, A( RK, K+1 ), LDA )
- END IF
-*
-* Update partial column norms.
-*
- IF( RK.LT.LASTRK ) THEN
- DO 30 J = K + 1, N
- IF( VN1( J ).NE.ZERO ) THEN
-*
-* NOTE: The following 4 lines follow from the analysis in
-* Lapack Working Note 176.
-*
- TEMP = ABS( A( RK, J ) ) / VN1( J )
- TEMP = MAX( ZERO, ( ONE+TEMP )*( ONE-TEMP ) )
- TEMP2 = TEMP*( VN1( J ) / VN2( J ) )**2
- IF( TEMP2 .LE. TOL3Z ) THEN
- VN2( J ) = DBLE( LSTICC )
- LSTICC = J
- ELSE
- VN1( J ) = VN1( J )*SQRT( TEMP )
- END IF
- END IF
- 30 CONTINUE
- END IF
-*
- A( RK, K ) = AKK
-*
-* End of while loop.
-*
- GO TO 10
- END IF
- KB = K
- RK = OFFSET + KB
-*
-* Apply the block reflector to the rest of the matrix:
-* A(OFFSET+KB+1:M,KB+1:N) := A(OFFSET+KB+1:M,KB+1:N) -
-* A(OFFSET+KB+1:M,1:KB)*F(KB+1:N,1:KB)'.
-*
- IF( KB.LT.MIN( N, M-OFFSET ) ) THEN
- CALL DGEMM( 'No transpose', 'Transpose', M-RK, N-KB, KB, -ONE,
- $ A( RK+1, 1 ), LDA, F( KB+1, 1 ), LDF, ONE,
- $ A( RK+1, KB+1 ), LDA )
- END IF
-*
-* Recomputation of difficult columns.
-*
- 40 CONTINUE
- IF( LSTICC.GT.0 ) THEN
- ITEMP = NINT( VN2( LSTICC ) )
- VN1( LSTICC ) = DNRM2( M-RK, A( RK+1, LSTICC ), 1 )
-*
-* NOTE: The computation of VN1( LSTICC ) relies on the fact that
-* SNRM2 does not fail on vectors with norm below the value of
-* SQRT(DLAMCH('S'))
-*
- VN2( LSTICC ) = VN1( LSTICC )
- LSTICC = ITEMP
- GO TO 40
- END IF
-*
- RETURN
-*
-* End of DLAQPS
-*
- END
diff --git a/src/lib/lapack/dlaqr0.f b/src/lib/lapack/dlaqr0.f
deleted file mode 100644
index 479da53d..00000000
--- a/src/lib/lapack/dlaqr0.f
+++ /dev/null
@@ -1,642 +0,0 @@
- SUBROUTINE DLAQR0( WANTT, WANTZ, N, ILO, IHI, H, LDH, WR, WI,
- $ ILOZ, IHIZ, Z, LDZ, WORK, LWORK, INFO )
-*
-* -- LAPACK auxiliary routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- INTEGER IHI, IHIZ, ILO, ILOZ, INFO, LDH, LDZ, LWORK, N
- LOGICAL WANTT, WANTZ
-* ..
-* .. Array Arguments ..
- DOUBLE PRECISION H( LDH, * ), WI( * ), WORK( * ), WR( * ),
- $ Z( LDZ, * )
-* ..
-*
-* Purpose
-* =======
-*
-* DLAQR0 computes the eigenvalues of a Hessenberg matrix H
-* and, optionally, the matrices T and Z from the Schur decomposition
-* H = Z T Z**T, where T is an upper quasi-triangular matrix (the
-* Schur form), and Z is the orthogonal matrix of Schur vectors.
-*
-* Optionally Z may be postmultiplied into an input orthogonal
-* matrix Q so that this routine can give the Schur factorization
-* of a matrix A which has been reduced to the Hessenberg form H
-* by the orthogonal matrix Q: A = Q*H*Q**T = (QZ)*T*(QZ)**T.
-*
-* Arguments
-* =========
-*
-* WANTT (input) LOGICAL
-* = .TRUE. : the full Schur form T is required;
-* = .FALSE.: only eigenvalues are required.
-*
-* WANTZ (input) LOGICAL
-* = .TRUE. : the matrix of Schur vectors Z is required;
-* = .FALSE.: Schur vectors are not required.
-*
-* N (input) INTEGER
-* The order of the matrix H. N .GE. 0.
-*
-* ILO (input) INTEGER
-* IHI (input) INTEGER
-* It is assumed that H is already upper triangular in rows
-* and columns 1:ILO-1 and IHI+1:N and, if ILO.GT.1,
-* H(ILO,ILO-1) is zero. ILO and IHI are normally set by a
-* previous call to DGEBAL, and then passed to DGEHRD when the
-* matrix output by DGEBAL is reduced to Hessenberg form.
-* Otherwise, ILO and IHI should be set to 1 and N,
-* respectively. If N.GT.0, then 1.LE.ILO.LE.IHI.LE.N.
-* If N = 0, then ILO = 1 and IHI = 0.
-*
-* H (input/output) DOUBLE PRECISION array, dimension (LDH,N)
-* On entry, the upper Hessenberg matrix H.
-* On exit, if INFO = 0 and WANTT is .TRUE., then H contains
-* the upper quasi-triangular matrix T from the Schur
-* decomposition (the Schur form); 2-by-2 diagonal blocks
-* (corresponding to complex conjugate pairs of eigenvalues)
-* are returned in standard form, with H(i,i) = H(i+1,i+1)
-* and H(i+1,i)*H(i,i+1).LT.0. If INFO = 0 and WANTT is
-* .FALSE., then the contents of H are unspecified on exit.
-* (The output value of H when INFO.GT.0 is given under the
-* description of INFO below.)
-*
-* This subroutine may explicitly set H(i,j) = 0 for i.GT.j and
-* j = 1, 2, ... ILO-1 or j = IHI+1, IHI+2, ... N.
-*
-* LDH (input) INTEGER
-* The leading dimension of the array H. LDH .GE. max(1,N).
-*
-* WR (output) DOUBLE PRECISION array, dimension (IHI)
-* WI (output) DOUBLE PRECISION array, dimension (IHI)
-* The real and imaginary parts, respectively, of the computed
-* eigenvalues of H(ILO:IHI,ILO:IHI) are stored WR(ILO:IHI)
-* and WI(ILO:IHI). If two eigenvalues are computed as a
-* complex conjugate pair, they are stored in consecutive
-* elements of WR and WI, say the i-th and (i+1)th, with
-* WI(i) .GT. 0 and WI(i+1) .LT. 0. If WANTT is .TRUE., then
-* the eigenvalues are stored in the same order as on the
-* diagonal of the Schur form returned in H, with
-* WR(i) = H(i,i) and, if H(i:i+1,i:i+1) is a 2-by-2 diagonal
-* block, WI(i) = sqrt(-H(i+1,i)*H(i,i+1)) and
-* WI(i+1) = -WI(i).
-*
-* ILOZ (input) INTEGER
-* IHIZ (input) INTEGER
-* Specify the rows of Z to which transformations must be
-* applied if WANTZ is .TRUE..
-* 1 .LE. ILOZ .LE. ILO; IHI .LE. IHIZ .LE. N.
-*
-* Z (input/output) DOUBLE PRECISION array, dimension (LDZ,IHI)
-* If WANTZ is .FALSE., then Z is not referenced.
-* If WANTZ is .TRUE., then Z(ILO:IHI,ILOZ:IHIZ) is
-* replaced by Z(ILO:IHI,ILOZ:IHIZ)*U where U is the
-* orthogonal Schur factor of H(ILO:IHI,ILO:IHI).
-* (The output value of Z when INFO.GT.0 is given under
-* the description of INFO below.)
-*
-* LDZ (input) INTEGER
-* The leading dimension of the array Z. if WANTZ is .TRUE.
-* then LDZ.GE.MAX(1,IHIZ). Otherwize, LDZ.GE.1.
-*
-* WORK (workspace/output) DOUBLE PRECISION array, dimension LWORK
-* On exit, if LWORK = -1, WORK(1) returns an estimate of
-* the optimal value for LWORK.
-*
-* LWORK (input) INTEGER
-* The dimension of the array WORK. LWORK .GE. max(1,N)
-* is sufficient, but LWORK typically as large as 6*N may
-* be required for optimal performance. A workspace query
-* to determine the optimal workspace size is recommended.
-*
-* If LWORK = -1, then DLAQR0 does a workspace query.
-* In this case, DLAQR0 checks the input parameters and
-* estimates the optimal workspace size for the given
-* values of N, ILO and IHI. The estimate is returned
-* in WORK(1). No error message related to LWORK is
-* issued by XERBLA. Neither H nor Z are accessed.
-*
-*
-* INFO (output) INTEGER
-* = 0: successful exit
-* .GT. 0: if INFO = i, DLAQR0 failed to compute all of
-* the eigenvalues. Elements 1:ilo-1 and i+1:n of WR
-* and WI contain those eigenvalues which have been
-* successfully computed. (Failures are rare.)
-*
-* If INFO .GT. 0 and WANT is .FALSE., then on exit,
-* the remaining unconverged eigenvalues are the eigen-
-* values of the upper Hessenberg matrix rows and
-* columns ILO through INFO of the final, output
-* value of H.
-*
-* If INFO .GT. 0 and WANTT is .TRUE., then on exit
-*
-* (*) (initial value of H)*U = U*(final value of H)
-*
-* where U is an orthogonal matrix. The final
-* value of H is upper Hessenberg and quasi-triangular
-* in rows and columns INFO+1 through IHI.
-*
-* If INFO .GT. 0 and WANTZ is .TRUE., then on exit
-*
-* (final value of Z(ILO:IHI,ILOZ:IHIZ)
-* = (initial value of Z(ILO:IHI,ILOZ:IHIZ)*U
-*
-* where U is the orthogonal matrix in (*) (regard-
-* less of the value of WANTT.)
-*
-* If INFO .GT. 0 and WANTZ is .FALSE., then Z is not
-* accessed.
-*
-*
-* ================================================================
-* Based on contributions by
-* Karen Braman and Ralph Byers, Department of Mathematics,
-* University of Kansas, USA
-*
-* ================================================================
-*
-* References:
-* K. Braman, R. Byers and R. Mathias, The Multi-Shift QR
-* Algorithm Part I: Maintaining Well Focused Shifts, and Level 3
-* Performance, SIAM Journal of Matrix Analysis, volume 23, pages
-* 929--947, 2002.
-*
-* K. Braman, R. Byers and R. Mathias, The Multi-Shift QR
-* Algorithm Part II: Aggressive Early Deflation, SIAM Journal
-* of Matrix Analysis, volume 23, pages 948--973, 2002.
-*
-* ================================================================
-* .. Parameters ..
-*
-* ==== Matrices of order NTINY or smaller must be processed by
-* . DLAHQR because of insufficient subdiagonal scratch space.
-* . (This is a hard limit.) ====
-*
-* ==== Exceptional deflation windows: try to cure rare
-* . slow convergence by increasing the size of the
-* . deflation window after KEXNW iterations. =====
-*
-* ==== Exceptional shifts: try to cure rare slow convergence
-* . with ad-hoc exceptional shifts every KEXSH iterations.
-* . The constants WILK1 and WILK2 are used to form the
-* . exceptional shifts. ====
-*
- INTEGER NTINY
- PARAMETER ( NTINY = 11 )
- INTEGER KEXNW, KEXSH
- PARAMETER ( KEXNW = 5, KEXSH = 6 )
- DOUBLE PRECISION WILK1, WILK2
- PARAMETER ( WILK1 = 0.75d0, WILK2 = -0.4375d0 )
- DOUBLE PRECISION ZERO, ONE
- PARAMETER ( ZERO = 0.0d0, ONE = 1.0d0 )
-* ..
-* .. Local Scalars ..
- DOUBLE PRECISION AA, BB, CC, CS, DD, SN, SS, SWAP
- INTEGER I, INF, IT, ITMAX, K, KACC22, KBOT, KDU, KS,
- $ KT, KTOP, KU, KV, KWH, KWTOP, KWV, LD, LS,
- $ LWKOPT, NDFL, NH, NHO, NIBBLE, NMIN, NS, NSMAX,
- $ NSR, NVE, NW, NWMAX, NWR
- LOGICAL NWINC, SORTED
- CHARACTER JBCMPZ*2
-* ..
-* .. External Functions ..
- INTEGER ILAENV
- EXTERNAL ILAENV
-* ..
-* .. Local Arrays ..
- DOUBLE PRECISION ZDUM( 1, 1 )
-* ..
-* .. External Subroutines ..
- EXTERNAL DLACPY, DLAHQR, DLANV2, DLAQR3, DLAQR4, DLAQR5
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC ABS, DBLE, INT, MAX, MIN, MOD
-* ..
-* .. Executable Statements ..
- INFO = 0
-*
-* ==== Quick return for N = 0: nothing to do. ====
-*
- IF( N.EQ.0 ) THEN
- WORK( 1 ) = ONE
- RETURN
- END IF
-*
-* ==== Set up job flags for ILAENV. ====
-*
- IF( WANTT ) THEN
- JBCMPZ( 1: 1 ) = 'S'
- ELSE
- JBCMPZ( 1: 1 ) = 'E'
- END IF
- IF( WANTZ ) THEN
- JBCMPZ( 2: 2 ) = 'V'
- ELSE
- JBCMPZ( 2: 2 ) = 'N'
- END IF
-*
-* ==== Tiny matrices must use DLAHQR. ====
-*
- IF( N.LE.NTINY ) THEN
-*
-* ==== Estimate optimal workspace. ====
-*
- LWKOPT = 1
- IF( LWORK.NE.-1 )
- $ CALL DLAHQR( WANTT, WANTZ, N, ILO, IHI, H, LDH, WR, WI,
- $ ILOZ, IHIZ, Z, LDZ, INFO )
- ELSE
-*
-* ==== Use small bulge multi-shift QR with aggressive early
-* . deflation on larger-than-tiny matrices. ====
-*
-* ==== Hope for the best. ====
-*
- INFO = 0
-*
-* ==== NWR = recommended deflation window size. At this
-* . point, N .GT. NTINY = 11, so there is enough
-* . subdiagonal workspace for NWR.GE.2 as required.
-* . (In fact, there is enough subdiagonal space for
-* . NWR.GE.3.) ====
-*
- NWR = ILAENV( 13, 'DLAQR0', JBCMPZ, N, ILO, IHI, LWORK )
- NWR = MAX( 2, NWR )
- NWR = MIN( IHI-ILO+1, ( N-1 ) / 3, NWR )
- NW = NWR
-*
-* ==== NSR = recommended number of simultaneous shifts.
-* . At this point N .GT. NTINY = 11, so there is at
-* . enough subdiagonal workspace for NSR to be even
-* . and greater than or equal to two as required. ====
-*
- NSR = ILAENV( 15, 'DLAQR0', JBCMPZ, N, ILO, IHI, LWORK )
- NSR = MIN( NSR, ( N+6 ) / 9, IHI-ILO )
- NSR = MAX( 2, NSR-MOD( NSR, 2 ) )
-*
-* ==== Estimate optimal workspace ====
-*
-* ==== Workspace query call to DLAQR3 ====
-*
- CALL DLAQR3( WANTT, WANTZ, N, ILO, IHI, NWR+1, H, LDH, ILOZ,
- $ IHIZ, Z, LDZ, LS, LD, WR, WI, H, LDH, N, H, LDH,
- $ N, H, LDH, WORK, -1 )
-*
-* ==== Optimal workspace = MAX(DLAQR5, DLAQR3) ====
-*
- LWKOPT = MAX( 3*NSR / 2, INT( WORK( 1 ) ) )
-*
-* ==== Quick return in case of workspace query. ====
-*
- IF( LWORK.EQ.-1 ) THEN
- WORK( 1 ) = DBLE( LWKOPT )
- RETURN
- END IF
-*
-* ==== DLAHQR/DLAQR0 crossover point ====
-*
- NMIN = ILAENV( 12, 'DLAQR0', JBCMPZ, N, ILO, IHI, LWORK )
- NMIN = MAX( NTINY, NMIN )
-*
-* ==== Nibble crossover point ====
-*
- NIBBLE = ILAENV( 14, 'DLAQR0', JBCMPZ, N, ILO, IHI, LWORK )
- NIBBLE = MAX( 0, NIBBLE )
-*
-* ==== Accumulate reflections during ttswp? Use block
-* . 2-by-2 structure during matrix-matrix multiply? ====
-*
- KACC22 = ILAENV( 16, 'DLAQR0', JBCMPZ, N, ILO, IHI, LWORK )
- KACC22 = MAX( 0, KACC22 )
- KACC22 = MIN( 2, KACC22 )
-*
-* ==== NWMAX = the largest possible deflation window for
-* . which there is sufficient workspace. ====
-*
- NWMAX = MIN( ( N-1 ) / 3, LWORK / 2 )
-*
-* ==== NSMAX = the Largest number of simultaneous shifts
-* . for which there is sufficient workspace. ====
-*
- NSMAX = MIN( ( N+6 ) / 9, 2*LWORK / 3 )
- NSMAX = NSMAX - MOD( NSMAX, 2 )
-*
-* ==== NDFL: an iteration count restarted at deflation. ====
-*
- NDFL = 1
-*
-* ==== ITMAX = iteration limit ====
-*
- ITMAX = MAX( 30, 2*KEXSH )*MAX( 10, ( IHI-ILO+1 ) )
-*
-* ==== Last row and column in the active block ====
-*
- KBOT = IHI
-*
-* ==== Main Loop ====
-*
- DO 80 IT = 1, ITMAX
-*
-* ==== Done when KBOT falls below ILO ====
-*
- IF( KBOT.LT.ILO )
- $ GO TO 90
-*
-* ==== Locate active block ====
-*
- DO 10 K = KBOT, ILO + 1, -1
- IF( H( K, K-1 ).EQ.ZERO )
- $ GO TO 20
- 10 CONTINUE
- K = ILO
- 20 CONTINUE
- KTOP = K
-*
-* ==== Select deflation window size ====
-*
- NH = KBOT - KTOP + 1
- IF( NDFL.LT.KEXNW .OR. NH.LT.NW ) THEN
-*
-* ==== Typical deflation window. If possible and
-* . advisable, nibble the entire active block.
-* . If not, use size NWR or NWR+1 depending upon
-* . which has the smaller corresponding subdiagonal
-* . entry (a heuristic). ====
-*
- NWINC = .TRUE.
- IF( NH.LE.MIN( NMIN, NWMAX ) ) THEN
- NW = NH
- ELSE
- NW = MIN( NWR, NH, NWMAX )
- IF( NW.LT.NWMAX ) THEN
- IF( NW.GE.NH-1 ) THEN
- NW = NH
- ELSE
- KWTOP = KBOT - NW + 1
- IF( ABS( H( KWTOP, KWTOP-1 ) ).GT.
- $ ABS( H( KWTOP-1, KWTOP-2 ) ) )NW = NW + 1
- END IF
- END IF
- END IF
- ELSE
-*
-* ==== Exceptional deflation window. If there have
-* . been no deflations in KEXNW or more iterations,
-* . then vary the deflation window size. At first,
-* . because, larger windows are, in general, more
-* . powerful than smaller ones, rapidly increase the
-* . window up to the maximum reasonable and possible.
-* . Then maybe try a slightly smaller window. ====
-*
- IF( NWINC .AND. NW.LT.MIN( NWMAX, NH ) ) THEN
- NW = MIN( NWMAX, NH, 2*NW )
- ELSE
- NWINC = .FALSE.
- IF( NW.EQ.NH .AND. NH.GT.2 )
- $ NW = NH - 1
- END IF
- END IF
-*
-* ==== Aggressive early deflation:
-* . split workspace under the subdiagonal into
-* . - an nw-by-nw work array V in the lower
-* . left-hand-corner,
-* . - an NW-by-at-least-NW-but-more-is-better
-* . (NW-by-NHO) horizontal work array along
-* . the bottom edge,
-* . - an at-least-NW-but-more-is-better (NHV-by-NW)
-* . vertical work array along the left-hand-edge.
-* . ====
-*
- KV = N - NW + 1
- KT = NW + 1
- NHO = ( N-NW-1 ) - KT + 1
- KWV = NW + 2
- NVE = ( N-NW ) - KWV + 1
-*
-* ==== Aggressive early deflation ====
-*
- CALL DLAQR3( WANTT, WANTZ, N, KTOP, KBOT, NW, H, LDH, ILOZ,
- $ IHIZ, Z, LDZ, LS, LD, WR, WI, H( KV, 1 ), LDH,
- $ NHO, H( KV, KT ), LDH, NVE, H( KWV, 1 ), LDH,
- $ WORK, LWORK )
-*
-* ==== Adjust KBOT accounting for new deflations. ====
-*
- KBOT = KBOT - LD
-*
-* ==== KS points to the shifts. ====
-*
- KS = KBOT - LS + 1
-*
-* ==== Skip an expensive QR sweep if there is a (partly
-* . heuristic) reason to expect that many eigenvalues
-* . will deflate without it. Here, the QR sweep is
-* . skipped if many eigenvalues have just been deflated
-* . or if the remaining active block is small.
-*
- IF( ( LD.EQ.0 ) .OR. ( ( 100*LD.LE.NW*NIBBLE ) .AND. ( KBOT-
- $ KTOP+1.GT.MIN( NMIN, NWMAX ) ) ) ) THEN
-*
-* ==== NS = nominal number of simultaneous shifts.
-* . This may be lowered (slightly) if DLAQR3
-* . did not provide that many shifts. ====
-*
- NS = MIN( NSMAX, NSR, MAX( 2, KBOT-KTOP ) )
- NS = NS - MOD( NS, 2 )
-*
-* ==== If there have been no deflations
-* . in a multiple of KEXSH iterations,
-* . then try exceptional shifts.
-* . Otherwise use shifts provided by
-* . DLAQR3 above or from the eigenvalues
-* . of a trailing principal submatrix. ====
-*
- IF( MOD( NDFL, KEXSH ).EQ.0 ) THEN
- KS = KBOT - NS + 1
- DO 30 I = KBOT, MAX( KS+1, KTOP+2 ), -2
- SS = ABS( H( I, I-1 ) ) + ABS( H( I-1, I-2 ) )
- AA = WILK1*SS + H( I, I )
- BB = SS
- CC = WILK2*SS
- DD = AA
- CALL DLANV2( AA, BB, CC, DD, WR( I-1 ), WI( I-1 ),
- $ WR( I ), WI( I ), CS, SN )
- 30 CONTINUE
- IF( KS.EQ.KTOP ) THEN
- WR( KS+1 ) = H( KS+1, KS+1 )
- WI( KS+1 ) = ZERO
- WR( KS ) = WR( KS+1 )
- WI( KS ) = WI( KS+1 )
- END IF
- ELSE
-*
-* ==== Got NS/2 or fewer shifts? Use DLAQR4 or
-* . DLAHQR on a trailing principal submatrix to
-* . get more. (Since NS.LE.NSMAX.LE.(N+6)/9,
-* . there is enough space below the subdiagonal
-* . to fit an NS-by-NS scratch array.) ====
-*
- IF( KBOT-KS+1.LE.NS / 2 ) THEN
- KS = KBOT - NS + 1
- KT = N - NS + 1
- CALL DLACPY( 'A', NS, NS, H( KS, KS ), LDH,
- $ H( KT, 1 ), LDH )
- IF( NS.GT.NMIN ) THEN
- CALL DLAQR4( .false., .false., NS, 1, NS,
- $ H( KT, 1 ), LDH, WR( KS ),
- $ WI( KS ), 1, 1, ZDUM, 1, WORK,
- $ LWORK, INF )
- ELSE
- CALL DLAHQR( .false., .false., NS, 1, NS,
- $ H( KT, 1 ), LDH, WR( KS ),
- $ WI( KS ), 1, 1, ZDUM, 1, INF )
- END IF
- KS = KS + INF
-*
-* ==== In case of a rare QR failure use
-* . eigenvalues of the trailing 2-by-2
-* . principal submatrix. ====
-*
- IF( KS.GE.KBOT ) THEN
- AA = H( KBOT-1, KBOT-1 )
- CC = H( KBOT, KBOT-1 )
- BB = H( KBOT-1, KBOT )
- DD = H( KBOT, KBOT )
- CALL DLANV2( AA, BB, CC, DD, WR( KBOT-1 ),
- $ WI( KBOT-1 ), WR( KBOT ),
- $ WI( KBOT ), CS, SN )
- KS = KBOT - 1
- END IF
- END IF
-*
- IF( KBOT-KS+1.GT.NS ) THEN
-*
-* ==== Sort the shifts (Helps a little)
-* . Bubble sort keeps complex conjugate
-* . pairs together. ====
-*
- SORTED = .false.
- DO 50 K = KBOT, KS + 1, -1
- IF( SORTED )
- $ GO TO 60
- SORTED = .true.
- DO 40 I = KS, K - 1
- IF( ABS( WR( I ) )+ABS( WI( I ) ).LT.
- $ ABS( WR( I+1 ) )+ABS( WI( I+1 ) ) ) THEN
- SORTED = .false.
-*
- SWAP = WR( I )
- WR( I ) = WR( I+1 )
- WR( I+1 ) = SWAP
-*
- SWAP = WI( I )
- WI( I ) = WI( I+1 )
- WI( I+1 ) = SWAP
- END IF
- 40 CONTINUE
- 50 CONTINUE
- 60 CONTINUE
- END IF
-*
-* ==== Shuffle shifts into pairs of real shifts
-* . and pairs of complex conjugate shifts
-* . assuming complex conjugate shifts are
-* . already adjacent to one another. (Yes,
-* . they are.) ====
-*
- DO 70 I = KBOT, KS + 2, -2
- IF( WI( I ).NE.-WI( I-1 ) ) THEN
-*
- SWAP = WR( I )
- WR( I ) = WR( I-1 )
- WR( I-1 ) = WR( I-2 )
- WR( I-2 ) = SWAP
-*
- SWAP = WI( I )
- WI( I ) = WI( I-1 )
- WI( I-1 ) = WI( I-2 )
- WI( I-2 ) = SWAP
- END IF
- 70 CONTINUE
- END IF
-*
-* ==== If there are only two shifts and both are
-* . real, then use only one. ====
-*
- IF( KBOT-KS+1.EQ.2 ) THEN
- IF( WI( KBOT ).EQ.ZERO ) THEN
- IF( ABS( WR( KBOT )-H( KBOT, KBOT ) ).LT.
- $ ABS( WR( KBOT-1 )-H( KBOT, KBOT ) ) ) THEN
- WR( KBOT-1 ) = WR( KBOT )
- ELSE
- WR( KBOT ) = WR( KBOT-1 )
- END IF
- END IF
- END IF
-*
-* ==== Use up to NS of the the smallest magnatiude
-* . shifts. If there aren't NS shifts available,
-* . then use them all, possibly dropping one to
-* . make the number of shifts even. ====
-*
- NS = MIN( NS, KBOT-KS+1 )
- NS = NS - MOD( NS, 2 )
- KS = KBOT - NS + 1
-*
-* ==== Small-bulge multi-shift QR sweep:
-* . split workspace under the subdiagonal into
-* . - a KDU-by-KDU work array U in the lower
-* . left-hand-corner,
-* . - a KDU-by-at-least-KDU-but-more-is-better
-* . (KDU-by-NHo) horizontal work array WH along
-* . the bottom edge,
-* . - and an at-least-KDU-but-more-is-better-by-KDU
-* . (NVE-by-KDU) vertical work WV arrow along
-* . the left-hand-edge. ====
-*
- KDU = 3*NS - 3
- KU = N - KDU + 1
- KWH = KDU + 1
- NHO = ( N-KDU+1-4 ) - ( KDU+1 ) + 1
- KWV = KDU + 4
- NVE = N - KDU - KWV + 1
-*
-* ==== Small-bulge multi-shift QR sweep ====
-*
- CALL DLAQR5( WANTT, WANTZ, KACC22, N, KTOP, KBOT, NS,
- $ WR( KS ), WI( KS ), H, LDH, ILOZ, IHIZ, Z,
- $ LDZ, WORK, 3, H( KU, 1 ), LDH, NVE,
- $ H( KWV, 1 ), LDH, NHO, H( KU, KWH ), LDH )
- END IF
-*
-* ==== Note progress (or the lack of it). ====
-*
- IF( LD.GT.0 ) THEN
- NDFL = 1
- ELSE
- NDFL = NDFL + 1
- END IF
-*
-* ==== End of main loop ====
- 80 CONTINUE
-*
-* ==== Iteration limit exceeded. Set INFO to show where
-* . the problem occurred and exit. ====
-*
- INFO = KBOT
- 90 CONTINUE
- END IF
-*
-* ==== Return the optimal value of LWORK. ====
-*
- WORK( 1 ) = DBLE( LWKOPT )
-*
-* ==== End of DLAQR0 ====
-*
- END
diff --git a/src/lib/lapack/dlaqr1.f b/src/lib/lapack/dlaqr1.f
deleted file mode 100644
index c80fe668..00000000
--- a/src/lib/lapack/dlaqr1.f
+++ /dev/null
@@ -1,97 +0,0 @@
- SUBROUTINE DLAQR1( N, H, LDH, SR1, SI1, SR2, SI2, V )
-*
-* -- LAPACK auxiliary routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- DOUBLE PRECISION SI1, SI2, SR1, SR2
- INTEGER LDH, N
-* ..
-* .. Array Arguments ..
- DOUBLE PRECISION H( LDH, * ), V( * )
-* ..
-*
-* Given a 2-by-2 or 3-by-3 matrix H, DLAQR1 sets v to a
-* scalar multiple of the first column of the product
-*
-* (*) K = (H - (sr1 + i*si1)*I)*(H - (sr2 + i*si2)*I)
-*
-* scaling to avoid overflows and most underflows. It
-* is assumed that either
-*
-* 1) sr1 = sr2 and si1 = -si2
-* or
-* 2) si1 = si2 = 0.
-*
-* This is useful for starting double implicit shift bulges
-* in the QR algorithm.
-*
-*
-* N (input) integer
-* Order of the matrix H. N must be either 2 or 3.
-*
-* H (input) DOUBLE PRECISION array of dimension (LDH,N)
-* The 2-by-2 or 3-by-3 matrix H in (*).
-*
-* LDH (input) integer
-* The leading dimension of H as declared in
-* the calling procedure. LDH.GE.N
-*
-* SR1 (input) DOUBLE PRECISION
-* SI1 The shifts in (*).
-* SR2
-* SI2
-*
-* V (output) DOUBLE PRECISION array of dimension N
-* A scalar multiple of the first column of the
-* matrix K in (*).
-*
-* ================================================================
-* Based on contributions by
-* Karen Braman and Ralph Byers, Department of Mathematics,
-* University of Kansas, USA
-*
-* ================================================================
-*
-* .. Parameters ..
- DOUBLE PRECISION ZERO
- PARAMETER ( ZERO = 0.0d0 )
-* ..
-* .. Local Scalars ..
- DOUBLE PRECISION H21S, H31S, S
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC ABS
-* ..
-* .. Executable Statements ..
- IF( N.EQ.2 ) THEN
- S = ABS( H( 1, 1 )-SR2 ) + ABS( SI2 ) + ABS( H( 2, 1 ) )
- IF( S.EQ.ZERO ) THEN
- V( 1 ) = ZERO
- V( 2 ) = ZERO
- ELSE
- H21S = H( 2, 1 ) / S
- V( 1 ) = H21S*H( 1, 2 ) + ( H( 1, 1 )-SR1 )*
- $ ( ( H( 1, 1 )-SR2 ) / S ) - SI1*( SI2 / S )
- V( 2 ) = H21S*( H( 1, 1 )+H( 2, 2 )-SR1-SR2 )
- END IF
- ELSE
- S = ABS( H( 1, 1 )-SR2 ) + ABS( SI2 ) + ABS( H( 2, 1 ) ) +
- $ ABS( H( 3, 1 ) )
- IF( S.EQ.ZERO ) THEN
- V( 1 ) = ZERO
- V( 2 ) = ZERO
- V( 3 ) = ZERO
- ELSE
- H21S = H( 2, 1 ) / S
- H31S = H( 3, 1 ) / S
- V( 1 ) = ( H( 1, 1 )-SR1 )*( ( H( 1, 1 )-SR2 ) / S ) -
- $ SI1*( SI2 / S ) + H( 1, 2 )*H21S + H( 1, 3 )*H31S
- V( 2 ) = H21S*( H( 1, 1 )+H( 2, 2 )-SR1-SR2 ) +
- $ H( 2, 3 )*H31S
- V( 3 ) = H31S*( H( 1, 1 )+H( 3, 3 )-SR1-SR2 ) +
- $ H21S*H( 3, 2 )
- END IF
- END IF
- END
diff --git a/src/lib/lapack/dlaqr2.f b/src/lib/lapack/dlaqr2.f
deleted file mode 100644
index 6ddb3309..00000000
--- a/src/lib/lapack/dlaqr2.f
+++ /dev/null
@@ -1,551 +0,0 @@
- SUBROUTINE DLAQR2( WANTT, WANTZ, N, KTOP, KBOT, NW, H, LDH, ILOZ,
- $ IHIZ, Z, LDZ, NS, ND, SR, SI, V, LDV, NH, T,
- $ LDT, NV, WV, LDWV, WORK, LWORK )
-*
-* -- LAPACK auxiliary routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- INTEGER IHIZ, ILOZ, KBOT, KTOP, LDH, LDT, LDV, LDWV,
- $ LDZ, LWORK, N, ND, NH, NS, NV, NW
- LOGICAL WANTT, WANTZ
-* ..
-* .. Array Arguments ..
- DOUBLE PRECISION H( LDH, * ), SI( * ), SR( * ), T( LDT, * ),
- $ V( LDV, * ), WORK( * ), WV( LDWV, * ),
- $ Z( LDZ, * )
-* ..
-*
-* This subroutine is identical to DLAQR3 except that it avoids
-* recursion by calling DLAHQR instead of DLAQR4.
-*
-*
-* ******************************************************************
-* Aggressive early deflation:
-*
-* This subroutine accepts as input an upper Hessenberg matrix
-* H and performs an orthogonal similarity transformation
-* designed to detect and deflate fully converged eigenvalues from
-* a trailing principal submatrix. On output H has been over-
-* written by a new Hessenberg matrix that is a perturbation of
-* an orthogonal similarity transformation of H. It is to be
-* hoped that the final version of H has many zero subdiagonal
-* entries.
-*
-* ******************************************************************
-* WANTT (input) LOGICAL
-* If .TRUE., then the Hessenberg matrix H is fully updated
-* so that the quasi-triangular Schur factor may be
-* computed (in cooperation with the calling subroutine).
-* If .FALSE., then only enough of H is updated to preserve
-* the eigenvalues.
-*
-* WANTZ (input) LOGICAL
-* If .TRUE., then the orthogonal matrix Z is updated so
-* so that the orthogonal Schur factor may be computed
-* (in cooperation with the calling subroutine).
-* If .FALSE., then Z is not referenced.
-*
-* N (input) INTEGER
-* The order of the matrix H and (if WANTZ is .TRUE.) the
-* order of the orthogonal matrix Z.
-*
-* KTOP (input) INTEGER
-* It is assumed that either KTOP = 1 or H(KTOP,KTOP-1)=0.
-* KBOT and KTOP together determine an isolated block
-* along the diagonal of the Hessenberg matrix.
-*
-* KBOT (input) INTEGER
-* It is assumed without a check that either
-* KBOT = N or H(KBOT+1,KBOT)=0. KBOT and KTOP together
-* determine an isolated block along the diagonal of the
-* Hessenberg matrix.
-*
-* NW (input) INTEGER
-* Deflation window size. 1 .LE. NW .LE. (KBOT-KTOP+1).
-*
-* H (input/output) DOUBLE PRECISION array, dimension (LDH,N)
-* On input the initial N-by-N section of H stores the
-* Hessenberg matrix undergoing aggressive early deflation.
-* On output H has been transformed by an orthogonal
-* similarity transformation, perturbed, and the returned
-* to Hessenberg form that (it is to be hoped) has some
-* zero subdiagonal entries.
-*
-* LDH (input) integer
-* Leading dimension of H just as declared in the calling
-* subroutine. N .LE. LDH
-*
-* ILOZ (input) INTEGER
-* IHIZ (input) INTEGER
-* Specify the rows of Z to which transformations must be
-* applied if WANTZ is .TRUE.. 1 .LE. ILOZ .LE. IHIZ .LE. N.
-*
-* Z (input/output) DOUBLE PRECISION array, dimension (LDZ,IHI)
-* IF WANTZ is .TRUE., then on output, the orthogonal
-* similarity transformation mentioned above has been
-* accumulated into Z(ILOZ:IHIZ,ILO:IHI) from the right.
-* If WANTZ is .FALSE., then Z is unreferenced.
-*
-* LDZ (input) integer
-* The leading dimension of Z just as declared in the
-* calling subroutine. 1 .LE. LDZ.
-*
-* NS (output) integer
-* The number of unconverged (ie approximate) eigenvalues
-* returned in SR and SI that may be used as shifts by the
-* calling subroutine.
-*
-* ND (output) integer
-* The number of converged eigenvalues uncovered by this
-* subroutine.
-*
-* SR (output) DOUBLE PRECISION array, dimension KBOT
-* SI (output) DOUBLE PRECISION array, dimension KBOT
-* On output, the real and imaginary parts of approximate
-* eigenvalues that may be used for shifts are stored in
-* SR(KBOT-ND-NS+1) through SR(KBOT-ND) and
-* SI(KBOT-ND-NS+1) through SI(KBOT-ND), respectively.
-* The real and imaginary parts of converged eigenvalues
-* are stored in SR(KBOT-ND+1) through SR(KBOT) and
-* SI(KBOT-ND+1) through SI(KBOT), respectively.
-*
-* V (workspace) DOUBLE PRECISION array, dimension (LDV,NW)
-* An NW-by-NW work array.
-*
-* LDV (input) integer scalar
-* The leading dimension of V just as declared in the
-* calling subroutine. NW .LE. LDV
-*
-* NH (input) integer scalar
-* The number of columns of T. NH.GE.NW.
-*
-* T (workspace) DOUBLE PRECISION array, dimension (LDT,NW)
-*
-* LDT (input) integer
-* The leading dimension of T just as declared in the
-* calling subroutine. NW .LE. LDT
-*
-* NV (input) integer
-* The number of rows of work array WV available for
-* workspace. NV.GE.NW.
-*
-* WV (workspace) DOUBLE PRECISION array, dimension (LDWV,NW)
-*
-* LDWV (input) integer
-* The leading dimension of W just as declared in the
-* calling subroutine. NW .LE. LDV
-*
-* WORK (workspace) DOUBLE PRECISION array, dimension LWORK.
-* On exit, WORK(1) is set to an estimate of the optimal value
-* of LWORK for the given values of N, NW, KTOP and KBOT.
-*
-* LWORK (input) integer
-* The dimension of the work array WORK. LWORK = 2*NW
-* suffices, but greater efficiency may result from larger
-* values of LWORK.
-*
-* If LWORK = -1, then a workspace query is assumed; DLAQR2
-* only estimates the optimal workspace size for the given
-* values of N, NW, KTOP and KBOT. The estimate is returned
-* in WORK(1). No error message related to LWORK is issued
-* by XERBLA. Neither H nor Z are accessed.
-*
-* ================================================================
-* Based on contributions by
-* Karen Braman and Ralph Byers, Department of Mathematics,
-* University of Kansas, USA
-*
-* ================================================================
-* .. Parameters ..
- DOUBLE PRECISION ZERO, ONE
- PARAMETER ( ZERO = 0.0d0, ONE = 1.0d0 )
-* ..
-* .. Local Scalars ..
- DOUBLE PRECISION AA, BB, BETA, CC, CS, DD, EVI, EVK, FOO, S,
- $ SAFMAX, SAFMIN, SMLNUM, SN, TAU, ULP
- INTEGER I, IFST, ILST, INFO, INFQR, J, JW, K, KCOL,
- $ KEND, KLN, KROW, KWTOP, LTOP, LWK1, LWK2,
- $ LWKOPT
- LOGICAL BULGE, SORTED
-* ..
-* .. External Functions ..
- DOUBLE PRECISION DLAMCH
- EXTERNAL DLAMCH
-* ..
-* .. External Subroutines ..
- EXTERNAL DCOPY, DGEHRD, DGEMM, DLABAD, DLACPY, DLAHQR,
- $ DLANV2, DLARF, DLARFG, DLASET, DORGHR, DTREXC
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC ABS, DBLE, INT, MAX, MIN, SQRT
-* ..
-* .. Executable Statements ..
-*
-* ==== Estimate optimal workspace. ====
-*
- JW = MIN( NW, KBOT-KTOP+1 )
- IF( JW.LE.2 ) THEN
- LWKOPT = 1
- ELSE
-*
-* ==== Workspace query call to DGEHRD ====
-*
- CALL DGEHRD( JW, 1, JW-1, T, LDT, WORK, WORK, -1, INFO )
- LWK1 = INT( WORK( 1 ) )
-*
-* ==== Workspace query call to DORGHR ====
-*
- CALL DORGHR( JW, 1, JW-1, T, LDT, WORK, WORK, -1, INFO )
- LWK2 = INT( WORK( 1 ) )
-*
-* ==== Optimal workspace ====
-*
- LWKOPT = JW + MAX( LWK1, LWK2 )
- END IF
-*
-* ==== Quick return in case of workspace query. ====
-*
- IF( LWORK.EQ.-1 ) THEN
- WORK( 1 ) = DBLE( LWKOPT )
- RETURN
- END IF
-*
-* ==== Nothing to do ...
-* ... for an empty active block ... ====
- NS = 0
- ND = 0
- IF( KTOP.GT.KBOT )
- $ RETURN
-* ... nor for an empty deflation window. ====
- IF( NW.LT.1 )
- $ RETURN
-*
-* ==== Machine constants ====
-*
- SAFMIN = DLAMCH( 'SAFE MINIMUM' )
- SAFMAX = ONE / SAFMIN
- CALL DLABAD( SAFMIN, SAFMAX )
- ULP = DLAMCH( 'PRECISION' )
- SMLNUM = SAFMIN*( DBLE( N ) / ULP )
-*
-* ==== Setup deflation window ====
-*
- JW = MIN( NW, KBOT-KTOP+1 )
- KWTOP = KBOT - JW + 1
- IF( KWTOP.EQ.KTOP ) THEN
- S = ZERO
- ELSE
- S = H( KWTOP, KWTOP-1 )
- END IF
-*
- IF( KBOT.EQ.KWTOP ) THEN
-*
-* ==== 1-by-1 deflation window: not much to do ====
-*
- SR( KWTOP ) = H( KWTOP, KWTOP )
- SI( KWTOP ) = ZERO
- NS = 1
- ND = 0
- IF( ABS( S ).LE.MAX( SMLNUM, ULP*ABS( H( KWTOP, KWTOP ) ) ) )
- $ THEN
- NS = 0
- ND = 1
- IF( KWTOP.GT.KTOP )
- $ H( KWTOP, KWTOP-1 ) = ZERO
- END IF
- RETURN
- END IF
-*
-* ==== Convert to spike-triangular form. (In case of a
-* . rare QR failure, this routine continues to do
-* . aggressive early deflation using that part of
-* . the deflation window that converged using INFQR
-* . here and there to keep track.) ====
-*
- CALL DLACPY( 'U', JW, JW, H( KWTOP, KWTOP ), LDH, T, LDT )
- CALL DCOPY( JW-1, H( KWTOP+1, KWTOP ), LDH+1, T( 2, 1 ), LDT+1 )
-*
- CALL DLASET( 'A', JW, JW, ZERO, ONE, V, LDV )
- CALL DLAHQR( .true., .true., JW, 1, JW, T, LDT, SR( KWTOP ),
- $ SI( KWTOP ), 1, JW, V, LDV, INFQR )
-*
-* ==== DTREXC needs a clean margin near the diagonal ====
-*
- DO 10 J = 1, JW - 3
- T( J+2, J ) = ZERO
- T( J+3, J ) = ZERO
- 10 CONTINUE
- IF( JW.GT.2 )
- $ T( JW, JW-2 ) = ZERO
-*
-* ==== Deflation detection loop ====
-*
- NS = JW
- ILST = INFQR + 1
- 20 CONTINUE
- IF( ILST.LE.NS ) THEN
- IF( NS.EQ.1 ) THEN
- BULGE = .FALSE.
- ELSE
- BULGE = T( NS, NS-1 ).NE.ZERO
- END IF
-*
-* ==== Small spike tip test for deflation ====
-*
- IF( .NOT.BULGE ) THEN
-*
-* ==== Real eigenvalue ====
-*
- FOO = ABS( T( NS, NS ) )
- IF( FOO.EQ.ZERO )
- $ FOO = ABS( S )
- IF( ABS( S*V( 1, NS ) ).LE.MAX( SMLNUM, ULP*FOO ) ) THEN
-*
-* ==== Deflatable ====
-*
- NS = NS - 1
- ELSE
-*
-* ==== Undeflatable. Move it up out of the way.
-* . (DTREXC can not fail in this case.) ====
-*
- IFST = NS
- CALL DTREXC( 'V', JW, T, LDT, V, LDV, IFST, ILST, WORK,
- $ INFO )
- ILST = ILST + 1
- END IF
- ELSE
-*
-* ==== Complex conjugate pair ====
-*
- FOO = ABS( T( NS, NS ) ) + SQRT( ABS( T( NS, NS-1 ) ) )*
- $ SQRT( ABS( T( NS-1, NS ) ) )
- IF( FOO.EQ.ZERO )
- $ FOO = ABS( S )
- IF( MAX( ABS( S*V( 1, NS ) ), ABS( S*V( 1, NS-1 ) ) ).LE.
- $ MAX( SMLNUM, ULP*FOO ) ) THEN
-*
-* ==== Deflatable ====
-*
- NS = NS - 2
- ELSE
-*
-* ==== Undflatable. Move them up out of the way.
-* . Fortunately, DTREXC does the right thing with
-* . ILST in case of a rare exchange failure. ====
-*
- IFST = NS
- CALL DTREXC( 'V', JW, T, LDT, V, LDV, IFST, ILST, WORK,
- $ INFO )
- ILST = ILST + 2
- END IF
- END IF
-*
-* ==== End deflation detection loop ====
-*
- GO TO 20
- END IF
-*
-* ==== Return to Hessenberg form ====
-*
- IF( NS.EQ.0 )
- $ S = ZERO
-*
- IF( NS.LT.JW ) THEN
-*
-* ==== sorting diagonal blocks of T improves accuracy for
-* . graded matrices. Bubble sort deals well with
-* . exchange failures. ====
-*
- SORTED = .false.
- I = NS + 1
- 30 CONTINUE
- IF( SORTED )
- $ GO TO 50
- SORTED = .true.
-*
- KEND = I - 1
- I = INFQR + 1
- IF( I.EQ.NS ) THEN
- K = I + 1
- ELSE IF( T( I+1, I ).EQ.ZERO ) THEN
- K = I + 1
- ELSE
- K = I + 2
- END IF
- 40 CONTINUE
- IF( K.LE.KEND ) THEN
- IF( K.EQ.I+1 ) THEN
- EVI = ABS( T( I, I ) )
- ELSE
- EVI = ABS( T( I, I ) ) + SQRT( ABS( T( I+1, I ) ) )*
- $ SQRT( ABS( T( I, I+1 ) ) )
- END IF
-*
- IF( K.EQ.KEND ) THEN
- EVK = ABS( T( K, K ) )
- ELSE IF( T( K+1, K ).EQ.ZERO ) THEN
- EVK = ABS( T( K, K ) )
- ELSE
- EVK = ABS( T( K, K ) ) + SQRT( ABS( T( K+1, K ) ) )*
- $ SQRT( ABS( T( K, K+1 ) ) )
- END IF
-*
- IF( EVI.GE.EVK ) THEN
- I = K
- ELSE
- SORTED = .false.
- IFST = I
- ILST = K
- CALL DTREXC( 'V', JW, T, LDT, V, LDV, IFST, ILST, WORK,
- $ INFO )
- IF( INFO.EQ.0 ) THEN
- I = ILST
- ELSE
- I = K
- END IF
- END IF
- IF( I.EQ.KEND ) THEN
- K = I + 1
- ELSE IF( T( I+1, I ).EQ.ZERO ) THEN
- K = I + 1
- ELSE
- K = I + 2
- END IF
- GO TO 40
- END IF
- GO TO 30
- 50 CONTINUE
- END IF
-*
-* ==== Restore shift/eigenvalue array from T ====
-*
- I = JW
- 60 CONTINUE
- IF( I.GE.INFQR+1 ) THEN
- IF( I.EQ.INFQR+1 ) THEN
- SR( KWTOP+I-1 ) = T( I, I )
- SI( KWTOP+I-1 ) = ZERO
- I = I - 1
- ELSE IF( T( I, I-1 ).EQ.ZERO ) THEN
- SR( KWTOP+I-1 ) = T( I, I )
- SI( KWTOP+I-1 ) = ZERO
- I = I - 1
- ELSE
- AA = T( I-1, I-1 )
- CC = T( I, I-1 )
- BB = T( I-1, I )
- DD = T( I, I )
- CALL DLANV2( AA, BB, CC, DD, SR( KWTOP+I-2 ),
- $ SI( KWTOP+I-2 ), SR( KWTOP+I-1 ),
- $ SI( KWTOP+I-1 ), CS, SN )
- I = I - 2
- END IF
- GO TO 60
- END IF
-*
- IF( NS.LT.JW .OR. S.EQ.ZERO ) THEN
- IF( NS.GT.1 .AND. S.NE.ZERO ) THEN
-*
-* ==== Reflect spike back into lower triangle ====
-*
- CALL DCOPY( NS, V, LDV, WORK, 1 )
- BETA = WORK( 1 )
- CALL DLARFG( NS, BETA, WORK( 2 ), 1, TAU )
- WORK( 1 ) = ONE
-*
- CALL DLASET( 'L', JW-2, JW-2, ZERO, ZERO, T( 3, 1 ), LDT )
-*
- CALL DLARF( 'L', NS, JW, WORK, 1, TAU, T, LDT,
- $ WORK( JW+1 ) )
- CALL DLARF( 'R', NS, NS, WORK, 1, TAU, T, LDT,
- $ WORK( JW+1 ) )
- CALL DLARF( 'R', JW, NS, WORK, 1, TAU, V, LDV,
- $ WORK( JW+1 ) )
-*
- CALL DGEHRD( JW, 1, NS, T, LDT, WORK, WORK( JW+1 ),
- $ LWORK-JW, INFO )
- END IF
-*
-* ==== Copy updated reduced window into place ====
-*
- IF( KWTOP.GT.1 )
- $ H( KWTOP, KWTOP-1 ) = S*V( 1, 1 )
- CALL DLACPY( 'U', JW, JW, T, LDT, H( KWTOP, KWTOP ), LDH )
- CALL DCOPY( JW-1, T( 2, 1 ), LDT+1, H( KWTOP+1, KWTOP ),
- $ LDH+1 )
-*
-* ==== Accumulate orthogonal matrix in order update
-* . H and Z, if requested. (A modified version
-* . of DORGHR that accumulates block Householder
-* . transformations into V directly might be
-* . marginally more efficient than the following.) ====
-*
- IF( NS.GT.1 .AND. S.NE.ZERO ) THEN
- CALL DORGHR( JW, 1, NS, T, LDT, WORK, WORK( JW+1 ),
- $ LWORK-JW, INFO )
- CALL DGEMM( 'N', 'N', JW, NS, NS, ONE, V, LDV, T, LDT, ZERO,
- $ WV, LDWV )
- CALL DLACPY( 'A', JW, NS, WV, LDWV, V, LDV )
- END IF
-*
-* ==== Update vertical slab in H ====
-*
- IF( WANTT ) THEN
- LTOP = 1
- ELSE
- LTOP = KTOP
- END IF
- DO 70 KROW = LTOP, KWTOP - 1, NV
- KLN = MIN( NV, KWTOP-KROW )
- CALL DGEMM( 'N', 'N', KLN, JW, JW, ONE, H( KROW, KWTOP ),
- $ LDH, V, LDV, ZERO, WV, LDWV )
- CALL DLACPY( 'A', KLN, JW, WV, LDWV, H( KROW, KWTOP ), LDH )
- 70 CONTINUE
-*
-* ==== Update horizontal slab in H ====
-*
- IF( WANTT ) THEN
- DO 80 KCOL = KBOT + 1, N, NH
- KLN = MIN( NH, N-KCOL+1 )
- CALL DGEMM( 'C', 'N', JW, KLN, JW, ONE, V, LDV,
- $ H( KWTOP, KCOL ), LDH, ZERO, T, LDT )
- CALL DLACPY( 'A', JW, KLN, T, LDT, H( KWTOP, KCOL ),
- $ LDH )
- 80 CONTINUE
- END IF
-*
-* ==== Update vertical slab in Z ====
-*
- IF( WANTZ ) THEN
- DO 90 KROW = ILOZ, IHIZ, NV
- KLN = MIN( NV, IHIZ-KROW+1 )
- CALL DGEMM( 'N', 'N', KLN, JW, JW, ONE, Z( KROW, KWTOP ),
- $ LDZ, V, LDV, ZERO, WV, LDWV )
- CALL DLACPY( 'A', KLN, JW, WV, LDWV, Z( KROW, KWTOP ),
- $ LDZ )
- 90 CONTINUE
- END IF
- END IF
-*
-* ==== Return the number of deflations ... ====
-*
- ND = JW - NS
-*
-* ==== ... and the number of shifts. (Subtracting
-* . INFQR from the spike length takes care
-* . of the case of a rare QR failure while
-* . calculating eigenvalues of the deflation
-* . window.) ====
-*
- NS = NS - INFQR
-*
-* ==== Return optimal workspace. ====
-*
- WORK( 1 ) = DBLE( LWKOPT )
-*
-* ==== End of DLAQR2 ====
-*
- END
diff --git a/src/lib/lapack/dlaqr3.f b/src/lib/lapack/dlaqr3.f
deleted file mode 100644
index 877b267a..00000000
--- a/src/lib/lapack/dlaqr3.f
+++ /dev/null
@@ -1,561 +0,0 @@
- SUBROUTINE DLAQR3( WANTT, WANTZ, N, KTOP, KBOT, NW, H, LDH, ILOZ,
- $ IHIZ, Z, LDZ, NS, ND, SR, SI, V, LDV, NH, T,
- $ LDT, NV, WV, LDWV, WORK, LWORK )
-*
-* -- LAPACK auxiliary routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- INTEGER IHIZ, ILOZ, KBOT, KTOP, LDH, LDT, LDV, LDWV,
- $ LDZ, LWORK, N, ND, NH, NS, NV, NW
- LOGICAL WANTT, WANTZ
-* ..
-* .. Array Arguments ..
- DOUBLE PRECISION H( LDH, * ), SI( * ), SR( * ), T( LDT, * ),
- $ V( LDV, * ), WORK( * ), WV( LDWV, * ),
- $ Z( LDZ, * )
-* ..
-*
-* ******************************************************************
-* Aggressive early deflation:
-*
-* This subroutine accepts as input an upper Hessenberg matrix
-* H and performs an orthogonal similarity transformation
-* designed to detect and deflate fully converged eigenvalues from
-* a trailing principal submatrix. On output H has been over-
-* written by a new Hessenberg matrix that is a perturbation of
-* an orthogonal similarity transformation of H. It is to be
-* hoped that the final version of H has many zero subdiagonal
-* entries.
-*
-* ******************************************************************
-* WANTT (input) LOGICAL
-* If .TRUE., then the Hessenberg matrix H is fully updated
-* so that the quasi-triangular Schur factor may be
-* computed (in cooperation with the calling subroutine).
-* If .FALSE., then only enough of H is updated to preserve
-* the eigenvalues.
-*
-* WANTZ (input) LOGICAL
-* If .TRUE., then the orthogonal matrix Z is updated so
-* so that the orthogonal Schur factor may be computed
-* (in cooperation with the calling subroutine).
-* If .FALSE., then Z is not referenced.
-*
-* N (input) INTEGER
-* The order of the matrix H and (if WANTZ is .TRUE.) the
-* order of the orthogonal matrix Z.
-*
-* KTOP (input) INTEGER
-* It is assumed that either KTOP = 1 or H(KTOP,KTOP-1)=0.
-* KBOT and KTOP together determine an isolated block
-* along the diagonal of the Hessenberg matrix.
-*
-* KBOT (input) INTEGER
-* It is assumed without a check that either
-* KBOT = N or H(KBOT+1,KBOT)=0. KBOT and KTOP together
-* determine an isolated block along the diagonal of the
-* Hessenberg matrix.
-*
-* NW (input) INTEGER
-* Deflation window size. 1 .LE. NW .LE. (KBOT-KTOP+1).
-*
-* H (input/output) DOUBLE PRECISION array, dimension (LDH,N)
-* On input the initial N-by-N section of H stores the
-* Hessenberg matrix undergoing aggressive early deflation.
-* On output H has been transformed by an orthogonal
-* similarity transformation, perturbed, and the returned
-* to Hessenberg form that (it is to be hoped) has some
-* zero subdiagonal entries.
-*
-* LDH (input) integer
-* Leading dimension of H just as declared in the calling
-* subroutine. N .LE. LDH
-*
-* ILOZ (input) INTEGER
-* IHIZ (input) INTEGER
-* Specify the rows of Z to which transformations must be
-* applied if WANTZ is .TRUE.. 1 .LE. ILOZ .LE. IHIZ .LE. N.
-*
-* Z (input/output) DOUBLE PRECISION array, dimension (LDZ,IHI)
-* IF WANTZ is .TRUE., then on output, the orthogonal
-* similarity transformation mentioned above has been
-* accumulated into Z(ILOZ:IHIZ,ILO:IHI) from the right.
-* If WANTZ is .FALSE., then Z is unreferenced.
-*
-* LDZ (input) integer
-* The leading dimension of Z just as declared in the
-* calling subroutine. 1 .LE. LDZ.
-*
-* NS (output) integer
-* The number of unconverged (ie approximate) eigenvalues
-* returned in SR and SI that may be used as shifts by the
-* calling subroutine.
-*
-* ND (output) integer
-* The number of converged eigenvalues uncovered by this
-* subroutine.
-*
-* SR (output) DOUBLE PRECISION array, dimension KBOT
-* SI (output) DOUBLE PRECISION array, dimension KBOT
-* On output, the real and imaginary parts of approximate
-* eigenvalues that may be used for shifts are stored in
-* SR(KBOT-ND-NS+1) through SR(KBOT-ND) and
-* SI(KBOT-ND-NS+1) through SI(KBOT-ND), respectively.
-* The real and imaginary parts of converged eigenvalues
-* are stored in SR(KBOT-ND+1) through SR(KBOT) and
-* SI(KBOT-ND+1) through SI(KBOT), respectively.
-*
-* V (workspace) DOUBLE PRECISION array, dimension (LDV,NW)
-* An NW-by-NW work array.
-*
-* LDV (input) integer scalar
-* The leading dimension of V just as declared in the
-* calling subroutine. NW .LE. LDV
-*
-* NH (input) integer scalar
-* The number of columns of T. NH.GE.NW.
-*
-* T (workspace) DOUBLE PRECISION array, dimension (LDT,NW)
-*
-* LDT (input) integer
-* The leading dimension of T just as declared in the
-* calling subroutine. NW .LE. LDT
-*
-* NV (input) integer
-* The number of rows of work array WV available for
-* workspace. NV.GE.NW.
-*
-* WV (workspace) DOUBLE PRECISION array, dimension (LDWV,NW)
-*
-* LDWV (input) integer
-* The leading dimension of W just as declared in the
-* calling subroutine. NW .LE. LDV
-*
-* WORK (workspace) DOUBLE PRECISION array, dimension LWORK.
-* On exit, WORK(1) is set to an estimate of the optimal value
-* of LWORK for the given values of N, NW, KTOP and KBOT.
-*
-* LWORK (input) integer
-* The dimension of the work array WORK. LWORK = 2*NW
-* suffices, but greater efficiency may result from larger
-* values of LWORK.
-*
-* If LWORK = -1, then a workspace query is assumed; DLAQR3
-* only estimates the optimal workspace size for the given
-* values of N, NW, KTOP and KBOT. The estimate is returned
-* in WORK(1). No error message related to LWORK is issued
-* by XERBLA. Neither H nor Z are accessed.
-*
-* ================================================================
-* Based on contributions by
-* Karen Braman and Ralph Byers, Department of Mathematics,
-* University of Kansas, USA
-*
-* ==================================================================
-* .. Parameters ..
- DOUBLE PRECISION ZERO, ONE
- PARAMETER ( ZERO = 0.0d0, ONE = 1.0d0 )
-* ..
-* .. Local Scalars ..
- DOUBLE PRECISION AA, BB, BETA, CC, CS, DD, EVI, EVK, FOO, S,
- $ SAFMAX, SAFMIN, SMLNUM, SN, TAU, ULP
- INTEGER I, IFST, ILST, INFO, INFQR, J, JW, K, KCOL,
- $ KEND, KLN, KROW, KWTOP, LTOP, LWK1, LWK2, LWK3,
- $ LWKOPT, NMIN
- LOGICAL BULGE, SORTED
-* ..
-* .. External Functions ..
- DOUBLE PRECISION DLAMCH
- INTEGER ILAENV
- EXTERNAL DLAMCH, ILAENV
-* ..
-* .. External Subroutines ..
- EXTERNAL DCOPY, DGEHRD, DGEMM, DLABAD, DLACPY, DLAHQR,
- $ DLANV2, DLAQR4, DLARF, DLARFG, DLASET, DORGHR,
- $ DTREXC
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC ABS, DBLE, INT, MAX, MIN, SQRT
-* ..
-* .. Executable Statements ..
-*
-* ==== Estimate optimal workspace. ====
-*
- JW = MIN( NW, KBOT-KTOP+1 )
- IF( JW.LE.2 ) THEN
- LWKOPT = 1
- ELSE
-*
-* ==== Workspace query call to DGEHRD ====
-*
- CALL DGEHRD( JW, 1, JW-1, T, LDT, WORK, WORK, -1, INFO )
- LWK1 = INT( WORK( 1 ) )
-*
-* ==== Workspace query call to DORGHR ====
-*
- CALL DORGHR( JW, 1, JW-1, T, LDT, WORK, WORK, -1, INFO )
- LWK2 = INT( WORK( 1 ) )
-*
-* ==== Workspace query call to DLAQR4 ====
-*
- CALL DLAQR4( .true., .true., JW, 1, JW, T, LDT, SR, SI, 1, JW,
- $ V, LDV, WORK, -1, INFQR )
- LWK3 = INT( WORK( 1 ) )
-*
-* ==== Optimal workspace ====
-*
- LWKOPT = MAX( JW+MAX( LWK1, LWK2 ), LWK3 )
- END IF
-*
-* ==== Quick return in case of workspace query. ====
-*
- IF( LWORK.EQ.-1 ) THEN
- WORK( 1 ) = DBLE( LWKOPT )
- RETURN
- END IF
-*
-* ==== Nothing to do ...
-* ... for an empty active block ... ====
- NS = 0
- ND = 0
- IF( KTOP.GT.KBOT )
- $ RETURN
-* ... nor for an empty deflation window. ====
- IF( NW.LT.1 )
- $ RETURN
-*
-* ==== Machine constants ====
-*
- SAFMIN = DLAMCH( 'SAFE MINIMUM' )
- SAFMAX = ONE / SAFMIN
- CALL DLABAD( SAFMIN, SAFMAX )
- ULP = DLAMCH( 'PRECISION' )
- SMLNUM = SAFMIN*( DBLE( N ) / ULP )
-*
-* ==== Setup deflation window ====
-*
- JW = MIN( NW, KBOT-KTOP+1 )
- KWTOP = KBOT - JW + 1
- IF( KWTOP.EQ.KTOP ) THEN
- S = ZERO
- ELSE
- S = H( KWTOP, KWTOP-1 )
- END IF
-*
- IF( KBOT.EQ.KWTOP ) THEN
-*
-* ==== 1-by-1 deflation window: not much to do ====
-*
- SR( KWTOP ) = H( KWTOP, KWTOP )
- SI( KWTOP ) = ZERO
- NS = 1
- ND = 0
- IF( ABS( S ).LE.MAX( SMLNUM, ULP*ABS( H( KWTOP, KWTOP ) ) ) )
- $ THEN
- NS = 0
- ND = 1
- IF( KWTOP.GT.KTOP )
- $ H( KWTOP, KWTOP-1 ) = ZERO
- END IF
- RETURN
- END IF
-*
-* ==== Convert to spike-triangular form. (In case of a
-* . rare QR failure, this routine continues to do
-* . aggressive early deflation using that part of
-* . the deflation window that converged using INFQR
-* . here and there to keep track.) ====
-*
- CALL DLACPY( 'U', JW, JW, H( KWTOP, KWTOP ), LDH, T, LDT )
- CALL DCOPY( JW-1, H( KWTOP+1, KWTOP ), LDH+1, T( 2, 1 ), LDT+1 )
-*
- CALL DLASET( 'A', JW, JW, ZERO, ONE, V, LDV )
- NMIN = ILAENV( 12, 'DLAQR3', 'SV', JW, 1, JW, LWORK )
- IF( JW.GT.NMIN ) THEN
- CALL DLAQR4( .true., .true., JW, 1, JW, T, LDT, SR( KWTOP ),
- $ SI( KWTOP ), 1, JW, V, LDV, WORK, LWORK, INFQR )
- ELSE
- CALL DLAHQR( .true., .true., JW, 1, JW, T, LDT, SR( KWTOP ),
- $ SI( KWTOP ), 1, JW, V, LDV, INFQR )
- END IF
-*
-* ==== DTREXC needs a clean margin near the diagonal ====
-*
- DO 10 J = 1, JW - 3
- T( J+2, J ) = ZERO
- T( J+3, J ) = ZERO
- 10 CONTINUE
- IF( JW.GT.2 )
- $ T( JW, JW-2 ) = ZERO
-*
-* ==== Deflation detection loop ====
-*
- NS = JW
- ILST = INFQR + 1
- 20 CONTINUE
- IF( ILST.LE.NS ) THEN
- IF( NS.EQ.1 ) THEN
- BULGE = .FALSE.
- ELSE
- BULGE = T( NS, NS-1 ).NE.ZERO
- END IF
-*
-* ==== Small spike tip test for deflation ====
-*
- IF( .NOT.BULGE ) THEN
-*
-* ==== Real eigenvalue ====
-*
- FOO = ABS( T( NS, NS ) )
- IF( FOO.EQ.ZERO )
- $ FOO = ABS( S )
- IF( ABS( S*V( 1, NS ) ).LE.MAX( SMLNUM, ULP*FOO ) ) THEN
-*
-* ==== Deflatable ====
-*
- NS = NS - 1
- ELSE
-*
-* ==== Undeflatable. Move it up out of the way.
-* . (DTREXC can not fail in this case.) ====
-*
- IFST = NS
- CALL DTREXC( 'V', JW, T, LDT, V, LDV, IFST, ILST, WORK,
- $ INFO )
- ILST = ILST + 1
- END IF
- ELSE
-*
-* ==== Complex conjugate pair ====
-*
- FOO = ABS( T( NS, NS ) ) + SQRT( ABS( T( NS, NS-1 ) ) )*
- $ SQRT( ABS( T( NS-1, NS ) ) )
- IF( FOO.EQ.ZERO )
- $ FOO = ABS( S )
- IF( MAX( ABS( S*V( 1, NS ) ), ABS( S*V( 1, NS-1 ) ) ).LE.
- $ MAX( SMLNUM, ULP*FOO ) ) THEN
-*
-* ==== Deflatable ====
-*
- NS = NS - 2
- ELSE
-*
-* ==== Undflatable. Move them up out of the way.
-* . Fortunately, DTREXC does the right thing with
-* . ILST in case of a rare exchange failure. ====
-*
- IFST = NS
- CALL DTREXC( 'V', JW, T, LDT, V, LDV, IFST, ILST, WORK,
- $ INFO )
- ILST = ILST + 2
- END IF
- END IF
-*
-* ==== End deflation detection loop ====
-*
- GO TO 20
- END IF
-*
-* ==== Return to Hessenberg form ====
-*
- IF( NS.EQ.0 )
- $ S = ZERO
-*
- IF( NS.LT.JW ) THEN
-*
-* ==== sorting diagonal blocks of T improves accuracy for
-* . graded matrices. Bubble sort deals well with
-* . exchange failures. ====
-*
- SORTED = .false.
- I = NS + 1
- 30 CONTINUE
- IF( SORTED )
- $ GO TO 50
- SORTED = .true.
-*
- KEND = I - 1
- I = INFQR + 1
- IF( I.EQ.NS ) THEN
- K = I + 1
- ELSE IF( T( I+1, I ).EQ.ZERO ) THEN
- K = I + 1
- ELSE
- K = I + 2
- END IF
- 40 CONTINUE
- IF( K.LE.KEND ) THEN
- IF( K.EQ.I+1 ) THEN
- EVI = ABS( T( I, I ) )
- ELSE
- EVI = ABS( T( I, I ) ) + SQRT( ABS( T( I+1, I ) ) )*
- $ SQRT( ABS( T( I, I+1 ) ) )
- END IF
-*
- IF( K.EQ.KEND ) THEN
- EVK = ABS( T( K, K ) )
- ELSE IF( T( K+1, K ).EQ.ZERO ) THEN
- EVK = ABS( T( K, K ) )
- ELSE
- EVK = ABS( T( K, K ) ) + SQRT( ABS( T( K+1, K ) ) )*
- $ SQRT( ABS( T( K, K+1 ) ) )
- END IF
-*
- IF( EVI.GE.EVK ) THEN
- I = K
- ELSE
- SORTED = .false.
- IFST = I
- ILST = K
- CALL DTREXC( 'V', JW, T, LDT, V, LDV, IFST, ILST, WORK,
- $ INFO )
- IF( INFO.EQ.0 ) THEN
- I = ILST
- ELSE
- I = K
- END IF
- END IF
- IF( I.EQ.KEND ) THEN
- K = I + 1
- ELSE IF( T( I+1, I ).EQ.ZERO ) THEN
- K = I + 1
- ELSE
- K = I + 2
- END IF
- GO TO 40
- END IF
- GO TO 30
- 50 CONTINUE
- END IF
-*
-* ==== Restore shift/eigenvalue array from T ====
-*
- I = JW
- 60 CONTINUE
- IF( I.GE.INFQR+1 ) THEN
- IF( I.EQ.INFQR+1 ) THEN
- SR( KWTOP+I-1 ) = T( I, I )
- SI( KWTOP+I-1 ) = ZERO
- I = I - 1
- ELSE IF( T( I, I-1 ).EQ.ZERO ) THEN
- SR( KWTOP+I-1 ) = T( I, I )
- SI( KWTOP+I-1 ) = ZERO
- I = I - 1
- ELSE
- AA = T( I-1, I-1 )
- CC = T( I, I-1 )
- BB = T( I-1, I )
- DD = T( I, I )
- CALL DLANV2( AA, BB, CC, DD, SR( KWTOP+I-2 ),
- $ SI( KWTOP+I-2 ), SR( KWTOP+I-1 ),
- $ SI( KWTOP+I-1 ), CS, SN )
- I = I - 2
- END IF
- GO TO 60
- END IF
-*
- IF( NS.LT.JW .OR. S.EQ.ZERO ) THEN
- IF( NS.GT.1 .AND. S.NE.ZERO ) THEN
-*
-* ==== Reflect spike back into lower triangle ====
-*
- CALL DCOPY( NS, V, LDV, WORK, 1 )
- BETA = WORK( 1 )
- CALL DLARFG( NS, BETA, WORK( 2 ), 1, TAU )
- WORK( 1 ) = ONE
-*
- CALL DLASET( 'L', JW-2, JW-2, ZERO, ZERO, T( 3, 1 ), LDT )
-*
- CALL DLARF( 'L', NS, JW, WORK, 1, TAU, T, LDT,
- $ WORK( JW+1 ) )
- CALL DLARF( 'R', NS, NS, WORK, 1, TAU, T, LDT,
- $ WORK( JW+1 ) )
- CALL DLARF( 'R', JW, NS, WORK, 1, TAU, V, LDV,
- $ WORK( JW+1 ) )
-*
- CALL DGEHRD( JW, 1, NS, T, LDT, WORK, WORK( JW+1 ),
- $ LWORK-JW, INFO )
- END IF
-*
-* ==== Copy updated reduced window into place ====
-*
- IF( KWTOP.GT.1 )
- $ H( KWTOP, KWTOP-1 ) = S*V( 1, 1 )
- CALL DLACPY( 'U', JW, JW, T, LDT, H( KWTOP, KWTOP ), LDH )
- CALL DCOPY( JW-1, T( 2, 1 ), LDT+1, H( KWTOP+1, KWTOP ),
- $ LDH+1 )
-*
-* ==== Accumulate orthogonal matrix in order update
-* . H and Z, if requested. (A modified version
-* . of DORGHR that accumulates block Householder
-* . transformations into V directly might be
-* . marginally more efficient than the following.) ====
-*
- IF( NS.GT.1 .AND. S.NE.ZERO ) THEN
- CALL DORGHR( JW, 1, NS, T, LDT, WORK, WORK( JW+1 ),
- $ LWORK-JW, INFO )
- CALL DGEMM( 'N', 'N', JW, NS, NS, ONE, V, LDV, T, LDT, ZERO,
- $ WV, LDWV )
- CALL DLACPY( 'A', JW, NS, WV, LDWV, V, LDV )
- END IF
-*
-* ==== Update vertical slab in H ====
-*
- IF( WANTT ) THEN
- LTOP = 1
- ELSE
- LTOP = KTOP
- END IF
- DO 70 KROW = LTOP, KWTOP - 1, NV
- KLN = MIN( NV, KWTOP-KROW )
- CALL DGEMM( 'N', 'N', KLN, JW, JW, ONE, H( KROW, KWTOP ),
- $ LDH, V, LDV, ZERO, WV, LDWV )
- CALL DLACPY( 'A', KLN, JW, WV, LDWV, H( KROW, KWTOP ), LDH )
- 70 CONTINUE
-*
-* ==== Update horizontal slab in H ====
-*
- IF( WANTT ) THEN
- DO 80 KCOL = KBOT + 1, N, NH
- KLN = MIN( NH, N-KCOL+1 )
- CALL DGEMM( 'C', 'N', JW, KLN, JW, ONE, V, LDV,
- $ H( KWTOP, KCOL ), LDH, ZERO, T, LDT )
- CALL DLACPY( 'A', JW, KLN, T, LDT, H( KWTOP, KCOL ),
- $ LDH )
- 80 CONTINUE
- END IF
-*
-* ==== Update vertical slab in Z ====
-*
- IF( WANTZ ) THEN
- DO 90 KROW = ILOZ, IHIZ, NV
- KLN = MIN( NV, IHIZ-KROW+1 )
- CALL DGEMM( 'N', 'N', KLN, JW, JW, ONE, Z( KROW, KWTOP ),
- $ LDZ, V, LDV, ZERO, WV, LDWV )
- CALL DLACPY( 'A', KLN, JW, WV, LDWV, Z( KROW, KWTOP ),
- $ LDZ )
- 90 CONTINUE
- END IF
- END IF
-*
-* ==== Return the number of deflations ... ====
-*
- ND = JW - NS
-*
-* ==== ... and the number of shifts. (Subtracting
-* . INFQR from the spike length takes care
-* . of the case of a rare QR failure while
-* . calculating eigenvalues of the deflation
-* . window.) ====
-*
- NS = NS - INFQR
-*
-* ==== Return optimal workspace. ====
-*
- WORK( 1 ) = DBLE( LWKOPT )
-*
-* ==== End of DLAQR3 ====
-*
- END
diff --git a/src/lib/lapack/dlaqr4.f b/src/lib/lapack/dlaqr4.f
deleted file mode 100644
index 8692e7f9..00000000
--- a/src/lib/lapack/dlaqr4.f
+++ /dev/null
@@ -1,640 +0,0 @@
- SUBROUTINE DLAQR4( WANTT, WANTZ, N, ILO, IHI, H, LDH, WR, WI,
- $ ILOZ, IHIZ, Z, LDZ, WORK, LWORK, INFO )
-*
-* -- LAPACK auxiliary routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- INTEGER IHI, IHIZ, ILO, ILOZ, INFO, LDH, LDZ, LWORK, N
- LOGICAL WANTT, WANTZ
-* ..
-* .. Array Arguments ..
- DOUBLE PRECISION H( LDH, * ), WI( * ), WORK( * ), WR( * ),
- $ Z( LDZ, * )
-* ..
-*
-* This subroutine implements one level of recursion for DLAQR0.
-* It is a complete implementation of the small bulge multi-shift
-* QR algorithm. It may be called by DLAQR0 and, for large enough
-* deflation window size, it may be called by DLAQR3. This
-* subroutine is identical to DLAQR0 except that it calls DLAQR2
-* instead of DLAQR3.
-*
-* Purpose
-* =======
-*
-* DLAQR4 computes the eigenvalues of a Hessenberg matrix H
-* and, optionally, the matrices T and Z from the Schur decomposition
-* H = Z T Z**T, where T is an upper quasi-triangular matrix (the
-* Schur form), and Z is the orthogonal matrix of Schur vectors.
-*
-* Optionally Z may be postmultiplied into an input orthogonal
-* matrix Q so that this routine can give the Schur factorization
-* of a matrix A which has been reduced to the Hessenberg form H
-* by the orthogonal matrix Q: A = Q*H*Q**T = (QZ)*T*(QZ)**T.
-*
-* Arguments
-* =========
-*
-* WANTT (input) LOGICAL
-* = .TRUE. : the full Schur form T is required;
-* = .FALSE.: only eigenvalues are required.
-*
-* WANTZ (input) LOGICAL
-* = .TRUE. : the matrix of Schur vectors Z is required;
-* = .FALSE.: Schur vectors are not required.
-*
-* N (input) INTEGER
-* The order of the matrix H. N .GE. 0.
-*
-* ILO (input) INTEGER
-* IHI (input) INTEGER
-* It is assumed that H is already upper triangular in rows
-* and columns 1:ILO-1 and IHI+1:N and, if ILO.GT.1,
-* H(ILO,ILO-1) is zero. ILO and IHI are normally set by a
-* previous call to DGEBAL, and then passed to DGEHRD when the
-* matrix output by DGEBAL is reduced to Hessenberg form.
-* Otherwise, ILO and IHI should be set to 1 and N,
-* respectively. If N.GT.0, then 1.LE.ILO.LE.IHI.LE.N.
-* If N = 0, then ILO = 1 and IHI = 0.
-*
-* H (input/output) DOUBLE PRECISION array, dimension (LDH,N)
-* On entry, the upper Hessenberg matrix H.
-* On exit, if INFO = 0 and WANTT is .TRUE., then H contains
-* the upper quasi-triangular matrix T from the Schur
-* decomposition (the Schur form); 2-by-2 diagonal blocks
-* (corresponding to complex conjugate pairs of eigenvalues)
-* are returned in standard form, with H(i,i) = H(i+1,i+1)
-* and H(i+1,i)*H(i,i+1).LT.0. If INFO = 0 and WANTT is
-* .FALSE., then the contents of H are unspecified on exit.
-* (The output value of H when INFO.GT.0 is given under the
-* description of INFO below.)
-*
-* This subroutine may explicitly set H(i,j) = 0 for i.GT.j and
-* j = 1, 2, ... ILO-1 or j = IHI+1, IHI+2, ... N.
-*
-* LDH (input) INTEGER
-* The leading dimension of the array H. LDH .GE. max(1,N).
-*
-* WR (output) DOUBLE PRECISION array, dimension (IHI)
-* WI (output) DOUBLE PRECISION array, dimension (IHI)
-* The real and imaginary parts, respectively, of the computed
-* eigenvalues of H(ILO:IHI,ILO:IHI) are stored WR(ILO:IHI)
-* and WI(ILO:IHI). If two eigenvalues are computed as a
-* complex conjugate pair, they are stored in consecutive
-* elements of WR and WI, say the i-th and (i+1)th, with
-* WI(i) .GT. 0 and WI(i+1) .LT. 0. If WANTT is .TRUE., then
-* the eigenvalues are stored in the same order as on the
-* diagonal of the Schur form returned in H, with
-* WR(i) = H(i,i) and, if H(i:i+1,i:i+1) is a 2-by-2 diagonal
-* block, WI(i) = sqrt(-H(i+1,i)*H(i,i+1)) and
-* WI(i+1) = -WI(i).
-*
-* ILOZ (input) INTEGER
-* IHIZ (input) INTEGER
-* Specify the rows of Z to which transformations must be
-* applied if WANTZ is .TRUE..
-* 1 .LE. ILOZ .LE. ILO; IHI .LE. IHIZ .LE. N.
-*
-* Z (input/output) DOUBLE PRECISION array, dimension (LDZ,IHI)
-* If WANTZ is .FALSE., then Z is not referenced.
-* If WANTZ is .TRUE., then Z(ILO:IHI,ILOZ:IHIZ) is
-* replaced by Z(ILO:IHI,ILOZ:IHIZ)*U where U is the
-* orthogonal Schur factor of H(ILO:IHI,ILO:IHI).
-* (The output value of Z when INFO.GT.0 is given under
-* the description of INFO below.)
-*
-* LDZ (input) INTEGER
-* The leading dimension of the array Z. if WANTZ is .TRUE.
-* then LDZ.GE.MAX(1,IHIZ). Otherwize, LDZ.GE.1.
-*
-* WORK (workspace/output) DOUBLE PRECISION array, dimension LWORK
-* On exit, if LWORK = -1, WORK(1) returns an estimate of
-* the optimal value for LWORK.
-*
-* LWORK (input) INTEGER
-* The dimension of the array WORK. LWORK .GE. max(1,N)
-* is sufficient, but LWORK typically as large as 6*N may
-* be required for optimal performance. A workspace query
-* to determine the optimal workspace size is recommended.
-*
-* If LWORK = -1, then DLAQR4 does a workspace query.
-* In this case, DLAQR4 checks the input parameters and
-* estimates the optimal workspace size for the given
-* values of N, ILO and IHI. The estimate is returned
-* in WORK(1). No error message related to LWORK is
-* issued by XERBLA. Neither H nor Z are accessed.
-*
-*
-* INFO (output) INTEGER
-* = 0: successful exit
-* .GT. 0: if INFO = i, DLAQR4 failed to compute all of
-* the eigenvalues. Elements 1:ilo-1 and i+1:n of WR
-* and WI contain those eigenvalues which have been
-* successfully computed. (Failures are rare.)
-*
-* If INFO .GT. 0 and WANT is .FALSE., then on exit,
-* the remaining unconverged eigenvalues are the eigen-
-* values of the upper Hessenberg matrix rows and
-* columns ILO through INFO of the final, output
-* value of H.
-*
-* If INFO .GT. 0 and WANTT is .TRUE., then on exit
-*
-* (*) (initial value of H)*U = U*(final value of H)
-*
-* where U is an orthogonal matrix. The final
-* value of H is upper Hessenberg and quasi-triangular
-* in rows and columns INFO+1 through IHI.
-*
-* If INFO .GT. 0 and WANTZ is .TRUE., then on exit
-*
-* (final value of Z(ILO:IHI,ILOZ:IHIZ)
-* = (initial value of Z(ILO:IHI,ILOZ:IHIZ)*U
-*
-* where U is the orthogonal matrix in (*) (regard-
-* less of the value of WANTT.)
-*
-* If INFO .GT. 0 and WANTZ is .FALSE., then Z is not
-* accessed.
-*
-* ================================================================
-* Based on contributions by
-* Karen Braman and Ralph Byers, Department of Mathematics,
-* University of Kansas, USA
-*
-* ================================================================
-* References:
-* K. Braman, R. Byers and R. Mathias, The Multi-Shift QR
-* Algorithm Part I: Maintaining Well Focused Shifts, and Level 3
-* Performance, SIAM Journal of Matrix Analysis, volume 23, pages
-* 929--947, 2002.
-*
-* K. Braman, R. Byers and R. Mathias, The Multi-Shift QR
-* Algorithm Part II: Aggressive Early Deflation, SIAM Journal
-* of Matrix Analysis, volume 23, pages 948--973, 2002.
-*
-* ================================================================
-* .. Parameters ..
-*
-* ==== Matrices of order NTINY or smaller must be processed by
-* . DLAHQR because of insufficient subdiagonal scratch space.
-* . (This is a hard limit.) ====
-*
-* ==== Exceptional deflation windows: try to cure rare
-* . slow convergence by increasing the size of the
-* . deflation window after KEXNW iterations. =====
-*
-* ==== Exceptional shifts: try to cure rare slow convergence
-* . with ad-hoc exceptional shifts every KEXSH iterations.
-* . The constants WILK1 and WILK2 are used to form the
-* . exceptional shifts. ====
-*
- INTEGER NTINY
- PARAMETER ( NTINY = 11 )
- INTEGER KEXNW, KEXSH
- PARAMETER ( KEXNW = 5, KEXSH = 6 )
- DOUBLE PRECISION WILK1, WILK2
- PARAMETER ( WILK1 = 0.75d0, WILK2 = -0.4375d0 )
- DOUBLE PRECISION ZERO, ONE
- PARAMETER ( ZERO = 0.0d0, ONE = 1.0d0 )
-* ..
-* .. Local Scalars ..
- DOUBLE PRECISION AA, BB, CC, CS, DD, SN, SS, SWAP
- INTEGER I, INF, IT, ITMAX, K, KACC22, KBOT, KDU, KS,
- $ KT, KTOP, KU, KV, KWH, KWTOP, KWV, LD, LS,
- $ LWKOPT, NDFL, NH, NHO, NIBBLE, NMIN, NS, NSMAX,
- $ NSR, NVE, NW, NWMAX, NWR
- LOGICAL NWINC, SORTED
- CHARACTER JBCMPZ*2
-* ..
-* .. External Functions ..
- INTEGER ILAENV
- EXTERNAL ILAENV
-* ..
-* .. Local Arrays ..
- DOUBLE PRECISION ZDUM( 1, 1 )
-* ..
-* .. External Subroutines ..
- EXTERNAL DLACPY, DLAHQR, DLANV2, DLAQR2, DLAQR5
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC ABS, DBLE, INT, MAX, MIN, MOD
-* ..
-* .. Executable Statements ..
- INFO = 0
-*
-* ==== Quick return for N = 0: nothing to do. ====
-*
- IF( N.EQ.0 ) THEN
- WORK( 1 ) = ONE
- RETURN
- END IF
-*
-* ==== Set up job flags for ILAENV. ====
-*
- IF( WANTT ) THEN
- JBCMPZ( 1: 1 ) = 'S'
- ELSE
- JBCMPZ( 1: 1 ) = 'E'
- END IF
- IF( WANTZ ) THEN
- JBCMPZ( 2: 2 ) = 'V'
- ELSE
- JBCMPZ( 2: 2 ) = 'N'
- END IF
-*
-* ==== Tiny matrices must use DLAHQR. ====
-*
- IF( N.LE.NTINY ) THEN
-*
-* ==== Estimate optimal workspace. ====
-*
- LWKOPT = 1
- IF( LWORK.NE.-1 )
- $ CALL DLAHQR( WANTT, WANTZ, N, ILO, IHI, H, LDH, WR, WI,
- $ ILOZ, IHIZ, Z, LDZ, INFO )
- ELSE
-*
-* ==== Use small bulge multi-shift QR with aggressive early
-* . deflation on larger-than-tiny matrices. ====
-*
-* ==== Hope for the best. ====
-*
- INFO = 0
-*
-* ==== NWR = recommended deflation window size. At this
-* . point, N .GT. NTINY = 11, so there is enough
-* . subdiagonal workspace for NWR.GE.2 as required.
-* . (In fact, there is enough subdiagonal space for
-* . NWR.GE.3.) ====
-*
- NWR = ILAENV( 13, 'DLAQR4', JBCMPZ, N, ILO, IHI, LWORK )
- NWR = MAX( 2, NWR )
- NWR = MIN( IHI-ILO+1, ( N-1 ) / 3, NWR )
- NW = NWR
-*
-* ==== NSR = recommended number of simultaneous shifts.
-* . At this point N .GT. NTINY = 11, so there is at
-* . enough subdiagonal workspace for NSR to be even
-* . and greater than or equal to two as required. ====
-*
- NSR = ILAENV( 15, 'DLAQR4', JBCMPZ, N, ILO, IHI, LWORK )
- NSR = MIN( NSR, ( N+6 ) / 9, IHI-ILO )
- NSR = MAX( 2, NSR-MOD( NSR, 2 ) )
-*
-* ==== Estimate optimal workspace ====
-*
-* ==== Workspace query call to DLAQR2 ====
-*
- CALL DLAQR2( WANTT, WANTZ, N, ILO, IHI, NWR+1, H, LDH, ILOZ,
- $ IHIZ, Z, LDZ, LS, LD, WR, WI, H, LDH, N, H, LDH,
- $ N, H, LDH, WORK, -1 )
-*
-* ==== Optimal workspace = MAX(DLAQR5, DLAQR2) ====
-*
- LWKOPT = MAX( 3*NSR / 2, INT( WORK( 1 ) ) )
-*
-* ==== Quick return in case of workspace query. ====
-*
- IF( LWORK.EQ.-1 ) THEN
- WORK( 1 ) = DBLE( LWKOPT )
- RETURN
- END IF
-*
-* ==== DLAHQR/DLAQR0 crossover point ====
-*
- NMIN = ILAENV( 12, 'DLAQR4', JBCMPZ, N, ILO, IHI, LWORK )
- NMIN = MAX( NTINY, NMIN )
-*
-* ==== Nibble crossover point ====
-*
- NIBBLE = ILAENV( 14, 'DLAQR4', JBCMPZ, N, ILO, IHI, LWORK )
- NIBBLE = MAX( 0, NIBBLE )
-*
-* ==== Accumulate reflections during ttswp? Use block
-* . 2-by-2 structure during matrix-matrix multiply? ====
-*
- KACC22 = ILAENV( 16, 'DLAQR4', JBCMPZ, N, ILO, IHI, LWORK )
- KACC22 = MAX( 0, KACC22 )
- KACC22 = MIN( 2, KACC22 )
-*
-* ==== NWMAX = the largest possible deflation window for
-* . which there is sufficient workspace. ====
-*
- NWMAX = MIN( ( N-1 ) / 3, LWORK / 2 )
-*
-* ==== NSMAX = the Largest number of simultaneous shifts
-* . for which there is sufficient workspace. ====
-*
- NSMAX = MIN( ( N+6 ) / 9, 2*LWORK / 3 )
- NSMAX = NSMAX - MOD( NSMAX, 2 )
-*
-* ==== NDFL: an iteration count restarted at deflation. ====
-*
- NDFL = 1
-*
-* ==== ITMAX = iteration limit ====
-*
- ITMAX = MAX( 30, 2*KEXSH )*MAX( 10, ( IHI-ILO+1 ) )
-*
-* ==== Last row and column in the active block ====
-*
- KBOT = IHI
-*
-* ==== Main Loop ====
-*
- DO 80 IT = 1, ITMAX
-*
-* ==== Done when KBOT falls below ILO ====
-*
- IF( KBOT.LT.ILO )
- $ GO TO 90
-*
-* ==== Locate active block ====
-*
- DO 10 K = KBOT, ILO + 1, -1
- IF( H( K, K-1 ).EQ.ZERO )
- $ GO TO 20
- 10 CONTINUE
- K = ILO
- 20 CONTINUE
- KTOP = K
-*
-* ==== Select deflation window size ====
-*
- NH = KBOT - KTOP + 1
- IF( NDFL.LT.KEXNW .OR. NH.LT.NW ) THEN
-*
-* ==== Typical deflation window. If possible and
-* . advisable, nibble the entire active block.
-* . If not, use size NWR or NWR+1 depending upon
-* . which has the smaller corresponding subdiagonal
-* . entry (a heuristic). ====
-*
- NWINC = .TRUE.
- IF( NH.LE.MIN( NMIN, NWMAX ) ) THEN
- NW = NH
- ELSE
- NW = MIN( NWR, NH, NWMAX )
- IF( NW.LT.NWMAX ) THEN
- IF( NW.GE.NH-1 ) THEN
- NW = NH
- ELSE
- KWTOP = KBOT - NW + 1
- IF( ABS( H( KWTOP, KWTOP-1 ) ).GT.
- $ ABS( H( KWTOP-1, KWTOP-2 ) ) )NW = NW + 1
- END IF
- END IF
- END IF
- ELSE
-*
-* ==== Exceptional deflation window. If there have
-* . been no deflations in KEXNW or more iterations,
-* . then vary the deflation window size. At first,
-* . because, larger windows are, in general, more
-* . powerful than smaller ones, rapidly increase the
-* . window up to the maximum reasonable and possible.
-* . Then maybe try a slightly smaller window. ====
-*
- IF( NWINC .AND. NW.LT.MIN( NWMAX, NH ) ) THEN
- NW = MIN( NWMAX, NH, 2*NW )
- ELSE
- NWINC = .FALSE.
- IF( NW.EQ.NH .AND. NH.GT.2 )
- $ NW = NH - 1
- END IF
- END IF
-*
-* ==== Aggressive early deflation:
-* . split workspace under the subdiagonal into
-* . - an nw-by-nw work array V in the lower
-* . left-hand-corner,
-* . - an NW-by-at-least-NW-but-more-is-better
-* . (NW-by-NHO) horizontal work array along
-* . the bottom edge,
-* . - an at-least-NW-but-more-is-better (NHV-by-NW)
-* . vertical work array along the left-hand-edge.
-* . ====
-*
- KV = N - NW + 1
- KT = NW + 1
- NHO = ( N-NW-1 ) - KT + 1
- KWV = NW + 2
- NVE = ( N-NW ) - KWV + 1
-*
-* ==== Aggressive early deflation ====
-*
- CALL DLAQR2( WANTT, WANTZ, N, KTOP, KBOT, NW, H, LDH, ILOZ,
- $ IHIZ, Z, LDZ, LS, LD, WR, WI, H( KV, 1 ), LDH,
- $ NHO, H( KV, KT ), LDH, NVE, H( KWV, 1 ), LDH,
- $ WORK, LWORK )
-*
-* ==== Adjust KBOT accounting for new deflations. ====
-*
- KBOT = KBOT - LD
-*
-* ==== KS points to the shifts. ====
-*
- KS = KBOT - LS + 1
-*
-* ==== Skip an expensive QR sweep if there is a (partly
-* . heuristic) reason to expect that many eigenvalues
-* . will deflate without it. Here, the QR sweep is
-* . skipped if many eigenvalues have just been deflated
-* . or if the remaining active block is small.
-*
- IF( ( LD.EQ.0 ) .OR. ( ( 100*LD.LE.NW*NIBBLE ) .AND. ( KBOT-
- $ KTOP+1.GT.MIN( NMIN, NWMAX ) ) ) ) THEN
-*
-* ==== NS = nominal number of simultaneous shifts.
-* . This may be lowered (slightly) if DLAQR2
-* . did not provide that many shifts. ====
-*
- NS = MIN( NSMAX, NSR, MAX( 2, KBOT-KTOP ) )
- NS = NS - MOD( NS, 2 )
-*
-* ==== If there have been no deflations
-* . in a multiple of KEXSH iterations,
-* . then try exceptional shifts.
-* . Otherwise use shifts provided by
-* . DLAQR2 above or from the eigenvalues
-* . of a trailing principal submatrix. ====
-*
- IF( MOD( NDFL, KEXSH ).EQ.0 ) THEN
- KS = KBOT - NS + 1
- DO 30 I = KBOT, MAX( KS+1, KTOP+2 ), -2
- SS = ABS( H( I, I-1 ) ) + ABS( H( I-1, I-2 ) )
- AA = WILK1*SS + H( I, I )
- BB = SS
- CC = WILK2*SS
- DD = AA
- CALL DLANV2( AA, BB, CC, DD, WR( I-1 ), WI( I-1 ),
- $ WR( I ), WI( I ), CS, SN )
- 30 CONTINUE
- IF( KS.EQ.KTOP ) THEN
- WR( KS+1 ) = H( KS+1, KS+1 )
- WI( KS+1 ) = ZERO
- WR( KS ) = WR( KS+1 )
- WI( KS ) = WI( KS+1 )
- END IF
- ELSE
-*
-* ==== Got NS/2 or fewer shifts? Use DLAHQR
-* . on a trailing principal submatrix to
-* . get more. (Since NS.LE.NSMAX.LE.(N+6)/9,
-* . there is enough space below the subdiagonal
-* . to fit an NS-by-NS scratch array.) ====
-*
- IF( KBOT-KS+1.LE.NS / 2 ) THEN
- KS = KBOT - NS + 1
- KT = N - NS + 1
- CALL DLACPY( 'A', NS, NS, H( KS, KS ), LDH,
- $ H( KT, 1 ), LDH )
- CALL DLAHQR( .false., .false., NS, 1, NS,
- $ H( KT, 1 ), LDH, WR( KS ), WI( KS ),
- $ 1, 1, ZDUM, 1, INF )
- KS = KS + INF
-*
-* ==== In case of a rare QR failure use
-* . eigenvalues of the trailing 2-by-2
-* . principal submatrix. ====
-*
- IF( KS.GE.KBOT ) THEN
- AA = H( KBOT-1, KBOT-1 )
- CC = H( KBOT, KBOT-1 )
- BB = H( KBOT-1, KBOT )
- DD = H( KBOT, KBOT )
- CALL DLANV2( AA, BB, CC, DD, WR( KBOT-1 ),
- $ WI( KBOT-1 ), WR( KBOT ),
- $ WI( KBOT ), CS, SN )
- KS = KBOT - 1
- END IF
- END IF
-*
- IF( KBOT-KS+1.GT.NS ) THEN
-*
-* ==== Sort the shifts (Helps a little)
-* . Bubble sort keeps complex conjugate
-* . pairs together. ====
-*
- SORTED = .false.
- DO 50 K = KBOT, KS + 1, -1
- IF( SORTED )
- $ GO TO 60
- SORTED = .true.
- DO 40 I = KS, K - 1
- IF( ABS( WR( I ) )+ABS( WI( I ) ).LT.
- $ ABS( WR( I+1 ) )+ABS( WI( I+1 ) ) ) THEN
- SORTED = .false.
-*
- SWAP = WR( I )
- WR( I ) = WR( I+1 )
- WR( I+1 ) = SWAP
-*
- SWAP = WI( I )
- WI( I ) = WI( I+1 )
- WI( I+1 ) = SWAP
- END IF
- 40 CONTINUE
- 50 CONTINUE
- 60 CONTINUE
- END IF
-*
-* ==== Shuffle shifts into pairs of real shifts
-* . and pairs of complex conjugate shifts
-* . assuming complex conjugate shifts are
-* . already adjacent to one another. (Yes,
-* . they are.) ====
-*
- DO 70 I = KBOT, KS + 2, -2
- IF( WI( I ).NE.-WI( I-1 ) ) THEN
-*
- SWAP = WR( I )
- WR( I ) = WR( I-1 )
- WR( I-1 ) = WR( I-2 )
- WR( I-2 ) = SWAP
-*
- SWAP = WI( I )
- WI( I ) = WI( I-1 )
- WI( I-1 ) = WI( I-2 )
- WI( I-2 ) = SWAP
- END IF
- 70 CONTINUE
- END IF
-*
-* ==== If there are only two shifts and both are
-* . real, then use only one. ====
-*
- IF( KBOT-KS+1.EQ.2 ) THEN
- IF( WI( KBOT ).EQ.ZERO ) THEN
- IF( ABS( WR( KBOT )-H( KBOT, KBOT ) ).LT.
- $ ABS( WR( KBOT-1 )-H( KBOT, KBOT ) ) ) THEN
- WR( KBOT-1 ) = WR( KBOT )
- ELSE
- WR( KBOT ) = WR( KBOT-1 )
- END IF
- END IF
- END IF
-*
-* ==== Use up to NS of the the smallest magnatiude
-* . shifts. If there aren't NS shifts available,
-* . then use them all, possibly dropping one to
-* . make the number of shifts even. ====
-*
- NS = MIN( NS, KBOT-KS+1 )
- NS = NS - MOD( NS, 2 )
- KS = KBOT - NS + 1
-*
-* ==== Small-bulge multi-shift QR sweep:
-* . split workspace under the subdiagonal into
-* . - a KDU-by-KDU work array U in the lower
-* . left-hand-corner,
-* . - a KDU-by-at-least-KDU-but-more-is-better
-* . (KDU-by-NHo) horizontal work array WH along
-* . the bottom edge,
-* . - and an at-least-KDU-but-more-is-better-by-KDU
-* . (NVE-by-KDU) vertical work WV arrow along
-* . the left-hand-edge. ====
-*
- KDU = 3*NS - 3
- KU = N - KDU + 1
- KWH = KDU + 1
- NHO = ( N-KDU+1-4 ) - ( KDU+1 ) + 1
- KWV = KDU + 4
- NVE = N - KDU - KWV + 1
-*
-* ==== Small-bulge multi-shift QR sweep ====
-*
- CALL DLAQR5( WANTT, WANTZ, KACC22, N, KTOP, KBOT, NS,
- $ WR( KS ), WI( KS ), H, LDH, ILOZ, IHIZ, Z,
- $ LDZ, WORK, 3, H( KU, 1 ), LDH, NVE,
- $ H( KWV, 1 ), LDH, NHO, H( KU, KWH ), LDH )
- END IF
-*
-* ==== Note progress (or the lack of it). ====
-*
- IF( LD.GT.0 ) THEN
- NDFL = 1
- ELSE
- NDFL = NDFL + 1
- END IF
-*
-* ==== End of main loop ====
- 80 CONTINUE
-*
-* ==== Iteration limit exceeded. Set INFO to show where
-* . the problem occurred and exit. ====
-*
- INFO = KBOT
- 90 CONTINUE
- END IF
-*
-* ==== Return the optimal value of LWORK. ====
-*
- WORK( 1 ) = DBLE( LWKOPT )
-*
-* ==== End of DLAQR4 ====
-*
- END
diff --git a/src/lib/lapack/dlaqr5.f b/src/lib/lapack/dlaqr5.f
deleted file mode 100644
index 17857572..00000000
--- a/src/lib/lapack/dlaqr5.f
+++ /dev/null
@@ -1,812 +0,0 @@
- SUBROUTINE DLAQR5( WANTT, WANTZ, KACC22, N, KTOP, KBOT, NSHFTS,
- $ SR, SI, H, LDH, ILOZ, IHIZ, Z, LDZ, V, LDV, U,
- $ LDU, NV, WV, LDWV, NH, WH, LDWH )
-*
-* -- LAPACK auxiliary routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- INTEGER IHIZ, ILOZ, KACC22, KBOT, KTOP, LDH, LDU, LDV,
- $ LDWH, LDWV, LDZ, N, NH, NSHFTS, NV
- LOGICAL WANTT, WANTZ
-* ..
-* .. Array Arguments ..
- DOUBLE PRECISION H( LDH, * ), SI( * ), SR( * ), U( LDU, * ),
- $ V( LDV, * ), WH( LDWH, * ), WV( LDWV, * ),
- $ Z( LDZ, * )
-* ..
-*
-* This auxiliary subroutine called by DLAQR0 performs a
-* single small-bulge multi-shift QR sweep.
-*
-* WANTT (input) logical scalar
-* WANTT = .true. if the quasi-triangular Schur factor
-* is being computed. WANTT is set to .false. otherwise.
-*
-* WANTZ (input) logical scalar
-* WANTZ = .true. if the orthogonal Schur factor is being
-* computed. WANTZ is set to .false. otherwise.
-*
-* KACC22 (input) integer with value 0, 1, or 2.
-* Specifies the computation mode of far-from-diagonal
-* orthogonal updates.
-* = 0: DLAQR5 does not accumulate reflections and does not
-* use matrix-matrix multiply to update far-from-diagonal
-* matrix entries.
-* = 1: DLAQR5 accumulates reflections and uses matrix-matrix
-* multiply to update the far-from-diagonal matrix entries.
-* = 2: DLAQR5 accumulates reflections, uses matrix-matrix
-* multiply to update the far-from-diagonal matrix entries,
-* and takes advantage of 2-by-2 block structure during
-* matrix multiplies.
-*
-* N (input) integer scalar
-* N is the order of the Hessenberg matrix H upon which this
-* subroutine operates.
-*
-* KTOP (input) integer scalar
-* KBOT (input) integer scalar
-* These are the first and last rows and columns of an
-* isolated diagonal block upon which the QR sweep is to be
-* applied. It is assumed without a check that
-* either KTOP = 1 or H(KTOP,KTOP-1) = 0
-* and
-* either KBOT = N or H(KBOT+1,KBOT) = 0.
-*
-* NSHFTS (input) integer scalar
-* NSHFTS gives the number of simultaneous shifts. NSHFTS
-* must be positive and even.
-*
-* SR (input) DOUBLE PRECISION array of size (NSHFTS)
-* SI (input) DOUBLE PRECISION array of size (NSHFTS)
-* SR contains the real parts and SI contains the imaginary
-* parts of the NSHFTS shifts of origin that define the
-* multi-shift QR sweep.
-*
-* H (input/output) DOUBLE PRECISION array of size (LDH,N)
-* On input H contains a Hessenberg matrix. On output a
-* multi-shift QR sweep with shifts SR(J)+i*SI(J) is applied
-* to the isolated diagonal block in rows and columns KTOP
-* through KBOT.
-*
-* LDH (input) integer scalar
-* LDH is the leading dimension of H just as declared in the
-* calling procedure. LDH.GE.MAX(1,N).
-*
-* ILOZ (input) INTEGER
-* IHIZ (input) INTEGER
-* Specify the rows of Z to which transformations must be
-* applied if WANTZ is .TRUE.. 1 .LE. ILOZ .LE. IHIZ .LE. N
-*
-* Z (input/output) DOUBLE PRECISION array of size (LDZ,IHI)
-* If WANTZ = .TRUE., then the QR Sweep orthogonal
-* similarity transformation is accumulated into
-* Z(ILOZ:IHIZ,ILO:IHI) from the right.
-* If WANTZ = .FALSE., then Z is unreferenced.
-*
-* LDZ (input) integer scalar
-* LDA is the leading dimension of Z just as declared in
-* the calling procedure. LDZ.GE.N.
-*
-* V (workspace) DOUBLE PRECISION array of size (LDV,NSHFTS/2)
-*
-* LDV (input) integer scalar
-* LDV is the leading dimension of V as declared in the
-* calling procedure. LDV.GE.3.
-*
-* U (workspace) DOUBLE PRECISION array of size
-* (LDU,3*NSHFTS-3)
-*
-* LDU (input) integer scalar
-* LDU is the leading dimension of U just as declared in the
-* in the calling subroutine. LDU.GE.3*NSHFTS-3.
-*
-* NH (input) integer scalar
-* NH is the number of columns in array WH available for
-* workspace. NH.GE.1.
-*
-* WH (workspace) DOUBLE PRECISION array of size (LDWH,NH)
-*
-* LDWH (input) integer scalar
-* Leading dimension of WH just as declared in the
-* calling procedure. LDWH.GE.3*NSHFTS-3.
-*
-* NV (input) integer scalar
-* NV is the number of rows in WV agailable for workspace.
-* NV.GE.1.
-*
-* WV (workspace) DOUBLE PRECISION array of size
-* (LDWV,3*NSHFTS-3)
-*
-* LDWV (input) integer scalar
-* LDWV is the leading dimension of WV as declared in the
-* in the calling subroutine. LDWV.GE.NV.
-*
-*
-* ================================================================
-* Based on contributions by
-* Karen Braman and Ralph Byers, Department of Mathematics,
-* University of Kansas, USA
-*
-* ============================================================
-* Reference:
-*
-* K. Braman, R. Byers and R. Mathias, The Multi-Shift QR
-* Algorithm Part I: Maintaining Well Focused Shifts, and
-* Level 3 Performance, SIAM Journal of Matrix Analysis,
-* volume 23, pages 929--947, 2002.
-*
-* ============================================================
-* .. Parameters ..
- DOUBLE PRECISION ZERO, ONE
- PARAMETER ( ZERO = 0.0d0, ONE = 1.0d0 )
-* ..
-* .. Local Scalars ..
- DOUBLE PRECISION ALPHA, BETA, H11, H12, H21, H22, REFSUM,
- $ SAFMAX, SAFMIN, SCL, SMLNUM, SWAP, TST1, TST2,
- $ ULP
- INTEGER I, I2, I4, INCOL, J, J2, J4, JBOT, JCOL, JLEN,
- $ JROW, JTOP, K, K1, KDU, KMS, KNZ, KRCOL, KZS,
- $ M, M22, MBOT, MEND, MSTART, MTOP, NBMPS, NDCOL,
- $ NS, NU
- LOGICAL ACCUM, BLK22, BMP22
-* ..
-* .. External Functions ..
- DOUBLE PRECISION DLAMCH
- EXTERNAL DLAMCH
-* ..
-* .. Intrinsic Functions ..
-*
- INTRINSIC ABS, DBLE, MAX, MIN, MOD
-* ..
-* .. Local Arrays ..
- DOUBLE PRECISION VT( 3 )
-* ..
-* .. External Subroutines ..
- EXTERNAL DGEMM, DLABAD, DLACPY, DLAQR1, DLARFG, DLASET,
- $ DTRMM
-* ..
-* .. Executable Statements ..
-*
-* ==== If there are no shifts, then there is nothing to do. ====
-*
- IF( NSHFTS.LT.2 )
- $ RETURN
-*
-* ==== If the active block is empty or 1-by-1, then there
-* . is nothing to do. ====
-*
- IF( KTOP.GE.KBOT )
- $ RETURN
-*
-* ==== Shuffle shifts into pairs of real shifts and pairs
-* . of complex conjugate shifts assuming complex
-* . conjugate shifts are already adjacent to one
-* . another. ====
-*
- DO 10 I = 1, NSHFTS - 2, 2
- IF( SI( I ).NE.-SI( I+1 ) ) THEN
-*
- SWAP = SR( I )
- SR( I ) = SR( I+1 )
- SR( I+1 ) = SR( I+2 )
- SR( I+2 ) = SWAP
-*
- SWAP = SI( I )
- SI( I ) = SI( I+1 )
- SI( I+1 ) = SI( I+2 )
- SI( I+2 ) = SWAP
- END IF
- 10 CONTINUE
-*
-* ==== NSHFTS is supposed to be even, but if is odd,
-* . then simply reduce it by one. The shuffle above
-* . ensures that the dropped shift is real and that
-* . the remaining shifts are paired. ====
-*
- NS = NSHFTS - MOD( NSHFTS, 2 )
-*
-* ==== Machine constants for deflation ====
-*
- SAFMIN = DLAMCH( 'SAFE MINIMUM' )
- SAFMAX = ONE / SAFMIN
- CALL DLABAD( SAFMIN, SAFMAX )
- ULP = DLAMCH( 'PRECISION' )
- SMLNUM = SAFMIN*( DBLE( N ) / ULP )
-*
-* ==== Use accumulated reflections to update far-from-diagonal
-* . entries ? ====
-*
- ACCUM = ( KACC22.EQ.1 ) .OR. ( KACC22.EQ.2 )
-*
-* ==== If so, exploit the 2-by-2 block structure? ====
-*
- BLK22 = ( NS.GT.2 ) .AND. ( KACC22.EQ.2 )
-*
-* ==== clear trash ====
-*
- IF( KTOP+2.LE.KBOT )
- $ H( KTOP+2, KTOP ) = ZERO
-*
-* ==== NBMPS = number of 2-shift bulges in the chain ====
-*
- NBMPS = NS / 2
-*
-* ==== KDU = width of slab ====
-*
- KDU = 6*NBMPS - 3
-*
-* ==== Create and chase chains of NBMPS bulges ====
-*
- DO 220 INCOL = 3*( 1-NBMPS ) + KTOP - 1, KBOT - 2, 3*NBMPS - 2
- NDCOL = INCOL + KDU
- IF( ACCUM )
- $ CALL DLASET( 'ALL', KDU, KDU, ZERO, ONE, U, LDU )
-*
-* ==== Near-the-diagonal bulge chase. The following loop
-* . performs the near-the-diagonal part of a small bulge
-* . multi-shift QR sweep. Each 6*NBMPS-2 column diagonal
-* . chunk extends from column INCOL to column NDCOL
-* . (including both column INCOL and column NDCOL). The
-* . following loop chases a 3*NBMPS column long chain of
-* . NBMPS bulges 3*NBMPS-2 columns to the right. (INCOL
-* . may be less than KTOP and and NDCOL may be greater than
-* . KBOT indicating phantom columns from which to chase
-* . bulges before they are actually introduced or to which
-* . to chase bulges beyond column KBOT.) ====
-*
- DO 150 KRCOL = INCOL, MIN( INCOL+3*NBMPS-3, KBOT-2 )
-*
-* ==== Bulges number MTOP to MBOT are active double implicit
-* . shift bulges. There may or may not also be small
-* . 2-by-2 bulge, if there is room. The inactive bulges
-* . (if any) must wait until the active bulges have moved
-* . down the diagonal to make room. The phantom matrix
-* . paradigm described above helps keep track. ====
-*
- MTOP = MAX( 1, ( ( KTOP-1 )-KRCOL+2 ) / 3+1 )
- MBOT = MIN( NBMPS, ( KBOT-KRCOL ) / 3 )
- M22 = MBOT + 1
- BMP22 = ( MBOT.LT.NBMPS ) .AND. ( KRCOL+3*( M22-1 ) ).EQ.
- $ ( KBOT-2 )
-*
-* ==== Generate reflections to chase the chain right
-* . one column. (The minimum value of K is KTOP-1.) ====
-*
- DO 20 M = MTOP, MBOT
- K = KRCOL + 3*( M-1 )
- IF( K.EQ.KTOP-1 ) THEN
- CALL DLAQR1( 3, H( KTOP, KTOP ), LDH, SR( 2*M-1 ),
- $ SI( 2*M-1 ), SR( 2*M ), SI( 2*M ),
- $ V( 1, M ) )
- ALPHA = V( 1, M )
- CALL DLARFG( 3, ALPHA, V( 2, M ), 1, V( 1, M ) )
- ELSE
- BETA = H( K+1, K )
- V( 2, M ) = H( K+2, K )
- V( 3, M ) = H( K+3, K )
- CALL DLARFG( 3, BETA, V( 2, M ), 1, V( 1, M ) )
-*
-* ==== A Bulge may collapse because of vigilant
-* . deflation or destructive underflow. (The
-* . initial bulge is always collapsed.) Use
-* . the two-small-subdiagonals trick to try
-* . to get it started again. If V(2,M).NE.0 and
-* . V(3,M) = H(K+3,K+1) = H(K+3,K+2) = 0, then
-* . this bulge is collapsing into a zero
-* . subdiagonal. It will be restarted next
-* . trip through the loop.)
-*
- IF( V( 1, M ).NE.ZERO .AND.
- $ ( V( 3, M ).NE.ZERO .OR. ( H( K+3,
- $ K+1 ).EQ.ZERO .AND. H( K+3, K+2 ).EQ.ZERO ) ) )
- $ THEN
-*
-* ==== Typical case: not collapsed (yet). ====
-*
- H( K+1, K ) = BETA
- H( K+2, K ) = ZERO
- H( K+3, K ) = ZERO
- ELSE
-*
-* ==== Atypical case: collapsed. Attempt to
-* . reintroduce ignoring H(K+1,K). If the
-* . fill resulting from the new reflector
-* . is too large, then abandon it.
-* . Otherwise, use the new one. ====
-*
- CALL DLAQR1( 3, H( K+1, K+1 ), LDH, SR( 2*M-1 ),
- $ SI( 2*M-1 ), SR( 2*M ), SI( 2*M ),
- $ VT )
- SCL = ABS( VT( 1 ) ) + ABS( VT( 2 ) ) +
- $ ABS( VT( 3 ) )
- IF( SCL.NE.ZERO ) THEN
- VT( 1 ) = VT( 1 ) / SCL
- VT( 2 ) = VT( 2 ) / SCL
- VT( 3 ) = VT( 3 ) / SCL
- END IF
-*
-* ==== The following is the traditional and
-* . conservative two-small-subdiagonals
-* . test. ====
-* .
- IF( ABS( H( K+1, K ) )*( ABS( VT( 2 ) )+
- $ ABS( VT( 3 ) ) ).GT.ULP*ABS( VT( 1 ) )*
- $ ( ABS( H( K, K ) )+ABS( H( K+1,
- $ K+1 ) )+ABS( H( K+2, K+2 ) ) ) ) THEN
-*
-* ==== Starting a new bulge here would
-* . create non-negligible fill. If
-* . the old reflector is diagonal (only
-* . possible with underflows), then
-* . change it to I. Otherwise, use
-* . it with trepidation. ====
-*
- IF( V( 2, M ).EQ.ZERO .AND. V( 3, M ).EQ.ZERO )
- $ THEN
- V( 1, M ) = ZERO
- ELSE
- H( K+1, K ) = BETA
- H( K+2, K ) = ZERO
- H( K+3, K ) = ZERO
- END IF
- ELSE
-*
-* ==== Stating a new bulge here would
-* . create only negligible fill.
-* . Replace the old reflector with
-* . the new one. ====
-*
- ALPHA = VT( 1 )
- CALL DLARFG( 3, ALPHA, VT( 2 ), 1, VT( 1 ) )
- REFSUM = H( K+1, K ) + H( K+2, K )*VT( 2 ) +
- $ H( K+3, K )*VT( 3 )
- H( K+1, K ) = H( K+1, K ) - VT( 1 )*REFSUM
- H( K+2, K ) = ZERO
- H( K+3, K ) = ZERO
- V( 1, M ) = VT( 1 )
- V( 2, M ) = VT( 2 )
- V( 3, M ) = VT( 3 )
- END IF
- END IF
- END IF
- 20 CONTINUE
-*
-* ==== Generate a 2-by-2 reflection, if needed. ====
-*
- K = KRCOL + 3*( M22-1 )
- IF( BMP22 ) THEN
- IF( K.EQ.KTOP-1 ) THEN
- CALL DLAQR1( 2, H( K+1, K+1 ), LDH, SR( 2*M22-1 ),
- $ SI( 2*M22-1 ), SR( 2*M22 ), SI( 2*M22 ),
- $ V( 1, M22 ) )
- BETA = V( 1, M22 )
- CALL DLARFG( 2, BETA, V( 2, M22 ), 1, V( 1, M22 ) )
- ELSE
- BETA = H( K+1, K )
- V( 2, M22 ) = H( K+2, K )
- CALL DLARFG( 2, BETA, V( 2, M22 ), 1, V( 1, M22 ) )
- H( K+1, K ) = BETA
- H( K+2, K ) = ZERO
- END IF
- ELSE
-*
-* ==== Initialize V(1,M22) here to avoid possible undefined
-* . variable problems later. ====
-*
- V( 1, M22 ) = ZERO
- END IF
-*
-* ==== Multiply H by reflections from the left ====
-*
- IF( ACCUM ) THEN
- JBOT = MIN( NDCOL, KBOT )
- ELSE IF( WANTT ) THEN
- JBOT = N
- ELSE
- JBOT = KBOT
- END IF
- DO 40 J = MAX( KTOP, KRCOL ), JBOT
- MEND = MIN( MBOT, ( J-KRCOL+2 ) / 3 )
- DO 30 M = MTOP, MEND
- K = KRCOL + 3*( M-1 )
- REFSUM = V( 1, M )*( H( K+1, J )+V( 2, M )*
- $ H( K+2, J )+V( 3, M )*H( K+3, J ) )
- H( K+1, J ) = H( K+1, J ) - REFSUM
- H( K+2, J ) = H( K+2, J ) - REFSUM*V( 2, M )
- H( K+3, J ) = H( K+3, J ) - REFSUM*V( 3, M )
- 30 CONTINUE
- 40 CONTINUE
- IF( BMP22 ) THEN
- K = KRCOL + 3*( M22-1 )
- DO 50 J = MAX( K+1, KTOP ), JBOT
- REFSUM = V( 1, M22 )*( H( K+1, J )+V( 2, M22 )*
- $ H( K+2, J ) )
- H( K+1, J ) = H( K+1, J ) - REFSUM
- H( K+2, J ) = H( K+2, J ) - REFSUM*V( 2, M22 )
- 50 CONTINUE
- END IF
-*
-* ==== Multiply H by reflections from the right.
-* . Delay filling in the last row until the
-* . vigilant deflation check is complete. ====
-*
- IF( ACCUM ) THEN
- JTOP = MAX( KTOP, INCOL )
- ELSE IF( WANTT ) THEN
- JTOP = 1
- ELSE
- JTOP = KTOP
- END IF
- DO 90 M = MTOP, MBOT
- IF( V( 1, M ).NE.ZERO ) THEN
- K = KRCOL + 3*( M-1 )
- DO 60 J = JTOP, MIN( KBOT, K+3 )
- REFSUM = V( 1, M )*( H( J, K+1 )+V( 2, M )*
- $ H( J, K+2 )+V( 3, M )*H( J, K+3 ) )
- H( J, K+1 ) = H( J, K+1 ) - REFSUM
- H( J, K+2 ) = H( J, K+2 ) - REFSUM*V( 2, M )
- H( J, K+3 ) = H( J, K+3 ) - REFSUM*V( 3, M )
- 60 CONTINUE
-*
- IF( ACCUM ) THEN
-*
-* ==== Accumulate U. (If necessary, update Z later
-* . with with an efficient matrix-matrix
-* . multiply.) ====
-*
- KMS = K - INCOL
- DO 70 J = MAX( 1, KTOP-INCOL ), KDU
- REFSUM = V( 1, M )*( U( J, KMS+1 )+V( 2, M )*
- $ U( J, KMS+2 )+V( 3, M )*U( J, KMS+3 ) )
- U( J, KMS+1 ) = U( J, KMS+1 ) - REFSUM
- U( J, KMS+2 ) = U( J, KMS+2 ) - REFSUM*V( 2, M )
- U( J, KMS+3 ) = U( J, KMS+3 ) - REFSUM*V( 3, M )
- 70 CONTINUE
- ELSE IF( WANTZ ) THEN
-*
-* ==== U is not accumulated, so update Z
-* . now by multiplying by reflections
-* . from the right. ====
-*
- DO 80 J = ILOZ, IHIZ
- REFSUM = V( 1, M )*( Z( J, K+1 )+V( 2, M )*
- $ Z( J, K+2 )+V( 3, M )*Z( J, K+3 ) )
- Z( J, K+1 ) = Z( J, K+1 ) - REFSUM
- Z( J, K+2 ) = Z( J, K+2 ) - REFSUM*V( 2, M )
- Z( J, K+3 ) = Z( J, K+3 ) - REFSUM*V( 3, M )
- 80 CONTINUE
- END IF
- END IF
- 90 CONTINUE
-*
-* ==== Special case: 2-by-2 reflection (if needed) ====
-*
- K = KRCOL + 3*( M22-1 )
- IF( BMP22 .AND. ( V( 1, M22 ).NE.ZERO ) ) THEN
- DO 100 J = JTOP, MIN( KBOT, K+3 )
- REFSUM = V( 1, M22 )*( H( J, K+1 )+V( 2, M22 )*
- $ H( J, K+2 ) )
- H( J, K+1 ) = H( J, K+1 ) - REFSUM
- H( J, K+2 ) = H( J, K+2 ) - REFSUM*V( 2, M22 )
- 100 CONTINUE
-*
- IF( ACCUM ) THEN
- KMS = K - INCOL
- DO 110 J = MAX( 1, KTOP-INCOL ), KDU
- REFSUM = V( 1, M22 )*( U( J, KMS+1 )+V( 2, M22 )*
- $ U( J, KMS+2 ) )
- U( J, KMS+1 ) = U( J, KMS+1 ) - REFSUM
- U( J, KMS+2 ) = U( J, KMS+2 ) - REFSUM*V( 2, M22 )
- 110 CONTINUE
- ELSE IF( WANTZ ) THEN
- DO 120 J = ILOZ, IHIZ
- REFSUM = V( 1, M22 )*( Z( J, K+1 )+V( 2, M22 )*
- $ Z( J, K+2 ) )
- Z( J, K+1 ) = Z( J, K+1 ) - REFSUM
- Z( J, K+2 ) = Z( J, K+2 ) - REFSUM*V( 2, M22 )
- 120 CONTINUE
- END IF
- END IF
-*
-* ==== Vigilant deflation check ====
-*
- MSTART = MTOP
- IF( KRCOL+3*( MSTART-1 ).LT.KTOP )
- $ MSTART = MSTART + 1
- MEND = MBOT
- IF( BMP22 )
- $ MEND = MEND + 1
- IF( KRCOL.EQ.KBOT-2 )
- $ MEND = MEND + 1
- DO 130 M = MSTART, MEND
- K = MIN( KBOT-1, KRCOL+3*( M-1 ) )
-*
-* ==== The following convergence test requires that
-* . the tradition small-compared-to-nearby-diagonals
-* . criterion and the Ahues & Tisseur (LAWN 122, 1997)
-* . criteria both be satisfied. The latter improves
-* . accuracy in some examples. Falling back on an
-* . alternate convergence criterion when TST1 or TST2
-* . is zero (as done here) is traditional but probably
-* . unnecessary. ====
-*
- IF( H( K+1, K ).NE.ZERO ) THEN
- TST1 = ABS( H( K, K ) ) + ABS( H( K+1, K+1 ) )
- IF( TST1.EQ.ZERO ) THEN
- IF( K.GE.KTOP+1 )
- $ TST1 = TST1 + ABS( H( K, K-1 ) )
- IF( K.GE.KTOP+2 )
- $ TST1 = TST1 + ABS( H( K, K-2 ) )
- IF( K.GE.KTOP+3 )
- $ TST1 = TST1 + ABS( H( K, K-3 ) )
- IF( K.LE.KBOT-2 )
- $ TST1 = TST1 + ABS( H( K+2, K+1 ) )
- IF( K.LE.KBOT-3 )
- $ TST1 = TST1 + ABS( H( K+3, K+1 ) )
- IF( K.LE.KBOT-4 )
- $ TST1 = TST1 + ABS( H( K+4, K+1 ) )
- END IF
- IF( ABS( H( K+1, K ) ).LE.MAX( SMLNUM, ULP*TST1 ) )
- $ THEN
- H12 = MAX( ABS( H( K+1, K ) ), ABS( H( K, K+1 ) ) )
- H21 = MIN( ABS( H( K+1, K ) ), ABS( H( K, K+1 ) ) )
- H11 = MAX( ABS( H( K+1, K+1 ) ),
- $ ABS( H( K, K )-H( K+1, K+1 ) ) )
- H22 = MIN( ABS( H( K+1, K+1 ) ),
- $ ABS( H( K, K )-H( K+1, K+1 ) ) )
- SCL = H11 + H12
- TST2 = H22*( H11 / SCL )
-*
- IF( TST2.EQ.ZERO .OR. H21*( H12 / SCL ).LE.
- $ MAX( SMLNUM, ULP*TST2 ) )H( K+1, K ) = ZERO
- END IF
- END IF
- 130 CONTINUE
-*
-* ==== Fill in the last row of each bulge. ====
-*
- MEND = MIN( NBMPS, ( KBOT-KRCOL-1 ) / 3 )
- DO 140 M = MTOP, MEND
- K = KRCOL + 3*( M-1 )
- REFSUM = V( 1, M )*V( 3, M )*H( K+4, K+3 )
- H( K+4, K+1 ) = -REFSUM
- H( K+4, K+2 ) = -REFSUM*V( 2, M )
- H( K+4, K+3 ) = H( K+4, K+3 ) - REFSUM*V( 3, M )
- 140 CONTINUE
-*
-* ==== End of near-the-diagonal bulge chase. ====
-*
- 150 CONTINUE
-*
-* ==== Use U (if accumulated) to update far-from-diagonal
-* . entries in H. If required, use U to update Z as
-* . well. ====
-*
- IF( ACCUM ) THEN
- IF( WANTT ) THEN
- JTOP = 1
- JBOT = N
- ELSE
- JTOP = KTOP
- JBOT = KBOT
- END IF
- IF( ( .NOT.BLK22 ) .OR. ( INCOL.LT.KTOP ) .OR.
- $ ( NDCOL.GT.KBOT ) .OR. ( NS.LE.2 ) ) THEN
-*
-* ==== Updates not exploiting the 2-by-2 block
-* . structure of U. K1 and NU keep track of
-* . the location and size of U in the special
-* . cases of introducing bulges and chasing
-* . bulges off the bottom. In these special
-* . cases and in case the number of shifts
-* . is NS = 2, there is no 2-by-2 block
-* . structure to exploit. ====
-*
- K1 = MAX( 1, KTOP-INCOL )
- NU = ( KDU-MAX( 0, NDCOL-KBOT ) ) - K1 + 1
-*
-* ==== Horizontal Multiply ====
-*
- DO 160 JCOL = MIN( NDCOL, KBOT ) + 1, JBOT, NH
- JLEN = MIN( NH, JBOT-JCOL+1 )
- CALL DGEMM( 'C', 'N', NU, JLEN, NU, ONE, U( K1, K1 ),
- $ LDU, H( INCOL+K1, JCOL ), LDH, ZERO, WH,
- $ LDWH )
- CALL DLACPY( 'ALL', NU, JLEN, WH, LDWH,
- $ H( INCOL+K1, JCOL ), LDH )
- 160 CONTINUE
-*
-* ==== Vertical multiply ====
-*
- DO 170 JROW = JTOP, MAX( KTOP, INCOL ) - 1, NV
- JLEN = MIN( NV, MAX( KTOP, INCOL )-JROW )
- CALL DGEMM( 'N', 'N', JLEN, NU, NU, ONE,
- $ H( JROW, INCOL+K1 ), LDH, U( K1, K1 ),
- $ LDU, ZERO, WV, LDWV )
- CALL DLACPY( 'ALL', JLEN, NU, WV, LDWV,
- $ H( JROW, INCOL+K1 ), LDH )
- 170 CONTINUE
-*
-* ==== Z multiply (also vertical) ====
-*
- IF( WANTZ ) THEN
- DO 180 JROW = ILOZ, IHIZ, NV
- JLEN = MIN( NV, IHIZ-JROW+1 )
- CALL DGEMM( 'N', 'N', JLEN, NU, NU, ONE,
- $ Z( JROW, INCOL+K1 ), LDZ, U( K1, K1 ),
- $ LDU, ZERO, WV, LDWV )
- CALL DLACPY( 'ALL', JLEN, NU, WV, LDWV,
- $ Z( JROW, INCOL+K1 ), LDZ )
- 180 CONTINUE
- END IF
- ELSE
-*
-* ==== Updates exploiting U's 2-by-2 block structure.
-* . (I2, I4, J2, J4 are the last rows and columns
-* . of the blocks.) ====
-*
- I2 = ( KDU+1 ) / 2
- I4 = KDU
- J2 = I4 - I2
- J4 = KDU
-*
-* ==== KZS and KNZ deal with the band of zeros
-* . along the diagonal of one of the triangular
-* . blocks. ====
-*
- KZS = ( J4-J2 ) - ( NS+1 )
- KNZ = NS + 1
-*
-* ==== Horizontal multiply ====
-*
- DO 190 JCOL = MIN( NDCOL, KBOT ) + 1, JBOT, NH
- JLEN = MIN( NH, JBOT-JCOL+1 )
-*
-* ==== Copy bottom of H to top+KZS of scratch ====
-* (The first KZS rows get multiplied by zero.) ====
-*
- CALL DLACPY( 'ALL', KNZ, JLEN, H( INCOL+1+J2, JCOL ),
- $ LDH, WH( KZS+1, 1 ), LDWH )
-*
-* ==== Multiply by U21' ====
-*
- CALL DLASET( 'ALL', KZS, JLEN, ZERO, ZERO, WH, LDWH )
- CALL DTRMM( 'L', 'U', 'C', 'N', KNZ, JLEN, ONE,
- $ U( J2+1, 1+KZS ), LDU, WH( KZS+1, 1 ),
- $ LDWH )
-*
-* ==== Multiply top of H by U11' ====
-*
- CALL DGEMM( 'C', 'N', I2, JLEN, J2, ONE, U, LDU,
- $ H( INCOL+1, JCOL ), LDH, ONE, WH, LDWH )
-*
-* ==== Copy top of H bottom of WH ====
-*
- CALL DLACPY( 'ALL', J2, JLEN, H( INCOL+1, JCOL ), LDH,
- $ WH( I2+1, 1 ), LDWH )
-*
-* ==== Multiply by U21' ====
-*
- CALL DTRMM( 'L', 'L', 'C', 'N', J2, JLEN, ONE,
- $ U( 1, I2+1 ), LDU, WH( I2+1, 1 ), LDWH )
-*
-* ==== Multiply by U22 ====
-*
- CALL DGEMM( 'C', 'N', I4-I2, JLEN, J4-J2, ONE,
- $ U( J2+1, I2+1 ), LDU,
- $ H( INCOL+1+J2, JCOL ), LDH, ONE,
- $ WH( I2+1, 1 ), LDWH )
-*
-* ==== Copy it back ====
-*
- CALL DLACPY( 'ALL', KDU, JLEN, WH, LDWH,
- $ H( INCOL+1, JCOL ), LDH )
- 190 CONTINUE
-*
-* ==== Vertical multiply ====
-*
- DO 200 JROW = JTOP, MAX( INCOL, KTOP ) - 1, NV
- JLEN = MIN( NV, MAX( INCOL, KTOP )-JROW )
-*
-* ==== Copy right of H to scratch (the first KZS
-* . columns get multiplied by zero) ====
-*
- CALL DLACPY( 'ALL', JLEN, KNZ, H( JROW, INCOL+1+J2 ),
- $ LDH, WV( 1, 1+KZS ), LDWV )
-*
-* ==== Multiply by U21 ====
-*
- CALL DLASET( 'ALL', JLEN, KZS, ZERO, ZERO, WV, LDWV )
- CALL DTRMM( 'R', 'U', 'N', 'N', JLEN, KNZ, ONE,
- $ U( J2+1, 1+KZS ), LDU, WV( 1, 1+KZS ),
- $ LDWV )
-*
-* ==== Multiply by U11 ====
-*
- CALL DGEMM( 'N', 'N', JLEN, I2, J2, ONE,
- $ H( JROW, INCOL+1 ), LDH, U, LDU, ONE, WV,
- $ LDWV )
-*
-* ==== Copy left of H to right of scratch ====
-*
- CALL DLACPY( 'ALL', JLEN, J2, H( JROW, INCOL+1 ), LDH,
- $ WV( 1, 1+I2 ), LDWV )
-*
-* ==== Multiply by U21 ====
-*
- CALL DTRMM( 'R', 'L', 'N', 'N', JLEN, I4-I2, ONE,
- $ U( 1, I2+1 ), LDU, WV( 1, 1+I2 ), LDWV )
-*
-* ==== Multiply by U22 ====
-*
- CALL DGEMM( 'N', 'N', JLEN, I4-I2, J4-J2, ONE,
- $ H( JROW, INCOL+1+J2 ), LDH,
- $ U( J2+1, I2+1 ), LDU, ONE, WV( 1, 1+I2 ),
- $ LDWV )
-*
-* ==== Copy it back ====
-*
- CALL DLACPY( 'ALL', JLEN, KDU, WV, LDWV,
- $ H( JROW, INCOL+1 ), LDH )
- 200 CONTINUE
-*
-* ==== Multiply Z (also vertical) ====
-*
- IF( WANTZ ) THEN
- DO 210 JROW = ILOZ, IHIZ, NV
- JLEN = MIN( NV, IHIZ-JROW+1 )
-*
-* ==== Copy right of Z to left of scratch (first
-* . KZS columns get multiplied by zero) ====
-*
- CALL DLACPY( 'ALL', JLEN, KNZ,
- $ Z( JROW, INCOL+1+J2 ), LDZ,
- $ WV( 1, 1+KZS ), LDWV )
-*
-* ==== Multiply by U12 ====
-*
- CALL DLASET( 'ALL', JLEN, KZS, ZERO, ZERO, WV,
- $ LDWV )
- CALL DTRMM( 'R', 'U', 'N', 'N', JLEN, KNZ, ONE,
- $ U( J2+1, 1+KZS ), LDU, WV( 1, 1+KZS ),
- $ LDWV )
-*
-* ==== Multiply by U11 ====
-*
- CALL DGEMM( 'N', 'N', JLEN, I2, J2, ONE,
- $ Z( JROW, INCOL+1 ), LDZ, U, LDU, ONE,
- $ WV, LDWV )
-*
-* ==== Copy left of Z to right of scratch ====
-*
- CALL DLACPY( 'ALL', JLEN, J2, Z( JROW, INCOL+1 ),
- $ LDZ, WV( 1, 1+I2 ), LDWV )
-*
-* ==== Multiply by U21 ====
-*
- CALL DTRMM( 'R', 'L', 'N', 'N', JLEN, I4-I2, ONE,
- $ U( 1, I2+1 ), LDU, WV( 1, 1+I2 ),
- $ LDWV )
-*
-* ==== Multiply by U22 ====
-*
- CALL DGEMM( 'N', 'N', JLEN, I4-I2, J4-J2, ONE,
- $ Z( JROW, INCOL+1+J2 ), LDZ,
- $ U( J2+1, I2+1 ), LDU, ONE,
- $ WV( 1, 1+I2 ), LDWV )
-*
-* ==== Copy the result back to Z ====
-*
- CALL DLACPY( 'ALL', JLEN, KDU, WV, LDWV,
- $ Z( JROW, INCOL+1 ), LDZ )
- 210 CONTINUE
- END IF
- END IF
- END IF
- 220 CONTINUE
-*
-* ==== End of DLAQR5 ====
-*
- END
diff --git a/src/lib/lapack/dlarf.f b/src/lib/lapack/dlarf.f
deleted file mode 100644
index 22edc899..00000000
--- a/src/lib/lapack/dlarf.f
+++ /dev/null
@@ -1,115 +0,0 @@
- SUBROUTINE DLARF( SIDE, M, N, V, INCV, TAU, C, LDC, WORK )
-*
-* -- LAPACK auxiliary routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- CHARACTER SIDE
- INTEGER INCV, LDC, M, N
- DOUBLE PRECISION TAU
-* ..
-* .. Array Arguments ..
- DOUBLE PRECISION C( LDC, * ), V( * ), WORK( * )
-* ..
-*
-* Purpose
-* =======
-*
-* DLARF applies a real elementary reflector H to a real m by n matrix
-* C, from either the left or the right. H is represented in the form
-*
-* H = I - tau * v * v'
-*
-* where tau is a real scalar and v is a real vector.
-*
-* If tau = 0, then H is taken to be the unit matrix.
-*
-* Arguments
-* =========
-*
-* SIDE (input) CHARACTER*1
-* = 'L': form H * C
-* = 'R': form C * H
-*
-* M (input) INTEGER
-* The number of rows of the matrix C.
-*
-* N (input) INTEGER
-* The number of columns of the matrix C.
-*
-* V (input) DOUBLE PRECISION array, dimension
-* (1 + (M-1)*abs(INCV)) if SIDE = 'L'
-* or (1 + (N-1)*abs(INCV)) if SIDE = 'R'
-* The vector v in the representation of H. V is not used if
-* TAU = 0.
-*
-* INCV (input) INTEGER
-* The increment between elements of v. INCV <> 0.
-*
-* TAU (input) DOUBLE PRECISION
-* The value tau in the representation of H.
-*
-* C (input/output) DOUBLE PRECISION array, dimension (LDC,N)
-* On entry, the m by n matrix C.
-* On exit, C is overwritten by the matrix H * C if SIDE = 'L',
-* or C * H if SIDE = 'R'.
-*
-* LDC (input) INTEGER
-* The leading dimension of the array C. LDC >= max(1,M).
-*
-* WORK (workspace) DOUBLE PRECISION array, dimension
-* (N) if SIDE = 'L'
-* or (M) if SIDE = 'R'
-*
-* =====================================================================
-*
-* .. Parameters ..
- DOUBLE PRECISION ONE, ZERO
- PARAMETER ( ONE = 1.0D+0, ZERO = 0.0D+0 )
-* ..
-* .. External Subroutines ..
- EXTERNAL DGEMV, DGER
-* ..
-* .. External Functions ..
- LOGICAL LSAME
- EXTERNAL LSAME
-* ..
-* .. Executable Statements ..
-*
- IF( LSAME( SIDE, 'L' ) ) THEN
-*
-* Form H * C
-*
- IF( TAU.NE.ZERO ) THEN
-*
-* w := C' * v
-*
- CALL DGEMV( 'Transpose', M, N, ONE, C, LDC, V, INCV, ZERO,
- $ WORK, 1 )
-*
-* C := C - v * w'
-*
- CALL DGER( M, N, -TAU, V, INCV, WORK, 1, C, LDC )
- END IF
- ELSE
-*
-* Form C * H
-*
- IF( TAU.NE.ZERO ) THEN
-*
-* w := C * v
-*
- CALL DGEMV( 'No transpose', M, N, ONE, C, LDC, V, INCV,
- $ ZERO, WORK, 1 )
-*
-* C := C - w * v'
-*
- CALL DGER( M, N, -TAU, WORK, 1, V, INCV, C, LDC )
- END IF
- END IF
- RETURN
-*
-* End of DLARF
-*
- END
diff --git a/src/lib/lapack/dlarfb.f b/src/lib/lapack/dlarfb.f
deleted file mode 100644
index d4422473..00000000
--- a/src/lib/lapack/dlarfb.f
+++ /dev/null
@@ -1,587 +0,0 @@
- SUBROUTINE DLARFB( SIDE, TRANS, DIRECT, STOREV, M, N, K, V, LDV,
- $ T, LDT, C, LDC, WORK, LDWORK )
-*
-* -- LAPACK auxiliary routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- CHARACTER DIRECT, SIDE, STOREV, TRANS
- INTEGER K, LDC, LDT, LDV, LDWORK, M, N
-* ..
-* .. Array Arguments ..
- DOUBLE PRECISION C( LDC, * ), T( LDT, * ), V( LDV, * ),
- $ WORK( LDWORK, * )
-* ..
-*
-* Purpose
-* =======
-*
-* DLARFB applies a real block reflector H or its transpose H' to a
-* real m by n matrix C, from either the left or the right.
-*
-* Arguments
-* =========
-*
-* SIDE (input) CHARACTER*1
-* = 'L': apply H or H' from the Left
-* = 'R': apply H or H' from the Right
-*
-* TRANS (input) CHARACTER*1
-* = 'N': apply H (No transpose)
-* = 'T': apply H' (Transpose)
-*
-* DIRECT (input) CHARACTER*1
-* Indicates how H is formed from a product of elementary
-* reflectors
-* = 'F': H = H(1) H(2) . . . H(k) (Forward)
-* = 'B': H = H(k) . . . H(2) H(1) (Backward)
-*
-* STOREV (input) CHARACTER*1
-* Indicates how the vectors which define the elementary
-* reflectors are stored:
-* = 'C': Columnwise
-* = 'R': Rowwise
-*
-* M (input) INTEGER
-* The number of rows of the matrix C.
-*
-* N (input) INTEGER
-* The number of columns of the matrix C.
-*
-* K (input) INTEGER
-* The order of the matrix T (= the number of elementary
-* reflectors whose product defines the block reflector).
-*
-* V (input) DOUBLE PRECISION array, dimension
-* (LDV,K) if STOREV = 'C'
-* (LDV,M) if STOREV = 'R' and SIDE = 'L'
-* (LDV,N) if STOREV = 'R' and SIDE = 'R'
-* The matrix V. See further details.
-*
-* LDV (input) INTEGER
-* The leading dimension of the array V.
-* If STOREV = 'C' and SIDE = 'L', LDV >= max(1,M);
-* if STOREV = 'C' and SIDE = 'R', LDV >= max(1,N);
-* if STOREV = 'R', LDV >= K.
-*
-* T (input) DOUBLE PRECISION array, dimension (LDT,K)
-* The triangular k by k matrix T in the representation of the
-* block reflector.
-*
-* LDT (input) INTEGER
-* The leading dimension of the array T. LDT >= K.
-*
-* C (input/output) DOUBLE PRECISION array, dimension (LDC,N)
-* On entry, the m by n matrix C.
-* On exit, C is overwritten by H*C or H'*C or C*H or C*H'.
-*
-* LDC (input) INTEGER
-* The leading dimension of the array C. LDA >= max(1,M).
-*
-* WORK (workspace) DOUBLE PRECISION array, dimension (LDWORK,K)
-*
-* LDWORK (input) INTEGER
-* The leading dimension of the array WORK.
-* If SIDE = 'L', LDWORK >= max(1,N);
-* if SIDE = 'R', LDWORK >= max(1,M).
-*
-* =====================================================================
-*
-* .. Parameters ..
- DOUBLE PRECISION ONE
- PARAMETER ( ONE = 1.0D+0 )
-* ..
-* .. Local Scalars ..
- CHARACTER TRANST
- INTEGER I, J
-* ..
-* .. External Functions ..
- LOGICAL LSAME
- EXTERNAL LSAME
-* ..
-* .. External Subroutines ..
- EXTERNAL DCOPY, DGEMM, DTRMM
-* ..
-* .. Executable Statements ..
-*
-* Quick return if possible
-*
- IF( M.LE.0 .OR. N.LE.0 )
- $ RETURN
-*
- IF( LSAME( TRANS, 'N' ) ) THEN
- TRANST = 'T'
- ELSE
- TRANST = 'N'
- END IF
-*
- IF( LSAME( STOREV, 'C' ) ) THEN
-*
- IF( LSAME( DIRECT, 'F' ) ) THEN
-*
-* Let V = ( V1 ) (first K rows)
-* ( V2 )
-* where V1 is unit lower triangular.
-*
- IF( LSAME( SIDE, 'L' ) ) THEN
-*
-* Form H * C or H' * C where C = ( C1 )
-* ( C2 )
-*
-* W := C' * V = (C1'*V1 + C2'*V2) (stored in WORK)
-*
-* W := C1'
-*
- DO 10 J = 1, K
- CALL DCOPY( N, C( J, 1 ), LDC, WORK( 1, J ), 1 )
- 10 CONTINUE
-*
-* W := W * V1
-*
- CALL DTRMM( 'Right', 'Lower', 'No transpose', 'Unit', N,
- $ K, ONE, V, LDV, WORK, LDWORK )
- IF( M.GT.K ) THEN
-*
-* W := W + C2'*V2
-*
- CALL DGEMM( 'Transpose', 'No transpose', N, K, M-K,
- $ ONE, C( K+1, 1 ), LDC, V( K+1, 1 ), LDV,
- $ ONE, WORK, LDWORK )
- END IF
-*
-* W := W * T' or W * T
-*
- CALL DTRMM( 'Right', 'Upper', TRANST, 'Non-unit', N, K,
- $ ONE, T, LDT, WORK, LDWORK )
-*
-* C := C - V * W'
-*
- IF( M.GT.K ) THEN
-*
-* C2 := C2 - V2 * W'
-*
- CALL DGEMM( 'No transpose', 'Transpose', M-K, N, K,
- $ -ONE, V( K+1, 1 ), LDV, WORK, LDWORK, ONE,
- $ C( K+1, 1 ), LDC )
- END IF
-*
-* W := W * V1'
-*
- CALL DTRMM( 'Right', 'Lower', 'Transpose', 'Unit', N, K,
- $ ONE, V, LDV, WORK, LDWORK )
-*
-* C1 := C1 - W'
-*
- DO 30 J = 1, K
- DO 20 I = 1, N
- C( J, I ) = C( J, I ) - WORK( I, J )
- 20 CONTINUE
- 30 CONTINUE
-*
- ELSE IF( LSAME( SIDE, 'R' ) ) THEN
-*
-* Form C * H or C * H' where C = ( C1 C2 )
-*
-* W := C * V = (C1*V1 + C2*V2) (stored in WORK)
-*
-* W := C1
-*
- DO 40 J = 1, K
- CALL DCOPY( M, C( 1, J ), 1, WORK( 1, J ), 1 )
- 40 CONTINUE
-*
-* W := W * V1
-*
- CALL DTRMM( 'Right', 'Lower', 'No transpose', 'Unit', M,
- $ K, ONE, V, LDV, WORK, LDWORK )
- IF( N.GT.K ) THEN
-*
-* W := W + C2 * V2
-*
- CALL DGEMM( 'No transpose', 'No transpose', M, K, N-K,
- $ ONE, C( 1, K+1 ), LDC, V( K+1, 1 ), LDV,
- $ ONE, WORK, LDWORK )
- END IF
-*
-* W := W * T or W * T'
-*
- CALL DTRMM( 'Right', 'Upper', TRANS, 'Non-unit', M, K,
- $ ONE, T, LDT, WORK, LDWORK )
-*
-* C := C - W * V'
-*
- IF( N.GT.K ) THEN
-*
-* C2 := C2 - W * V2'
-*
- CALL DGEMM( 'No transpose', 'Transpose', M, N-K, K,
- $ -ONE, WORK, LDWORK, V( K+1, 1 ), LDV, ONE,
- $ C( 1, K+1 ), LDC )
- END IF
-*
-* W := W * V1'
-*
- CALL DTRMM( 'Right', 'Lower', 'Transpose', 'Unit', M, K,
- $ ONE, V, LDV, WORK, LDWORK )
-*
-* C1 := C1 - W
-*
- DO 60 J = 1, K
- DO 50 I = 1, M
- C( I, J ) = C( I, J ) - WORK( I, J )
- 50 CONTINUE
- 60 CONTINUE
- END IF
-*
- ELSE
-*
-* Let V = ( V1 )
-* ( V2 ) (last K rows)
-* where V2 is unit upper triangular.
-*
- IF( LSAME( SIDE, 'L' ) ) THEN
-*
-* Form H * C or H' * C where C = ( C1 )
-* ( C2 )
-*
-* W := C' * V = (C1'*V1 + C2'*V2) (stored in WORK)
-*
-* W := C2'
-*
- DO 70 J = 1, K
- CALL DCOPY( N, C( M-K+J, 1 ), LDC, WORK( 1, J ), 1 )
- 70 CONTINUE
-*
-* W := W * V2
-*
- CALL DTRMM( 'Right', 'Upper', 'No transpose', 'Unit', N,
- $ K, ONE, V( M-K+1, 1 ), LDV, WORK, LDWORK )
- IF( M.GT.K ) THEN
-*
-* W := W + C1'*V1
-*
- CALL DGEMM( 'Transpose', 'No transpose', N, K, M-K,
- $ ONE, C, LDC, V, LDV, ONE, WORK, LDWORK )
- END IF
-*
-* W := W * T' or W * T
-*
- CALL DTRMM( 'Right', 'Lower', TRANST, 'Non-unit', N, K,
- $ ONE, T, LDT, WORK, LDWORK )
-*
-* C := C - V * W'
-*
- IF( M.GT.K ) THEN
-*
-* C1 := C1 - V1 * W'
-*
- CALL DGEMM( 'No transpose', 'Transpose', M-K, N, K,
- $ -ONE, V, LDV, WORK, LDWORK, ONE, C, LDC )
- END IF
-*
-* W := W * V2'
-*
- CALL DTRMM( 'Right', 'Upper', 'Transpose', 'Unit', N, K,
- $ ONE, V( M-K+1, 1 ), LDV, WORK, LDWORK )
-*
-* C2 := C2 - W'
-*
- DO 90 J = 1, K
- DO 80 I = 1, N
- C( M-K+J, I ) = C( M-K+J, I ) - WORK( I, J )
- 80 CONTINUE
- 90 CONTINUE
-*
- ELSE IF( LSAME( SIDE, 'R' ) ) THEN
-*
-* Form C * H or C * H' where C = ( C1 C2 )
-*
-* W := C * V = (C1*V1 + C2*V2) (stored in WORK)
-*
-* W := C2
-*
- DO 100 J = 1, K
- CALL DCOPY( M, C( 1, N-K+J ), 1, WORK( 1, J ), 1 )
- 100 CONTINUE
-*
-* W := W * V2
-*
- CALL DTRMM( 'Right', 'Upper', 'No transpose', 'Unit', M,
- $ K, ONE, V( N-K+1, 1 ), LDV, WORK, LDWORK )
- IF( N.GT.K ) THEN
-*
-* W := W + C1 * V1
-*
- CALL DGEMM( 'No transpose', 'No transpose', M, K, N-K,
- $ ONE, C, LDC, V, LDV, ONE, WORK, LDWORK )
- END IF
-*
-* W := W * T or W * T'
-*
- CALL DTRMM( 'Right', 'Lower', TRANS, 'Non-unit', M, K,
- $ ONE, T, LDT, WORK, LDWORK )
-*
-* C := C - W * V'
-*
- IF( N.GT.K ) THEN
-*
-* C1 := C1 - W * V1'
-*
- CALL DGEMM( 'No transpose', 'Transpose', M, N-K, K,
- $ -ONE, WORK, LDWORK, V, LDV, ONE, C, LDC )
- END IF
-*
-* W := W * V2'
-*
- CALL DTRMM( 'Right', 'Upper', 'Transpose', 'Unit', M, K,
- $ ONE, V( N-K+1, 1 ), LDV, WORK, LDWORK )
-*
-* C2 := C2 - W
-*
- DO 120 J = 1, K
- DO 110 I = 1, M
- C( I, N-K+J ) = C( I, N-K+J ) - WORK( I, J )
- 110 CONTINUE
- 120 CONTINUE
- END IF
- END IF
-*
- ELSE IF( LSAME( STOREV, 'R' ) ) THEN
-*
- IF( LSAME( DIRECT, 'F' ) ) THEN
-*
-* Let V = ( V1 V2 ) (V1: first K columns)
-* where V1 is unit upper triangular.
-*
- IF( LSAME( SIDE, 'L' ) ) THEN
-*
-* Form H * C or H' * C where C = ( C1 )
-* ( C2 )
-*
-* W := C' * V' = (C1'*V1' + C2'*V2') (stored in WORK)
-*
-* W := C1'
-*
- DO 130 J = 1, K
- CALL DCOPY( N, C( J, 1 ), LDC, WORK( 1, J ), 1 )
- 130 CONTINUE
-*
-* W := W * V1'
-*
- CALL DTRMM( 'Right', 'Upper', 'Transpose', 'Unit', N, K,
- $ ONE, V, LDV, WORK, LDWORK )
- IF( M.GT.K ) THEN
-*
-* W := W + C2'*V2'
-*
- CALL DGEMM( 'Transpose', 'Transpose', N, K, M-K, ONE,
- $ C( K+1, 1 ), LDC, V( 1, K+1 ), LDV, ONE,
- $ WORK, LDWORK )
- END IF
-*
-* W := W * T' or W * T
-*
- CALL DTRMM( 'Right', 'Upper', TRANST, 'Non-unit', N, K,
- $ ONE, T, LDT, WORK, LDWORK )
-*
-* C := C - V' * W'
-*
- IF( M.GT.K ) THEN
-*
-* C2 := C2 - V2' * W'
-*
- CALL DGEMM( 'Transpose', 'Transpose', M-K, N, K, -ONE,
- $ V( 1, K+1 ), LDV, WORK, LDWORK, ONE,
- $ C( K+1, 1 ), LDC )
- END IF
-*
-* W := W * V1
-*
- CALL DTRMM( 'Right', 'Upper', 'No transpose', 'Unit', N,
- $ K, ONE, V, LDV, WORK, LDWORK )
-*
-* C1 := C1 - W'
-*
- DO 150 J = 1, K
- DO 140 I = 1, N
- C( J, I ) = C( J, I ) - WORK( I, J )
- 140 CONTINUE
- 150 CONTINUE
-*
- ELSE IF( LSAME( SIDE, 'R' ) ) THEN
-*
-* Form C * H or C * H' where C = ( C1 C2 )
-*
-* W := C * V' = (C1*V1' + C2*V2') (stored in WORK)
-*
-* W := C1
-*
- DO 160 J = 1, K
- CALL DCOPY( M, C( 1, J ), 1, WORK( 1, J ), 1 )
- 160 CONTINUE
-*
-* W := W * V1'
-*
- CALL DTRMM( 'Right', 'Upper', 'Transpose', 'Unit', M, K,
- $ ONE, V, LDV, WORK, LDWORK )
- IF( N.GT.K ) THEN
-*
-* W := W + C2 * V2'
-*
- CALL DGEMM( 'No transpose', 'Transpose', M, K, N-K,
- $ ONE, C( 1, K+1 ), LDC, V( 1, K+1 ), LDV,
- $ ONE, WORK, LDWORK )
- END IF
-*
-* W := W * T or W * T'
-*
- CALL DTRMM( 'Right', 'Upper', TRANS, 'Non-unit', M, K,
- $ ONE, T, LDT, WORK, LDWORK )
-*
-* C := C - W * V
-*
- IF( N.GT.K ) THEN
-*
-* C2 := C2 - W * V2
-*
- CALL DGEMM( 'No transpose', 'No transpose', M, N-K, K,
- $ -ONE, WORK, LDWORK, V( 1, K+1 ), LDV, ONE,
- $ C( 1, K+1 ), LDC )
- END IF
-*
-* W := W * V1
-*
- CALL DTRMM( 'Right', 'Upper', 'No transpose', 'Unit', M,
- $ K, ONE, V, LDV, WORK, LDWORK )
-*
-* C1 := C1 - W
-*
- DO 180 J = 1, K
- DO 170 I = 1, M
- C( I, J ) = C( I, J ) - WORK( I, J )
- 170 CONTINUE
- 180 CONTINUE
-*
- END IF
-*
- ELSE
-*
-* Let V = ( V1 V2 ) (V2: last K columns)
-* where V2 is unit lower triangular.
-*
- IF( LSAME( SIDE, 'L' ) ) THEN
-*
-* Form H * C or H' * C where C = ( C1 )
-* ( C2 )
-*
-* W := C' * V' = (C1'*V1' + C2'*V2') (stored in WORK)
-*
-* W := C2'
-*
- DO 190 J = 1, K
- CALL DCOPY( N, C( M-K+J, 1 ), LDC, WORK( 1, J ), 1 )
- 190 CONTINUE
-*
-* W := W * V2'
-*
- CALL DTRMM( 'Right', 'Lower', 'Transpose', 'Unit', N, K,
- $ ONE, V( 1, M-K+1 ), LDV, WORK, LDWORK )
- IF( M.GT.K ) THEN
-*
-* W := W + C1'*V1'
-*
- CALL DGEMM( 'Transpose', 'Transpose', N, K, M-K, ONE,
- $ C, LDC, V, LDV, ONE, WORK, LDWORK )
- END IF
-*
-* W := W * T' or W * T
-*
- CALL DTRMM( 'Right', 'Lower', TRANST, 'Non-unit', N, K,
- $ ONE, T, LDT, WORK, LDWORK )
-*
-* C := C - V' * W'
-*
- IF( M.GT.K ) THEN
-*
-* C1 := C1 - V1' * W'
-*
- CALL DGEMM( 'Transpose', 'Transpose', M-K, N, K, -ONE,
- $ V, LDV, WORK, LDWORK, ONE, C, LDC )
- END IF
-*
-* W := W * V2
-*
- CALL DTRMM( 'Right', 'Lower', 'No transpose', 'Unit', N,
- $ K, ONE, V( 1, M-K+1 ), LDV, WORK, LDWORK )
-*
-* C2 := C2 - W'
-*
- DO 210 J = 1, K
- DO 200 I = 1, N
- C( M-K+J, I ) = C( M-K+J, I ) - WORK( I, J )
- 200 CONTINUE
- 210 CONTINUE
-*
- ELSE IF( LSAME( SIDE, 'R' ) ) THEN
-*
-* Form C * H or C * H' where C = ( C1 C2 )
-*
-* W := C * V' = (C1*V1' + C2*V2') (stored in WORK)
-*
-* W := C2
-*
- DO 220 J = 1, K
- CALL DCOPY( M, C( 1, N-K+J ), 1, WORK( 1, J ), 1 )
- 220 CONTINUE
-*
-* W := W * V2'
-*
- CALL DTRMM( 'Right', 'Lower', 'Transpose', 'Unit', M, K,
- $ ONE, V( 1, N-K+1 ), LDV, WORK, LDWORK )
- IF( N.GT.K ) THEN
-*
-* W := W + C1 * V1'
-*
- CALL DGEMM( 'No transpose', 'Transpose', M, K, N-K,
- $ ONE, C, LDC, V, LDV, ONE, WORK, LDWORK )
- END IF
-*
-* W := W * T or W * T'
-*
- CALL DTRMM( 'Right', 'Lower', TRANS, 'Non-unit', M, K,
- $ ONE, T, LDT, WORK, LDWORK )
-*
-* C := C - W * V
-*
- IF( N.GT.K ) THEN
-*
-* C1 := C1 - W * V1
-*
- CALL DGEMM( 'No transpose', 'No transpose', M, N-K, K,
- $ -ONE, WORK, LDWORK, V, LDV, ONE, C, LDC )
- END IF
-*
-* W := W * V2
-*
- CALL DTRMM( 'Right', 'Lower', 'No transpose', 'Unit', M,
- $ K, ONE, V( 1, N-K+1 ), LDV, WORK, LDWORK )
-*
-* C1 := C1 - W
-*
- DO 240 J = 1, K
- DO 230 I = 1, M
- C( I, N-K+J ) = C( I, N-K+J ) - WORK( I, J )
- 230 CONTINUE
- 240 CONTINUE
-*
- END IF
-*
- END IF
- END IF
-*
- RETURN
-*
-* End of DLARFB
-*
- END
diff --git a/src/lib/lapack/dlarfg.f b/src/lib/lapack/dlarfg.f
deleted file mode 100644
index be981880..00000000
--- a/src/lib/lapack/dlarfg.f
+++ /dev/null
@@ -1,137 +0,0 @@
- SUBROUTINE DLARFG( N, ALPHA, X, INCX, TAU )
-*
-* -- LAPACK auxiliary routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- INTEGER INCX, N
- DOUBLE PRECISION ALPHA, TAU
-* ..
-* .. Array Arguments ..
- DOUBLE PRECISION X( * )
-* ..
-*
-* Purpose
-* =======
-*
-* DLARFG generates a real elementary reflector H of order n, such
-* that
-*
-* H * ( alpha ) = ( beta ), H' * H = I.
-* ( x ) ( 0 )
-*
-* where alpha and beta are scalars, and x is an (n-1)-element real
-* vector. H is represented in the form
-*
-* H = I - tau * ( 1 ) * ( 1 v' ) ,
-* ( v )
-*
-* where tau is a real scalar and v is a real (n-1)-element
-* vector.
-*
-* If the elements of x are all zero, then tau = 0 and H is taken to be
-* the unit matrix.
-*
-* Otherwise 1 <= tau <= 2.
-*
-* Arguments
-* =========
-*
-* N (input) INTEGER
-* The order of the elementary reflector.
-*
-* ALPHA (input/output) DOUBLE PRECISION
-* On entry, the value alpha.
-* On exit, it is overwritten with the value beta.
-*
-* X (input/output) DOUBLE PRECISION array, dimension
-* (1+(N-2)*abs(INCX))
-* On entry, the vector x.
-* On exit, it is overwritten with the vector v.
-*
-* INCX (input) INTEGER
-* The increment between elements of X. INCX > 0.
-*
-* TAU (output) DOUBLE PRECISION
-* The value tau.
-*
-* =====================================================================
-*
-* .. Parameters ..
- DOUBLE PRECISION ONE, ZERO
- PARAMETER ( ONE = 1.0D+0, ZERO = 0.0D+0 )
-* ..
-* .. Local Scalars ..
- INTEGER J, KNT
- DOUBLE PRECISION BETA, RSAFMN, SAFMIN, XNORM
-* ..
-* .. External Functions ..
- DOUBLE PRECISION DLAMCH, DLAPY2, DNRM2
- EXTERNAL DLAMCH, DLAPY2, DNRM2
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC ABS, SIGN
-* ..
-* .. External Subroutines ..
- EXTERNAL DSCAL
-* ..
-* .. Executable Statements ..
-*
- IF( N.LE.1 ) THEN
- TAU = ZERO
- RETURN
- END IF
-*
- XNORM = DNRM2( N-1, X, INCX )
-*
- IF( XNORM.EQ.ZERO ) THEN
-*
-* H = I
-*
- TAU = ZERO
- ELSE
-*
-* general case
-*
- BETA = -SIGN( DLAPY2( ALPHA, XNORM ), ALPHA )
- SAFMIN = DLAMCH( 'S' ) / DLAMCH( 'E' )
- IF( ABS( BETA ).LT.SAFMIN ) THEN
-*
-* XNORM, BETA may be inaccurate; scale X and recompute them
-*
- RSAFMN = ONE / SAFMIN
- KNT = 0
- 10 CONTINUE
- KNT = KNT + 1
- CALL DSCAL( N-1, RSAFMN, X, INCX )
- BETA = BETA*RSAFMN
- ALPHA = ALPHA*RSAFMN
- IF( ABS( BETA ).LT.SAFMIN )
- $ GO TO 10
-*
-* New BETA is at most 1, at least SAFMIN
-*
- XNORM = DNRM2( N-1, X, INCX )
- BETA = -SIGN( DLAPY2( ALPHA, XNORM ), ALPHA )
- TAU = ( BETA-ALPHA ) / BETA
- CALL DSCAL( N-1, ONE / ( ALPHA-BETA ), X, INCX )
-*
-* If ALPHA is subnormal, it may lose relative accuracy
-*
- ALPHA = BETA
- DO 20 J = 1, KNT
- ALPHA = ALPHA*SAFMIN
- 20 CONTINUE
- ELSE
- TAU = ( BETA-ALPHA ) / BETA
- CALL DSCAL( N-1, ONE / ( ALPHA-BETA ), X, INCX )
- ALPHA = BETA
- END IF
- END IF
-*
- RETURN
-*
-* End of DLARFG
-*
- END
diff --git a/src/lib/lapack/dlarft.f b/src/lib/lapack/dlarft.f
deleted file mode 100644
index 2cd115f4..00000000
--- a/src/lib/lapack/dlarft.f
+++ /dev/null
@@ -1,217 +0,0 @@
- SUBROUTINE DLARFT( DIRECT, STOREV, N, K, V, LDV, TAU, T, LDT )
-*
-* -- LAPACK auxiliary routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- CHARACTER DIRECT, STOREV
- INTEGER K, LDT, LDV, N
-* ..
-* .. Array Arguments ..
- DOUBLE PRECISION T( LDT, * ), TAU( * ), V( LDV, * )
-* ..
-*
-* Purpose
-* =======
-*
-* DLARFT forms the triangular factor T of a real block reflector H
-* of order n, which is defined as a product of k elementary reflectors.
-*
-* If DIRECT = 'F', H = H(1) H(2) . . . H(k) and T is upper triangular;
-*
-* If DIRECT = 'B', H = H(k) . . . H(2) H(1) and T is lower triangular.
-*
-* If STOREV = 'C', the vector which defines the elementary reflector
-* H(i) is stored in the i-th column of the array V, and
-*
-* H = I - V * T * V'
-*
-* If STOREV = 'R', the vector which defines the elementary reflector
-* H(i) is stored in the i-th row of the array V, and
-*
-* H = I - V' * T * V
-*
-* Arguments
-* =========
-*
-* DIRECT (input) CHARACTER*1
-* Specifies the order in which the elementary reflectors are
-* multiplied to form the block reflector:
-* = 'F': H = H(1) H(2) . . . H(k) (Forward)
-* = 'B': H = H(k) . . . H(2) H(1) (Backward)
-*
-* STOREV (input) CHARACTER*1
-* Specifies how the vectors which define the elementary
-* reflectors are stored (see also Further Details):
-* = 'C': columnwise
-* = 'R': rowwise
-*
-* N (input) INTEGER
-* The order of the block reflector H. N >= 0.
-*
-* K (input) INTEGER
-* The order of the triangular factor T (= the number of
-* elementary reflectors). K >= 1.
-*
-* V (input/output) DOUBLE PRECISION array, dimension
-* (LDV,K) if STOREV = 'C'
-* (LDV,N) if STOREV = 'R'
-* The matrix V. See further details.
-*
-* LDV (input) INTEGER
-* The leading dimension of the array V.
-* If STOREV = 'C', LDV >= max(1,N); if STOREV = 'R', LDV >= K.
-*
-* TAU (input) DOUBLE PRECISION array, dimension (K)
-* TAU(i) must contain the scalar factor of the elementary
-* reflector H(i).
-*
-* T (output) DOUBLE PRECISION array, dimension (LDT,K)
-* The k by k triangular factor T of the block reflector.
-* If DIRECT = 'F', T is upper triangular; if DIRECT = 'B', T is
-* lower triangular. The rest of the array is not used.
-*
-* LDT (input) INTEGER
-* The leading dimension of the array T. LDT >= K.
-*
-* Further Details
-* ===============
-*
-* The shape of the matrix V and the storage of the vectors which define
-* the H(i) is best illustrated by the following example with n = 5 and
-* k = 3. The elements equal to 1 are not stored; the corresponding
-* array elements are modified but restored on exit. The rest of the
-* array is not used.
-*
-* DIRECT = 'F' and STOREV = 'C': DIRECT = 'F' and STOREV = 'R':
-*
-* V = ( 1 ) V = ( 1 v1 v1 v1 v1 )
-* ( v1 1 ) ( 1 v2 v2 v2 )
-* ( v1 v2 1 ) ( 1 v3 v3 )
-* ( v1 v2 v3 )
-* ( v1 v2 v3 )
-*
-* DIRECT = 'B' and STOREV = 'C': DIRECT = 'B' and STOREV = 'R':
-*
-* V = ( v1 v2 v3 ) V = ( v1 v1 1 )
-* ( v1 v2 v3 ) ( v2 v2 v2 1 )
-* ( 1 v2 v3 ) ( v3 v3 v3 v3 1 )
-* ( 1 v3 )
-* ( 1 )
-*
-* =====================================================================
-*
-* .. Parameters ..
- DOUBLE PRECISION ONE, ZERO
- PARAMETER ( ONE = 1.0D+0, ZERO = 0.0D+0 )
-* ..
-* .. Local Scalars ..
- INTEGER I, J
- DOUBLE PRECISION VII
-* ..
-* .. External Subroutines ..
- EXTERNAL DGEMV, DTRMV
-* ..
-* .. External Functions ..
- LOGICAL LSAME
- EXTERNAL LSAME
-* ..
-* .. Executable Statements ..
-*
-* Quick return if possible
-*
- IF( N.EQ.0 )
- $ RETURN
-*
- IF( LSAME( DIRECT, 'F' ) ) THEN
- DO 20 I = 1, K
- IF( TAU( I ).EQ.ZERO ) THEN
-*
-* H(i) = I
-*
- DO 10 J = 1, I
- T( J, I ) = ZERO
- 10 CONTINUE
- ELSE
-*
-* general case
-*
- VII = V( I, I )
- V( I, I ) = ONE
- IF( LSAME( STOREV, 'C' ) ) THEN
-*
-* T(1:i-1,i) := - tau(i) * V(i:n,1:i-1)' * V(i:n,i)
-*
- CALL DGEMV( 'Transpose', N-I+1, I-1, -TAU( I ),
- $ V( I, 1 ), LDV, V( I, I ), 1, ZERO,
- $ T( 1, I ), 1 )
- ELSE
-*
-* T(1:i-1,i) := - tau(i) * V(1:i-1,i:n) * V(i,i:n)'
-*
- CALL DGEMV( 'No transpose', I-1, N-I+1, -TAU( I ),
- $ V( 1, I ), LDV, V( I, I ), LDV, ZERO,
- $ T( 1, I ), 1 )
- END IF
- V( I, I ) = VII
-*
-* T(1:i-1,i) := T(1:i-1,1:i-1) * T(1:i-1,i)
-*
- CALL DTRMV( 'Upper', 'No transpose', 'Non-unit', I-1, T,
- $ LDT, T( 1, I ), 1 )
- T( I, I ) = TAU( I )
- END IF
- 20 CONTINUE
- ELSE
- DO 40 I = K, 1, -1
- IF( TAU( I ).EQ.ZERO ) THEN
-*
-* H(i) = I
-*
- DO 30 J = I, K
- T( J, I ) = ZERO
- 30 CONTINUE
- ELSE
-*
-* general case
-*
- IF( I.LT.K ) THEN
- IF( LSAME( STOREV, 'C' ) ) THEN
- VII = V( N-K+I, I )
- V( N-K+I, I ) = ONE
-*
-* T(i+1:k,i) :=
-* - tau(i) * V(1:n-k+i,i+1:k)' * V(1:n-k+i,i)
-*
- CALL DGEMV( 'Transpose', N-K+I, K-I, -TAU( I ),
- $ V( 1, I+1 ), LDV, V( 1, I ), 1, ZERO,
- $ T( I+1, I ), 1 )
- V( N-K+I, I ) = VII
- ELSE
- VII = V( I, N-K+I )
- V( I, N-K+I ) = ONE
-*
-* T(i+1:k,i) :=
-* - tau(i) * V(i+1:k,1:n-k+i) * V(i,1:n-k+i)'
-*
- CALL DGEMV( 'No transpose', K-I, N-K+I, -TAU( I ),
- $ V( I+1, 1 ), LDV, V( I, 1 ), LDV, ZERO,
- $ T( I+1, I ), 1 )
- V( I, N-K+I ) = VII
- END IF
-*
-* T(i+1:k,i) := T(i+1:k,i+1:k) * T(i+1:k,i)
-*
- CALL DTRMV( 'Lower', 'No transpose', 'Non-unit', K-I,
- $ T( I+1, I+1 ), LDT, T( I+1, I ), 1 )
- END IF
- T( I, I ) = TAU( I )
- END IF
- 40 CONTINUE
- END IF
- RETURN
-*
-* End of DLARFT
-*
- END
diff --git a/src/lib/lapack/dlarfx.f b/src/lib/lapack/dlarfx.f
deleted file mode 100644
index cc4654e0..00000000
--- a/src/lib/lapack/dlarfx.f
+++ /dev/null
@@ -1,638 +0,0 @@
- SUBROUTINE DLARFX( SIDE, M, N, V, TAU, C, LDC, WORK )
-*
-* -- LAPACK auxiliary routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- CHARACTER SIDE
- INTEGER LDC, M, N
- DOUBLE PRECISION TAU
-* ..
-* .. Array Arguments ..
- DOUBLE PRECISION C( LDC, * ), V( * ), WORK( * )
-* ..
-*
-* Purpose
-* =======
-*
-* DLARFX applies a real elementary reflector H to a real m by n
-* matrix C, from either the left or the right. H is represented in the
-* form
-*
-* H = I - tau * v * v'
-*
-* where tau is a real scalar and v is a real vector.
-*
-* If tau = 0, then H is taken to be the unit matrix
-*
-* This version uses inline code if H has order < 11.
-*
-* Arguments
-* =========
-*
-* SIDE (input) CHARACTER*1
-* = 'L': form H * C
-* = 'R': form C * H
-*
-* M (input) INTEGER
-* The number of rows of the matrix C.
-*
-* N (input) INTEGER
-* The number of columns of the matrix C.
-*
-* V (input) DOUBLE PRECISION array, dimension (M) if SIDE = 'L'
-* or (N) if SIDE = 'R'
-* The vector v in the representation of H.
-*
-* TAU (input) DOUBLE PRECISION
-* The value tau in the representation of H.
-*
-* C (input/output) DOUBLE PRECISION array, dimension (LDC,N)
-* On entry, the m by n matrix C.
-* On exit, C is overwritten by the matrix H * C if SIDE = 'L',
-* or C * H if SIDE = 'R'.
-*
-* LDC (input) INTEGER
-* The leading dimension of the array C. LDA >= (1,M).
-*
-* WORK (workspace) DOUBLE PRECISION array, dimension
-* (N) if SIDE = 'L'
-* or (M) if SIDE = 'R'
-* WORK is not referenced if H has order < 11.
-*
-* =====================================================================
-*
-* .. Parameters ..
- DOUBLE PRECISION ZERO, ONE
- PARAMETER ( ZERO = 0.0D+0, ONE = 1.0D+0 )
-* ..
-* .. Local Scalars ..
- INTEGER J
- DOUBLE PRECISION SUM, T1, T10, T2, T3, T4, T5, T6, T7, T8, T9,
- $ V1, V10, V2, V3, V4, V5, V6, V7, V8, V9
-* ..
-* .. External Functions ..
- LOGICAL LSAME
- EXTERNAL LSAME
-* ..
-* .. External Subroutines ..
- EXTERNAL DGEMV, DGER
-* ..
-* .. Executable Statements ..
-*
- IF( TAU.EQ.ZERO )
- $ RETURN
- IF( LSAME( SIDE, 'L' ) ) THEN
-*
-* Form H * C, where H has order m.
-*
- GO TO ( 10, 30, 50, 70, 90, 110, 130, 150,
- $ 170, 190 )M
-*
-* Code for general M
-*
-* w := C'*v
-*
- CALL DGEMV( 'Transpose', M, N, ONE, C, LDC, V, 1, ZERO, WORK,
- $ 1 )
-*
-* C := C - tau * v * w'
-*
- CALL DGER( M, N, -TAU, V, 1, WORK, 1, C, LDC )
- GO TO 410
- 10 CONTINUE
-*
-* Special code for 1 x 1 Householder
-*
- T1 = ONE - TAU*V( 1 )*V( 1 )
- DO 20 J = 1, N
- C( 1, J ) = T1*C( 1, J )
- 20 CONTINUE
- GO TO 410
- 30 CONTINUE
-*
-* Special code for 2 x 2 Householder
-*
- V1 = V( 1 )
- T1 = TAU*V1
- V2 = V( 2 )
- T2 = TAU*V2
- DO 40 J = 1, N
- SUM = V1*C( 1, J ) + V2*C( 2, J )
- C( 1, J ) = C( 1, J ) - SUM*T1
- C( 2, J ) = C( 2, J ) - SUM*T2
- 40 CONTINUE
- GO TO 410
- 50 CONTINUE
-*
-* Special code for 3 x 3 Householder
-*
- V1 = V( 1 )
- T1 = TAU*V1
- V2 = V( 2 )
- T2 = TAU*V2
- V3 = V( 3 )
- T3 = TAU*V3
- DO 60 J = 1, N
- SUM = V1*C( 1, J ) + V2*C( 2, J ) + V3*C( 3, J )
- C( 1, J ) = C( 1, J ) - SUM*T1
- C( 2, J ) = C( 2, J ) - SUM*T2
- C( 3, J ) = C( 3, J ) - SUM*T3
- 60 CONTINUE
- GO TO 410
- 70 CONTINUE
-*
-* Special code for 4 x 4 Householder
-*
- V1 = V( 1 )
- T1 = TAU*V1
- V2 = V( 2 )
- T2 = TAU*V2
- V3 = V( 3 )
- T3 = TAU*V3
- V4 = V( 4 )
- T4 = TAU*V4
- DO 80 J = 1, N
- SUM = V1*C( 1, J ) + V2*C( 2, J ) + V3*C( 3, J ) +
- $ V4*C( 4, J )
- C( 1, J ) = C( 1, J ) - SUM*T1
- C( 2, J ) = C( 2, J ) - SUM*T2
- C( 3, J ) = C( 3, J ) - SUM*T3
- C( 4, J ) = C( 4, J ) - SUM*T4
- 80 CONTINUE
- GO TO 410
- 90 CONTINUE
-*
-* Special code for 5 x 5 Householder
-*
- V1 = V( 1 )
- T1 = TAU*V1
- V2 = V( 2 )
- T2 = TAU*V2
- V3 = V( 3 )
- T3 = TAU*V3
- V4 = V( 4 )
- T4 = TAU*V4
- V5 = V( 5 )
- T5 = TAU*V5
- DO 100 J = 1, N
- SUM = V1*C( 1, J ) + V2*C( 2, J ) + V3*C( 3, J ) +
- $ V4*C( 4, J ) + V5*C( 5, J )
- C( 1, J ) = C( 1, J ) - SUM*T1
- C( 2, J ) = C( 2, J ) - SUM*T2
- C( 3, J ) = C( 3, J ) - SUM*T3
- C( 4, J ) = C( 4, J ) - SUM*T4
- C( 5, J ) = C( 5, J ) - SUM*T5
- 100 CONTINUE
- GO TO 410
- 110 CONTINUE
-*
-* Special code for 6 x 6 Householder
-*
- V1 = V( 1 )
- T1 = TAU*V1
- V2 = V( 2 )
- T2 = TAU*V2
- V3 = V( 3 )
- T3 = TAU*V3
- V4 = V( 4 )
- T4 = TAU*V4
- V5 = V( 5 )
- T5 = TAU*V5
- V6 = V( 6 )
- T6 = TAU*V6
- DO 120 J = 1, N
- SUM = V1*C( 1, J ) + V2*C( 2, J ) + V3*C( 3, J ) +
- $ V4*C( 4, J ) + V5*C( 5, J ) + V6*C( 6, J )
- C( 1, J ) = C( 1, J ) - SUM*T1
- C( 2, J ) = C( 2, J ) - SUM*T2
- C( 3, J ) = C( 3, J ) - SUM*T3
- C( 4, J ) = C( 4, J ) - SUM*T4
- C( 5, J ) = C( 5, J ) - SUM*T5
- C( 6, J ) = C( 6, J ) - SUM*T6
- 120 CONTINUE
- GO TO 410
- 130 CONTINUE
-*
-* Special code for 7 x 7 Householder
-*
- V1 = V( 1 )
- T1 = TAU*V1
- V2 = V( 2 )
- T2 = TAU*V2
- V3 = V( 3 )
- T3 = TAU*V3
- V4 = V( 4 )
- T4 = TAU*V4
- V5 = V( 5 )
- T5 = TAU*V5
- V6 = V( 6 )
- T6 = TAU*V6
- V7 = V( 7 )
- T7 = TAU*V7
- DO 140 J = 1, N
- SUM = V1*C( 1, J ) + V2*C( 2, J ) + V3*C( 3, J ) +
- $ V4*C( 4, J ) + V5*C( 5, J ) + V6*C( 6, J ) +
- $ V7*C( 7, J )
- C( 1, J ) = C( 1, J ) - SUM*T1
- C( 2, J ) = C( 2, J ) - SUM*T2
- C( 3, J ) = C( 3, J ) - SUM*T3
- C( 4, J ) = C( 4, J ) - SUM*T4
- C( 5, J ) = C( 5, J ) - SUM*T5
- C( 6, J ) = C( 6, J ) - SUM*T6
- C( 7, J ) = C( 7, J ) - SUM*T7
- 140 CONTINUE
- GO TO 410
- 150 CONTINUE
-*
-* Special code for 8 x 8 Householder
-*
- V1 = V( 1 )
- T1 = TAU*V1
- V2 = V( 2 )
- T2 = TAU*V2
- V3 = V( 3 )
- T3 = TAU*V3
- V4 = V( 4 )
- T4 = TAU*V4
- V5 = V( 5 )
- T5 = TAU*V5
- V6 = V( 6 )
- T6 = TAU*V6
- V7 = V( 7 )
- T7 = TAU*V7
- V8 = V( 8 )
- T8 = TAU*V8
- DO 160 J = 1, N
- SUM = V1*C( 1, J ) + V2*C( 2, J ) + V3*C( 3, J ) +
- $ V4*C( 4, J ) + V5*C( 5, J ) + V6*C( 6, J ) +
- $ V7*C( 7, J ) + V8*C( 8, J )
- C( 1, J ) = C( 1, J ) - SUM*T1
- C( 2, J ) = C( 2, J ) - SUM*T2
- C( 3, J ) = C( 3, J ) - SUM*T3
- C( 4, J ) = C( 4, J ) - SUM*T4
- C( 5, J ) = C( 5, J ) - SUM*T5
- C( 6, J ) = C( 6, J ) - SUM*T6
- C( 7, J ) = C( 7, J ) - SUM*T7
- C( 8, J ) = C( 8, J ) - SUM*T8
- 160 CONTINUE
- GO TO 410
- 170 CONTINUE
-*
-* Special code for 9 x 9 Householder
-*
- V1 = V( 1 )
- T1 = TAU*V1
- V2 = V( 2 )
- T2 = TAU*V2
- V3 = V( 3 )
- T3 = TAU*V3
- V4 = V( 4 )
- T4 = TAU*V4
- V5 = V( 5 )
- T5 = TAU*V5
- V6 = V( 6 )
- T6 = TAU*V6
- V7 = V( 7 )
- T7 = TAU*V7
- V8 = V( 8 )
- T8 = TAU*V8
- V9 = V( 9 )
- T9 = TAU*V9
- DO 180 J = 1, N
- SUM = V1*C( 1, J ) + V2*C( 2, J ) + V3*C( 3, J ) +
- $ V4*C( 4, J ) + V5*C( 5, J ) + V6*C( 6, J ) +
- $ V7*C( 7, J ) + V8*C( 8, J ) + V9*C( 9, J )
- C( 1, J ) = C( 1, J ) - SUM*T1
- C( 2, J ) = C( 2, J ) - SUM*T2
- C( 3, J ) = C( 3, J ) - SUM*T3
- C( 4, J ) = C( 4, J ) - SUM*T4
- C( 5, J ) = C( 5, J ) - SUM*T5
- C( 6, J ) = C( 6, J ) - SUM*T6
- C( 7, J ) = C( 7, J ) - SUM*T7
- C( 8, J ) = C( 8, J ) - SUM*T8
- C( 9, J ) = C( 9, J ) - SUM*T9
- 180 CONTINUE
- GO TO 410
- 190 CONTINUE
-*
-* Special code for 10 x 10 Householder
-*
- V1 = V( 1 )
- T1 = TAU*V1
- V2 = V( 2 )
- T2 = TAU*V2
- V3 = V( 3 )
- T3 = TAU*V3
- V4 = V( 4 )
- T4 = TAU*V4
- V5 = V( 5 )
- T5 = TAU*V5
- V6 = V( 6 )
- T6 = TAU*V6
- V7 = V( 7 )
- T7 = TAU*V7
- V8 = V( 8 )
- T8 = TAU*V8
- V9 = V( 9 )
- T9 = TAU*V9
- V10 = V( 10 )
- T10 = TAU*V10
- DO 200 J = 1, N
- SUM = V1*C( 1, J ) + V2*C( 2, J ) + V3*C( 3, J ) +
- $ V4*C( 4, J ) + V5*C( 5, J ) + V6*C( 6, J ) +
- $ V7*C( 7, J ) + V8*C( 8, J ) + V9*C( 9, J ) +
- $ V10*C( 10, J )
- C( 1, J ) = C( 1, J ) - SUM*T1
- C( 2, J ) = C( 2, J ) - SUM*T2
- C( 3, J ) = C( 3, J ) - SUM*T3
- C( 4, J ) = C( 4, J ) - SUM*T4
- C( 5, J ) = C( 5, J ) - SUM*T5
- C( 6, J ) = C( 6, J ) - SUM*T6
- C( 7, J ) = C( 7, J ) - SUM*T7
- C( 8, J ) = C( 8, J ) - SUM*T8
- C( 9, J ) = C( 9, J ) - SUM*T9
- C( 10, J ) = C( 10, J ) - SUM*T10
- 200 CONTINUE
- GO TO 410
- ELSE
-*
-* Form C * H, where H has order n.
-*
- GO TO ( 210, 230, 250, 270, 290, 310, 330, 350,
- $ 370, 390 )N
-*
-* Code for general N
-*
-* w := C * v
-*
- CALL DGEMV( 'No transpose', M, N, ONE, C, LDC, V, 1, ZERO,
- $ WORK, 1 )
-*
-* C := C - tau * w * v'
-*
- CALL DGER( M, N, -TAU, WORK, 1, V, 1, C, LDC )
- GO TO 410
- 210 CONTINUE
-*
-* Special code for 1 x 1 Householder
-*
- T1 = ONE - TAU*V( 1 )*V( 1 )
- DO 220 J = 1, M
- C( J, 1 ) = T1*C( J, 1 )
- 220 CONTINUE
- GO TO 410
- 230 CONTINUE
-*
-* Special code for 2 x 2 Householder
-*
- V1 = V( 1 )
- T1 = TAU*V1
- V2 = V( 2 )
- T2 = TAU*V2
- DO 240 J = 1, M
- SUM = V1*C( J, 1 ) + V2*C( J, 2 )
- C( J, 1 ) = C( J, 1 ) - SUM*T1
- C( J, 2 ) = C( J, 2 ) - SUM*T2
- 240 CONTINUE
- GO TO 410
- 250 CONTINUE
-*
-* Special code for 3 x 3 Householder
-*
- V1 = V( 1 )
- T1 = TAU*V1
- V2 = V( 2 )
- T2 = TAU*V2
- V3 = V( 3 )
- T3 = TAU*V3
- DO 260 J = 1, M
- SUM = V1*C( J, 1 ) + V2*C( J, 2 ) + V3*C( J, 3 )
- C( J, 1 ) = C( J, 1 ) - SUM*T1
- C( J, 2 ) = C( J, 2 ) - SUM*T2
- C( J, 3 ) = C( J, 3 ) - SUM*T3
- 260 CONTINUE
- GO TO 410
- 270 CONTINUE
-*
-* Special code for 4 x 4 Householder
-*
- V1 = V( 1 )
- T1 = TAU*V1
- V2 = V( 2 )
- T2 = TAU*V2
- V3 = V( 3 )
- T3 = TAU*V3
- V4 = V( 4 )
- T4 = TAU*V4
- DO 280 J = 1, M
- SUM = V1*C( J, 1 ) + V2*C( J, 2 ) + V3*C( J, 3 ) +
- $ V4*C( J, 4 )
- C( J, 1 ) = C( J, 1 ) - SUM*T1
- C( J, 2 ) = C( J, 2 ) - SUM*T2
- C( J, 3 ) = C( J, 3 ) - SUM*T3
- C( J, 4 ) = C( J, 4 ) - SUM*T4
- 280 CONTINUE
- GO TO 410
- 290 CONTINUE
-*
-* Special code for 5 x 5 Householder
-*
- V1 = V( 1 )
- T1 = TAU*V1
- V2 = V( 2 )
- T2 = TAU*V2
- V3 = V( 3 )
- T3 = TAU*V3
- V4 = V( 4 )
- T4 = TAU*V4
- V5 = V( 5 )
- T5 = TAU*V5
- DO 300 J = 1, M
- SUM = V1*C( J, 1 ) + V2*C( J, 2 ) + V3*C( J, 3 ) +
- $ V4*C( J, 4 ) + V5*C( J, 5 )
- C( J, 1 ) = C( J, 1 ) - SUM*T1
- C( J, 2 ) = C( J, 2 ) - SUM*T2
- C( J, 3 ) = C( J, 3 ) - SUM*T3
- C( J, 4 ) = C( J, 4 ) - SUM*T4
- C( J, 5 ) = C( J, 5 ) - SUM*T5
- 300 CONTINUE
- GO TO 410
- 310 CONTINUE
-*
-* Special code for 6 x 6 Householder
-*
- V1 = V( 1 )
- T1 = TAU*V1
- V2 = V( 2 )
- T2 = TAU*V2
- V3 = V( 3 )
- T3 = TAU*V3
- V4 = V( 4 )
- T4 = TAU*V4
- V5 = V( 5 )
- T5 = TAU*V5
- V6 = V( 6 )
- T6 = TAU*V6
- DO 320 J = 1, M
- SUM = V1*C( J, 1 ) + V2*C( J, 2 ) + V3*C( J, 3 ) +
- $ V4*C( J, 4 ) + V5*C( J, 5 ) + V6*C( J, 6 )
- C( J, 1 ) = C( J, 1 ) - SUM*T1
- C( J, 2 ) = C( J, 2 ) - SUM*T2
- C( J, 3 ) = C( J, 3 ) - SUM*T3
- C( J, 4 ) = C( J, 4 ) - SUM*T4
- C( J, 5 ) = C( J, 5 ) - SUM*T5
- C( J, 6 ) = C( J, 6 ) - SUM*T6
- 320 CONTINUE
- GO TO 410
- 330 CONTINUE
-*
-* Special code for 7 x 7 Householder
-*
- V1 = V( 1 )
- T1 = TAU*V1
- V2 = V( 2 )
- T2 = TAU*V2
- V3 = V( 3 )
- T3 = TAU*V3
- V4 = V( 4 )
- T4 = TAU*V4
- V5 = V( 5 )
- T5 = TAU*V5
- V6 = V( 6 )
- T6 = TAU*V6
- V7 = V( 7 )
- T7 = TAU*V7
- DO 340 J = 1, M
- SUM = V1*C( J, 1 ) + V2*C( J, 2 ) + V3*C( J, 3 ) +
- $ V4*C( J, 4 ) + V5*C( J, 5 ) + V6*C( J, 6 ) +
- $ V7*C( J, 7 )
- C( J, 1 ) = C( J, 1 ) - SUM*T1
- C( J, 2 ) = C( J, 2 ) - SUM*T2
- C( J, 3 ) = C( J, 3 ) - SUM*T3
- C( J, 4 ) = C( J, 4 ) - SUM*T4
- C( J, 5 ) = C( J, 5 ) - SUM*T5
- C( J, 6 ) = C( J, 6 ) - SUM*T6
- C( J, 7 ) = C( J, 7 ) - SUM*T7
- 340 CONTINUE
- GO TO 410
- 350 CONTINUE
-*
-* Special code for 8 x 8 Householder
-*
- V1 = V( 1 )
- T1 = TAU*V1
- V2 = V( 2 )
- T2 = TAU*V2
- V3 = V( 3 )
- T3 = TAU*V3
- V4 = V( 4 )
- T4 = TAU*V4
- V5 = V( 5 )
- T5 = TAU*V5
- V6 = V( 6 )
- T6 = TAU*V6
- V7 = V( 7 )
- T7 = TAU*V7
- V8 = V( 8 )
- T8 = TAU*V8
- DO 360 J = 1, M
- SUM = V1*C( J, 1 ) + V2*C( J, 2 ) + V3*C( J, 3 ) +
- $ V4*C( J, 4 ) + V5*C( J, 5 ) + V6*C( J, 6 ) +
- $ V7*C( J, 7 ) + V8*C( J, 8 )
- C( J, 1 ) = C( J, 1 ) - SUM*T1
- C( J, 2 ) = C( J, 2 ) - SUM*T2
- C( J, 3 ) = C( J, 3 ) - SUM*T3
- C( J, 4 ) = C( J, 4 ) - SUM*T4
- C( J, 5 ) = C( J, 5 ) - SUM*T5
- C( J, 6 ) = C( J, 6 ) - SUM*T6
- C( J, 7 ) = C( J, 7 ) - SUM*T7
- C( J, 8 ) = C( J, 8 ) - SUM*T8
- 360 CONTINUE
- GO TO 410
- 370 CONTINUE
-*
-* Special code for 9 x 9 Householder
-*
- V1 = V( 1 )
- T1 = TAU*V1
- V2 = V( 2 )
- T2 = TAU*V2
- V3 = V( 3 )
- T3 = TAU*V3
- V4 = V( 4 )
- T4 = TAU*V4
- V5 = V( 5 )
- T5 = TAU*V5
- V6 = V( 6 )
- T6 = TAU*V6
- V7 = V( 7 )
- T7 = TAU*V7
- V8 = V( 8 )
- T8 = TAU*V8
- V9 = V( 9 )
- T9 = TAU*V9
- DO 380 J = 1, M
- SUM = V1*C( J, 1 ) + V2*C( J, 2 ) + V3*C( J, 3 ) +
- $ V4*C( J, 4 ) + V5*C( J, 5 ) + V6*C( J, 6 ) +
- $ V7*C( J, 7 ) + V8*C( J, 8 ) + V9*C( J, 9 )
- C( J, 1 ) = C( J, 1 ) - SUM*T1
- C( J, 2 ) = C( J, 2 ) - SUM*T2
- C( J, 3 ) = C( J, 3 ) - SUM*T3
- C( J, 4 ) = C( J, 4 ) - SUM*T4
- C( J, 5 ) = C( J, 5 ) - SUM*T5
- C( J, 6 ) = C( J, 6 ) - SUM*T6
- C( J, 7 ) = C( J, 7 ) - SUM*T7
- C( J, 8 ) = C( J, 8 ) - SUM*T8
- C( J, 9 ) = C( J, 9 ) - SUM*T9
- 380 CONTINUE
- GO TO 410
- 390 CONTINUE
-*
-* Special code for 10 x 10 Householder
-*
- V1 = V( 1 )
- T1 = TAU*V1
- V2 = V( 2 )
- T2 = TAU*V2
- V3 = V( 3 )
- T3 = TAU*V3
- V4 = V( 4 )
- T4 = TAU*V4
- V5 = V( 5 )
- T5 = TAU*V5
- V6 = V( 6 )
- T6 = TAU*V6
- V7 = V( 7 )
- T7 = TAU*V7
- V8 = V( 8 )
- T8 = TAU*V8
- V9 = V( 9 )
- T9 = TAU*V9
- V10 = V( 10 )
- T10 = TAU*V10
- DO 400 J = 1, M
- SUM = V1*C( J, 1 ) + V2*C( J, 2 ) + V3*C( J, 3 ) +
- $ V4*C( J, 4 ) + V5*C( J, 5 ) + V6*C( J, 6 ) +
- $ V7*C( J, 7 ) + V8*C( J, 8 ) + V9*C( J, 9 ) +
- $ V10*C( J, 10 )
- C( J, 1 ) = C( J, 1 ) - SUM*T1
- C( J, 2 ) = C( J, 2 ) - SUM*T2
- C( J, 3 ) = C( J, 3 ) - SUM*T3
- C( J, 4 ) = C( J, 4 ) - SUM*T4
- C( J, 5 ) = C( J, 5 ) - SUM*T5
- C( J, 6 ) = C( J, 6 ) - SUM*T6
- C( J, 7 ) = C( J, 7 ) - SUM*T7
- C( J, 8 ) = C( J, 8 ) - SUM*T8
- C( J, 9 ) = C( J, 9 ) - SUM*T9
- C( J, 10 ) = C( J, 10 ) - SUM*T10
- 400 CONTINUE
- GO TO 410
- END IF
- 410 CONTINUE
- RETURN
-*
-* End of DLARFX
-*
- END
diff --git a/src/lib/lapack/dlartg.f b/src/lib/lapack/dlartg.f
deleted file mode 100644
index eb807c1d..00000000
--- a/src/lib/lapack/dlartg.f
+++ /dev/null
@@ -1,145 +0,0 @@
- SUBROUTINE DLARTG( F, G, CS, SN, R )
-*
-* -- LAPACK auxiliary routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- DOUBLE PRECISION CS, F, G, R, SN
-* ..
-*
-* Purpose
-* =======
-*
-* DLARTG generate a plane rotation so that
-*
-* [ CS SN ] . [ F ] = [ R ] where CS**2 + SN**2 = 1.
-* [ -SN CS ] [ G ] [ 0 ]
-*
-* This is a slower, more accurate version of the BLAS1 routine DROTG,
-* with the following other differences:
-* F and G are unchanged on return.
-* If G=0, then CS=1 and SN=0.
-* If F=0 and (G .ne. 0), then CS=0 and SN=1 without doing any
-* floating point operations (saves work in DBDSQR when
-* there are zeros on the diagonal).
-*
-* If F exceeds G in magnitude, CS will be positive.
-*
-* Arguments
-* =========
-*
-* F (input) DOUBLE PRECISION
-* The first component of vector to be rotated.
-*
-* G (input) DOUBLE PRECISION
-* The second component of vector to be rotated.
-*
-* CS (output) DOUBLE PRECISION
-* The cosine of the rotation.
-*
-* SN (output) DOUBLE PRECISION
-* The sine of the rotation.
-*
-* R (output) DOUBLE PRECISION
-* The nonzero component of the rotated vector.
-*
-* This version has a few statements commented out for thread safety
-* (machine parameters are computed on each entry). 10 feb 03, SJH.
-*
-* =====================================================================
-*
-* .. Parameters ..
- DOUBLE PRECISION ZERO
- PARAMETER ( ZERO = 0.0D0 )
- DOUBLE PRECISION ONE
- PARAMETER ( ONE = 1.0D0 )
- DOUBLE PRECISION TWO
- PARAMETER ( TWO = 2.0D0 )
-* ..
-* .. Local Scalars ..
-* LOGICAL FIRST
- INTEGER COUNT, I
- DOUBLE PRECISION EPS, F1, G1, SAFMIN, SAFMN2, SAFMX2, SCALE
-* ..
-* .. External Functions ..
- DOUBLE PRECISION DLAMCH
- EXTERNAL DLAMCH
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC ABS, INT, LOG, MAX, SQRT
-* ..
-* .. Save statement ..
-* SAVE FIRST, SAFMX2, SAFMIN, SAFMN2
-* ..
-* .. Data statements ..
-* DATA FIRST / .TRUE. /
-* ..
-* .. Executable Statements ..
-*
-* IF( FIRST ) THEN
- SAFMIN = DLAMCH( 'S' )
- EPS = DLAMCH( 'E' )
- SAFMN2 = DLAMCH( 'B' )**INT( LOG( SAFMIN / EPS ) /
- $ LOG( DLAMCH( 'B' ) ) / TWO )
- SAFMX2 = ONE / SAFMN2
-* FIRST = .FALSE.
-* END IF
- IF( G.EQ.ZERO ) THEN
- CS = ONE
- SN = ZERO
- R = F
- ELSE IF( F.EQ.ZERO ) THEN
- CS = ZERO
- SN = ONE
- R = G
- ELSE
- F1 = F
- G1 = G
- SCALE = MAX( ABS( F1 ), ABS( G1 ) )
- IF( SCALE.GE.SAFMX2 ) THEN
- COUNT = 0
- 10 CONTINUE
- COUNT = COUNT + 1
- F1 = F1*SAFMN2
- G1 = G1*SAFMN2
- SCALE = MAX( ABS( F1 ), ABS( G1 ) )
- IF( SCALE.GE.SAFMX2 )
- $ GO TO 10
- R = SQRT( F1**2+G1**2 )
- CS = F1 / R
- SN = G1 / R
- DO 20 I = 1, COUNT
- R = R*SAFMX2
- 20 CONTINUE
- ELSE IF( SCALE.LE.SAFMN2 ) THEN
- COUNT = 0
- 30 CONTINUE
- COUNT = COUNT + 1
- F1 = F1*SAFMX2
- G1 = G1*SAFMX2
- SCALE = MAX( ABS( F1 ), ABS( G1 ) )
- IF( SCALE.LE.SAFMN2 )
- $ GO TO 30
- R = SQRT( F1**2+G1**2 )
- CS = F1 / R
- SN = G1 / R
- DO 40 I = 1, COUNT
- R = R*SAFMN2
- 40 CONTINUE
- ELSE
- R = SQRT( F1**2+G1**2 )
- CS = F1 / R
- SN = G1 / R
- END IF
- IF( ABS( F ).GT.ABS( G ) .AND. CS.LT.ZERO ) THEN
- CS = -CS
- SN = -SN
- R = -R
- END IF
- END IF
- RETURN
-*
-* End of DLARTG
-*
- END
diff --git a/src/lib/lapack/dlarz.f b/src/lib/lapack/dlarz.f
deleted file mode 100644
index b302fdc2..00000000
--- a/src/lib/lapack/dlarz.f
+++ /dev/null
@@ -1,152 +0,0 @@
- SUBROUTINE DLARZ( SIDE, M, N, L, V, INCV, TAU, C, LDC, WORK )
-*
-* -- LAPACK routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- CHARACTER SIDE
- INTEGER INCV, L, LDC, M, N
- DOUBLE PRECISION TAU
-* ..
-* .. Array Arguments ..
- DOUBLE PRECISION C( LDC, * ), V( * ), WORK( * )
-* ..
-*
-* Purpose
-* =======
-*
-* DLARZ applies a real elementary reflector H to a real M-by-N
-* matrix C, from either the left or the right. H is represented in the
-* form
-*
-* H = I - tau * v * v'
-*
-* where tau is a real scalar and v is a real vector.
-*
-* If tau = 0, then H is taken to be the unit matrix.
-*
-*
-* H is a product of k elementary reflectors as returned by DTZRZF.
-*
-* Arguments
-* =========
-*
-* SIDE (input) CHARACTER*1
-* = 'L': form H * C
-* = 'R': form C * H
-*
-* M (input) INTEGER
-* The number of rows of the matrix C.
-*
-* N (input) INTEGER
-* The number of columns of the matrix C.
-*
-* L (input) INTEGER
-* The number of entries of the vector V containing
-* the meaningful part of the Householder vectors.
-* If SIDE = 'L', M >= L >= 0, if SIDE = 'R', N >= L >= 0.
-*
-* V (input) DOUBLE PRECISION array, dimension (1+(L-1)*abs(INCV))
-* The vector v in the representation of H as returned by
-* DTZRZF. V is not used if TAU = 0.
-*
-* INCV (input) INTEGER
-* The increment between elements of v. INCV <> 0.
-*
-* TAU (input) DOUBLE PRECISION
-* The value tau in the representation of H.
-*
-* C (input/output) DOUBLE PRECISION array, dimension (LDC,N)
-* On entry, the M-by-N matrix C.
-* On exit, C is overwritten by the matrix H * C if SIDE = 'L',
-* or C * H if SIDE = 'R'.
-*
-* LDC (input) INTEGER
-* The leading dimension of the array C. LDC >= max(1,M).
-*
-* WORK (workspace) DOUBLE PRECISION array, dimension
-* (N) if SIDE = 'L'
-* or (M) if SIDE = 'R'
-*
-* Further Details
-* ===============
-*
-* Based on contributions by
-* A. Petitet, Computer Science Dept., Univ. of Tenn., Knoxville, USA
-*
-* =====================================================================
-*
-* .. Parameters ..
- DOUBLE PRECISION ONE, ZERO
- PARAMETER ( ONE = 1.0D+0, ZERO = 0.0D+0 )
-* ..
-* .. External Subroutines ..
- EXTERNAL DAXPY, DCOPY, DGEMV, DGER
-* ..
-* .. External Functions ..
- LOGICAL LSAME
- EXTERNAL LSAME
-* ..
-* .. Executable Statements ..
-*
- IF( LSAME( SIDE, 'L' ) ) THEN
-*
-* Form H * C
-*
- IF( TAU.NE.ZERO ) THEN
-*
-* w( 1:n ) = C( 1, 1:n )
-*
- CALL DCOPY( N, C, LDC, WORK, 1 )
-*
-* w( 1:n ) = w( 1:n ) + C( m-l+1:m, 1:n )' * v( 1:l )
-*
- CALL DGEMV( 'Transpose', L, N, ONE, C( M-L+1, 1 ), LDC, V,
- $ INCV, ONE, WORK, 1 )
-*
-* C( 1, 1:n ) = C( 1, 1:n ) - tau * w( 1:n )
-*
- CALL DAXPY( N, -TAU, WORK, 1, C, LDC )
-*
-* C( m-l+1:m, 1:n ) = C( m-l+1:m, 1:n ) - ...
-* tau * v( 1:l ) * w( 1:n )'
-*
- CALL DGER( L, N, -TAU, V, INCV, WORK, 1, C( M-L+1, 1 ),
- $ LDC )
- END IF
-*
- ELSE
-*
-* Form C * H
-*
- IF( TAU.NE.ZERO ) THEN
-*
-* w( 1:m ) = C( 1:m, 1 )
-*
- CALL DCOPY( M, C, 1, WORK, 1 )
-*
-* w( 1:m ) = w( 1:m ) + C( 1:m, n-l+1:n, 1:n ) * v( 1:l )
-*
- CALL DGEMV( 'No transpose', M, L, ONE, C( 1, N-L+1 ), LDC,
- $ V, INCV, ONE, WORK, 1 )
-*
-* C( 1:m, 1 ) = C( 1:m, 1 ) - tau * w( 1:m )
-*
- CALL DAXPY( M, -TAU, WORK, 1, C, 1 )
-*
-* C( 1:m, n-l+1:n ) = C( 1:m, n-l+1:n ) - ...
-* tau * w( 1:m ) * v( 1:l )'
-*
- CALL DGER( M, L, -TAU, WORK, 1, V, INCV, C( 1, N-L+1 ),
- $ LDC )
-*
- END IF
-*
- END IF
-*
- RETURN
-*
-* End of DLARZ
-*
- END
diff --git a/src/lib/lapack/dlarzb.f b/src/lib/lapack/dlarzb.f
deleted file mode 100644
index ec59d8d5..00000000
--- a/src/lib/lapack/dlarzb.f
+++ /dev/null
@@ -1,220 +0,0 @@
- SUBROUTINE DLARZB( SIDE, TRANS, DIRECT, STOREV, M, N, K, L, V,
- $ LDV, T, LDT, C, LDC, WORK, LDWORK )
-*
-* -- LAPACK routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- CHARACTER DIRECT, SIDE, STOREV, TRANS
- INTEGER K, L, LDC, LDT, LDV, LDWORK, M, N
-* ..
-* .. Array Arguments ..
- DOUBLE PRECISION C( LDC, * ), T( LDT, * ), V( LDV, * ),
- $ WORK( LDWORK, * )
-* ..
-*
-* Purpose
-* =======
-*
-* DLARZB applies a real block reflector H or its transpose H**T to
-* a real distributed M-by-N C from the left or the right.
-*
-* Currently, only STOREV = 'R' and DIRECT = 'B' are supported.
-*
-* Arguments
-* =========
-*
-* SIDE (input) CHARACTER*1
-* = 'L': apply H or H' from the Left
-* = 'R': apply H or H' from the Right
-*
-* TRANS (input) CHARACTER*1
-* = 'N': apply H (No transpose)
-* = 'C': apply H' (Transpose)
-*
-* DIRECT (input) CHARACTER*1
-* Indicates how H is formed from a product of elementary
-* reflectors
-* = 'F': H = H(1) H(2) . . . H(k) (Forward, not supported yet)
-* = 'B': H = H(k) . . . H(2) H(1) (Backward)
-*
-* STOREV (input) CHARACTER*1
-* Indicates how the vectors which define the elementary
-* reflectors are stored:
-* = 'C': Columnwise (not supported yet)
-* = 'R': Rowwise
-*
-* M (input) INTEGER
-* The number of rows of the matrix C.
-*
-* N (input) INTEGER
-* The number of columns of the matrix C.
-*
-* K (input) INTEGER
-* The order of the matrix T (= the number of elementary
-* reflectors whose product defines the block reflector).
-*
-* L (input) INTEGER
-* The number of columns of the matrix V containing the
-* meaningful part of the Householder reflectors.
-* If SIDE = 'L', M >= L >= 0, if SIDE = 'R', N >= L >= 0.
-*
-* V (input) DOUBLE PRECISION array, dimension (LDV,NV).
-* If STOREV = 'C', NV = K; if STOREV = 'R', NV = L.
-*
-* LDV (input) INTEGER
-* The leading dimension of the array V.
-* If STOREV = 'C', LDV >= L; if STOREV = 'R', LDV >= K.
-*
-* T (input) DOUBLE PRECISION array, dimension (LDT,K)
-* The triangular K-by-K matrix T in the representation of the
-* block reflector.
-*
-* LDT (input) INTEGER
-* The leading dimension of the array T. LDT >= K.
-*
-* C (input/output) DOUBLE PRECISION array, dimension (LDC,N)
-* On entry, the M-by-N matrix C.
-* On exit, C is overwritten by H*C or H'*C or C*H or C*H'.
-*
-* LDC (input) INTEGER
-* The leading dimension of the array C. LDC >= max(1,M).
-*
-* WORK (workspace) DOUBLE PRECISION array, dimension (LDWORK,K)
-*
-* LDWORK (input) INTEGER
-* The leading dimension of the array WORK.
-* If SIDE = 'L', LDWORK >= max(1,N);
-* if SIDE = 'R', LDWORK >= max(1,M).
-*
-* Further Details
-* ===============
-*
-* Based on contributions by
-* A. Petitet, Computer Science Dept., Univ. of Tenn., Knoxville, USA
-*
-* =====================================================================
-*
-* .. Parameters ..
- DOUBLE PRECISION ONE
- PARAMETER ( ONE = 1.0D+0 )
-* ..
-* .. Local Scalars ..
- CHARACTER TRANST
- INTEGER I, INFO, J
-* ..
-* .. External Functions ..
- LOGICAL LSAME
- EXTERNAL LSAME
-* ..
-* .. External Subroutines ..
- EXTERNAL DCOPY, DGEMM, DTRMM, XERBLA
-* ..
-* .. Executable Statements ..
-*
-* Quick return if possible
-*
- IF( M.LE.0 .OR. N.LE.0 )
- $ RETURN
-*
-* Check for currently supported options
-*
- INFO = 0
- IF( .NOT.LSAME( DIRECT, 'B' ) ) THEN
- INFO = -3
- ELSE IF( .NOT.LSAME( STOREV, 'R' ) ) THEN
- INFO = -4
- END IF
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'DLARZB', -INFO )
- RETURN
- END IF
-*
- IF( LSAME( TRANS, 'N' ) ) THEN
- TRANST = 'T'
- ELSE
- TRANST = 'N'
- END IF
-*
- IF( LSAME( SIDE, 'L' ) ) THEN
-*
-* Form H * C or H' * C
-*
-* W( 1:n, 1:k ) = C( 1:k, 1:n )'
-*
- DO 10 J = 1, K
- CALL DCOPY( N, C( J, 1 ), LDC, WORK( 1, J ), 1 )
- 10 CONTINUE
-*
-* W( 1:n, 1:k ) = W( 1:n, 1:k ) + ...
-* C( m-l+1:m, 1:n )' * V( 1:k, 1:l )'
-*
- IF( L.GT.0 )
- $ CALL DGEMM( 'Transpose', 'Transpose', N, K, L, ONE,
- $ C( M-L+1, 1 ), LDC, V, LDV, ONE, WORK, LDWORK )
-*
-* W( 1:n, 1:k ) = W( 1:n, 1:k ) * T' or W( 1:m, 1:k ) * T
-*
- CALL DTRMM( 'Right', 'Lower', TRANST, 'Non-unit', N, K, ONE, T,
- $ LDT, WORK, LDWORK )
-*
-* C( 1:k, 1:n ) = C( 1:k, 1:n ) - W( 1:n, 1:k )'
-*
- DO 30 J = 1, N
- DO 20 I = 1, K
- C( I, J ) = C( I, J ) - WORK( J, I )
- 20 CONTINUE
- 30 CONTINUE
-*
-* C( m-l+1:m, 1:n ) = C( m-l+1:m, 1:n ) - ...
-* V( 1:k, 1:l )' * W( 1:n, 1:k )'
-*
- IF( L.GT.0 )
- $ CALL DGEMM( 'Transpose', 'Transpose', L, N, K, -ONE, V, LDV,
- $ WORK, LDWORK, ONE, C( M-L+1, 1 ), LDC )
-*
- ELSE IF( LSAME( SIDE, 'R' ) ) THEN
-*
-* Form C * H or C * H'
-*
-* W( 1:m, 1:k ) = C( 1:m, 1:k )
-*
- DO 40 J = 1, K
- CALL DCOPY( M, C( 1, J ), 1, WORK( 1, J ), 1 )
- 40 CONTINUE
-*
-* W( 1:m, 1:k ) = W( 1:m, 1:k ) + ...
-* C( 1:m, n-l+1:n ) * V( 1:k, 1:l )'
-*
- IF( L.GT.0 )
- $ CALL DGEMM( 'No transpose', 'Transpose', M, K, L, ONE,
- $ C( 1, N-L+1 ), LDC, V, LDV, ONE, WORK, LDWORK )
-*
-* W( 1:m, 1:k ) = W( 1:m, 1:k ) * T or W( 1:m, 1:k ) * T'
-*
- CALL DTRMM( 'Right', 'Lower', TRANS, 'Non-unit', M, K, ONE, T,
- $ LDT, WORK, LDWORK )
-*
-* C( 1:m, 1:k ) = C( 1:m, 1:k ) - W( 1:m, 1:k )
-*
- DO 60 J = 1, K
- DO 50 I = 1, M
- C( I, J ) = C( I, J ) - WORK( I, J )
- 50 CONTINUE
- 60 CONTINUE
-*
-* C( 1:m, n-l+1:n ) = C( 1:m, n-l+1:n ) - ...
-* W( 1:m, 1:k ) * V( 1:k, 1:l )
-*
- IF( L.GT.0 )
- $ CALL DGEMM( 'No transpose', 'No transpose', M, L, K, -ONE,
- $ WORK, LDWORK, V, LDV, ONE, C( 1, N-L+1 ), LDC )
-*
- END IF
-*
- RETURN
-*
-* End of DLARZB
-*
- END
diff --git a/src/lib/lapack/dlarzt.f b/src/lib/lapack/dlarzt.f
deleted file mode 100644
index d79636e0..00000000
--- a/src/lib/lapack/dlarzt.f
+++ /dev/null
@@ -1,184 +0,0 @@
- SUBROUTINE DLARZT( DIRECT, STOREV, N, K, V, LDV, TAU, T, LDT )
-*
-* -- LAPACK routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- CHARACTER DIRECT, STOREV
- INTEGER K, LDT, LDV, N
-* ..
-* .. Array Arguments ..
- DOUBLE PRECISION T( LDT, * ), TAU( * ), V( LDV, * )
-* ..
-*
-* Purpose
-* =======
-*
-* DLARZT forms the triangular factor T of a real block reflector
-* H of order > n, which is defined as a product of k elementary
-* reflectors.
-*
-* If DIRECT = 'F', H = H(1) H(2) . . . H(k) and T is upper triangular;
-*
-* If DIRECT = 'B', H = H(k) . . . H(2) H(1) and T is lower triangular.
-*
-* If STOREV = 'C', the vector which defines the elementary reflector
-* H(i) is stored in the i-th column of the array V, and
-*
-* H = I - V * T * V'
-*
-* If STOREV = 'R', the vector which defines the elementary reflector
-* H(i) is stored in the i-th row of the array V, and
-*
-* H = I - V' * T * V
-*
-* Currently, only STOREV = 'R' and DIRECT = 'B' are supported.
-*
-* Arguments
-* =========
-*
-* DIRECT (input) CHARACTER*1
-* Specifies the order in which the elementary reflectors are
-* multiplied to form the block reflector:
-* = 'F': H = H(1) H(2) . . . H(k) (Forward, not supported yet)
-* = 'B': H = H(k) . . . H(2) H(1) (Backward)
-*
-* STOREV (input) CHARACTER*1
-* Specifies how the vectors which define the elementary
-* reflectors are stored (see also Further Details):
-* = 'C': columnwise (not supported yet)
-* = 'R': rowwise
-*
-* N (input) INTEGER
-* The order of the block reflector H. N >= 0.
-*
-* K (input) INTEGER
-* The order of the triangular factor T (= the number of
-* elementary reflectors). K >= 1.
-*
-* V (input/output) DOUBLE PRECISION array, dimension
-* (LDV,K) if STOREV = 'C'
-* (LDV,N) if STOREV = 'R'
-* The matrix V. See further details.
-*
-* LDV (input) INTEGER
-* The leading dimension of the array V.
-* If STOREV = 'C', LDV >= max(1,N); if STOREV = 'R', LDV >= K.
-*
-* TAU (input) DOUBLE PRECISION array, dimension (K)
-* TAU(i) must contain the scalar factor of the elementary
-* reflector H(i).
-*
-* T (output) DOUBLE PRECISION array, dimension (LDT,K)
-* The k by k triangular factor T of the block reflector.
-* If DIRECT = 'F', T is upper triangular; if DIRECT = 'B', T is
-* lower triangular. The rest of the array is not used.
-*
-* LDT (input) INTEGER
-* The leading dimension of the array T. LDT >= K.
-*
-* Further Details
-* ===============
-*
-* Based on contributions by
-* A. Petitet, Computer Science Dept., Univ. of Tenn., Knoxville, USA
-*
-* The shape of the matrix V and the storage of the vectors which define
-* the H(i) is best illustrated by the following example with n = 5 and
-* k = 3. The elements equal to 1 are not stored; the corresponding
-* array elements are modified but restored on exit. The rest of the
-* array is not used.
-*
-* DIRECT = 'F' and STOREV = 'C': DIRECT = 'F' and STOREV = 'R':
-*
-* ______V_____
-* ( v1 v2 v3 ) / \
-* ( v1 v2 v3 ) ( v1 v1 v1 v1 v1 . . . . 1 )
-* V = ( v1 v2 v3 ) ( v2 v2 v2 v2 v2 . . . 1 )
-* ( v1 v2 v3 ) ( v3 v3 v3 v3 v3 . . 1 )
-* ( v1 v2 v3 )
-* . . .
-* . . .
-* 1 . .
-* 1 .
-* 1
-*
-* DIRECT = 'B' and STOREV = 'C': DIRECT = 'B' and STOREV = 'R':
-*
-* ______V_____
-* 1 / \
-* . 1 ( 1 . . . . v1 v1 v1 v1 v1 )
-* . . 1 ( . 1 . . . v2 v2 v2 v2 v2 )
-* . . . ( . . 1 . . v3 v3 v3 v3 v3 )
-* . . .
-* ( v1 v2 v3 )
-* ( v1 v2 v3 )
-* V = ( v1 v2 v3 )
-* ( v1 v2 v3 )
-* ( v1 v2 v3 )
-*
-* =====================================================================
-*
-* .. Parameters ..
- DOUBLE PRECISION ZERO
- PARAMETER ( ZERO = 0.0D+0 )
-* ..
-* .. Local Scalars ..
- INTEGER I, INFO, J
-* ..
-* .. External Subroutines ..
- EXTERNAL DGEMV, DTRMV, XERBLA
-* ..
-* .. External Functions ..
- LOGICAL LSAME
- EXTERNAL LSAME
-* ..
-* .. Executable Statements ..
-*
-* Check for currently supported options
-*
- INFO = 0
- IF( .NOT.LSAME( DIRECT, 'B' ) ) THEN
- INFO = -1
- ELSE IF( .NOT.LSAME( STOREV, 'R' ) ) THEN
- INFO = -2
- END IF
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'DLARZT', -INFO )
- RETURN
- END IF
-*
- DO 20 I = K, 1, -1
- IF( TAU( I ).EQ.ZERO ) THEN
-*
-* H(i) = I
-*
- DO 10 J = I, K
- T( J, I ) = ZERO
- 10 CONTINUE
- ELSE
-*
-* general case
-*
- IF( I.LT.K ) THEN
-*
-* T(i+1:k,i) = - tau(i) * V(i+1:k,1:n) * V(i,1:n)'
-*
- CALL DGEMV( 'No transpose', K-I, N, -TAU( I ),
- $ V( I+1, 1 ), LDV, V( I, 1 ), LDV, ZERO,
- $ T( I+1, I ), 1 )
-*
-* T(i+1:k,i) = T(i+1:k,i+1:k) * T(i+1:k,i)
-*
- CALL DTRMV( 'Lower', 'No transpose', 'Non-unit', K-I,
- $ T( I+1, I+1 ), LDT, T( I+1, I ), 1 )
- END IF
- T( I, I ) = TAU( I )
- END IF
- 20 CONTINUE
- RETURN
-*
-* End of DLARZT
-*
- END
diff --git a/src/lib/lapack/dlas2.f b/src/lib/lapack/dlas2.f
deleted file mode 100644
index e100a4d8..00000000
--- a/src/lib/lapack/dlas2.f
+++ /dev/null
@@ -1,121 +0,0 @@
- SUBROUTINE DLAS2( F, G, H, SSMIN, SSMAX )
-*
-* -- LAPACK auxiliary routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- DOUBLE PRECISION F, G, H, SSMAX, SSMIN
-* ..
-*
-* Purpose
-* =======
-*
-* DLAS2 computes the singular values of the 2-by-2 matrix
-* [ F G ]
-* [ 0 H ].
-* On return, SSMIN is the smaller singular value and SSMAX is the
-* larger singular value.
-*
-* Arguments
-* =========
-*
-* F (input) DOUBLE PRECISION
-* The (1,1) element of the 2-by-2 matrix.
-*
-* G (input) DOUBLE PRECISION
-* The (1,2) element of the 2-by-2 matrix.
-*
-* H (input) DOUBLE PRECISION
-* The (2,2) element of the 2-by-2 matrix.
-*
-* SSMIN (output) DOUBLE PRECISION
-* The smaller singular value.
-*
-* SSMAX (output) DOUBLE PRECISION
-* The larger singular value.
-*
-* Further Details
-* ===============
-*
-* Barring over/underflow, all output quantities are correct to within
-* a few units in the last place (ulps), even in the absence of a guard
-* digit in addition/subtraction.
-*
-* In IEEE arithmetic, the code works correctly if one matrix element is
-* infinite.
-*
-* Overflow will not occur unless the largest singular value itself
-* overflows, or is within a few ulps of overflow. (On machines with
-* partial overflow, like the Cray, overflow may occur if the largest
-* singular value is within a factor of 2 of overflow.)
-*
-* Underflow is harmless if underflow is gradual. Otherwise, results
-* may correspond to a matrix modified by perturbations of size near
-* the underflow threshold.
-*
-* ====================================================================
-*
-* .. Parameters ..
- DOUBLE PRECISION ZERO
- PARAMETER ( ZERO = 0.0D0 )
- DOUBLE PRECISION ONE
- PARAMETER ( ONE = 1.0D0 )
- DOUBLE PRECISION TWO
- PARAMETER ( TWO = 2.0D0 )
-* ..
-* .. Local Scalars ..
- DOUBLE PRECISION AS, AT, AU, C, FA, FHMN, FHMX, GA, HA
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC ABS, MAX, MIN, SQRT
-* ..
-* .. Executable Statements ..
-*
- FA = ABS( F )
- GA = ABS( G )
- HA = ABS( H )
- FHMN = MIN( FA, HA )
- FHMX = MAX( FA, HA )
- IF( FHMN.EQ.ZERO ) THEN
- SSMIN = ZERO
- IF( FHMX.EQ.ZERO ) THEN
- SSMAX = GA
- ELSE
- SSMAX = MAX( FHMX, GA )*SQRT( ONE+
- $ ( MIN( FHMX, GA ) / MAX( FHMX, GA ) )**2 )
- END IF
- ELSE
- IF( GA.LT.FHMX ) THEN
- AS = ONE + FHMN / FHMX
- AT = ( FHMX-FHMN ) / FHMX
- AU = ( GA / FHMX )**2
- C = TWO / ( SQRT( AS*AS+AU )+SQRT( AT*AT+AU ) )
- SSMIN = FHMN*C
- SSMAX = FHMX / C
- ELSE
- AU = FHMX / GA
- IF( AU.EQ.ZERO ) THEN
-*
-* Avoid possible harmful underflow if exponent range
-* asymmetric (true SSMIN may not underflow even if
-* AU underflows)
-*
- SSMIN = ( FHMN*FHMX ) / GA
- SSMAX = GA
- ELSE
- AS = ONE + FHMN / FHMX
- AT = ( FHMX-FHMN ) / FHMX
- C = ONE / ( SQRT( ONE+( AS*AU )**2 )+
- $ SQRT( ONE+( AT*AU )**2 ) )
- SSMIN = ( FHMN*C )*AU
- SSMIN = SSMIN + SSMIN
- SSMAX = GA / ( C+C )
- END IF
- END IF
- END IF
- RETURN
-*
-* End of DLAS2
-*
- END
diff --git a/src/lib/lapack/dlascl.f b/src/lib/lapack/dlascl.f
deleted file mode 100644
index 7a7a78fd..00000000
--- a/src/lib/lapack/dlascl.f
+++ /dev/null
@@ -1,267 +0,0 @@
- SUBROUTINE DLASCL( TYPE, KL, KU, CFROM, CTO, M, N, A, LDA, INFO )
-*
-* -- LAPACK auxiliary routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- CHARACTER TYPE
- INTEGER INFO, KL, KU, LDA, M, N
- DOUBLE PRECISION CFROM, CTO
-* ..
-* .. Array Arguments ..
- DOUBLE PRECISION A( LDA, * )
-* ..
-*
-* Purpose
-* =======
-*
-* DLASCL multiplies the M by N real matrix A by the real scalar
-* CTO/CFROM. This is done without over/underflow as long as the final
-* result CTO*A(I,J)/CFROM does not over/underflow. TYPE specifies that
-* A may be full, upper triangular, lower triangular, upper Hessenberg,
-* or banded.
-*
-* Arguments
-* =========
-*
-* TYPE (input) CHARACTER*1
-* TYPE indices the storage type of the input matrix.
-* = 'G': A is a full matrix.
-* = 'L': A is a lower triangular matrix.
-* = 'U': A is an upper triangular matrix.
-* = 'H': A is an upper Hessenberg matrix.
-* = 'B': A is a symmetric band matrix with lower bandwidth KL
-* and upper bandwidth KU and with the only the lower
-* half stored.
-* = 'Q': A is a symmetric band matrix with lower bandwidth KL
-* and upper bandwidth KU and with the only the upper
-* half stored.
-* = 'Z': A is a band matrix with lower bandwidth KL and upper
-* bandwidth KU.
-*
-* KL (input) INTEGER
-* The lower bandwidth of A. Referenced only if TYPE = 'B',
-* 'Q' or 'Z'.
-*
-* KU (input) INTEGER
-* The upper bandwidth of A. Referenced only if TYPE = 'B',
-* 'Q' or 'Z'.
-*
-* CFROM (input) DOUBLE PRECISION
-* CTO (input) DOUBLE PRECISION
-* The matrix A is multiplied by CTO/CFROM. A(I,J) is computed
-* without over/underflow if the final result CTO*A(I,J)/CFROM
-* can be represented without over/underflow. CFROM must be
-* nonzero.
-*
-* M (input) INTEGER
-* The number of rows of the matrix A. M >= 0.
-*
-* N (input) INTEGER
-* The number of columns of the matrix A. N >= 0.
-*
-* A (input/output) DOUBLE PRECISION array, dimension (LDA,N)
-* The matrix to be multiplied by CTO/CFROM. See TYPE for the
-* storage type.
-*
-* LDA (input) INTEGER
-* The leading dimension of the array A. LDA >= max(1,M).
-*
-* INFO (output) INTEGER
-* 0 - successful exit
-* <0 - if INFO = -i, the i-th argument had an illegal value.
-*
-* =====================================================================
-*
-* .. Parameters ..
- DOUBLE PRECISION ZERO, ONE
- PARAMETER ( ZERO = 0.0D0, ONE = 1.0D0 )
-* ..
-* .. Local Scalars ..
- LOGICAL DONE
- INTEGER I, ITYPE, J, K1, K2, K3, K4
- DOUBLE PRECISION BIGNUM, CFROM1, CFROMC, CTO1, CTOC, MUL, SMLNUM
-* ..
-* .. External Functions ..
- LOGICAL LSAME
- DOUBLE PRECISION DLAMCH
- EXTERNAL LSAME, DLAMCH
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC ABS, MAX, MIN
-* ..
-* .. External Subroutines ..
- EXTERNAL XERBLA
-* ..
-* .. Executable Statements ..
-*
-* Test the input arguments
-*
- INFO = 0
-*
- IF( LSAME( TYPE, 'G' ) ) THEN
- ITYPE = 0
- ELSE IF( LSAME( TYPE, 'L' ) ) THEN
- ITYPE = 1
- ELSE IF( LSAME( TYPE, 'U' ) ) THEN
- ITYPE = 2
- ELSE IF( LSAME( TYPE, 'H' ) ) THEN
- ITYPE = 3
- ELSE IF( LSAME( TYPE, 'B' ) ) THEN
- ITYPE = 4
- ELSE IF( LSAME( TYPE, 'Q' ) ) THEN
- ITYPE = 5
- ELSE IF( LSAME( TYPE, 'Z' ) ) THEN
- ITYPE = 6
- ELSE
- ITYPE = -1
- END IF
-*
- IF( ITYPE.EQ.-1 ) THEN
- INFO = -1
- ELSE IF( CFROM.EQ.ZERO ) THEN
- INFO = -4
- ELSE IF( M.LT.0 ) THEN
- INFO = -6
- ELSE IF( N.LT.0 .OR. ( ITYPE.EQ.4 .AND. N.NE.M ) .OR.
- $ ( ITYPE.EQ.5 .AND. N.NE.M ) ) THEN
- INFO = -7
- ELSE IF( ITYPE.LE.3 .AND. LDA.LT.MAX( 1, M ) ) THEN
- INFO = -9
- ELSE IF( ITYPE.GE.4 ) THEN
- IF( KL.LT.0 .OR. KL.GT.MAX( M-1, 0 ) ) THEN
- INFO = -2
- ELSE IF( KU.LT.0 .OR. KU.GT.MAX( N-1, 0 ) .OR.
- $ ( ( ITYPE.EQ.4 .OR. ITYPE.EQ.5 ) .AND. KL.NE.KU ) )
- $ THEN
- INFO = -3
- ELSE IF( ( ITYPE.EQ.4 .AND. LDA.LT.KL+1 ) .OR.
- $ ( ITYPE.EQ.5 .AND. LDA.LT.KU+1 ) .OR.
- $ ( ITYPE.EQ.6 .AND. LDA.LT.2*KL+KU+1 ) ) THEN
- INFO = -9
- END IF
- END IF
-*
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'DLASCL', -INFO )
- RETURN
- END IF
-*
-* Quick return if possible
-*
- IF( N.EQ.0 .OR. M.EQ.0 )
- $ RETURN
-*
-* Get machine parameters
-*
- SMLNUM = DLAMCH( 'S' )
- BIGNUM = ONE / SMLNUM
-*
- CFROMC = CFROM
- CTOC = CTO
-*
- 10 CONTINUE
- CFROM1 = CFROMC*SMLNUM
- CTO1 = CTOC / BIGNUM
- IF( ABS( CFROM1 ).GT.ABS( CTOC ) .AND. CTOC.NE.ZERO ) THEN
- MUL = SMLNUM
- DONE = .FALSE.
- CFROMC = CFROM1
- ELSE IF( ABS( CTO1 ).GT.ABS( CFROMC ) ) THEN
- MUL = BIGNUM
- DONE = .FALSE.
- CTOC = CTO1
- ELSE
- MUL = CTOC / CFROMC
- DONE = .TRUE.
- END IF
-*
- IF( ITYPE.EQ.0 ) THEN
-*
-* Full matrix
-*
- DO 30 J = 1, N
- DO 20 I = 1, M
- A( I, J ) = A( I, J )*MUL
- 20 CONTINUE
- 30 CONTINUE
-*
- ELSE IF( ITYPE.EQ.1 ) THEN
-*
-* Lower triangular matrix
-*
- DO 50 J = 1, N
- DO 40 I = J, M
- A( I, J ) = A( I, J )*MUL
- 40 CONTINUE
- 50 CONTINUE
-*
- ELSE IF( ITYPE.EQ.2 ) THEN
-*
-* Upper triangular matrix
-*
- DO 70 J = 1, N
- DO 60 I = 1, MIN( J, M )
- A( I, J ) = A( I, J )*MUL
- 60 CONTINUE
- 70 CONTINUE
-*
- ELSE IF( ITYPE.EQ.3 ) THEN
-*
-* Upper Hessenberg matrix
-*
- DO 90 J = 1, N
- DO 80 I = 1, MIN( J+1, M )
- A( I, J ) = A( I, J )*MUL
- 80 CONTINUE
- 90 CONTINUE
-*
- ELSE IF( ITYPE.EQ.4 ) THEN
-*
-* Lower half of a symmetric band matrix
-*
- K3 = KL + 1
- K4 = N + 1
- DO 110 J = 1, N
- DO 100 I = 1, MIN( K3, K4-J )
- A( I, J ) = A( I, J )*MUL
- 100 CONTINUE
- 110 CONTINUE
-*
- ELSE IF( ITYPE.EQ.5 ) THEN
-*
-* Upper half of a symmetric band matrix
-*
- K1 = KU + 2
- K3 = KU + 1
- DO 130 J = 1, N
- DO 120 I = MAX( K1-J, 1 ), K3
- A( I, J ) = A( I, J )*MUL
- 120 CONTINUE
- 130 CONTINUE
-*
- ELSE IF( ITYPE.EQ.6 ) THEN
-*
-* Band matrix
-*
- K1 = KL + KU + 2
- K2 = KL + 1
- K3 = 2*KL + KU + 1
- K4 = KL + KU + 1 + M
- DO 150 J = 1, N
- DO 140 I = MAX( K1-J, K2 ), MIN( K3, K4-J )
- A( I, J ) = A( I, J )*MUL
- 140 CONTINUE
- 150 CONTINUE
-*
- END IF
-*
- IF( .NOT.DONE )
- $ GO TO 10
-*
- RETURN
-*
-* End of DLASCL
-*
- END
diff --git a/src/lib/lapack/dlaset.f b/src/lib/lapack/dlaset.f
deleted file mode 100644
index fc7bc2f5..00000000
--- a/src/lib/lapack/dlaset.f
+++ /dev/null
@@ -1,114 +0,0 @@
- SUBROUTINE DLASET( UPLO, M, N, ALPHA, BETA, A, LDA )
-*
-* -- LAPACK auxiliary routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- CHARACTER UPLO
- INTEGER LDA, M, N
- DOUBLE PRECISION ALPHA, BETA
-* ..
-* .. Array Arguments ..
- DOUBLE PRECISION A( LDA, * )
-* ..
-*
-* Purpose
-* =======
-*
-* DLASET initializes an m-by-n matrix A to BETA on the diagonal and
-* ALPHA on the offdiagonals.
-*
-* Arguments
-* =========
-*
-* UPLO (input) CHARACTER*1
-* Specifies the part of the matrix A to be set.
-* = 'U': Upper triangular part is set; the strictly lower
-* triangular part of A is not changed.
-* = 'L': Lower triangular part is set; the strictly upper
-* triangular part of A is not changed.
-* Otherwise: All of the matrix A is set.
-*
-* M (input) INTEGER
-* The number of rows of the matrix A. M >= 0.
-*
-* N (input) INTEGER
-* The number of columns of the matrix A. N >= 0.
-*
-* ALPHA (input) DOUBLE PRECISION
-* The constant to which the offdiagonal elements are to be set.
-*
-* BETA (input) DOUBLE PRECISION
-* The constant to which the diagonal elements are to be set.
-*
-* A (input/output) DOUBLE PRECISION array, dimension (LDA,N)
-* On exit, the leading m-by-n submatrix of A is set as follows:
-*
-* if UPLO = 'U', A(i,j) = ALPHA, 1<=i<=j-1, 1<=j<=n,
-* if UPLO = 'L', A(i,j) = ALPHA, j+1<=i<=m, 1<=j<=n,
-* otherwise, A(i,j) = ALPHA, 1<=i<=m, 1<=j<=n, i.ne.j,
-*
-* and, for all UPLO, A(i,i) = BETA, 1<=i<=min(m,n).
-*
-* LDA (input) INTEGER
-* The leading dimension of the array A. LDA >= max(1,M).
-*
-* =====================================================================
-*
-* .. Local Scalars ..
- INTEGER I, J
-* ..
-* .. External Functions ..
- LOGICAL LSAME
- EXTERNAL LSAME
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC MIN
-* ..
-* .. Executable Statements ..
-*
- IF( LSAME( UPLO, 'U' ) ) THEN
-*
-* Set the strictly upper triangular or trapezoidal part of the
-* array to ALPHA.
-*
- DO 20 J = 2, N
- DO 10 I = 1, MIN( J-1, M )
- A( I, J ) = ALPHA
- 10 CONTINUE
- 20 CONTINUE
-*
- ELSE IF( LSAME( UPLO, 'L' ) ) THEN
-*
-* Set the strictly lower triangular or trapezoidal part of the
-* array to ALPHA.
-*
- DO 40 J = 1, MIN( M, N )
- DO 30 I = J + 1, M
- A( I, J ) = ALPHA
- 30 CONTINUE
- 40 CONTINUE
-*
- ELSE
-*
-* Set the leading m-by-n submatrix to ALPHA.
-*
- DO 60 J = 1, N
- DO 50 I = 1, M
- A( I, J ) = ALPHA
- 50 CONTINUE
- 60 CONTINUE
- END IF
-*
-* Set the first min(M,N) diagonal elements to BETA.
-*
- DO 70 I = 1, MIN( M, N )
- A( I, I ) = BETA
- 70 CONTINUE
-*
- RETURN
-*
-* End of DLASET
-*
- END
diff --git a/src/lib/lapack/dlasq1.f b/src/lib/lapack/dlasq1.f
deleted file mode 100644
index 6f4c3413..00000000
--- a/src/lib/lapack/dlasq1.f
+++ /dev/null
@@ -1,148 +0,0 @@
- SUBROUTINE DLASQ1( N, D, E, WORK, INFO )
-*
-* -- LAPACK routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- INTEGER INFO, N
-* ..
-* .. Array Arguments ..
- DOUBLE PRECISION D( * ), E( * ), WORK( * )
-* ..
-*
-* Purpose
-* =======
-*
-* DLASQ1 computes the singular values of a real N-by-N bidiagonal
-* matrix with diagonal D and off-diagonal E. The singular values
-* are computed to high relative accuracy, in the absence of
-* denormalization, underflow and overflow. The algorithm was first
-* presented in
-*
-* "Accurate singular values and differential qd algorithms" by K. V.
-* Fernando and B. N. Parlett, Numer. Math., Vol-67, No. 2, pp. 191-230,
-* 1994,
-*
-* and the present implementation is described in "An implementation of
-* the dqds Algorithm (Positive Case)", LAPACK Working Note.
-*
-* Arguments
-* =========
-*
-* N (input) INTEGER
-* The number of rows and columns in the matrix. N >= 0.
-*
-* D (input/output) DOUBLE PRECISION array, dimension (N)
-* On entry, D contains the diagonal elements of the
-* bidiagonal matrix whose SVD is desired. On normal exit,
-* D contains the singular values in decreasing order.
-*
-* E (input/output) DOUBLE PRECISION array, dimension (N)
-* On entry, elements E(1:N-1) contain the off-diagonal elements
-* of the bidiagonal matrix whose SVD is desired.
-* On exit, E is overwritten.
-*
-* WORK (workspace) DOUBLE PRECISION array, dimension (4*N)
-*
-* INFO (output) INTEGER
-* = 0: successful exit
-* < 0: if INFO = -i, the i-th argument had an illegal value
-* > 0: the algorithm failed
-* = 1, a split was marked by a positive value in E
-* = 2, current block of Z not diagonalized after 30*N
-* iterations (in inner while loop)
-* = 3, termination criterion of outer while loop not met
-* (program created more than N unreduced blocks)
-*
-* =====================================================================
-*
-* .. Parameters ..
- DOUBLE PRECISION ZERO
- PARAMETER ( ZERO = 0.0D0 )
-* ..
-* .. Local Scalars ..
- INTEGER I, IINFO
- DOUBLE PRECISION EPS, SCALE, SAFMIN, SIGMN, SIGMX
-* ..
-* .. External Subroutines ..
- EXTERNAL DCOPY, DLAS2, DLASCL, DLASQ2, DLASRT, XERBLA
-* ..
-* .. External Functions ..
- DOUBLE PRECISION DLAMCH
- EXTERNAL DLAMCH
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC ABS, MAX, SQRT
-* ..
-* .. Executable Statements ..
-*
- INFO = 0
- IF( N.LT.0 ) THEN
- INFO = -2
- CALL XERBLA( 'DLASQ1', -INFO )
- RETURN
- ELSE IF( N.EQ.0 ) THEN
- RETURN
- ELSE IF( N.EQ.1 ) THEN
- D( 1 ) = ABS( D( 1 ) )
- RETURN
- ELSE IF( N.EQ.2 ) THEN
- CALL DLAS2( D( 1 ), E( 1 ), D( 2 ), SIGMN, SIGMX )
- D( 1 ) = SIGMX
- D( 2 ) = SIGMN
- RETURN
- END IF
-*
-* Estimate the largest singular value.
-*
- SIGMX = ZERO
- DO 10 I = 1, N - 1
- D( I ) = ABS( D( I ) )
- SIGMX = MAX( SIGMX, ABS( E( I ) ) )
- 10 CONTINUE
- D( N ) = ABS( D( N ) )
-*
-* Early return if SIGMX is zero (matrix is already diagonal).
-*
- IF( SIGMX.EQ.ZERO ) THEN
- CALL DLASRT( 'D', N, D, IINFO )
- RETURN
- END IF
-*
- DO 20 I = 1, N
- SIGMX = MAX( SIGMX, D( I ) )
- 20 CONTINUE
-*
-* Copy D and E into WORK (in the Z format) and scale (squaring the
-* input data makes scaling by a power of the radix pointless).
-*
- EPS = DLAMCH( 'Precision' )
- SAFMIN = DLAMCH( 'Safe minimum' )
- SCALE = SQRT( EPS / SAFMIN )
- CALL DCOPY( N, D, 1, WORK( 1 ), 2 )
- CALL DCOPY( N-1, E, 1, WORK( 2 ), 2 )
- CALL DLASCL( 'G', 0, 0, SIGMX, SCALE, 2*N-1, 1, WORK, 2*N-1,
- $ IINFO )
-*
-* Compute the q's and e's.
-*
- DO 30 I = 1, 2*N - 1
- WORK( I ) = WORK( I )**2
- 30 CONTINUE
- WORK( 2*N ) = ZERO
-*
- CALL DLASQ2( N, WORK, INFO )
-*
- IF( INFO.EQ.0 ) THEN
- DO 40 I = 1, N
- D( I ) = SQRT( WORK( I ) )
- 40 CONTINUE
- CALL DLASCL( 'G', 0, 0, SCALE, SIGMX, N, 1, D, N, IINFO )
- END IF
-*
- RETURN
-*
-* End of DLASQ1
-*
- END
diff --git a/src/lib/lapack/dlasq2.f b/src/lib/lapack/dlasq2.f
deleted file mode 100644
index b6b79aeb..00000000
--- a/src/lib/lapack/dlasq2.f
+++ /dev/null
@@ -1,448 +0,0 @@
- SUBROUTINE DLASQ2( N, Z, INFO )
-*
-* -- LAPACK routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* Modified to call DLAZQ3 in place of DLASQ3, 13 Feb 03, SJH.
-*
-* .. Scalar Arguments ..
- INTEGER INFO, N
-* ..
-* .. Array Arguments ..
- DOUBLE PRECISION Z( * )
-* ..
-*
-* Purpose
-* =======
-*
-* DLASQ2 computes all the eigenvalues of the symmetric positive
-* definite tridiagonal matrix associated with the qd array Z to high
-* relative accuracy are computed to high relative accuracy, in the
-* absence of denormalization, underflow and overflow.
-*
-* To see the relation of Z to the tridiagonal matrix, let L be a
-* unit lower bidiagonal matrix with subdiagonals Z(2,4,6,,..) and
-* let U be an upper bidiagonal matrix with 1's above and diagonal
-* Z(1,3,5,,..). The tridiagonal is L*U or, if you prefer, the
-* symmetric tridiagonal to which it is similar.
-*
-* Note : DLASQ2 defines a logical variable, IEEE, which is true
-* on machines which follow ieee-754 floating-point standard in their
-* handling of infinities and NaNs, and false otherwise. This variable
-* is passed to DLAZQ3.
-*
-* Arguments
-* =========
-*
-* N (input) INTEGER
-* The number of rows and columns in the matrix. N >= 0.
-*
-* Z (workspace) DOUBLE PRECISION array, dimension ( 4*N )
-* On entry Z holds the qd array. On exit, entries 1 to N hold
-* the eigenvalues in decreasing order, Z( 2*N+1 ) holds the
-* trace, and Z( 2*N+2 ) holds the sum of the eigenvalues. If
-* N > 2, then Z( 2*N+3 ) holds the iteration count, Z( 2*N+4 )
-* holds NDIVS/NIN^2, and Z( 2*N+5 ) holds the percentage of
-* shifts that failed.
-*
-* INFO (output) INTEGER
-* = 0: successful exit
-* < 0: if the i-th argument is a scalar and had an illegal
-* value, then INFO = -i, if the i-th argument is an
-* array and the j-entry had an illegal value, then
-* INFO = -(i*100+j)
-* > 0: the algorithm failed
-* = 1, a split was marked by a positive value in E
-* = 2, current block of Z not diagonalized after 30*N
-* iterations (in inner while loop)
-* = 3, termination criterion of outer while loop not met
-* (program created more than N unreduced blocks)
-*
-* Further Details
-* ===============
-* Local Variables: I0:N0 defines a current unreduced segment of Z.
-* The shifts are accumulated in SIGMA. Iteration count is in ITER.
-* Ping-pong is controlled by PP (alternates between 0 and 1).
-*
-* =====================================================================
-*
-* .. Parameters ..
- DOUBLE PRECISION CBIAS
- PARAMETER ( CBIAS = 1.50D0 )
- DOUBLE PRECISION ZERO, HALF, ONE, TWO, FOUR, HUNDRD
- PARAMETER ( ZERO = 0.0D0, HALF = 0.5D0, ONE = 1.0D0,
- $ TWO = 2.0D0, FOUR = 4.0D0, HUNDRD = 100.0D0 )
-* ..
-* .. Local Scalars ..
- LOGICAL IEEE
- INTEGER I0, I4, IINFO, IPN4, ITER, IWHILA, IWHILB, K,
- $ N0, NBIG, NDIV, NFAIL, PP, SPLT, TTYPE
- DOUBLE PRECISION D, DESIG, DMIN, DMIN1, DMIN2, DN, DN1, DN2, E,
- $ EMAX, EMIN, EPS, OLDEMN, QMAX, QMIN, S, SAFMIN,
- $ SIGMA, T, TAU, TEMP, TOL, TOL2, TRACE, ZMAX
-* ..
-* .. External Subroutines ..
- EXTERNAL DLAZQ3, DLASRT, XERBLA
-* ..
-* .. External Functions ..
- INTEGER ILAENV
- DOUBLE PRECISION DLAMCH
- EXTERNAL DLAMCH, ILAENV
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC ABS, DBLE, MAX, MIN, SQRT
-* ..
-* .. Executable Statements ..
-*
-* Test the input arguments.
-* (in case DLASQ2 is not called by DLASQ1)
-*
- INFO = 0
- EPS = DLAMCH( 'Precision' )
- SAFMIN = DLAMCH( 'Safe minimum' )
- TOL = EPS*HUNDRD
- TOL2 = TOL**2
-*
- IF( N.LT.0 ) THEN
- INFO = -1
- CALL XERBLA( 'DLASQ2', 1 )
- RETURN
- ELSE IF( N.EQ.0 ) THEN
- RETURN
- ELSE IF( N.EQ.1 ) THEN
-*
-* 1-by-1 case.
-*
- IF( Z( 1 ).LT.ZERO ) THEN
- INFO = -201
- CALL XERBLA( 'DLASQ2', 2 )
- END IF
- RETURN
- ELSE IF( N.EQ.2 ) THEN
-*
-* 2-by-2 case.
-*
- IF( Z( 2 ).LT.ZERO .OR. Z( 3 ).LT.ZERO ) THEN
- INFO = -2
- CALL XERBLA( 'DLASQ2', 2 )
- RETURN
- ELSE IF( Z( 3 ).GT.Z( 1 ) ) THEN
- D = Z( 3 )
- Z( 3 ) = Z( 1 )
- Z( 1 ) = D
- END IF
- Z( 5 ) = Z( 1 ) + Z( 2 ) + Z( 3 )
- IF( Z( 2 ).GT.Z( 3 )*TOL2 ) THEN
- T = HALF*( ( Z( 1 )-Z( 3 ) )+Z( 2 ) )
- S = Z( 3 )*( Z( 2 ) / T )
- IF( S.LE.T ) THEN
- S = Z( 3 )*( Z( 2 ) / ( T*( ONE+SQRT( ONE+S / T ) ) ) )
- ELSE
- S = Z( 3 )*( Z( 2 ) / ( T+SQRT( T )*SQRT( T+S ) ) )
- END IF
- T = Z( 1 ) + ( S+Z( 2 ) )
- Z( 3 ) = Z( 3 )*( Z( 1 ) / T )
- Z( 1 ) = T
- END IF
- Z( 2 ) = Z( 3 )
- Z( 6 ) = Z( 2 ) + Z( 1 )
- RETURN
- END IF
-*
-* Check for negative data and compute sums of q's and e's.
-*
- Z( 2*N ) = ZERO
- EMIN = Z( 2 )
- QMAX = ZERO
- ZMAX = ZERO
- D = ZERO
- E = ZERO
-*
- DO 10 K = 1, 2*( N-1 ), 2
- IF( Z( K ).LT.ZERO ) THEN
- INFO = -( 200+K )
- CALL XERBLA( 'DLASQ2', 2 )
- RETURN
- ELSE IF( Z( K+1 ).LT.ZERO ) THEN
- INFO = -( 200+K+1 )
- CALL XERBLA( 'DLASQ2', 2 )
- RETURN
- END IF
- D = D + Z( K )
- E = E + Z( K+1 )
- QMAX = MAX( QMAX, Z( K ) )
- EMIN = MIN( EMIN, Z( K+1 ) )
- ZMAX = MAX( QMAX, ZMAX, Z( K+1 ) )
- 10 CONTINUE
- IF( Z( 2*N-1 ).LT.ZERO ) THEN
- INFO = -( 200+2*N-1 )
- CALL XERBLA( 'DLASQ2', 2 )
- RETURN
- END IF
- D = D + Z( 2*N-1 )
- QMAX = MAX( QMAX, Z( 2*N-1 ) )
- ZMAX = MAX( QMAX, ZMAX )
-*
-* Check for diagonality.
-*
- IF( E.EQ.ZERO ) THEN
- DO 20 K = 2, N
- Z( K ) = Z( 2*K-1 )
- 20 CONTINUE
- CALL DLASRT( 'D', N, Z, IINFO )
- Z( 2*N-1 ) = D
- RETURN
- END IF
-*
- TRACE = D + E
-*
-* Check for zero data.
-*
- IF( TRACE.EQ.ZERO ) THEN
- Z( 2*N-1 ) = ZERO
- RETURN
- END IF
-*
-* Check whether the machine is IEEE conformable.
-*
- IEEE = ILAENV( 10, 'DLASQ2', 'N', 1, 2, 3, 4 ).EQ.1 .AND.
- $ ILAENV( 11, 'DLASQ2', 'N', 1, 2, 3, 4 ).EQ.1
-*
-* Rearrange data for locality: Z=(q1,qq1,e1,ee1,q2,qq2,e2,ee2,...).
-*
- DO 30 K = 2*N, 2, -2
- Z( 2*K ) = ZERO
- Z( 2*K-1 ) = Z( K )
- Z( 2*K-2 ) = ZERO
- Z( 2*K-3 ) = Z( K-1 )
- 30 CONTINUE
-*
- I0 = 1
- N0 = N
-*
-* Reverse the qd-array, if warranted.
-*
- IF( CBIAS*Z( 4*I0-3 ).LT.Z( 4*N0-3 ) ) THEN
- IPN4 = 4*( I0+N0 )
- DO 40 I4 = 4*I0, 2*( I0+N0-1 ), 4
- TEMP = Z( I4-3 )
- Z( I4-3 ) = Z( IPN4-I4-3 )
- Z( IPN4-I4-3 ) = TEMP
- TEMP = Z( I4-1 )
- Z( I4-1 ) = Z( IPN4-I4-5 )
- Z( IPN4-I4-5 ) = TEMP
- 40 CONTINUE
- END IF
-*
-* Initial split checking via dqd and Li's test.
-*
- PP = 0
-*
- DO 80 K = 1, 2
-*
- D = Z( 4*N0+PP-3 )
- DO 50 I4 = 4*( N0-1 ) + PP, 4*I0 + PP, -4
- IF( Z( I4-1 ).LE.TOL2*D ) THEN
- Z( I4-1 ) = -ZERO
- D = Z( I4-3 )
- ELSE
- D = Z( I4-3 )*( D / ( D+Z( I4-1 ) ) )
- END IF
- 50 CONTINUE
-*
-* dqd maps Z to ZZ plus Li's test.
-*
- EMIN = Z( 4*I0+PP+1 )
- D = Z( 4*I0+PP-3 )
- DO 60 I4 = 4*I0 + PP, 4*( N0-1 ) + PP, 4
- Z( I4-2*PP-2 ) = D + Z( I4-1 )
- IF( Z( I4-1 ).LE.TOL2*D ) THEN
- Z( I4-1 ) = -ZERO
- Z( I4-2*PP-2 ) = D
- Z( I4-2*PP ) = ZERO
- D = Z( I4+1 )
- ELSE IF( SAFMIN*Z( I4+1 ).LT.Z( I4-2*PP-2 ) .AND.
- $ SAFMIN*Z( I4-2*PP-2 ).LT.Z( I4+1 ) ) THEN
- TEMP = Z( I4+1 ) / Z( I4-2*PP-2 )
- Z( I4-2*PP ) = Z( I4-1 )*TEMP
- D = D*TEMP
- ELSE
- Z( I4-2*PP ) = Z( I4+1 )*( Z( I4-1 ) / Z( I4-2*PP-2 ) )
- D = Z( I4+1 )*( D / Z( I4-2*PP-2 ) )
- END IF
- EMIN = MIN( EMIN, Z( I4-2*PP ) )
- 60 CONTINUE
- Z( 4*N0-PP-2 ) = D
-*
-* Now find qmax.
-*
- QMAX = Z( 4*I0-PP-2 )
- DO 70 I4 = 4*I0 - PP + 2, 4*N0 - PP - 2, 4
- QMAX = MAX( QMAX, Z( I4 ) )
- 70 CONTINUE
-*
-* Prepare for the next iteration on K.
-*
- PP = 1 - PP
- 80 CONTINUE
-*
-* Initialise variables to pass to DLAZQ3
-*
- TTYPE = 0
- DMIN1 = ZERO
- DMIN2 = ZERO
- DN = ZERO
- DN1 = ZERO
- DN2 = ZERO
- TAU = ZERO
-*
- ITER = 2
- NFAIL = 0
- NDIV = 2*( N0-I0 )
-*
- DO 140 IWHILA = 1, N + 1
- IF( N0.LT.1 )
- $ GO TO 150
-*
-* While array unfinished do
-*
-* E(N0) holds the value of SIGMA when submatrix in I0:N0
-* splits from the rest of the array, but is negated.
-*
- DESIG = ZERO
- IF( N0.EQ.N ) THEN
- SIGMA = ZERO
- ELSE
- SIGMA = -Z( 4*N0-1 )
- END IF
- IF( SIGMA.LT.ZERO ) THEN
- INFO = 1
- RETURN
- END IF
-*
-* Find last unreduced submatrix's top index I0, find QMAX and
-* EMIN. Find Gershgorin-type bound if Q's much greater than E's.
-*
- EMAX = ZERO
- IF( N0.GT.I0 ) THEN
- EMIN = ABS( Z( 4*N0-5 ) )
- ELSE
- EMIN = ZERO
- END IF
- QMIN = Z( 4*N0-3 )
- QMAX = QMIN
- DO 90 I4 = 4*N0, 8, -4
- IF( Z( I4-5 ).LE.ZERO )
- $ GO TO 100
- IF( QMIN.GE.FOUR*EMAX ) THEN
- QMIN = MIN( QMIN, Z( I4-3 ) )
- EMAX = MAX( EMAX, Z( I4-5 ) )
- END IF
- QMAX = MAX( QMAX, Z( I4-7 )+Z( I4-5 ) )
- EMIN = MIN( EMIN, Z( I4-5 ) )
- 90 CONTINUE
- I4 = 4
-*
- 100 CONTINUE
- I0 = I4 / 4
-*
-* Store EMIN for passing to DLAZQ3.
-*
- Z( 4*N0-1 ) = EMIN
-*
-* Put -(initial shift) into DMIN.
-*
- DMIN = -MAX( ZERO, QMIN-TWO*SQRT( QMIN )*SQRT( EMAX ) )
-*
-* Now I0:N0 is unreduced. PP = 0 for ping, PP = 1 for pong.
-*
- PP = 0
-*
- NBIG = 30*( N0-I0+1 )
- DO 120 IWHILB = 1, NBIG
- IF( I0.GT.N0 )
- $ GO TO 130
-*
-* While submatrix unfinished take a good dqds step.
-*
- CALL DLAZQ3( I0, N0, Z, PP, DMIN, SIGMA, DESIG, QMAX, NFAIL,
- $ ITER, NDIV, IEEE, TTYPE, DMIN1, DMIN2, DN, DN1,
- $ DN2, TAU )
-*
- PP = 1 - PP
-*
-* When EMIN is very small check for splits.
-*
- IF( PP.EQ.0 .AND. N0-I0.GE.3 ) THEN
- IF( Z( 4*N0 ).LE.TOL2*QMAX .OR.
- $ Z( 4*N0-1 ).LE.TOL2*SIGMA ) THEN
- SPLT = I0 - 1
- QMAX = Z( 4*I0-3 )
- EMIN = Z( 4*I0-1 )
- OLDEMN = Z( 4*I0 )
- DO 110 I4 = 4*I0, 4*( N0-3 ), 4
- IF( Z( I4 ).LE.TOL2*Z( I4-3 ) .OR.
- $ Z( I4-1 ).LE.TOL2*SIGMA ) THEN
- Z( I4-1 ) = -SIGMA
- SPLT = I4 / 4
- QMAX = ZERO
- EMIN = Z( I4+3 )
- OLDEMN = Z( I4+4 )
- ELSE
- QMAX = MAX( QMAX, Z( I4+1 ) )
- EMIN = MIN( EMIN, Z( I4-1 ) )
- OLDEMN = MIN( OLDEMN, Z( I4 ) )
- END IF
- 110 CONTINUE
- Z( 4*N0-1 ) = EMIN
- Z( 4*N0 ) = OLDEMN
- I0 = SPLT + 1
- END IF
- END IF
-*
- 120 CONTINUE
-*
- INFO = 2
- RETURN
-*
-* end IWHILB
-*
- 130 CONTINUE
-*
- 140 CONTINUE
-*
- INFO = 3
- RETURN
-*
-* end IWHILA
-*
- 150 CONTINUE
-*
-* Move q's to the front.
-*
- DO 160 K = 2, N
- Z( K ) = Z( 4*K-3 )
- 160 CONTINUE
-*
-* Sort and compute sum of eigenvalues.
-*
- CALL DLASRT( 'D', N, Z, IINFO )
-*
- E = ZERO
- DO 170 K = N, 1, -1
- E = E + Z( K )
- 170 CONTINUE
-*
-* Store trace, sum(eigenvalues) and information on performance.
-*
- Z( 2*N+1 ) = TRACE
- Z( 2*N+2 ) = E
- Z( 2*N+3 ) = DBLE( ITER )
- Z( 2*N+4 ) = DBLE( NDIV ) / DBLE( N**2 )
- Z( 2*N+5 ) = HUNDRD*NFAIL / DBLE( ITER )
- RETURN
-*
-* End of DLASQ2
-*
- END
diff --git a/src/lib/lapack/dlasq3.f b/src/lib/lapack/dlasq3.f
deleted file mode 100644
index ce4055d8..00000000
--- a/src/lib/lapack/dlasq3.f
+++ /dev/null
@@ -1,295 +0,0 @@
- SUBROUTINE DLASQ3( I0, N0, Z, PP, DMIN, SIGMA, DESIG, QMAX, NFAIL,
- $ ITER, NDIV, IEEE )
-*
-* -- LAPACK auxiliary routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- LOGICAL IEEE
- INTEGER I0, ITER, N0, NDIV, NFAIL, PP
- DOUBLE PRECISION DESIG, DMIN, QMAX, SIGMA
-* ..
-* .. Array Arguments ..
- DOUBLE PRECISION Z( * )
-* ..
-*
-* Purpose
-* =======
-*
-* DLASQ3 checks for deflation, computes a shift (TAU) and calls dqds.
-* In case of failure it changes shifts, and tries again until output
-* is positive.
-*
-* Arguments
-* =========
-*
-* I0 (input) INTEGER
-* First index.
-*
-* N0 (input) INTEGER
-* Last index.
-*
-* Z (input) DOUBLE PRECISION array, dimension ( 4*N )
-* Z holds the qd array.
-*
-* PP (input) INTEGER
-* PP=0 for ping, PP=1 for pong.
-*
-* DMIN (output) DOUBLE PRECISION
-* Minimum value of d.
-*
-* SIGMA (output) DOUBLE PRECISION
-* Sum of shifts used in current segment.
-*
-* DESIG (input/output) DOUBLE PRECISION
-* Lower order part of SIGMA
-*
-* QMAX (input) DOUBLE PRECISION
-* Maximum value of q.
-*
-* NFAIL (output) INTEGER
-* Number of times shift was too big.
-*
-* ITER (output) INTEGER
-* Number of iterations.
-*
-* NDIV (output) INTEGER
-* Number of divisions.
-*
-* TTYPE (output) INTEGER
-* Shift type.
-*
-* IEEE (input) LOGICAL
-* Flag for IEEE or non IEEE arithmetic (passed to DLASQ5).
-*
-* =====================================================================
-*
-* .. Parameters ..
- DOUBLE PRECISION CBIAS
- PARAMETER ( CBIAS = 1.50D0 )
- DOUBLE PRECISION ZERO, QURTR, HALF, ONE, TWO, HUNDRD
- PARAMETER ( ZERO = 0.0D0, QURTR = 0.250D0, HALF = 0.5D0,
- $ ONE = 1.0D0, TWO = 2.0D0, HUNDRD = 100.0D0 )
-* ..
-* .. Local Scalars ..
- INTEGER IPN4, J4, N0IN, NN, TTYPE
- DOUBLE PRECISION DMIN1, DMIN2, DN, DN1, DN2, EPS, S, SAFMIN, T,
- $ TAU, TEMP, TOL, TOL2
-* ..
-* .. External Subroutines ..
- EXTERNAL DLASQ4, DLASQ5, DLASQ6
-* ..
-* .. External Function ..
- DOUBLE PRECISION DLAMCH
- EXTERNAL DLAMCH
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC ABS, MAX, MIN, SQRT
-* ..
-* .. Save statement ..
- SAVE TTYPE
- SAVE DMIN1, DMIN2, DN, DN1, DN2, TAU
-* ..
-* .. Data statement ..
- DATA TTYPE / 0 /
- DATA DMIN1 / ZERO /, DMIN2 / ZERO /, DN / ZERO /,
- $ DN1 / ZERO /, DN2 / ZERO /, TAU / ZERO /
-* ..
-* .. Executable Statements ..
-*
- N0IN = N0
- EPS = DLAMCH( 'Precision' )
- SAFMIN = DLAMCH( 'Safe minimum' )
- TOL = EPS*HUNDRD
- TOL2 = TOL**2
-*
-* Check for deflation.
-*
- 10 CONTINUE
-*
- IF( N0.LT.I0 )
- $ RETURN
- IF( N0.EQ.I0 )
- $ GO TO 20
- NN = 4*N0 + PP
- IF( N0.EQ.( I0+1 ) )
- $ GO TO 40
-*
-* Check whether E(N0-1) is negligible, 1 eigenvalue.
-*
- IF( Z( NN-5 ).GT.TOL2*( SIGMA+Z( NN-3 ) ) .AND.
- $ Z( NN-2*PP-4 ).GT.TOL2*Z( NN-7 ) )
- $ GO TO 30
-*
- 20 CONTINUE
-*
- Z( 4*N0-3 ) = Z( 4*N0+PP-3 ) + SIGMA
- N0 = N0 - 1
- GO TO 10
-*
-* Check whether E(N0-2) is negligible, 2 eigenvalues.
-*
- 30 CONTINUE
-*
- IF( Z( NN-9 ).GT.TOL2*SIGMA .AND.
- $ Z( NN-2*PP-8 ).GT.TOL2*Z( NN-11 ) )
- $ GO TO 50
-*
- 40 CONTINUE
-*
- IF( Z( NN-3 ).GT.Z( NN-7 ) ) THEN
- S = Z( NN-3 )
- Z( NN-3 ) = Z( NN-7 )
- Z( NN-7 ) = S
- END IF
- IF( Z( NN-5 ).GT.Z( NN-3 )*TOL2 ) THEN
- T = HALF*( ( Z( NN-7 )-Z( NN-3 ) )+Z( NN-5 ) )
- S = Z( NN-3 )*( Z( NN-5 ) / T )
- IF( S.LE.T ) THEN
- S = Z( NN-3 )*( Z( NN-5 ) /
- $ ( T*( ONE+SQRT( ONE+S / T ) ) ) )
- ELSE
- S = Z( NN-3 )*( Z( NN-5 ) / ( T+SQRT( T )*SQRT( T+S ) ) )
- END IF
- T = Z( NN-7 ) + ( S+Z( NN-5 ) )
- Z( NN-3 ) = Z( NN-3 )*( Z( NN-7 ) / T )
- Z( NN-7 ) = T
- END IF
- Z( 4*N0-7 ) = Z( NN-7 ) + SIGMA
- Z( 4*N0-3 ) = Z( NN-3 ) + SIGMA
- N0 = N0 - 2
- GO TO 10
-*
- 50 CONTINUE
-*
-* Reverse the qd-array, if warranted.
-*
- IF( DMIN.LE.ZERO .OR. N0.LT.N0IN ) THEN
- IF( CBIAS*Z( 4*I0+PP-3 ).LT.Z( 4*N0+PP-3 ) ) THEN
- IPN4 = 4*( I0+N0 )
- DO 60 J4 = 4*I0, 2*( I0+N0-1 ), 4
- TEMP = Z( J4-3 )
- Z( J4-3 ) = Z( IPN4-J4-3 )
- Z( IPN4-J4-3 ) = TEMP
- TEMP = Z( J4-2 )
- Z( J4-2 ) = Z( IPN4-J4-2 )
- Z( IPN4-J4-2 ) = TEMP
- TEMP = Z( J4-1 )
- Z( J4-1 ) = Z( IPN4-J4-5 )
- Z( IPN4-J4-5 ) = TEMP
- TEMP = Z( J4 )
- Z( J4 ) = Z( IPN4-J4-4 )
- Z( IPN4-J4-4 ) = TEMP
- 60 CONTINUE
- IF( N0-I0.LE.4 ) THEN
- Z( 4*N0+PP-1 ) = Z( 4*I0+PP-1 )
- Z( 4*N0-PP ) = Z( 4*I0-PP )
- END IF
- DMIN2 = MIN( DMIN2, Z( 4*N0+PP-1 ) )
- Z( 4*N0+PP-1 ) = MIN( Z( 4*N0+PP-1 ), Z( 4*I0+PP-1 ),
- $ Z( 4*I0+PP+3 ) )
- Z( 4*N0-PP ) = MIN( Z( 4*N0-PP ), Z( 4*I0-PP ),
- $ Z( 4*I0-PP+4 ) )
- QMAX = MAX( QMAX, Z( 4*I0+PP-3 ), Z( 4*I0+PP+1 ) )
- DMIN = -ZERO
- END IF
- END IF
-*
- IF( DMIN.LT.ZERO .OR. SAFMIN*QMAX.LT.MIN( Z( 4*N0+PP-1 ),
- $ Z( 4*N0+PP-9 ), DMIN2+Z( 4*N0-PP ) ) ) THEN
-*
-* Choose a shift.
-*
- CALL DLASQ4( I0, N0, Z, PP, N0IN, DMIN, DMIN1, DMIN2, DN, DN1,
- $ DN2, TAU, TTYPE )
-*
-* Call dqds until DMIN > 0.
-*
- 80 CONTINUE
-*
- CALL DLASQ5( I0, N0, Z, PP, TAU, DMIN, DMIN1, DMIN2, DN,
- $ DN1, DN2, IEEE )
-*
- NDIV = NDIV + ( N0-I0+2 )
- ITER = ITER + 1
-*
-* Check status.
-*
- IF( DMIN.GE.ZERO .AND. DMIN1.GT.ZERO ) THEN
-*
-* Success.
-*
- GO TO 100
-*
- ELSE IF( DMIN.LT.ZERO .AND. DMIN1.GT.ZERO .AND.
- $ Z( 4*( N0-1 )-PP ).LT.TOL*( SIGMA+DN1 ) .AND.
- $ ABS( DN ).LT.TOL*SIGMA ) THEN
-*
-* Convergence hidden by negative DN.
-*
- Z( 4*( N0-1 )-PP+2 ) = ZERO
- DMIN = ZERO
- GO TO 100
- ELSE IF( DMIN.LT.ZERO ) THEN
-*
-* TAU too big. Select new TAU and try again.
-*
- NFAIL = NFAIL + 1
- IF( TTYPE.LT.-22 ) THEN
-*
-* Failed twice. Play it safe.
-*
- TAU = ZERO
- ELSE IF( DMIN1.GT.ZERO ) THEN
-*
-* Late failure. Gives excellent shift.
-*
- TAU = ( TAU+DMIN )*( ONE-TWO*EPS )
- TTYPE = TTYPE - 11
- ELSE
-*
-* Early failure. Divide by 4.
-*
- TAU = QURTR*TAU
- TTYPE = TTYPE - 12
- END IF
- GO TO 80
- ELSE IF( DMIN.NE.DMIN ) THEN
-*
-* NaN.
-*
- TAU = ZERO
- GO TO 80
- ELSE
-*
-* Possible underflow. Play it safe.
-*
- GO TO 90
- END IF
- END IF
-*
-* Risk of underflow.
-*
- 90 CONTINUE
- CALL DLASQ6( I0, N0, Z, PP, DMIN, DMIN1, DMIN2, DN, DN1, DN2 )
- NDIV = NDIV + ( N0-I0+2 )
- ITER = ITER + 1
- TAU = ZERO
-*
- 100 CONTINUE
- IF( TAU.LT.SIGMA ) THEN
- DESIG = DESIG + TAU
- T = SIGMA + DESIG
- DESIG = DESIG - ( T-SIGMA )
- ELSE
- T = SIGMA + TAU
- DESIG = SIGMA - ( T-TAU ) + DESIG
- END IF
- SIGMA = T
-*
- RETURN
-*
-* End of DLASQ3
-*
- END
diff --git a/src/lib/lapack/dlasq4.f b/src/lib/lapack/dlasq4.f
deleted file mode 100644
index db2b6fe5..00000000
--- a/src/lib/lapack/dlasq4.f
+++ /dev/null
@@ -1,329 +0,0 @@
- SUBROUTINE DLASQ4( I0, N0, Z, PP, N0IN, DMIN, DMIN1, DMIN2, DN,
- $ DN1, DN2, TAU, TTYPE )
-*
-* -- LAPACK auxiliary routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- INTEGER I0, N0, N0IN, PP, TTYPE
- DOUBLE PRECISION DMIN, DMIN1, DMIN2, DN, DN1, DN2, TAU
-* ..
-* .. Array Arguments ..
- DOUBLE PRECISION Z( * )
-* ..
-*
-* Purpose
-* =======
-*
-* DLASQ4 computes an approximation TAU to the smallest eigenvalue
-* using values of d from the previous transform.
-*
-* I0 (input) INTEGER
-* First index.
-*
-* N0 (input) INTEGER
-* Last index.
-*
-* Z (input) DOUBLE PRECISION array, dimension ( 4*N )
-* Z holds the qd array.
-*
-* PP (input) INTEGER
-* PP=0 for ping, PP=1 for pong.
-*
-* N0IN (input) INTEGER
-* The value of N0 at start of EIGTEST.
-*
-* DMIN (input) DOUBLE PRECISION
-* Minimum value of d.
-*
-* DMIN1 (input) DOUBLE PRECISION
-* Minimum value of d, excluding D( N0 ).
-*
-* DMIN2 (input) DOUBLE PRECISION
-* Minimum value of d, excluding D( N0 ) and D( N0-1 ).
-*
-* DN (input) DOUBLE PRECISION
-* d(N)
-*
-* DN1 (input) DOUBLE PRECISION
-* d(N-1)
-*
-* DN2 (input) DOUBLE PRECISION
-* d(N-2)
-*
-* TAU (output) DOUBLE PRECISION
-* This is the shift.
-*
-* TTYPE (output) INTEGER
-* Shift type.
-*
-* Further Details
-* ===============
-* CNST1 = 9/16
-*
-* =====================================================================
-*
-* .. Parameters ..
- DOUBLE PRECISION CNST1, CNST2, CNST3
- PARAMETER ( CNST1 = 0.5630D0, CNST2 = 1.010D0,
- $ CNST3 = 1.050D0 )
- DOUBLE PRECISION QURTR, THIRD, HALF, ZERO, ONE, TWO, HUNDRD
- PARAMETER ( QURTR = 0.250D0, THIRD = 0.3330D0,
- $ HALF = 0.50D0, ZERO = 0.0D0, ONE = 1.0D0,
- $ TWO = 2.0D0, HUNDRD = 100.0D0 )
-* ..
-* .. Local Scalars ..
- INTEGER I4, NN, NP
- DOUBLE PRECISION A2, B1, B2, G, GAM, GAP1, GAP2, S
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC MAX, MIN, SQRT
-* ..
-* .. Save statement ..
- SAVE G
-* ..
-* .. Data statement ..
- DATA G / ZERO /
-* ..
-* .. Executable Statements ..
-*
-* A negative DMIN forces the shift to take that absolute value
-* TTYPE records the type of shift.
-*
- IF( DMIN.LE.ZERO ) THEN
- TAU = -DMIN
- TTYPE = -1
- RETURN
- END IF
-*
- NN = 4*N0 + PP
- IF( N0IN.EQ.N0 ) THEN
-*
-* No eigenvalues deflated.
-*
- IF( DMIN.EQ.DN .OR. DMIN.EQ.DN1 ) THEN
-*
- B1 = SQRT( Z( NN-3 ) )*SQRT( Z( NN-5 ) )
- B2 = SQRT( Z( NN-7 ) )*SQRT( Z( NN-9 ) )
- A2 = Z( NN-7 ) + Z( NN-5 )
-*
-* Cases 2 and 3.
-*
- IF( DMIN.EQ.DN .AND. DMIN1.EQ.DN1 ) THEN
- GAP2 = DMIN2 - A2 - DMIN2*QURTR
- IF( GAP2.GT.ZERO .AND. GAP2.GT.B2 ) THEN
- GAP1 = A2 - DN - ( B2 / GAP2 )*B2
- ELSE
- GAP1 = A2 - DN - ( B1+B2 )
- END IF
- IF( GAP1.GT.ZERO .AND. GAP1.GT.B1 ) THEN
- S = MAX( DN-( B1 / GAP1 )*B1, HALF*DMIN )
- TTYPE = -2
- ELSE
- S = ZERO
- IF( DN.GT.B1 )
- $ S = DN - B1
- IF( A2.GT.( B1+B2 ) )
- $ S = MIN( S, A2-( B1+B2 ) )
- S = MAX( S, THIRD*DMIN )
- TTYPE = -3
- END IF
- ELSE
-*
-* Case 4.
-*
- TTYPE = -4
- S = QURTR*DMIN
- IF( DMIN.EQ.DN ) THEN
- GAM = DN
- A2 = ZERO
- IF( Z( NN-5 ) .GT. Z( NN-7 ) )
- $ RETURN
- B2 = Z( NN-5 ) / Z( NN-7 )
- NP = NN - 9
- ELSE
- NP = NN - 2*PP
- B2 = Z( NP-2 )
- GAM = DN1
- IF( Z( NP-4 ) .GT. Z( NP-2 ) )
- $ RETURN
- A2 = Z( NP-4 ) / Z( NP-2 )
- IF( Z( NN-9 ) .GT. Z( NN-11 ) )
- $ RETURN
- B2 = Z( NN-9 ) / Z( NN-11 )
- NP = NN - 13
- END IF
-*
-* Approximate contribution to norm squared from I < NN-1.
-*
- A2 = A2 + B2
- DO 10 I4 = NP, 4*I0 - 1 + PP, -4
- IF( B2.EQ.ZERO )
- $ GO TO 20
- B1 = B2
- IF( Z( I4 ) .GT. Z( I4-2 ) )
- $ RETURN
- B2 = B2*( Z( I4 ) / Z( I4-2 ) )
- A2 = A2 + B2
- IF( HUNDRD*MAX( B2, B1 ).LT.A2 .OR. CNST1.LT.A2 )
- $ GO TO 20
- 10 CONTINUE
- 20 CONTINUE
- A2 = CNST3*A2
-*
-* Rayleigh quotient residual bound.
-*
- IF( A2.LT.CNST1 )
- $ S = GAM*( ONE-SQRT( A2 ) ) / ( ONE+A2 )
- END IF
- ELSE IF( DMIN.EQ.DN2 ) THEN
-*
-* Case 5.
-*
- TTYPE = -5
- S = QURTR*DMIN
-*
-* Compute contribution to norm squared from I > NN-2.
-*
- NP = NN - 2*PP
- B1 = Z( NP-2 )
- B2 = Z( NP-6 )
- GAM = DN2
- IF( Z( NP-8 ).GT.B2 .OR. Z( NP-4 ).GT.B1 )
- $ RETURN
- A2 = ( Z( NP-8 ) / B2 )*( ONE+Z( NP-4 ) / B1 )
-*
-* Approximate contribution to norm squared from I < NN-2.
-*
- IF( N0-I0.GT.2 ) THEN
- B2 = Z( NN-13 ) / Z( NN-15 )
- A2 = A2 + B2
- DO 30 I4 = NN - 17, 4*I0 - 1 + PP, -4
- IF( B2.EQ.ZERO )
- $ GO TO 40
- B1 = B2
- IF( Z( I4 ) .GT. Z( I4-2 ) )
- $ RETURN
- B2 = B2*( Z( I4 ) / Z( I4-2 ) )
- A2 = A2 + B2
- IF( HUNDRD*MAX( B2, B1 ).LT.A2 .OR. CNST1.LT.A2 )
- $ GO TO 40
- 30 CONTINUE
- 40 CONTINUE
- A2 = CNST3*A2
- END IF
-*
- IF( A2.LT.CNST1 )
- $ S = GAM*( ONE-SQRT( A2 ) ) / ( ONE+A2 )
- ELSE
-*
-* Case 6, no information to guide us.
-*
- IF( TTYPE.EQ.-6 ) THEN
- G = G + THIRD*( ONE-G )
- ELSE IF( TTYPE.EQ.-18 ) THEN
- G = QURTR*THIRD
- ELSE
- G = QURTR
- END IF
- S = G*DMIN
- TTYPE = -6
- END IF
-*
- ELSE IF( N0IN.EQ.( N0+1 ) ) THEN
-*
-* One eigenvalue just deflated. Use DMIN1, DN1 for DMIN and DN.
-*
- IF( DMIN1.EQ.DN1 .AND. DMIN2.EQ.DN2 ) THEN
-*
-* Cases 7 and 8.
-*
- TTYPE = -7
- S = THIRD*DMIN1
- IF( Z( NN-5 ).GT.Z( NN-7 ) )
- $ RETURN
- B1 = Z( NN-5 ) / Z( NN-7 )
- B2 = B1
- IF( B2.EQ.ZERO )
- $ GO TO 60
- DO 50 I4 = 4*N0 - 9 + PP, 4*I0 - 1 + PP, -4
- A2 = B1
- IF( Z( I4 ).GT.Z( I4-2 ) )
- $ RETURN
- B1 = B1*( Z( I4 ) / Z( I4-2 ) )
- B2 = B2 + B1
- IF( HUNDRD*MAX( B1, A2 ).LT.B2 )
- $ GO TO 60
- 50 CONTINUE
- 60 CONTINUE
- B2 = SQRT( CNST3*B2 )
- A2 = DMIN1 / ( ONE+B2**2 )
- GAP2 = HALF*DMIN2 - A2
- IF( GAP2.GT.ZERO .AND. GAP2.GT.B2*A2 ) THEN
- S = MAX( S, A2*( ONE-CNST2*A2*( B2 / GAP2 )*B2 ) )
- ELSE
- S = MAX( S, A2*( ONE-CNST2*B2 ) )
- TTYPE = -8
- END IF
- ELSE
-*
-* Case 9.
-*
- S = QURTR*DMIN1
- IF( DMIN1.EQ.DN1 )
- $ S = HALF*DMIN1
- TTYPE = -9
- END IF
-*
- ELSE IF( N0IN.EQ.( N0+2 ) ) THEN
-*
-* Two eigenvalues deflated. Use DMIN2, DN2 for DMIN and DN.
-*
-* Cases 10 and 11.
-*
- IF( DMIN2.EQ.DN2 .AND. TWO*Z( NN-5 ).LT.Z( NN-7 ) ) THEN
- TTYPE = -10
- S = THIRD*DMIN2
- IF( Z( NN-5 ).GT.Z( NN-7 ) )
- $ RETURN
- B1 = Z( NN-5 ) / Z( NN-7 )
- B2 = B1
- IF( B2.EQ.ZERO )
- $ GO TO 80
- DO 70 I4 = 4*N0 - 9 + PP, 4*I0 - 1 + PP, -4
- IF( Z( I4 ).GT.Z( I4-2 ) )
- $ RETURN
- B1 = B1*( Z( I4 ) / Z( I4-2 ) )
- B2 = B2 + B1
- IF( HUNDRD*B1.LT.B2 )
- $ GO TO 80
- 70 CONTINUE
- 80 CONTINUE
- B2 = SQRT( CNST3*B2 )
- A2 = DMIN2 / ( ONE+B2**2 )
- GAP2 = Z( NN-7 ) + Z( NN-9 ) -
- $ SQRT( Z( NN-11 ) )*SQRT( Z( NN-9 ) ) - A2
- IF( GAP2.GT.ZERO .AND. GAP2.GT.B2*A2 ) THEN
- S = MAX( S, A2*( ONE-CNST2*A2*( B2 / GAP2 )*B2 ) )
- ELSE
- S = MAX( S, A2*( ONE-CNST2*B2 ) )
- END IF
- ELSE
- S = QURTR*DMIN2
- TTYPE = -11
- END IF
- ELSE IF( N0IN.GT.( N0+2 ) ) THEN
-*
-* Case 12, more than two eigenvalues deflated. No information.
-*
- S = ZERO
- TTYPE = -12
- END IF
-*
- TAU = S
- RETURN
-*
-* End of DLASQ4
-*
- END
diff --git a/src/lib/lapack/dlasq5.f b/src/lib/lapack/dlasq5.f
deleted file mode 100644
index a006c99e..00000000
--- a/src/lib/lapack/dlasq5.f
+++ /dev/null
@@ -1,195 +0,0 @@
- SUBROUTINE DLASQ5( I0, N0, Z, PP, TAU, DMIN, DMIN1, DMIN2, DN,
- $ DNM1, DNM2, IEEE )
-*
-* -- LAPACK auxiliary routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- LOGICAL IEEE
- INTEGER I0, N0, PP
- DOUBLE PRECISION DMIN, DMIN1, DMIN2, DN, DNM1, DNM2, TAU
-* ..
-* .. Array Arguments ..
- DOUBLE PRECISION Z( * )
-* ..
-*
-* Purpose
-* =======
-*
-* DLASQ5 computes one dqds transform in ping-pong form, one
-* version for IEEE machines another for non IEEE machines.
-*
-* Arguments
-* =========
-*
-* I0 (input) INTEGER
-* First index.
-*
-* N0 (input) INTEGER
-* Last index.
-*
-* Z (input) DOUBLE PRECISION array, dimension ( 4*N )
-* Z holds the qd array. EMIN is stored in Z(4*N0) to avoid
-* an extra argument.
-*
-* PP (input) INTEGER
-* PP=0 for ping, PP=1 for pong.
-*
-* TAU (input) DOUBLE PRECISION
-* This is the shift.
-*
-* DMIN (output) DOUBLE PRECISION
-* Minimum value of d.
-*
-* DMIN1 (output) DOUBLE PRECISION
-* Minimum value of d, excluding D( N0 ).
-*
-* DMIN2 (output) DOUBLE PRECISION
-* Minimum value of d, excluding D( N0 ) and D( N0-1 ).
-*
-* DN (output) DOUBLE PRECISION
-* d(N0), the last value of d.
-*
-* DNM1 (output) DOUBLE PRECISION
-* d(N0-1).
-*
-* DNM2 (output) DOUBLE PRECISION
-* d(N0-2).
-*
-* IEEE (input) LOGICAL
-* Flag for IEEE or non IEEE arithmetic.
-*
-* =====================================================================
-*
-* .. Parameter ..
- DOUBLE PRECISION ZERO
- PARAMETER ( ZERO = 0.0D0 )
-* ..
-* .. Local Scalars ..
- INTEGER J4, J4P2
- DOUBLE PRECISION D, EMIN, TEMP
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC MIN
-* ..
-* .. Executable Statements ..
-*
- IF( ( N0-I0-1 ).LE.0 )
- $ RETURN
-*
- J4 = 4*I0 + PP - 3
- EMIN = Z( J4+4 )
- D = Z( J4 ) - TAU
- DMIN = D
- DMIN1 = -Z( J4 )
-*
- IF( IEEE ) THEN
-*
-* Code for IEEE arithmetic.
-*
- IF( PP.EQ.0 ) THEN
- DO 10 J4 = 4*I0, 4*( N0-3 ), 4
- Z( J4-2 ) = D + Z( J4-1 )
- TEMP = Z( J4+1 ) / Z( J4-2 )
- D = D*TEMP - TAU
- DMIN = MIN( DMIN, D )
- Z( J4 ) = Z( J4-1 )*TEMP
- EMIN = MIN( Z( J4 ), EMIN )
- 10 CONTINUE
- ELSE
- DO 20 J4 = 4*I0, 4*( N0-3 ), 4
- Z( J4-3 ) = D + Z( J4 )
- TEMP = Z( J4+2 ) / Z( J4-3 )
- D = D*TEMP - TAU
- DMIN = MIN( DMIN, D )
- Z( J4-1 ) = Z( J4 )*TEMP
- EMIN = MIN( Z( J4-1 ), EMIN )
- 20 CONTINUE
- END IF
-*
-* Unroll last two steps.
-*
- DNM2 = D
- DMIN2 = DMIN
- J4 = 4*( N0-2 ) - PP
- J4P2 = J4 + 2*PP - 1
- Z( J4-2 ) = DNM2 + Z( J4P2 )
- Z( J4 ) = Z( J4P2+2 )*( Z( J4P2 ) / Z( J4-2 ) )
- DNM1 = Z( J4P2+2 )*( DNM2 / Z( J4-2 ) ) - TAU
- DMIN = MIN( DMIN, DNM1 )
-*
- DMIN1 = DMIN
- J4 = J4 + 4
- J4P2 = J4 + 2*PP - 1
- Z( J4-2 ) = DNM1 + Z( J4P2 )
- Z( J4 ) = Z( J4P2+2 )*( Z( J4P2 ) / Z( J4-2 ) )
- DN = Z( J4P2+2 )*( DNM1 / Z( J4-2 ) ) - TAU
- DMIN = MIN( DMIN, DN )
-*
- ELSE
-*
-* Code for non IEEE arithmetic.
-*
- IF( PP.EQ.0 ) THEN
- DO 30 J4 = 4*I0, 4*( N0-3 ), 4
- Z( J4-2 ) = D + Z( J4-1 )
- IF( D.LT.ZERO ) THEN
- RETURN
- ELSE
- Z( J4 ) = Z( J4+1 )*( Z( J4-1 ) / Z( J4-2 ) )
- D = Z( J4+1 )*( D / Z( J4-2 ) ) - TAU
- END IF
- DMIN = MIN( DMIN, D )
- EMIN = MIN( EMIN, Z( J4 ) )
- 30 CONTINUE
- ELSE
- DO 40 J4 = 4*I0, 4*( N0-3 ), 4
- Z( J4-3 ) = D + Z( J4 )
- IF( D.LT.ZERO ) THEN
- RETURN
- ELSE
- Z( J4-1 ) = Z( J4+2 )*( Z( J4 ) / Z( J4-3 ) )
- D = Z( J4+2 )*( D / Z( J4-3 ) ) - TAU
- END IF
- DMIN = MIN( DMIN, D )
- EMIN = MIN( EMIN, Z( J4-1 ) )
- 40 CONTINUE
- END IF
-*
-* Unroll last two steps.
-*
- DNM2 = D
- DMIN2 = DMIN
- J4 = 4*( N0-2 ) - PP
- J4P2 = J4 + 2*PP - 1
- Z( J4-2 ) = DNM2 + Z( J4P2 )
- IF( DNM2.LT.ZERO ) THEN
- RETURN
- ELSE
- Z( J4 ) = Z( J4P2+2 )*( Z( J4P2 ) / Z( J4-2 ) )
- DNM1 = Z( J4P2+2 )*( DNM2 / Z( J4-2 ) ) - TAU
- END IF
- DMIN = MIN( DMIN, DNM1 )
-*
- DMIN1 = DMIN
- J4 = J4 + 4
- J4P2 = J4 + 2*PP - 1
- Z( J4-2 ) = DNM1 + Z( J4P2 )
- IF( DNM1.LT.ZERO ) THEN
- RETURN
- ELSE
- Z( J4 ) = Z( J4P2+2 )*( Z( J4P2 ) / Z( J4-2 ) )
- DN = Z( J4P2+2 )*( DNM1 / Z( J4-2 ) ) - TAU
- END IF
- DMIN = MIN( DMIN, DN )
-*
- END IF
-*
- Z( J4+2 ) = DN
- Z( 4*N0-PP ) = EMIN
- RETURN
-*
-* End of DLASQ5
-*
- END
diff --git a/src/lib/lapack/dlasq6.f b/src/lib/lapack/dlasq6.f
deleted file mode 100644
index e7eb7d0a..00000000
--- a/src/lib/lapack/dlasq6.f
+++ /dev/null
@@ -1,175 +0,0 @@
- SUBROUTINE DLASQ6( I0, N0, Z, PP, DMIN, DMIN1, DMIN2, DN,
- $ DNM1, DNM2 )
-*
-* -- LAPACK auxiliary routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- INTEGER I0, N0, PP
- DOUBLE PRECISION DMIN, DMIN1, DMIN2, DN, DNM1, DNM2
-* ..
-* .. Array Arguments ..
- DOUBLE PRECISION Z( * )
-* ..
-*
-* Purpose
-* =======
-*
-* DLASQ6 computes one dqd (shift equal to zero) transform in
-* ping-pong form, with protection against underflow and overflow.
-*
-* Arguments
-* =========
-*
-* I0 (input) INTEGER
-* First index.
-*
-* N0 (input) INTEGER
-* Last index.
-*
-* Z (input) DOUBLE PRECISION array, dimension ( 4*N )
-* Z holds the qd array. EMIN is stored in Z(4*N0) to avoid
-* an extra argument.
-*
-* PP (input) INTEGER
-* PP=0 for ping, PP=1 for pong.
-*
-* DMIN (output) DOUBLE PRECISION
-* Minimum value of d.
-*
-* DMIN1 (output) DOUBLE PRECISION
-* Minimum value of d, excluding D( N0 ).
-*
-* DMIN2 (output) DOUBLE PRECISION
-* Minimum value of d, excluding D( N0 ) and D( N0-1 ).
-*
-* DN (output) DOUBLE PRECISION
-* d(N0), the last value of d.
-*
-* DNM1 (output) DOUBLE PRECISION
-* d(N0-1).
-*
-* DNM2 (output) DOUBLE PRECISION
-* d(N0-2).
-*
-* =====================================================================
-*
-* .. Parameter ..
- DOUBLE PRECISION ZERO
- PARAMETER ( ZERO = 0.0D0 )
-* ..
-* .. Local Scalars ..
- INTEGER J4, J4P2
- DOUBLE PRECISION D, EMIN, SAFMIN, TEMP
-* ..
-* .. External Function ..
- DOUBLE PRECISION DLAMCH
- EXTERNAL DLAMCH
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC MIN
-* ..
-* .. Executable Statements ..
-*
- IF( ( N0-I0-1 ).LE.0 )
- $ RETURN
-*
- SAFMIN = DLAMCH( 'Safe minimum' )
- J4 = 4*I0 + PP - 3
- EMIN = Z( J4+4 )
- D = Z( J4 )
- DMIN = D
-*
- IF( PP.EQ.0 ) THEN
- DO 10 J4 = 4*I0, 4*( N0-3 ), 4
- Z( J4-2 ) = D + Z( J4-1 )
- IF( Z( J4-2 ).EQ.ZERO ) THEN
- Z( J4 ) = ZERO
- D = Z( J4+1 )
- DMIN = D
- EMIN = ZERO
- ELSE IF( SAFMIN*Z( J4+1 ).LT.Z( J4-2 ) .AND.
- $ SAFMIN*Z( J4-2 ).LT.Z( J4+1 ) ) THEN
- TEMP = Z( J4+1 ) / Z( J4-2 )
- Z( J4 ) = Z( J4-1 )*TEMP
- D = D*TEMP
- ELSE
- Z( J4 ) = Z( J4+1 )*( Z( J4-1 ) / Z( J4-2 ) )
- D = Z( J4+1 )*( D / Z( J4-2 ) )
- END IF
- DMIN = MIN( DMIN, D )
- EMIN = MIN( EMIN, Z( J4 ) )
- 10 CONTINUE
- ELSE
- DO 20 J4 = 4*I0, 4*( N0-3 ), 4
- Z( J4-3 ) = D + Z( J4 )
- IF( Z( J4-3 ).EQ.ZERO ) THEN
- Z( J4-1 ) = ZERO
- D = Z( J4+2 )
- DMIN = D
- EMIN = ZERO
- ELSE IF( SAFMIN*Z( J4+2 ).LT.Z( J4-3 ) .AND.
- $ SAFMIN*Z( J4-3 ).LT.Z( J4+2 ) ) THEN
- TEMP = Z( J4+2 ) / Z( J4-3 )
- Z( J4-1 ) = Z( J4 )*TEMP
- D = D*TEMP
- ELSE
- Z( J4-1 ) = Z( J4+2 )*( Z( J4 ) / Z( J4-3 ) )
- D = Z( J4+2 )*( D / Z( J4-3 ) )
- END IF
- DMIN = MIN( DMIN, D )
- EMIN = MIN( EMIN, Z( J4-1 ) )
- 20 CONTINUE
- END IF
-*
-* Unroll last two steps.
-*
- DNM2 = D
- DMIN2 = DMIN
- J4 = 4*( N0-2 ) - PP
- J4P2 = J4 + 2*PP - 1
- Z( J4-2 ) = DNM2 + Z( J4P2 )
- IF( Z( J4-2 ).EQ.ZERO ) THEN
- Z( J4 ) = ZERO
- DNM1 = Z( J4P2+2 )
- DMIN = DNM1
- EMIN = ZERO
- ELSE IF( SAFMIN*Z( J4P2+2 ).LT.Z( J4-2 ) .AND.
- $ SAFMIN*Z( J4-2 ).LT.Z( J4P2+2 ) ) THEN
- TEMP = Z( J4P2+2 ) / Z( J4-2 )
- Z( J4 ) = Z( J4P2 )*TEMP
- DNM1 = DNM2*TEMP
- ELSE
- Z( J4 ) = Z( J4P2+2 )*( Z( J4P2 ) / Z( J4-2 ) )
- DNM1 = Z( J4P2+2 )*( DNM2 / Z( J4-2 ) )
- END IF
- DMIN = MIN( DMIN, DNM1 )
-*
- DMIN1 = DMIN
- J4 = J4 + 4
- J4P2 = J4 + 2*PP - 1
- Z( J4-2 ) = DNM1 + Z( J4P2 )
- IF( Z( J4-2 ).EQ.ZERO ) THEN
- Z( J4 ) = ZERO
- DN = Z( J4P2+2 )
- DMIN = DN
- EMIN = ZERO
- ELSE IF( SAFMIN*Z( J4P2+2 ).LT.Z( J4-2 ) .AND.
- $ SAFMIN*Z( J4-2 ).LT.Z( J4P2+2 ) ) THEN
- TEMP = Z( J4P2+2 ) / Z( J4-2 )
- Z( J4 ) = Z( J4P2 )*TEMP
- DN = DNM1*TEMP
- ELSE
- Z( J4 ) = Z( J4P2+2 )*( Z( J4P2 ) / Z( J4-2 ) )
- DN = Z( J4P2+2 )*( DNM1 / Z( J4-2 ) )
- END IF
- DMIN = MIN( DMIN, DN )
-*
- Z( J4+2 ) = DN
- Z( 4*N0-PP ) = EMIN
- RETURN
-*
-* End of DLASQ6
-*
- END
diff --git a/src/lib/lapack/dlasr.f b/src/lib/lapack/dlasr.f
deleted file mode 100644
index 7e54bfc7..00000000
--- a/src/lib/lapack/dlasr.f
+++ /dev/null
@@ -1,361 +0,0 @@
- SUBROUTINE DLASR( SIDE, PIVOT, DIRECT, M, N, C, S, A, LDA )
-*
-* -- LAPACK auxiliary routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- CHARACTER DIRECT, PIVOT, SIDE
- INTEGER LDA, M, N
-* ..
-* .. Array Arguments ..
- DOUBLE PRECISION A( LDA, * ), C( * ), S( * )
-* ..
-*
-* Purpose
-* =======
-*
-* DLASR applies a sequence of plane rotations to a real matrix A,
-* from either the left or the right.
-*
-* When SIDE = 'L', the transformation takes the form
-*
-* A := P*A
-*
-* and when SIDE = 'R', the transformation takes the form
-*
-* A := A*P**T
-*
-* where P is an orthogonal matrix consisting of a sequence of z plane
-* rotations, with z = M when SIDE = 'L' and z = N when SIDE = 'R',
-* and P**T is the transpose of P.
-*
-* When DIRECT = 'F' (Forward sequence), then
-*
-* P = P(z-1) * ... * P(2) * P(1)
-*
-* and when DIRECT = 'B' (Backward sequence), then
-*
-* P = P(1) * P(2) * ... * P(z-1)
-*
-* where P(k) is a plane rotation matrix defined by the 2-by-2 rotation
-*
-* R(k) = ( c(k) s(k) )
-* = ( -s(k) c(k) ).
-*
-* When PIVOT = 'V' (Variable pivot), the rotation is performed
-* for the plane (k,k+1), i.e., P(k) has the form
-*
-* P(k) = ( 1 )
-* ( ... )
-* ( 1 )
-* ( c(k) s(k) )
-* ( -s(k) c(k) )
-* ( 1 )
-* ( ... )
-* ( 1 )
-*
-* where R(k) appears as a rank-2 modification to the identity matrix in
-* rows and columns k and k+1.
-*
-* When PIVOT = 'T' (Top pivot), the rotation is performed for the
-* plane (1,k+1), so P(k) has the form
-*
-* P(k) = ( c(k) s(k) )
-* ( 1 )
-* ( ... )
-* ( 1 )
-* ( -s(k) c(k) )
-* ( 1 )
-* ( ... )
-* ( 1 )
-*
-* where R(k) appears in rows and columns 1 and k+1.
-*
-* Similarly, when PIVOT = 'B' (Bottom pivot), the rotation is
-* performed for the plane (k,z), giving P(k) the form
-*
-* P(k) = ( 1 )
-* ( ... )
-* ( 1 )
-* ( c(k) s(k) )
-* ( 1 )
-* ( ... )
-* ( 1 )
-* ( -s(k) c(k) )
-*
-* where R(k) appears in rows and columns k and z. The rotations are
-* performed without ever forming P(k) explicitly.
-*
-* Arguments
-* =========
-*
-* SIDE (input) CHARACTER*1
-* Specifies whether the plane rotation matrix P is applied to
-* A on the left or the right.
-* = 'L': Left, compute A := P*A
-* = 'R': Right, compute A:= A*P**T
-*
-* PIVOT (input) CHARACTER*1
-* Specifies the plane for which P(k) is a plane rotation
-* matrix.
-* = 'V': Variable pivot, the plane (k,k+1)
-* = 'T': Top pivot, the plane (1,k+1)
-* = 'B': Bottom pivot, the plane (k,z)
-*
-* DIRECT (input) CHARACTER*1
-* Specifies whether P is a forward or backward sequence of
-* plane rotations.
-* = 'F': Forward, P = P(z-1)*...*P(2)*P(1)
-* = 'B': Backward, P = P(1)*P(2)*...*P(z-1)
-*
-* M (input) INTEGER
-* The number of rows of the matrix A. If m <= 1, an immediate
-* return is effected.
-*
-* N (input) INTEGER
-* The number of columns of the matrix A. If n <= 1, an
-* immediate return is effected.
-*
-* C (input) DOUBLE PRECISION array, dimension
-* (M-1) if SIDE = 'L'
-* (N-1) if SIDE = 'R'
-* The cosines c(k) of the plane rotations.
-*
-* S (input) DOUBLE PRECISION array, dimension
-* (M-1) if SIDE = 'L'
-* (N-1) if SIDE = 'R'
-* The sines s(k) of the plane rotations. The 2-by-2 plane
-* rotation part of the matrix P(k), R(k), has the form
-* R(k) = ( c(k) s(k) )
-* ( -s(k) c(k) ).
-*
-* A (input/output) DOUBLE PRECISION array, dimension (LDA,N)
-* The M-by-N matrix A. On exit, A is overwritten by P*A if
-* SIDE = 'R' or by A*P**T if SIDE = 'L'.
-*
-* LDA (input) INTEGER
-* The leading dimension of the array A. LDA >= max(1,M).
-*
-* =====================================================================
-*
-* .. Parameters ..
- DOUBLE PRECISION ONE, ZERO
- PARAMETER ( ONE = 1.0D+0, ZERO = 0.0D+0 )
-* ..
-* .. Local Scalars ..
- INTEGER I, INFO, J
- DOUBLE PRECISION CTEMP, STEMP, TEMP
-* ..
-* .. External Functions ..
- LOGICAL LSAME
- EXTERNAL LSAME
-* ..
-* .. External Subroutines ..
- EXTERNAL XERBLA
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC MAX
-* ..
-* .. Executable Statements ..
-*
-* Test the input parameters
-*
- INFO = 0
- IF( .NOT.( LSAME( SIDE, 'L' ) .OR. LSAME( SIDE, 'R' ) ) ) THEN
- INFO = 1
- ELSE IF( .NOT.( LSAME( PIVOT, 'V' ) .OR. LSAME( PIVOT,
- $ 'T' ) .OR. LSAME( PIVOT, 'B' ) ) ) THEN
- INFO = 2
- ELSE IF( .NOT.( LSAME( DIRECT, 'F' ) .OR. LSAME( DIRECT, 'B' ) ) )
- $ THEN
- INFO = 3
- ELSE IF( M.LT.0 ) THEN
- INFO = 4
- ELSE IF( N.LT.0 ) THEN
- INFO = 5
- ELSE IF( LDA.LT.MAX( 1, M ) ) THEN
- INFO = 9
- END IF
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'DLASR ', INFO )
- RETURN
- END IF
-*
-* Quick return if possible
-*
- IF( ( M.EQ.0 ) .OR. ( N.EQ.0 ) )
- $ RETURN
- IF( LSAME( SIDE, 'L' ) ) THEN
-*
-* Form P * A
-*
- IF( LSAME( PIVOT, 'V' ) ) THEN
- IF( LSAME( DIRECT, 'F' ) ) THEN
- DO 20 J = 1, M - 1
- CTEMP = C( J )
- STEMP = S( J )
- IF( ( CTEMP.NE.ONE ) .OR. ( STEMP.NE.ZERO ) ) THEN
- DO 10 I = 1, N
- TEMP = A( J+1, I )
- A( J+1, I ) = CTEMP*TEMP - STEMP*A( J, I )
- A( J, I ) = STEMP*TEMP + CTEMP*A( J, I )
- 10 CONTINUE
- END IF
- 20 CONTINUE
- ELSE IF( LSAME( DIRECT, 'B' ) ) THEN
- DO 40 J = M - 1, 1, -1
- CTEMP = C( J )
- STEMP = S( J )
- IF( ( CTEMP.NE.ONE ) .OR. ( STEMP.NE.ZERO ) ) THEN
- DO 30 I = 1, N
- TEMP = A( J+1, I )
- A( J+1, I ) = CTEMP*TEMP - STEMP*A( J, I )
- A( J, I ) = STEMP*TEMP + CTEMP*A( J, I )
- 30 CONTINUE
- END IF
- 40 CONTINUE
- END IF
- ELSE IF( LSAME( PIVOT, 'T' ) ) THEN
- IF( LSAME( DIRECT, 'F' ) ) THEN
- DO 60 J = 2, M
- CTEMP = C( J-1 )
- STEMP = S( J-1 )
- IF( ( CTEMP.NE.ONE ) .OR. ( STEMP.NE.ZERO ) ) THEN
- DO 50 I = 1, N
- TEMP = A( J, I )
- A( J, I ) = CTEMP*TEMP - STEMP*A( 1, I )
- A( 1, I ) = STEMP*TEMP + CTEMP*A( 1, I )
- 50 CONTINUE
- END IF
- 60 CONTINUE
- ELSE IF( LSAME( DIRECT, 'B' ) ) THEN
- DO 80 J = M, 2, -1
- CTEMP = C( J-1 )
- STEMP = S( J-1 )
- IF( ( CTEMP.NE.ONE ) .OR. ( STEMP.NE.ZERO ) ) THEN
- DO 70 I = 1, N
- TEMP = A( J, I )
- A( J, I ) = CTEMP*TEMP - STEMP*A( 1, I )
- A( 1, I ) = STEMP*TEMP + CTEMP*A( 1, I )
- 70 CONTINUE
- END IF
- 80 CONTINUE
- END IF
- ELSE IF( LSAME( PIVOT, 'B' ) ) THEN
- IF( LSAME( DIRECT, 'F' ) ) THEN
- DO 100 J = 1, M - 1
- CTEMP = C( J )
- STEMP = S( J )
- IF( ( CTEMP.NE.ONE ) .OR. ( STEMP.NE.ZERO ) ) THEN
- DO 90 I = 1, N
- TEMP = A( J, I )
- A( J, I ) = STEMP*A( M, I ) + CTEMP*TEMP
- A( M, I ) = CTEMP*A( M, I ) - STEMP*TEMP
- 90 CONTINUE
- END IF
- 100 CONTINUE
- ELSE IF( LSAME( DIRECT, 'B' ) ) THEN
- DO 120 J = M - 1, 1, -1
- CTEMP = C( J )
- STEMP = S( J )
- IF( ( CTEMP.NE.ONE ) .OR. ( STEMP.NE.ZERO ) ) THEN
- DO 110 I = 1, N
- TEMP = A( J, I )
- A( J, I ) = STEMP*A( M, I ) + CTEMP*TEMP
- A( M, I ) = CTEMP*A( M, I ) - STEMP*TEMP
- 110 CONTINUE
- END IF
- 120 CONTINUE
- END IF
- END IF
- ELSE IF( LSAME( SIDE, 'R' ) ) THEN
-*
-* Form A * P'
-*
- IF( LSAME( PIVOT, 'V' ) ) THEN
- IF( LSAME( DIRECT, 'F' ) ) THEN
- DO 140 J = 1, N - 1
- CTEMP = C( J )
- STEMP = S( J )
- IF( ( CTEMP.NE.ONE ) .OR. ( STEMP.NE.ZERO ) ) THEN
- DO 130 I = 1, M
- TEMP = A( I, J+1 )
- A( I, J+1 ) = CTEMP*TEMP - STEMP*A( I, J )
- A( I, J ) = STEMP*TEMP + CTEMP*A( I, J )
- 130 CONTINUE
- END IF
- 140 CONTINUE
- ELSE IF( LSAME( DIRECT, 'B' ) ) THEN
- DO 160 J = N - 1, 1, -1
- CTEMP = C( J )
- STEMP = S( J )
- IF( ( CTEMP.NE.ONE ) .OR. ( STEMP.NE.ZERO ) ) THEN
- DO 150 I = 1, M
- TEMP = A( I, J+1 )
- A( I, J+1 ) = CTEMP*TEMP - STEMP*A( I, J )
- A( I, J ) = STEMP*TEMP + CTEMP*A( I, J )
- 150 CONTINUE
- END IF
- 160 CONTINUE
- END IF
- ELSE IF( LSAME( PIVOT, 'T' ) ) THEN
- IF( LSAME( DIRECT, 'F' ) ) THEN
- DO 180 J = 2, N
- CTEMP = C( J-1 )
- STEMP = S( J-1 )
- IF( ( CTEMP.NE.ONE ) .OR. ( STEMP.NE.ZERO ) ) THEN
- DO 170 I = 1, M
- TEMP = A( I, J )
- A( I, J ) = CTEMP*TEMP - STEMP*A( I, 1 )
- A( I, 1 ) = STEMP*TEMP + CTEMP*A( I, 1 )
- 170 CONTINUE
- END IF
- 180 CONTINUE
- ELSE IF( LSAME( DIRECT, 'B' ) ) THEN
- DO 200 J = N, 2, -1
- CTEMP = C( J-1 )
- STEMP = S( J-1 )
- IF( ( CTEMP.NE.ONE ) .OR. ( STEMP.NE.ZERO ) ) THEN
- DO 190 I = 1, M
- TEMP = A( I, J )
- A( I, J ) = CTEMP*TEMP - STEMP*A( I, 1 )
- A( I, 1 ) = STEMP*TEMP + CTEMP*A( I, 1 )
- 190 CONTINUE
- END IF
- 200 CONTINUE
- END IF
- ELSE IF( LSAME( PIVOT, 'B' ) ) THEN
- IF( LSAME( DIRECT, 'F' ) ) THEN
- DO 220 J = 1, N - 1
- CTEMP = C( J )
- STEMP = S( J )
- IF( ( CTEMP.NE.ONE ) .OR. ( STEMP.NE.ZERO ) ) THEN
- DO 210 I = 1, M
- TEMP = A( I, J )
- A( I, J ) = STEMP*A( I, N ) + CTEMP*TEMP
- A( I, N ) = CTEMP*A( I, N ) - STEMP*TEMP
- 210 CONTINUE
- END IF
- 220 CONTINUE
- ELSE IF( LSAME( DIRECT, 'B' ) ) THEN
- DO 240 J = N - 1, 1, -1
- CTEMP = C( J )
- STEMP = S( J )
- IF( ( CTEMP.NE.ONE ) .OR. ( STEMP.NE.ZERO ) ) THEN
- DO 230 I = 1, M
- TEMP = A( I, J )
- A( I, J ) = STEMP*A( I, N ) + CTEMP*TEMP
- A( I, N ) = CTEMP*A( I, N ) - STEMP*TEMP
- 230 CONTINUE
- END IF
- 240 CONTINUE
- END IF
- END IF
- END IF
-*
- RETURN
-*
-* End of DLASR
-*
- END
diff --git a/src/lib/lapack/dlasrt.f b/src/lib/lapack/dlasrt.f
deleted file mode 100644
index 37e02178..00000000
--- a/src/lib/lapack/dlasrt.f
+++ /dev/null
@@ -1,243 +0,0 @@
- SUBROUTINE DLASRT( ID, N, D, INFO )
-*
-* -- LAPACK routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- CHARACTER ID
- INTEGER INFO, N
-* ..
-* .. Array Arguments ..
- DOUBLE PRECISION D( * )
-* ..
-*
-* Purpose
-* =======
-*
-* Sort the numbers in D in increasing order (if ID = 'I') or
-* in decreasing order (if ID = 'D' ).
-*
-* Use Quick Sort, reverting to Insertion sort on arrays of
-* size <= 20. Dimension of STACK limits N to about 2**32.
-*
-* Arguments
-* =========
-*
-* ID (input) CHARACTER*1
-* = 'I': sort D in increasing order;
-* = 'D': sort D in decreasing order.
-*
-* N (input) INTEGER
-* The length of the array D.
-*
-* D (input/output) DOUBLE PRECISION array, dimension (N)
-* On entry, the array to be sorted.
-* On exit, D has been sorted into increasing order
-* (D(1) <= ... <= D(N) ) or into decreasing order
-* (D(1) >= ... >= D(N) ), depending on ID.
-*
-* INFO (output) INTEGER
-* = 0: successful exit
-* < 0: if INFO = -i, the i-th argument had an illegal value
-*
-* =====================================================================
-*
-* .. Parameters ..
- INTEGER SELECT
- PARAMETER ( SELECT = 20 )
-* ..
-* .. Local Scalars ..
- INTEGER DIR, ENDD, I, J, START, STKPNT
- DOUBLE PRECISION D1, D2, D3, DMNMX, TMP
-* ..
-* .. Local Arrays ..
- INTEGER STACK( 2, 32 )
-* ..
-* .. External Functions ..
- LOGICAL LSAME
- EXTERNAL LSAME
-* ..
-* .. External Subroutines ..
- EXTERNAL XERBLA
-* ..
-* .. Executable Statements ..
-*
-* Test the input paramters.
-*
- INFO = 0
- DIR = -1
- IF( LSAME( ID, 'D' ) ) THEN
- DIR = 0
- ELSE IF( LSAME( ID, 'I' ) ) THEN
- DIR = 1
- END IF
- IF( DIR.EQ.-1 ) THEN
- INFO = -1
- ELSE IF( N.LT.0 ) THEN
- INFO = -2
- END IF
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'DLASRT', -INFO )
- RETURN
- END IF
-*
-* Quick return if possible
-*
- IF( N.LE.1 )
- $ RETURN
-*
- STKPNT = 1
- STACK( 1, 1 ) = 1
- STACK( 2, 1 ) = N
- 10 CONTINUE
- START = STACK( 1, STKPNT )
- ENDD = STACK( 2, STKPNT )
- STKPNT = STKPNT - 1
- IF( ENDD-START.LE.SELECT .AND. ENDD-START.GT.0 ) THEN
-*
-* Do Insertion sort on D( START:ENDD )
-*
- IF( DIR.EQ.0 ) THEN
-*
-* Sort into decreasing order
-*
- DO 30 I = START + 1, ENDD
- DO 20 J = I, START + 1, -1
- IF( D( J ).GT.D( J-1 ) ) THEN
- DMNMX = D( J )
- D( J ) = D( J-1 )
- D( J-1 ) = DMNMX
- ELSE
- GO TO 30
- END IF
- 20 CONTINUE
- 30 CONTINUE
-*
- ELSE
-*
-* Sort into increasing order
-*
- DO 50 I = START + 1, ENDD
- DO 40 J = I, START + 1, -1
- IF( D( J ).LT.D( J-1 ) ) THEN
- DMNMX = D( J )
- D( J ) = D( J-1 )
- D( J-1 ) = DMNMX
- ELSE
- GO TO 50
- END IF
- 40 CONTINUE
- 50 CONTINUE
-*
- END IF
-*
- ELSE IF( ENDD-START.GT.SELECT ) THEN
-*
-* Partition D( START:ENDD ) and stack parts, largest one first
-*
-* Choose partition entry as median of 3
-*
- D1 = D( START )
- D2 = D( ENDD )
- I = ( START+ENDD ) / 2
- D3 = D( I )
- IF( D1.LT.D2 ) THEN
- IF( D3.LT.D1 ) THEN
- DMNMX = D1
- ELSE IF( D3.LT.D2 ) THEN
- DMNMX = D3
- ELSE
- DMNMX = D2
- END IF
- ELSE
- IF( D3.LT.D2 ) THEN
- DMNMX = D2
- ELSE IF( D3.LT.D1 ) THEN
- DMNMX = D3
- ELSE
- DMNMX = D1
- END IF
- END IF
-*
- IF( DIR.EQ.0 ) THEN
-*
-* Sort into decreasing order
-*
- I = START - 1
- J = ENDD + 1
- 60 CONTINUE
- 70 CONTINUE
- J = J - 1
- IF( D( J ).LT.DMNMX )
- $ GO TO 70
- 80 CONTINUE
- I = I + 1
- IF( D( I ).GT.DMNMX )
- $ GO TO 80
- IF( I.LT.J ) THEN
- TMP = D( I )
- D( I ) = D( J )
- D( J ) = TMP
- GO TO 60
- END IF
- IF( J-START.GT.ENDD-J-1 ) THEN
- STKPNT = STKPNT + 1
- STACK( 1, STKPNT ) = START
- STACK( 2, STKPNT ) = J
- STKPNT = STKPNT + 1
- STACK( 1, STKPNT ) = J + 1
- STACK( 2, STKPNT ) = ENDD
- ELSE
- STKPNT = STKPNT + 1
- STACK( 1, STKPNT ) = J + 1
- STACK( 2, STKPNT ) = ENDD
- STKPNT = STKPNT + 1
- STACK( 1, STKPNT ) = START
- STACK( 2, STKPNT ) = J
- END IF
- ELSE
-*
-* Sort into increasing order
-*
- I = START - 1
- J = ENDD + 1
- 90 CONTINUE
- 100 CONTINUE
- J = J - 1
- IF( D( J ).GT.DMNMX )
- $ GO TO 100
- 110 CONTINUE
- I = I + 1
- IF( D( I ).LT.DMNMX )
- $ GO TO 110
- IF( I.LT.J ) THEN
- TMP = D( I )
- D( I ) = D( J )
- D( J ) = TMP
- GO TO 90
- END IF
- IF( J-START.GT.ENDD-J-1 ) THEN
- STKPNT = STKPNT + 1
- STACK( 1, STKPNT ) = START
- STACK( 2, STKPNT ) = J
- STKPNT = STKPNT + 1
- STACK( 1, STKPNT ) = J + 1
- STACK( 2, STKPNT ) = ENDD
- ELSE
- STKPNT = STKPNT + 1
- STACK( 1, STKPNT ) = J + 1
- STACK( 2, STKPNT ) = ENDD
- STKPNT = STKPNT + 1
- STACK( 1, STKPNT ) = START
- STACK( 2, STKPNT ) = J
- END IF
- END IF
- END IF
- IF( STKPNT.GT.0 )
- $ GO TO 10
- RETURN
-*
-* End of DLASRT
-*
- END
diff --git a/src/lib/lapack/dlassq.f b/src/lib/lapack/dlassq.f
deleted file mode 100644
index 217e794d..00000000
--- a/src/lib/lapack/dlassq.f
+++ /dev/null
@@ -1,88 +0,0 @@
- SUBROUTINE DLASSQ( N, X, INCX, SCALE, SUMSQ )
-*
-* -- LAPACK auxiliary routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- INTEGER INCX, N
- DOUBLE PRECISION SCALE, SUMSQ
-* ..
-* .. Array Arguments ..
- DOUBLE PRECISION X( * )
-* ..
-*
-* Purpose
-* =======
-*
-* DLASSQ returns the values scl and smsq such that
-*
-* ( scl**2 )*smsq = x( 1 )**2 +...+ x( n )**2 + ( scale**2 )*sumsq,
-*
-* where x( i ) = X( 1 + ( i - 1 )*INCX ). The value of sumsq is
-* assumed to be non-negative and scl returns the value
-*
-* scl = max( scale, abs( x( i ) ) ).
-*
-* scale and sumsq must be supplied in SCALE and SUMSQ and
-* scl and smsq are overwritten on SCALE and SUMSQ respectively.
-*
-* The routine makes only one pass through the vector x.
-*
-* Arguments
-* =========
-*
-* N (input) INTEGER
-* The number of elements to be used from the vector X.
-*
-* X (input) DOUBLE PRECISION array, dimension (N)
-* The vector for which a scaled sum of squares is computed.
-* x( i ) = X( 1 + ( i - 1 )*INCX ), 1 <= i <= n.
-*
-* INCX (input) INTEGER
-* The increment between successive values of the vector X.
-* INCX > 0.
-*
-* SCALE (input/output) DOUBLE PRECISION
-* On entry, the value scale in the equation above.
-* On exit, SCALE is overwritten with scl , the scaling factor
-* for the sum of squares.
-*
-* SUMSQ (input/output) DOUBLE PRECISION
-* On entry, the value sumsq in the equation above.
-* On exit, SUMSQ is overwritten with smsq , the basic sum of
-* squares from which scl has been factored out.
-*
-* =====================================================================
-*
-* .. Parameters ..
- DOUBLE PRECISION ZERO
- PARAMETER ( ZERO = 0.0D+0 )
-* ..
-* .. Local Scalars ..
- INTEGER IX
- DOUBLE PRECISION ABSXI
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC ABS
-* ..
-* .. Executable Statements ..
-*
- IF( N.GT.0 ) THEN
- DO 10 IX = 1, 1 + ( N-1 )*INCX, INCX
- IF( X( IX ).NE.ZERO ) THEN
- ABSXI = ABS( X( IX ) )
- IF( SCALE.LT.ABSXI ) THEN
- SUMSQ = 1 + SUMSQ*( SCALE / ABSXI )**2
- SCALE = ABSXI
- ELSE
- SUMSQ = SUMSQ + ( ABSXI / SCALE )**2
- END IF
- END IF
- 10 CONTINUE
- END IF
- RETURN
-*
-* End of DLASSQ
-*
- END
diff --git a/src/lib/lapack/dlasv2.f b/src/lib/lapack/dlasv2.f
deleted file mode 100644
index 4a00b25d..00000000
--- a/src/lib/lapack/dlasv2.f
+++ /dev/null
@@ -1,249 +0,0 @@
- SUBROUTINE DLASV2( F, G, H, SSMIN, SSMAX, SNR, CSR, SNL, CSL )
-*
-* -- LAPACK auxiliary routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- DOUBLE PRECISION CSL, CSR, F, G, H, SNL, SNR, SSMAX, SSMIN
-* ..
-*
-* Purpose
-* =======
-*
-* DLASV2 computes the singular value decomposition of a 2-by-2
-* triangular matrix
-* [ F G ]
-* [ 0 H ].
-* On return, abs(SSMAX) is the larger singular value, abs(SSMIN) is the
-* smaller singular value, and (CSL,SNL) and (CSR,SNR) are the left and
-* right singular vectors for abs(SSMAX), giving the decomposition
-*
-* [ CSL SNL ] [ F G ] [ CSR -SNR ] = [ SSMAX 0 ]
-* [-SNL CSL ] [ 0 H ] [ SNR CSR ] [ 0 SSMIN ].
-*
-* Arguments
-* =========
-*
-* F (input) DOUBLE PRECISION
-* The (1,1) element of the 2-by-2 matrix.
-*
-* G (input) DOUBLE PRECISION
-* The (1,2) element of the 2-by-2 matrix.
-*
-* H (input) DOUBLE PRECISION
-* The (2,2) element of the 2-by-2 matrix.
-*
-* SSMIN (output) DOUBLE PRECISION
-* abs(SSMIN) is the smaller singular value.
-*
-* SSMAX (output) DOUBLE PRECISION
-* abs(SSMAX) is the larger singular value.
-*
-* SNL (output) DOUBLE PRECISION
-* CSL (output) DOUBLE PRECISION
-* The vector (CSL, SNL) is a unit left singular vector for the
-* singular value abs(SSMAX).
-*
-* SNR (output) DOUBLE PRECISION
-* CSR (output) DOUBLE PRECISION
-* The vector (CSR, SNR) is a unit right singular vector for the
-* singular value abs(SSMAX).
-*
-* Further Details
-* ===============
-*
-* Any input parameter may be aliased with any output parameter.
-*
-* Barring over/underflow and assuming a guard digit in subtraction, all
-* output quantities are correct to within a few units in the last
-* place (ulps).
-*
-* In IEEE arithmetic, the code works correctly if one matrix element is
-* infinite.
-*
-* Overflow will not occur unless the largest singular value itself
-* overflows or is within a few ulps of overflow. (On machines with
-* partial overflow, like the Cray, overflow may occur if the largest
-* singular value is within a factor of 2 of overflow.)
-*
-* Underflow is harmless if underflow is gradual. Otherwise, results
-* may correspond to a matrix modified by perturbations of size near
-* the underflow threshold.
-*
-* =====================================================================
-*
-* .. Parameters ..
- DOUBLE PRECISION ZERO
- PARAMETER ( ZERO = 0.0D0 )
- DOUBLE PRECISION HALF
- PARAMETER ( HALF = 0.5D0 )
- DOUBLE PRECISION ONE
- PARAMETER ( ONE = 1.0D0 )
- DOUBLE PRECISION TWO
- PARAMETER ( TWO = 2.0D0 )
- DOUBLE PRECISION FOUR
- PARAMETER ( FOUR = 4.0D0 )
-* ..
-* .. Local Scalars ..
- LOGICAL GASMAL, SWAP
- INTEGER PMAX
- DOUBLE PRECISION A, CLT, CRT, D, FA, FT, GA, GT, HA, HT, L, M,
- $ MM, R, S, SLT, SRT, T, TEMP, TSIGN, TT
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC ABS, SIGN, SQRT
-* ..
-* .. External Functions ..
- DOUBLE PRECISION DLAMCH
- EXTERNAL DLAMCH
-* ..
-* .. Executable Statements ..
-*
- FT = F
- FA = ABS( FT )
- HT = H
- HA = ABS( H )
-*
-* PMAX points to the maximum absolute element of matrix
-* PMAX = 1 if F largest in absolute values
-* PMAX = 2 if G largest in absolute values
-* PMAX = 3 if H largest in absolute values
-*
- PMAX = 1
- SWAP = ( HA.GT.FA )
- IF( SWAP ) THEN
- PMAX = 3
- TEMP = FT
- FT = HT
- HT = TEMP
- TEMP = FA
- FA = HA
- HA = TEMP
-*
-* Now FA .ge. HA
-*
- END IF
- GT = G
- GA = ABS( GT )
- IF( GA.EQ.ZERO ) THEN
-*
-* Diagonal matrix
-*
- SSMIN = HA
- SSMAX = FA
- CLT = ONE
- CRT = ONE
- SLT = ZERO
- SRT = ZERO
- ELSE
- GASMAL = .TRUE.
- IF( GA.GT.FA ) THEN
- PMAX = 2
- IF( ( FA / GA ).LT.DLAMCH( 'EPS' ) ) THEN
-*
-* Case of very large GA
-*
- GASMAL = .FALSE.
- SSMAX = GA
- IF( HA.GT.ONE ) THEN
- SSMIN = FA / ( GA / HA )
- ELSE
- SSMIN = ( FA / GA )*HA
- END IF
- CLT = ONE
- SLT = HT / GT
- SRT = ONE
- CRT = FT / GT
- END IF
- END IF
- IF( GASMAL ) THEN
-*
-* Normal case
-*
- D = FA - HA
- IF( D.EQ.FA ) THEN
-*
-* Copes with infinite F or H
-*
- L = ONE
- ELSE
- L = D / FA
- END IF
-*
-* Note that 0 .le. L .le. 1
-*
- M = GT / FT
-*
-* Note that abs(M) .le. 1/macheps
-*
- T = TWO - L
-*
-* Note that T .ge. 1
-*
- MM = M*M
- TT = T*T
- S = SQRT( TT+MM )
-*
-* Note that 1 .le. S .le. 1 + 1/macheps
-*
- IF( L.EQ.ZERO ) THEN
- R = ABS( M )
- ELSE
- R = SQRT( L*L+MM )
- END IF
-*
-* Note that 0 .le. R .le. 1 + 1/macheps
-*
- A = HALF*( S+R )
-*
-* Note that 1 .le. A .le. 1 + abs(M)
-*
- SSMIN = HA / A
- SSMAX = FA*A
- IF( MM.EQ.ZERO ) THEN
-*
-* Note that M is very tiny
-*
- IF( L.EQ.ZERO ) THEN
- T = SIGN( TWO, FT )*SIGN( ONE, GT )
- ELSE
- T = GT / SIGN( D, FT ) + M / T
- END IF
- ELSE
- T = ( M / ( S+T )+M / ( R+L ) )*( ONE+A )
- END IF
- L = SQRT( T*T+FOUR )
- CRT = TWO / L
- SRT = T / L
- CLT = ( CRT+SRT*M ) / A
- SLT = ( HT / FT )*SRT / A
- END IF
- END IF
- IF( SWAP ) THEN
- CSL = SRT
- SNL = CRT
- CSR = SLT
- SNR = CLT
- ELSE
- CSL = CLT
- SNL = SLT
- CSR = CRT
- SNR = SRT
- END IF
-*
-* Correct signs of SSMAX and SSMIN
-*
- IF( PMAX.EQ.1 )
- $ TSIGN = SIGN( ONE, CSR )*SIGN( ONE, CSL )*SIGN( ONE, F )
- IF( PMAX.EQ.2 )
- $ TSIGN = SIGN( ONE, SNR )*SIGN( ONE, CSL )*SIGN( ONE, G )
- IF( PMAX.EQ.3 )
- $ TSIGN = SIGN( ONE, SNR )*SIGN( ONE, SNL )*SIGN( ONE, H )
- SSMAX = SIGN( SSMAX, TSIGN )
- SSMIN = SIGN( SSMIN, TSIGN*SIGN( ONE, F )*SIGN( ONE, H ) )
- RETURN
-*
-* End of DLASV2
-*
- END
diff --git a/src/lib/lapack/dlaswp.f b/src/lib/lapack/dlaswp.f
deleted file mode 100644
index a11a87e9..00000000
--- a/src/lib/lapack/dlaswp.f
+++ /dev/null
@@ -1,119 +0,0 @@
- SUBROUTINE DLASWP( N, A, LDA, K1, K2, IPIV, INCX )
-*
-* -- LAPACK auxiliary routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- INTEGER INCX, K1, K2, LDA, N
-* ..
-* .. Array Arguments ..
- INTEGER IPIV( * )
- DOUBLE PRECISION A( LDA, * )
-* ..
-*
-* Purpose
-* =======
-*
-* DLASWP performs a series of row interchanges on the matrix A.
-* One row interchange is initiated for each of rows K1 through K2 of A.
-*
-* Arguments
-* =========
-*
-* N (input) INTEGER
-* The number of columns of the matrix A.
-*
-* A (input/output) DOUBLE PRECISION array, dimension (LDA,N)
-* On entry, the matrix of column dimension N to which the row
-* interchanges will be applied.
-* On exit, the permuted matrix.
-*
-* LDA (input) INTEGER
-* The leading dimension of the array A.
-*
-* K1 (input) INTEGER
-* The first element of IPIV for which a row interchange will
-* be done.
-*
-* K2 (input) INTEGER
-* The last element of IPIV for which a row interchange will
-* be done.
-*
-* IPIV (input) INTEGER array, dimension (K2*abs(INCX))
-* The vector of pivot indices. Only the elements in positions
-* K1 through K2 of IPIV are accessed.
-* IPIV(K) = L implies rows K and L are to be interchanged.
-*
-* INCX (input) INTEGER
-* The increment between successive values of IPIV. If IPIV
-* is negative, the pivots are applied in reverse order.
-*
-* Further Details
-* ===============
-*
-* Modified by
-* R. C. Whaley, Computer Science Dept., Univ. of Tenn., Knoxville, USA
-*
-* =====================================================================
-*
-* .. Local Scalars ..
- INTEGER I, I1, I2, INC, IP, IX, IX0, J, K, N32
- DOUBLE PRECISION TEMP
-* ..
-* .. Executable Statements ..
-*
-* Interchange row I with row IPIV(I) for each of rows K1 through K2.
-*
- IF( INCX.GT.0 ) THEN
- IX0 = K1
- I1 = K1
- I2 = K2
- INC = 1
- ELSE IF( INCX.LT.0 ) THEN
- IX0 = 1 + ( 1-K2 )*INCX
- I1 = K2
- I2 = K1
- INC = -1
- ELSE
- RETURN
- END IF
-*
- N32 = ( N / 32 )*32
- IF( N32.NE.0 ) THEN
- DO 30 J = 1, N32, 32
- IX = IX0
- DO 20 I = I1, I2, INC
- IP = IPIV( IX )
- IF( IP.NE.I ) THEN
- DO 10 K = J, J + 31
- TEMP = A( I, K )
- A( I, K ) = A( IP, K )
- A( IP, K ) = TEMP
- 10 CONTINUE
- END IF
- IX = IX + INCX
- 20 CONTINUE
- 30 CONTINUE
- END IF
- IF( N32.NE.N ) THEN
- N32 = N32 + 1
- IX = IX0
- DO 50 I = I1, I2, INC
- IP = IPIV( IX )
- IF( IP.NE.I ) THEN
- DO 40 K = N32, N
- TEMP = A( I, K )
- A( I, K ) = A( IP, K )
- A( IP, K ) = TEMP
- 40 CONTINUE
- END IF
- IX = IX + INCX
- 50 CONTINUE
- END IF
-*
- RETURN
-*
-* End of DLASWP
-*
- END
diff --git a/src/lib/lapack/dlasy2.f b/src/lib/lapack/dlasy2.f
deleted file mode 100644
index 3ff12070..00000000
--- a/src/lib/lapack/dlasy2.f
+++ /dev/null
@@ -1,381 +0,0 @@
- SUBROUTINE DLASY2( LTRANL, LTRANR, ISGN, N1, N2, TL, LDTL, TR,
- $ LDTR, B, LDB, SCALE, X, LDX, XNORM, INFO )
-*
-* -- LAPACK auxiliary routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- LOGICAL LTRANL, LTRANR
- INTEGER INFO, ISGN, LDB, LDTL, LDTR, LDX, N1, N2
- DOUBLE PRECISION SCALE, XNORM
-* ..
-* .. Array Arguments ..
- DOUBLE PRECISION B( LDB, * ), TL( LDTL, * ), TR( LDTR, * ),
- $ X( LDX, * )
-* ..
-*
-* Purpose
-* =======
-*
-* DLASY2 solves for the N1 by N2 matrix X, 1 <= N1,N2 <= 2, in
-*
-* op(TL)*X + ISGN*X*op(TR) = SCALE*B,
-*
-* where TL is N1 by N1, TR is N2 by N2, B is N1 by N2, and ISGN = 1 or
-* -1. op(T) = T or T', where T' denotes the transpose of T.
-*
-* Arguments
-* =========
-*
-* LTRANL (input) LOGICAL
-* On entry, LTRANL specifies the op(TL):
-* = .FALSE., op(TL) = TL,
-* = .TRUE., op(TL) = TL'.
-*
-* LTRANR (input) LOGICAL
-* On entry, LTRANR specifies the op(TR):
-* = .FALSE., op(TR) = TR,
-* = .TRUE., op(TR) = TR'.
-*
-* ISGN (input) INTEGER
-* On entry, ISGN specifies the sign of the equation
-* as described before. ISGN may only be 1 or -1.
-*
-* N1 (input) INTEGER
-* On entry, N1 specifies the order of matrix TL.
-* N1 may only be 0, 1 or 2.
-*
-* N2 (input) INTEGER
-* On entry, N2 specifies the order of matrix TR.
-* N2 may only be 0, 1 or 2.
-*
-* TL (input) DOUBLE PRECISION array, dimension (LDTL,2)
-* On entry, TL contains an N1 by N1 matrix.
-*
-* LDTL (input) INTEGER
-* The leading dimension of the matrix TL. LDTL >= max(1,N1).
-*
-* TR (input) DOUBLE PRECISION array, dimension (LDTR,2)
-* On entry, TR contains an N2 by N2 matrix.
-*
-* LDTR (input) INTEGER
-* The leading dimension of the matrix TR. LDTR >= max(1,N2).
-*
-* B (input) DOUBLE PRECISION array, dimension (LDB,2)
-* On entry, the N1 by N2 matrix B contains the right-hand
-* side of the equation.
-*
-* LDB (input) INTEGER
-* The leading dimension of the matrix B. LDB >= max(1,N1).
-*
-* SCALE (output) DOUBLE PRECISION
-* On exit, SCALE contains the scale factor. SCALE is chosen
-* less than or equal to 1 to prevent the solution overflowing.
-*
-* X (output) DOUBLE PRECISION array, dimension (LDX,2)
-* On exit, X contains the N1 by N2 solution.
-*
-* LDX (input) INTEGER
-* The leading dimension of the matrix X. LDX >= max(1,N1).
-*
-* XNORM (output) DOUBLE PRECISION
-* On exit, XNORM is the infinity-norm of the solution.
-*
-* INFO (output) INTEGER
-* On exit, INFO is set to
-* 0: successful exit.
-* 1: TL and TR have too close eigenvalues, so TL or
-* TR is perturbed to get a nonsingular equation.
-* NOTE: In the interests of speed, this routine does not
-* check the inputs for errors.
-*
-* =====================================================================
-*
-* .. Parameters ..
- DOUBLE PRECISION ZERO, ONE
- PARAMETER ( ZERO = 0.0D+0, ONE = 1.0D+0 )
- DOUBLE PRECISION TWO, HALF, EIGHT
- PARAMETER ( TWO = 2.0D+0, HALF = 0.5D+0, EIGHT = 8.0D+0 )
-* ..
-* .. Local Scalars ..
- LOGICAL BSWAP, XSWAP
- INTEGER I, IP, IPIV, IPSV, J, JP, JPSV, K
- DOUBLE PRECISION BET, EPS, GAM, L21, SGN, SMIN, SMLNUM, TAU1,
- $ TEMP, U11, U12, U22, XMAX
-* ..
-* .. Local Arrays ..
- LOGICAL BSWPIV( 4 ), XSWPIV( 4 )
- INTEGER JPIV( 4 ), LOCL21( 4 ), LOCU12( 4 ),
- $ LOCU22( 4 )
- DOUBLE PRECISION BTMP( 4 ), T16( 4, 4 ), TMP( 4 ), X2( 2 )
-* ..
-* .. External Functions ..
- INTEGER IDAMAX
- DOUBLE PRECISION DLAMCH
- EXTERNAL IDAMAX, DLAMCH
-* ..
-* .. External Subroutines ..
- EXTERNAL DCOPY, DSWAP
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC ABS, MAX
-* ..
-* .. Data statements ..
- DATA LOCU12 / 3, 4, 1, 2 / , LOCL21 / 2, 1, 4, 3 / ,
- $ LOCU22 / 4, 3, 2, 1 /
- DATA XSWPIV / .FALSE., .FALSE., .TRUE., .TRUE. /
- DATA BSWPIV / .FALSE., .TRUE., .FALSE., .TRUE. /
-* ..
-* .. Executable Statements ..
-*
-* Do not check the input parameters for errors
-*
- INFO = 0
-*
-* Quick return if possible
-*
- IF( N1.EQ.0 .OR. N2.EQ.0 )
- $ RETURN
-*
-* Set constants to control overflow
-*
- EPS = DLAMCH( 'P' )
- SMLNUM = DLAMCH( 'S' ) / EPS
- SGN = ISGN
-*
- K = N1 + N1 + N2 - 2
- GO TO ( 10, 20, 30, 50 )K
-*
-* 1 by 1: TL11*X + SGN*X*TR11 = B11
-*
- 10 CONTINUE
- TAU1 = TL( 1, 1 ) + SGN*TR( 1, 1 )
- BET = ABS( TAU1 )
- IF( BET.LE.SMLNUM ) THEN
- TAU1 = SMLNUM
- BET = SMLNUM
- INFO = 1
- END IF
-*
- SCALE = ONE
- GAM = ABS( B( 1, 1 ) )
- IF( SMLNUM*GAM.GT.BET )
- $ SCALE = ONE / GAM
-*
- X( 1, 1 ) = ( B( 1, 1 )*SCALE ) / TAU1
- XNORM = ABS( X( 1, 1 ) )
- RETURN
-*
-* 1 by 2:
-* TL11*[X11 X12] + ISGN*[X11 X12]*op[TR11 TR12] = [B11 B12]
-* [TR21 TR22]
-*
- 20 CONTINUE
-*
- SMIN = MAX( EPS*MAX( ABS( TL( 1, 1 ) ), ABS( TR( 1, 1 ) ),
- $ ABS( TR( 1, 2 ) ), ABS( TR( 2, 1 ) ), ABS( TR( 2, 2 ) ) ),
- $ SMLNUM )
- TMP( 1 ) = TL( 1, 1 ) + SGN*TR( 1, 1 )
- TMP( 4 ) = TL( 1, 1 ) + SGN*TR( 2, 2 )
- IF( LTRANR ) THEN
- TMP( 2 ) = SGN*TR( 2, 1 )
- TMP( 3 ) = SGN*TR( 1, 2 )
- ELSE
- TMP( 2 ) = SGN*TR( 1, 2 )
- TMP( 3 ) = SGN*TR( 2, 1 )
- END IF
- BTMP( 1 ) = B( 1, 1 )
- BTMP( 2 ) = B( 1, 2 )
- GO TO 40
-*
-* 2 by 1:
-* op[TL11 TL12]*[X11] + ISGN* [X11]*TR11 = [B11]
-* [TL21 TL22] [X21] [X21] [B21]
-*
- 30 CONTINUE
- SMIN = MAX( EPS*MAX( ABS( TR( 1, 1 ) ), ABS( TL( 1, 1 ) ),
- $ ABS( TL( 1, 2 ) ), ABS( TL( 2, 1 ) ), ABS( TL( 2, 2 ) ) ),
- $ SMLNUM )
- TMP( 1 ) = TL( 1, 1 ) + SGN*TR( 1, 1 )
- TMP( 4 ) = TL( 2, 2 ) + SGN*TR( 1, 1 )
- IF( LTRANL ) THEN
- TMP( 2 ) = TL( 1, 2 )
- TMP( 3 ) = TL( 2, 1 )
- ELSE
- TMP( 2 ) = TL( 2, 1 )
- TMP( 3 ) = TL( 1, 2 )
- END IF
- BTMP( 1 ) = B( 1, 1 )
- BTMP( 2 ) = B( 2, 1 )
- 40 CONTINUE
-*
-* Solve 2 by 2 system using complete pivoting.
-* Set pivots less than SMIN to SMIN.
-*
- IPIV = IDAMAX( 4, TMP, 1 )
- U11 = TMP( IPIV )
- IF( ABS( U11 ).LE.SMIN ) THEN
- INFO = 1
- U11 = SMIN
- END IF
- U12 = TMP( LOCU12( IPIV ) )
- L21 = TMP( LOCL21( IPIV ) ) / U11
- U22 = TMP( LOCU22( IPIV ) ) - U12*L21
- XSWAP = XSWPIV( IPIV )
- BSWAP = BSWPIV( IPIV )
- IF( ABS( U22 ).LE.SMIN ) THEN
- INFO = 1
- U22 = SMIN
- END IF
- IF( BSWAP ) THEN
- TEMP = BTMP( 2 )
- BTMP( 2 ) = BTMP( 1 ) - L21*TEMP
- BTMP( 1 ) = TEMP
- ELSE
- BTMP( 2 ) = BTMP( 2 ) - L21*BTMP( 1 )
- END IF
- SCALE = ONE
- IF( ( TWO*SMLNUM )*ABS( BTMP( 2 ) ).GT.ABS( U22 ) .OR.
- $ ( TWO*SMLNUM )*ABS( BTMP( 1 ) ).GT.ABS( U11 ) ) THEN
- SCALE = HALF / MAX( ABS( BTMP( 1 ) ), ABS( BTMP( 2 ) ) )
- BTMP( 1 ) = BTMP( 1 )*SCALE
- BTMP( 2 ) = BTMP( 2 )*SCALE
- END IF
- X2( 2 ) = BTMP( 2 ) / U22
- X2( 1 ) = BTMP( 1 ) / U11 - ( U12 / U11 )*X2( 2 )
- IF( XSWAP ) THEN
- TEMP = X2( 2 )
- X2( 2 ) = X2( 1 )
- X2( 1 ) = TEMP
- END IF
- X( 1, 1 ) = X2( 1 )
- IF( N1.EQ.1 ) THEN
- X( 1, 2 ) = X2( 2 )
- XNORM = ABS( X( 1, 1 ) ) + ABS( X( 1, 2 ) )
- ELSE
- X( 2, 1 ) = X2( 2 )
- XNORM = MAX( ABS( X( 1, 1 ) ), ABS( X( 2, 1 ) ) )
- END IF
- RETURN
-*
-* 2 by 2:
-* op[TL11 TL12]*[X11 X12] +ISGN* [X11 X12]*op[TR11 TR12] = [B11 B12]
-* [TL21 TL22] [X21 X22] [X21 X22] [TR21 TR22] [B21 B22]
-*
-* Solve equivalent 4 by 4 system using complete pivoting.
-* Set pivots less than SMIN to SMIN.
-*
- 50 CONTINUE
- SMIN = MAX( ABS( TR( 1, 1 ) ), ABS( TR( 1, 2 ) ),
- $ ABS( TR( 2, 1 ) ), ABS( TR( 2, 2 ) ) )
- SMIN = MAX( SMIN, ABS( TL( 1, 1 ) ), ABS( TL( 1, 2 ) ),
- $ ABS( TL( 2, 1 ) ), ABS( TL( 2, 2 ) ) )
- SMIN = MAX( EPS*SMIN, SMLNUM )
- BTMP( 1 ) = ZERO
- CALL DCOPY( 16, BTMP, 0, T16, 1 )
- T16( 1, 1 ) = TL( 1, 1 ) + SGN*TR( 1, 1 )
- T16( 2, 2 ) = TL( 2, 2 ) + SGN*TR( 1, 1 )
- T16( 3, 3 ) = TL( 1, 1 ) + SGN*TR( 2, 2 )
- T16( 4, 4 ) = TL( 2, 2 ) + SGN*TR( 2, 2 )
- IF( LTRANL ) THEN
- T16( 1, 2 ) = TL( 2, 1 )
- T16( 2, 1 ) = TL( 1, 2 )
- T16( 3, 4 ) = TL( 2, 1 )
- T16( 4, 3 ) = TL( 1, 2 )
- ELSE
- T16( 1, 2 ) = TL( 1, 2 )
- T16( 2, 1 ) = TL( 2, 1 )
- T16( 3, 4 ) = TL( 1, 2 )
- T16( 4, 3 ) = TL( 2, 1 )
- END IF
- IF( LTRANR ) THEN
- T16( 1, 3 ) = SGN*TR( 1, 2 )
- T16( 2, 4 ) = SGN*TR( 1, 2 )
- T16( 3, 1 ) = SGN*TR( 2, 1 )
- T16( 4, 2 ) = SGN*TR( 2, 1 )
- ELSE
- T16( 1, 3 ) = SGN*TR( 2, 1 )
- T16( 2, 4 ) = SGN*TR( 2, 1 )
- T16( 3, 1 ) = SGN*TR( 1, 2 )
- T16( 4, 2 ) = SGN*TR( 1, 2 )
- END IF
- BTMP( 1 ) = B( 1, 1 )
- BTMP( 2 ) = B( 2, 1 )
- BTMP( 3 ) = B( 1, 2 )
- BTMP( 4 ) = B( 2, 2 )
-*
-* Perform elimination
-*
- DO 100 I = 1, 3
- XMAX = ZERO
- DO 70 IP = I, 4
- DO 60 JP = I, 4
- IF( ABS( T16( IP, JP ) ).GE.XMAX ) THEN
- XMAX = ABS( T16( IP, JP ) )
- IPSV = IP
- JPSV = JP
- END IF
- 60 CONTINUE
- 70 CONTINUE
- IF( IPSV.NE.I ) THEN
- CALL DSWAP( 4, T16( IPSV, 1 ), 4, T16( I, 1 ), 4 )
- TEMP = BTMP( I )
- BTMP( I ) = BTMP( IPSV )
- BTMP( IPSV ) = TEMP
- END IF
- IF( JPSV.NE.I )
- $ CALL DSWAP( 4, T16( 1, JPSV ), 1, T16( 1, I ), 1 )
- JPIV( I ) = JPSV
- IF( ABS( T16( I, I ) ).LT.SMIN ) THEN
- INFO = 1
- T16( I, I ) = SMIN
- END IF
- DO 90 J = I + 1, 4
- T16( J, I ) = T16( J, I ) / T16( I, I )
- BTMP( J ) = BTMP( J ) - T16( J, I )*BTMP( I )
- DO 80 K = I + 1, 4
- T16( J, K ) = T16( J, K ) - T16( J, I )*T16( I, K )
- 80 CONTINUE
- 90 CONTINUE
- 100 CONTINUE
- IF( ABS( T16( 4, 4 ) ).LT.SMIN )
- $ T16( 4, 4 ) = SMIN
- SCALE = ONE
- IF( ( EIGHT*SMLNUM )*ABS( BTMP( 1 ) ).GT.ABS( T16( 1, 1 ) ) .OR.
- $ ( EIGHT*SMLNUM )*ABS( BTMP( 2 ) ).GT.ABS( T16( 2, 2 ) ) .OR.
- $ ( EIGHT*SMLNUM )*ABS( BTMP( 3 ) ).GT.ABS( T16( 3, 3 ) ) .OR.
- $ ( EIGHT*SMLNUM )*ABS( BTMP( 4 ) ).GT.ABS( T16( 4, 4 ) ) ) THEN
- SCALE = ( ONE / EIGHT ) / MAX( ABS( BTMP( 1 ) ),
- $ ABS( BTMP( 2 ) ), ABS( BTMP( 3 ) ), ABS( BTMP( 4 ) ) )
- BTMP( 1 ) = BTMP( 1 )*SCALE
- BTMP( 2 ) = BTMP( 2 )*SCALE
- BTMP( 3 ) = BTMP( 3 )*SCALE
- BTMP( 4 ) = BTMP( 4 )*SCALE
- END IF
- DO 120 I = 1, 4
- K = 5 - I
- TEMP = ONE / T16( K, K )
- TMP( K ) = BTMP( K )*TEMP
- DO 110 J = K + 1, 4
- TMP( K ) = TMP( K ) - ( TEMP*T16( K, J ) )*TMP( J )
- 110 CONTINUE
- 120 CONTINUE
- DO 130 I = 1, 3
- IF( JPIV( 4-I ).NE.4-I ) THEN
- TEMP = TMP( 4-I )
- TMP( 4-I ) = TMP( JPIV( 4-I ) )
- TMP( JPIV( 4-I ) ) = TEMP
- END IF
- 130 CONTINUE
- X( 1, 1 ) = TMP( 1 )
- X( 2, 1 ) = TMP( 2 )
- X( 1, 2 ) = TMP( 3 )
- X( 2, 2 ) = TMP( 4 )
- XNORM = MAX( ABS( TMP( 1 ) )+ABS( TMP( 3 ) ),
- $ ABS( TMP( 2 ) )+ABS( TMP( 4 ) ) )
- RETURN
-*
-* End of DLASY2
-*
- END
diff --git a/src/lib/lapack/dlasyf.f b/src/lib/lapack/dlasyf.f
deleted file mode 100644
index 67b9c147..00000000
--- a/src/lib/lapack/dlasyf.f
+++ /dev/null
@@ -1,587 +0,0 @@
- SUBROUTINE DLASYF( UPLO, N, NB, KB, A, LDA, IPIV, W, LDW, INFO )
-*
-* -- LAPACK routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- CHARACTER UPLO
- INTEGER INFO, KB, LDA, LDW, N, NB
-* ..
-* .. Array Arguments ..
- INTEGER IPIV( * )
- DOUBLE PRECISION A( LDA, * ), W( LDW, * )
-* ..
-*
-* Purpose
-* =======
-*
-* DLASYF computes a partial factorization of a real symmetric matrix A
-* using the Bunch-Kaufman diagonal pivoting method. The partial
-* factorization has the form:
-*
-* A = ( I U12 ) ( A11 0 ) ( I 0 ) if UPLO = 'U', or:
-* ( 0 U22 ) ( 0 D ) ( U12' U22' )
-*
-* A = ( L11 0 ) ( D 0 ) ( L11' L21' ) if UPLO = 'L'
-* ( L21 I ) ( 0 A22 ) ( 0 I )
-*
-* where the order of D is at most NB. The actual order is returned in
-* the argument KB, and is either NB or NB-1, or N if N <= NB.
-*
-* DLASYF is an auxiliary routine called by DSYTRF. It uses blocked code
-* (calling Level 3 BLAS) to update the submatrix A11 (if UPLO = 'U') or
-* A22 (if UPLO = 'L').
-*
-* Arguments
-* =========
-*
-* UPLO (input) CHARACTER*1
-* Specifies whether the upper or lower triangular part of the
-* symmetric matrix A is stored:
-* = 'U': Upper triangular
-* = 'L': Lower triangular
-*
-* N (input) INTEGER
-* The order of the matrix A. N >= 0.
-*
-* NB (input) INTEGER
-* The maximum number of columns of the matrix A that should be
-* factored. NB should be at least 2 to allow for 2-by-2 pivot
-* blocks.
-*
-* KB (output) INTEGER
-* The number of columns of A that were actually factored.
-* KB is either NB-1 or NB, or N if N <= NB.
-*
-* A (input/output) DOUBLE PRECISION array, dimension (LDA,N)
-* On entry, the symmetric matrix A. If UPLO = 'U', the leading
-* n-by-n upper triangular part of A contains the upper
-* triangular part of the matrix A, and the strictly lower
-* triangular part of A is not referenced. If UPLO = 'L', the
-* leading n-by-n lower triangular part of A contains the lower
-* triangular part of the matrix A, and the strictly upper
-* triangular part of A is not referenced.
-* On exit, A contains details of the partial factorization.
-*
-* LDA (input) INTEGER
-* The leading dimension of the array A. LDA >= max(1,N).
-*
-* IPIV (output) INTEGER array, dimension (N)
-* Details of the interchanges and the block structure of D.
-* If UPLO = 'U', only the last KB elements of IPIV are set;
-* if UPLO = 'L', only the first KB elements are set.
-*
-* If IPIV(k) > 0, then rows and columns k and IPIV(k) were
-* interchanged and D(k,k) is a 1-by-1 diagonal block.
-* If UPLO = 'U' and IPIV(k) = IPIV(k-1) < 0, then rows and
-* columns k-1 and -IPIV(k) were interchanged and D(k-1:k,k-1:k)
-* is a 2-by-2 diagonal block. If UPLO = 'L' and IPIV(k) =
-* IPIV(k+1) < 0, then rows and columns k+1 and -IPIV(k) were
-* interchanged and D(k:k+1,k:k+1) is a 2-by-2 diagonal block.
-*
-* W (workspace) DOUBLE PRECISION array, dimension (LDW,NB)
-*
-* LDW (input) INTEGER
-* The leading dimension of the array W. LDW >= max(1,N).
-*
-* INFO (output) INTEGER
-* = 0: successful exit
-* > 0: if INFO = k, D(k,k) is exactly zero. The factorization
-* has been completed, but the block diagonal matrix D is
-* exactly singular.
-*
-* =====================================================================
-*
-* .. Parameters ..
- DOUBLE PRECISION ZERO, ONE
- PARAMETER ( ZERO = 0.0D+0, ONE = 1.0D+0 )
- DOUBLE PRECISION EIGHT, SEVTEN
- PARAMETER ( EIGHT = 8.0D+0, SEVTEN = 17.0D+0 )
-* ..
-* .. Local Scalars ..
- INTEGER IMAX, J, JB, JJ, JMAX, JP, K, KK, KKW, KP,
- $ KSTEP, KW
- DOUBLE PRECISION ABSAKK, ALPHA, COLMAX, D11, D21, D22, R1,
- $ ROWMAX, T
-* ..
-* .. External Functions ..
- LOGICAL LSAME
- INTEGER IDAMAX
- EXTERNAL LSAME, IDAMAX
-* ..
-* .. External Subroutines ..
- EXTERNAL DCOPY, DGEMM, DGEMV, DSCAL, DSWAP
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC ABS, MAX, MIN, SQRT
-* ..
-* .. Executable Statements ..
-*
- INFO = 0
-*
-* Initialize ALPHA for use in choosing pivot block size.
-*
- ALPHA = ( ONE+SQRT( SEVTEN ) ) / EIGHT
-*
- IF( LSAME( UPLO, 'U' ) ) THEN
-*
-* Factorize the trailing columns of A using the upper triangle
-* of A and working backwards, and compute the matrix W = U12*D
-* for use in updating A11
-*
-* K is the main loop index, decreasing from N in steps of 1 or 2
-*
-* KW is the column of W which corresponds to column K of A
-*
- K = N
- 10 CONTINUE
- KW = NB + K - N
-*
-* Exit from loop
-*
- IF( ( K.LE.N-NB+1 .AND. NB.LT.N ) .OR. K.LT.1 )
- $ GO TO 30
-*
-* Copy column K of A to column KW of W and update it
-*
- CALL DCOPY( K, A( 1, K ), 1, W( 1, KW ), 1 )
- IF( K.LT.N )
- $ CALL DGEMV( 'No transpose', K, N-K, -ONE, A( 1, K+1 ), LDA,
- $ W( K, KW+1 ), LDW, ONE, W( 1, KW ), 1 )
-*
- KSTEP = 1
-*
-* Determine rows and columns to be interchanged and whether
-* a 1-by-1 or 2-by-2 pivot block will be used
-*
- ABSAKK = ABS( W( K, KW ) )
-*
-* IMAX is the row-index of the largest off-diagonal element in
-* column K, and COLMAX is its absolute value
-*
- IF( K.GT.1 ) THEN
- IMAX = IDAMAX( K-1, W( 1, KW ), 1 )
- COLMAX = ABS( W( IMAX, KW ) )
- ELSE
- COLMAX = ZERO
- END IF
-*
- IF( MAX( ABSAKK, COLMAX ).EQ.ZERO ) THEN
-*
-* Column K is zero: set INFO and continue
-*
- IF( INFO.EQ.0 )
- $ INFO = K
- KP = K
- ELSE
- IF( ABSAKK.GE.ALPHA*COLMAX ) THEN
-*
-* no interchange, use 1-by-1 pivot block
-*
- KP = K
- ELSE
-*
-* Copy column IMAX to column KW-1 of W and update it
-*
- CALL DCOPY( IMAX, A( 1, IMAX ), 1, W( 1, KW-1 ), 1 )
- CALL DCOPY( K-IMAX, A( IMAX, IMAX+1 ), LDA,
- $ W( IMAX+1, KW-1 ), 1 )
- IF( K.LT.N )
- $ CALL DGEMV( 'No transpose', K, N-K, -ONE, A( 1, K+1 ),
- $ LDA, W( IMAX, KW+1 ), LDW, ONE,
- $ W( 1, KW-1 ), 1 )
-*
-* JMAX is the column-index of the largest off-diagonal
-* element in row IMAX, and ROWMAX is its absolute value
-*
- JMAX = IMAX + IDAMAX( K-IMAX, W( IMAX+1, KW-1 ), 1 )
- ROWMAX = ABS( W( JMAX, KW-1 ) )
- IF( IMAX.GT.1 ) THEN
- JMAX = IDAMAX( IMAX-1, W( 1, KW-1 ), 1 )
- ROWMAX = MAX( ROWMAX, ABS( W( JMAX, KW-1 ) ) )
- END IF
-*
- IF( ABSAKK.GE.ALPHA*COLMAX*( COLMAX / ROWMAX ) ) THEN
-*
-* no interchange, use 1-by-1 pivot block
-*
- KP = K
- ELSE IF( ABS( W( IMAX, KW-1 ) ).GE.ALPHA*ROWMAX ) THEN
-*
-* interchange rows and columns K and IMAX, use 1-by-1
-* pivot block
-*
- KP = IMAX
-*
-* copy column KW-1 of W to column KW
-*
- CALL DCOPY( K, W( 1, KW-1 ), 1, W( 1, KW ), 1 )
- ELSE
-*
-* interchange rows and columns K-1 and IMAX, use 2-by-2
-* pivot block
-*
- KP = IMAX
- KSTEP = 2
- END IF
- END IF
-*
- KK = K - KSTEP + 1
- KKW = NB + KK - N
-*
-* Updated column KP is already stored in column KKW of W
-*
- IF( KP.NE.KK ) THEN
-*
-* Copy non-updated column KK to column KP
-*
- A( KP, K ) = A( KK, K )
- CALL DCOPY( K-1-KP, A( KP+1, KK ), 1, A( KP, KP+1 ),
- $ LDA )
- CALL DCOPY( KP, A( 1, KK ), 1, A( 1, KP ), 1 )
-*
-* Interchange rows KK and KP in last KK columns of A and W
-*
- CALL DSWAP( N-KK+1, A( KK, KK ), LDA, A( KP, KK ), LDA )
- CALL DSWAP( N-KK+1, W( KK, KKW ), LDW, W( KP, KKW ),
- $ LDW )
- END IF
-*
- IF( KSTEP.EQ.1 ) THEN
-*
-* 1-by-1 pivot block D(k): column KW of W now holds
-*
-* W(k) = U(k)*D(k)
-*
-* where U(k) is the k-th column of U
-*
-* Store U(k) in column k of A
-*
- CALL DCOPY( K, W( 1, KW ), 1, A( 1, K ), 1 )
- R1 = ONE / A( K, K )
- CALL DSCAL( K-1, R1, A( 1, K ), 1 )
- ELSE
-*
-* 2-by-2 pivot block D(k): columns KW and KW-1 of W now
-* hold
-*
-* ( W(k-1) W(k) ) = ( U(k-1) U(k) )*D(k)
-*
-* where U(k) and U(k-1) are the k-th and (k-1)-th columns
-* of U
-*
- IF( K.GT.2 ) THEN
-*
-* Store U(k) and U(k-1) in columns k and k-1 of A
-*
- D21 = W( K-1, KW )
- D11 = W( K, KW ) / D21
- D22 = W( K-1, KW-1 ) / D21
- T = ONE / ( D11*D22-ONE )
- D21 = T / D21
- DO 20 J = 1, K - 2
- A( J, K-1 ) = D21*( D11*W( J, KW-1 )-W( J, KW ) )
- A( J, K ) = D21*( D22*W( J, KW )-W( J, KW-1 ) )
- 20 CONTINUE
- END IF
-*
-* Copy D(k) to A
-*
- A( K-1, K-1 ) = W( K-1, KW-1 )
- A( K-1, K ) = W( K-1, KW )
- A( K, K ) = W( K, KW )
- END IF
- END IF
-*
-* Store details of the interchanges in IPIV
-*
- IF( KSTEP.EQ.1 ) THEN
- IPIV( K ) = KP
- ELSE
- IPIV( K ) = -KP
- IPIV( K-1 ) = -KP
- END IF
-*
-* Decrease K and return to the start of the main loop
-*
- K = K - KSTEP
- GO TO 10
-*
- 30 CONTINUE
-*
-* Update the upper triangle of A11 (= A(1:k,1:k)) as
-*
-* A11 := A11 - U12*D*U12' = A11 - U12*W'
-*
-* computing blocks of NB columns at a time
-*
- DO 50 J = ( ( K-1 ) / NB )*NB + 1, 1, -NB
- JB = MIN( NB, K-J+1 )
-*
-* Update the upper triangle of the diagonal block
-*
- DO 40 JJ = J, J + JB - 1
- CALL DGEMV( 'No transpose', JJ-J+1, N-K, -ONE,
- $ A( J, K+1 ), LDA, W( JJ, KW+1 ), LDW, ONE,
- $ A( J, JJ ), 1 )
- 40 CONTINUE
-*
-* Update the rectangular superdiagonal block
-*
- CALL DGEMM( 'No transpose', 'Transpose', J-1, JB, N-K, -ONE,
- $ A( 1, K+1 ), LDA, W( J, KW+1 ), LDW, ONE,
- $ A( 1, J ), LDA )
- 50 CONTINUE
-*
-* Put U12 in standard form by partially undoing the interchanges
-* in columns k+1:n
-*
- J = K + 1
- 60 CONTINUE
- JJ = J
- JP = IPIV( J )
- IF( JP.LT.0 ) THEN
- JP = -JP
- J = J + 1
- END IF
- J = J + 1
- IF( JP.NE.JJ .AND. J.LE.N )
- $ CALL DSWAP( N-J+1, A( JP, J ), LDA, A( JJ, J ), LDA )
- IF( J.LE.N )
- $ GO TO 60
-*
-* Set KB to the number of columns factorized
-*
- KB = N - K
-*
- ELSE
-*
-* Factorize the leading columns of A using the lower triangle
-* of A and working forwards, and compute the matrix W = L21*D
-* for use in updating A22
-*
-* K is the main loop index, increasing from 1 in steps of 1 or 2
-*
- K = 1
- 70 CONTINUE
-*
-* Exit from loop
-*
- IF( ( K.GE.NB .AND. NB.LT.N ) .OR. K.GT.N )
- $ GO TO 90
-*
-* Copy column K of A to column K of W and update it
-*
- CALL DCOPY( N-K+1, A( K, K ), 1, W( K, K ), 1 )
- CALL DGEMV( 'No transpose', N-K+1, K-1, -ONE, A( K, 1 ), LDA,
- $ W( K, 1 ), LDW, ONE, W( K, K ), 1 )
-*
- KSTEP = 1
-*
-* Determine rows and columns to be interchanged and whether
-* a 1-by-1 or 2-by-2 pivot block will be used
-*
- ABSAKK = ABS( W( K, K ) )
-*
-* IMAX is the row-index of the largest off-diagonal element in
-* column K, and COLMAX is its absolute value
-*
- IF( K.LT.N ) THEN
- IMAX = K + IDAMAX( N-K, W( K+1, K ), 1 )
- COLMAX = ABS( W( IMAX, K ) )
- ELSE
- COLMAX = ZERO
- END IF
-*
- IF( MAX( ABSAKK, COLMAX ).EQ.ZERO ) THEN
-*
-* Column K is zero: set INFO and continue
-*
- IF( INFO.EQ.0 )
- $ INFO = K
- KP = K
- ELSE
- IF( ABSAKK.GE.ALPHA*COLMAX ) THEN
-*
-* no interchange, use 1-by-1 pivot block
-*
- KP = K
- ELSE
-*
-* Copy column IMAX to column K+1 of W and update it
-*
- CALL DCOPY( IMAX-K, A( IMAX, K ), LDA, W( K, K+1 ), 1 )
- CALL DCOPY( N-IMAX+1, A( IMAX, IMAX ), 1, W( IMAX, K+1 ),
- $ 1 )
- CALL DGEMV( 'No transpose', N-K+1, K-1, -ONE, A( K, 1 ),
- $ LDA, W( IMAX, 1 ), LDW, ONE, W( K, K+1 ), 1 )
-*
-* JMAX is the column-index of the largest off-diagonal
-* element in row IMAX, and ROWMAX is its absolute value
-*
- JMAX = K - 1 + IDAMAX( IMAX-K, W( K, K+1 ), 1 )
- ROWMAX = ABS( W( JMAX, K+1 ) )
- IF( IMAX.LT.N ) THEN
- JMAX = IMAX + IDAMAX( N-IMAX, W( IMAX+1, K+1 ), 1 )
- ROWMAX = MAX( ROWMAX, ABS( W( JMAX, K+1 ) ) )
- END IF
-*
- IF( ABSAKK.GE.ALPHA*COLMAX*( COLMAX / ROWMAX ) ) THEN
-*
-* no interchange, use 1-by-1 pivot block
-*
- KP = K
- ELSE IF( ABS( W( IMAX, K+1 ) ).GE.ALPHA*ROWMAX ) THEN
-*
-* interchange rows and columns K and IMAX, use 1-by-1
-* pivot block
-*
- KP = IMAX
-*
-* copy column K+1 of W to column K
-*
- CALL DCOPY( N-K+1, W( K, K+1 ), 1, W( K, K ), 1 )
- ELSE
-*
-* interchange rows and columns K+1 and IMAX, use 2-by-2
-* pivot block
-*
- KP = IMAX
- KSTEP = 2
- END IF
- END IF
-*
- KK = K + KSTEP - 1
-*
-* Updated column KP is already stored in column KK of W
-*
- IF( KP.NE.KK ) THEN
-*
-* Copy non-updated column KK to column KP
-*
- A( KP, K ) = A( KK, K )
- CALL DCOPY( KP-K-1, A( K+1, KK ), 1, A( KP, K+1 ), LDA )
- CALL DCOPY( N-KP+1, A( KP, KK ), 1, A( KP, KP ), 1 )
-*
-* Interchange rows KK and KP in first KK columns of A and W
-*
- CALL DSWAP( KK, A( KK, 1 ), LDA, A( KP, 1 ), LDA )
- CALL DSWAP( KK, W( KK, 1 ), LDW, W( KP, 1 ), LDW )
- END IF
-*
- IF( KSTEP.EQ.1 ) THEN
-*
-* 1-by-1 pivot block D(k): column k of W now holds
-*
-* W(k) = L(k)*D(k)
-*
-* where L(k) is the k-th column of L
-*
-* Store L(k) in column k of A
-*
- CALL DCOPY( N-K+1, W( K, K ), 1, A( K, K ), 1 )
- IF( K.LT.N ) THEN
- R1 = ONE / A( K, K )
- CALL DSCAL( N-K, R1, A( K+1, K ), 1 )
- END IF
- ELSE
-*
-* 2-by-2 pivot block D(k): columns k and k+1 of W now hold
-*
-* ( W(k) W(k+1) ) = ( L(k) L(k+1) )*D(k)
-*
-* where L(k) and L(k+1) are the k-th and (k+1)-th columns
-* of L
-*
- IF( K.LT.N-1 ) THEN
-*
-* Store L(k) and L(k+1) in columns k and k+1 of A
-*
- D21 = W( K+1, K )
- D11 = W( K+1, K+1 ) / D21
- D22 = W( K, K ) / D21
- T = ONE / ( D11*D22-ONE )
- D21 = T / D21
- DO 80 J = K + 2, N
- A( J, K ) = D21*( D11*W( J, K )-W( J, K+1 ) )
- A( J, K+1 ) = D21*( D22*W( J, K+1 )-W( J, K ) )
- 80 CONTINUE
- END IF
-*
-* Copy D(k) to A
-*
- A( K, K ) = W( K, K )
- A( K+1, K ) = W( K+1, K )
- A( K+1, K+1 ) = W( K+1, K+1 )
- END IF
- END IF
-*
-* Store details of the interchanges in IPIV
-*
- IF( KSTEP.EQ.1 ) THEN
- IPIV( K ) = KP
- ELSE
- IPIV( K ) = -KP
- IPIV( K+1 ) = -KP
- END IF
-*
-* Increase K and return to the start of the main loop
-*
- K = K + KSTEP
- GO TO 70
-*
- 90 CONTINUE
-*
-* Update the lower triangle of A22 (= A(k:n,k:n)) as
-*
-* A22 := A22 - L21*D*L21' = A22 - L21*W'
-*
-* computing blocks of NB columns at a time
-*
- DO 110 J = K, N, NB
- JB = MIN( NB, N-J+1 )
-*
-* Update the lower triangle of the diagonal block
-*
- DO 100 JJ = J, J + JB - 1
- CALL DGEMV( 'No transpose', J+JB-JJ, K-1, -ONE,
- $ A( JJ, 1 ), LDA, W( JJ, 1 ), LDW, ONE,
- $ A( JJ, JJ ), 1 )
- 100 CONTINUE
-*
-* Update the rectangular subdiagonal block
-*
- IF( J+JB.LE.N )
- $ CALL DGEMM( 'No transpose', 'Transpose', N-J-JB+1, JB,
- $ K-1, -ONE, A( J+JB, 1 ), LDA, W( J, 1 ), LDW,
- $ ONE, A( J+JB, J ), LDA )
- 110 CONTINUE
-*
-* Put L21 in standard form by partially undoing the interchanges
-* in columns 1:k-1
-*
- J = K - 1
- 120 CONTINUE
- JJ = J
- JP = IPIV( J )
- IF( JP.LT.0 ) THEN
- JP = -JP
- J = J - 1
- END IF
- J = J - 1
- IF( JP.NE.JJ .AND. J.GE.1 )
- $ CALL DSWAP( J, A( JP, 1 ), LDA, A( JJ, 1 ), LDA )
- IF( J.GE.1 )
- $ GO TO 120
-*
-* Set KB to the number of columns factorized
-*
- KB = K - 1
-*
- END IF
- RETURN
-*
-* End of DLASYF
-*
- END
diff --git a/src/lib/lapack/dlatdf.f b/src/lib/lapack/dlatdf.f
deleted file mode 100644
index 91fa46e3..00000000
--- a/src/lib/lapack/dlatdf.f
+++ /dev/null
@@ -1,237 +0,0 @@
- SUBROUTINE DLATDF( IJOB, N, Z, LDZ, RHS, RDSUM, RDSCAL, IPIV,
- $ JPIV )
-*
-* -- LAPACK auxiliary routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- INTEGER IJOB, LDZ, N
- DOUBLE PRECISION RDSCAL, RDSUM
-* ..
-* .. Array Arguments ..
- INTEGER IPIV( * ), JPIV( * )
- DOUBLE PRECISION RHS( * ), Z( LDZ, * )
-* ..
-*
-* Purpose
-* =======
-*
-* DLATDF uses the LU factorization of the n-by-n matrix Z computed by
-* DGETC2 and computes a contribution to the reciprocal Dif-estimate
-* by solving Z * x = b for x, and choosing the r.h.s. b such that
-* the norm of x is as large as possible. On entry RHS = b holds the
-* contribution from earlier solved sub-systems, and on return RHS = x.
-*
-* The factorization of Z returned by DGETC2 has the form Z = P*L*U*Q,
-* where P and Q are permutation matrices. L is lower triangular with
-* unit diagonal elements and U is upper triangular.
-*
-* Arguments
-* =========
-*
-* IJOB (input) INTEGER
-* IJOB = 2: First compute an approximative null-vector e
-* of Z using DGECON, e is normalized and solve for
-* Zx = +-e - f with the sign giving the greater value
-* of 2-norm(x). About 5 times as expensive as Default.
-* IJOB .ne. 2: Local look ahead strategy where all entries of
-* the r.h.s. b is choosen as either +1 or -1 (Default).
-*
-* N (input) INTEGER
-* The number of columns of the matrix Z.
-*
-* Z (input) DOUBLE PRECISION array, dimension (LDZ, N)
-* On entry, the LU part of the factorization of the n-by-n
-* matrix Z computed by DGETC2: Z = P * L * U * Q
-*
-* LDZ (input) INTEGER
-* The leading dimension of the array Z. LDA >= max(1, N).
-*
-* RHS (input/output) DOUBLE PRECISION array, dimension N.
-* On entry, RHS contains contributions from other subsystems.
-* On exit, RHS contains the solution of the subsystem with
-* entries acoording to the value of IJOB (see above).
-*
-* RDSUM (input/output) DOUBLE PRECISION
-* On entry, the sum of squares of computed contributions to
-* the Dif-estimate under computation by DTGSYL, where the
-* scaling factor RDSCAL (see below) has been factored out.
-* On exit, the corresponding sum of squares updated with the
-* contributions from the current sub-system.
-* If TRANS = 'T' RDSUM is not touched.
-* NOTE: RDSUM only makes sense when DTGSY2 is called by STGSYL.
-*
-* RDSCAL (input/output) DOUBLE PRECISION
-* On entry, scaling factor used to prevent overflow in RDSUM.
-* On exit, RDSCAL is updated w.r.t. the current contributions
-* in RDSUM.
-* If TRANS = 'T', RDSCAL is not touched.
-* NOTE: RDSCAL only makes sense when DTGSY2 is called by
-* DTGSYL.
-*
-* IPIV (input) INTEGER array, dimension (N).
-* The pivot indices; for 1 <= i <= N, row i of the
-* matrix has been interchanged with row IPIV(i).
-*
-* JPIV (input) INTEGER array, dimension (N).
-* The pivot indices; for 1 <= j <= N, column j of the
-* matrix has been interchanged with column JPIV(j).
-*
-* Further Details
-* ===============
-*
-* Based on contributions by
-* Bo Kagstrom and Peter Poromaa, Department of Computing Science,
-* Umea University, S-901 87 Umea, Sweden.
-*
-* This routine is a further developed implementation of algorithm
-* BSOLVE in [1] using complete pivoting in the LU factorization.
-*
-* [1] Bo Kagstrom and Lars Westin,
-* Generalized Schur Methods with Condition Estimators for
-* Solving the Generalized Sylvester Equation, IEEE Transactions
-* on Automatic Control, Vol. 34, No. 7, July 1989, pp 745-751.
-*
-* [2] Peter Poromaa,
-* On Efficient and Robust Estimators for the Separation
-* between two Regular Matrix Pairs with Applications in
-* Condition Estimation. Report IMINF-95.05, Departement of
-* Computing Science, Umea University, S-901 87 Umea, Sweden, 1995.
-*
-* =====================================================================
-*
-* .. Parameters ..
- INTEGER MAXDIM
- PARAMETER ( MAXDIM = 8 )
- DOUBLE PRECISION ZERO, ONE
- PARAMETER ( ZERO = 0.0D+0, ONE = 1.0D+0 )
-* ..
-* .. Local Scalars ..
- INTEGER I, INFO, J, K
- DOUBLE PRECISION BM, BP, PMONE, SMINU, SPLUS, TEMP
-* ..
-* .. Local Arrays ..
- INTEGER IWORK( MAXDIM )
- DOUBLE PRECISION WORK( 4*MAXDIM ), XM( MAXDIM ), XP( MAXDIM )
-* ..
-* .. External Subroutines ..
- EXTERNAL DAXPY, DCOPY, DGECON, DGESC2, DLASSQ, DLASWP,
- $ DSCAL
-* ..
-* .. External Functions ..
- DOUBLE PRECISION DASUM, DDOT
- EXTERNAL DASUM, DDOT
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC ABS, SQRT
-* ..
-* .. Executable Statements ..
-*
- IF( IJOB.NE.2 ) THEN
-*
-* Apply permutations IPIV to RHS
-*
- CALL DLASWP( 1, RHS, LDZ, 1, N-1, IPIV, 1 )
-*
-* Solve for L-part choosing RHS either to +1 or -1.
-*
- PMONE = -ONE
-*
- DO 10 J = 1, N - 1
- BP = RHS( J ) + ONE
- BM = RHS( J ) - ONE
- SPLUS = ONE
-*
-* Look-ahead for L-part RHS(1:N-1) = + or -1, SPLUS and
-* SMIN computed more efficiently than in BSOLVE [1].
-*
- SPLUS = SPLUS + DDOT( N-J, Z( J+1, J ), 1, Z( J+1, J ), 1 )
- SMINU = DDOT( N-J, Z( J+1, J ), 1, RHS( J+1 ), 1 )
- SPLUS = SPLUS*RHS( J )
- IF( SPLUS.GT.SMINU ) THEN
- RHS( J ) = BP
- ELSE IF( SMINU.GT.SPLUS ) THEN
- RHS( J ) = BM
- ELSE
-*
-* In this case the updating sums are equal and we can
-* choose RHS(J) +1 or -1. The first time this happens
-* we choose -1, thereafter +1. This is a simple way to
-* get good estimates of matrices like Byers well-known
-* example (see [1]). (Not done in BSOLVE.)
-*
- RHS( J ) = RHS( J ) + PMONE
- PMONE = ONE
- END IF
-*
-* Compute the remaining r.h.s.
-*
- TEMP = -RHS( J )
- CALL DAXPY( N-J, TEMP, Z( J+1, J ), 1, RHS( J+1 ), 1 )
-*
- 10 CONTINUE
-*
-* Solve for U-part, look-ahead for RHS(N) = +-1. This is not done
-* in BSOLVE and will hopefully give us a better estimate because
-* any ill-conditioning of the original matrix is transfered to U
-* and not to L. U(N, N) is an approximation to sigma_min(LU).
-*
- CALL DCOPY( N-1, RHS, 1, XP, 1 )
- XP( N ) = RHS( N ) + ONE
- RHS( N ) = RHS( N ) - ONE
- SPLUS = ZERO
- SMINU = ZERO
- DO 30 I = N, 1, -1
- TEMP = ONE / Z( I, I )
- XP( I ) = XP( I )*TEMP
- RHS( I ) = RHS( I )*TEMP
- DO 20 K = I + 1, N
- XP( I ) = XP( I ) - XP( K )*( Z( I, K )*TEMP )
- RHS( I ) = RHS( I ) - RHS( K )*( Z( I, K )*TEMP )
- 20 CONTINUE
- SPLUS = SPLUS + ABS( XP( I ) )
- SMINU = SMINU + ABS( RHS( I ) )
- 30 CONTINUE
- IF( SPLUS.GT.SMINU )
- $ CALL DCOPY( N, XP, 1, RHS, 1 )
-*
-* Apply the permutations JPIV to the computed solution (RHS)
-*
- CALL DLASWP( 1, RHS, LDZ, 1, N-1, JPIV, -1 )
-*
-* Compute the sum of squares
-*
- CALL DLASSQ( N, RHS, 1, RDSCAL, RDSUM )
-*
- ELSE
-*
-* IJOB = 2, Compute approximate nullvector XM of Z
-*
- CALL DGECON( 'I', N, Z, LDZ, ONE, TEMP, WORK, IWORK, INFO )
- CALL DCOPY( N, WORK( N+1 ), 1, XM, 1 )
-*
-* Compute RHS
-*
- CALL DLASWP( 1, XM, LDZ, 1, N-1, IPIV, -1 )
- TEMP = ONE / SQRT( DDOT( N, XM, 1, XM, 1 ) )
- CALL DSCAL( N, TEMP, XM, 1 )
- CALL DCOPY( N, XM, 1, XP, 1 )
- CALL DAXPY( N, ONE, RHS, 1, XP, 1 )
- CALL DAXPY( N, -ONE, XM, 1, RHS, 1 )
- CALL DGESC2( N, Z, LDZ, RHS, IPIV, JPIV, TEMP )
- CALL DGESC2( N, Z, LDZ, XP, IPIV, JPIV, TEMP )
- IF( DASUM( N, XP, 1 ).GT.DASUM( N, RHS, 1 ) )
- $ CALL DCOPY( N, XP, 1, RHS, 1 )
-*
-* Compute the sum of squares
-*
- CALL DLASSQ( N, RHS, 1, RDSCAL, RDSUM )
-*
- END IF
-*
- RETURN
-*
-* End of DLATDF
-*
- END
diff --git a/src/lib/lapack/dlatrd.f b/src/lib/lapack/dlatrd.f
deleted file mode 100644
index 27bf9b98..00000000
--- a/src/lib/lapack/dlatrd.f
+++ /dev/null
@@ -1,258 +0,0 @@
- SUBROUTINE DLATRD( UPLO, N, NB, A, LDA, E, TAU, W, LDW )
-*
-* -- LAPACK auxiliary routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- CHARACTER UPLO
- INTEGER LDA, LDW, N, NB
-* ..
-* .. Array Arguments ..
- DOUBLE PRECISION A( LDA, * ), E( * ), TAU( * ), W( LDW, * )
-* ..
-*
-* Purpose
-* =======
-*
-* DLATRD reduces NB rows and columns of a real symmetric matrix A to
-* symmetric tridiagonal form by an orthogonal similarity
-* transformation Q' * A * Q, and returns the matrices V and W which are
-* needed to apply the transformation to the unreduced part of A.
-*
-* If UPLO = 'U', DLATRD reduces the last NB rows and columns of a
-* matrix, of which the upper triangle is supplied;
-* if UPLO = 'L', DLATRD reduces the first NB rows and columns of a
-* matrix, of which the lower triangle is supplied.
-*
-* This is an auxiliary routine called by DSYTRD.
-*
-* Arguments
-* =========
-*
-* UPLO (input) CHARACTER*1
-* Specifies whether the upper or lower triangular part of the
-* symmetric matrix A is stored:
-* = 'U': Upper triangular
-* = 'L': Lower triangular
-*
-* N (input) INTEGER
-* The order of the matrix A.
-*
-* NB (input) INTEGER
-* The number of rows and columns to be reduced.
-*
-* A (input/output) DOUBLE PRECISION array, dimension (LDA,N)
-* On entry, the symmetric matrix A. If UPLO = 'U', the leading
-* n-by-n upper triangular part of A contains the upper
-* triangular part of the matrix A, and the strictly lower
-* triangular part of A is not referenced. If UPLO = 'L', the
-* leading n-by-n lower triangular part of A contains the lower
-* triangular part of the matrix A, and the strictly upper
-* triangular part of A is not referenced.
-* On exit:
-* if UPLO = 'U', the last NB columns have been reduced to
-* tridiagonal form, with the diagonal elements overwriting
-* the diagonal elements of A; the elements above the diagonal
-* with the array TAU, represent the orthogonal matrix Q as a
-* product of elementary reflectors;
-* if UPLO = 'L', the first NB columns have been reduced to
-* tridiagonal form, with the diagonal elements overwriting
-* the diagonal elements of A; the elements below the diagonal
-* with the array TAU, represent the orthogonal matrix Q as a
-* product of elementary reflectors.
-* See Further Details.
-*
-* LDA (input) INTEGER
-* The leading dimension of the array A. LDA >= (1,N).
-*
-* E (output) DOUBLE PRECISION array, dimension (N-1)
-* If UPLO = 'U', E(n-nb:n-1) contains the superdiagonal
-* elements of the last NB columns of the reduced matrix;
-* if UPLO = 'L', E(1:nb) contains the subdiagonal elements of
-* the first NB columns of the reduced matrix.
-*
-* TAU (output) DOUBLE PRECISION array, dimension (N-1)
-* The scalar factors of the elementary reflectors, stored in
-* TAU(n-nb:n-1) if UPLO = 'U', and in TAU(1:nb) if UPLO = 'L'.
-* See Further Details.
-*
-* W (output) DOUBLE PRECISION array, dimension (LDW,NB)
-* The n-by-nb matrix W required to update the unreduced part
-* of A.
-*
-* LDW (input) INTEGER
-* The leading dimension of the array W. LDW >= max(1,N).
-*
-* Further Details
-* ===============
-*
-* If UPLO = 'U', the matrix Q is represented as a product of elementary
-* reflectors
-*
-* Q = H(n) H(n-1) . . . H(n-nb+1).
-*
-* Each H(i) has the form
-*
-* H(i) = I - tau * v * v'
-*
-* where tau is a real scalar, and v is a real vector with
-* v(i:n) = 0 and v(i-1) = 1; v(1:i-1) is stored on exit in A(1:i-1,i),
-* and tau in TAU(i-1).
-*
-* If UPLO = 'L', the matrix Q is represented as a product of elementary
-* reflectors
-*
-* Q = H(1) H(2) . . . H(nb).
-*
-* Each H(i) has the form
-*
-* H(i) = I - tau * v * v'
-*
-* where tau is a real scalar, and v is a real vector with
-* v(1:i) = 0 and v(i+1) = 1; v(i+1:n) is stored on exit in A(i+1:n,i),
-* and tau in TAU(i).
-*
-* The elements of the vectors v together form the n-by-nb matrix V
-* which is needed, with W, to apply the transformation to the unreduced
-* part of the matrix, using a symmetric rank-2k update of the form:
-* A := A - V*W' - W*V'.
-*
-* The contents of A on exit are illustrated by the following examples
-* with n = 5 and nb = 2:
-*
-* if UPLO = 'U': if UPLO = 'L':
-*
-* ( a a a v4 v5 ) ( d )
-* ( a a v4 v5 ) ( 1 d )
-* ( a 1 v5 ) ( v1 1 a )
-* ( d 1 ) ( v1 v2 a a )
-* ( d ) ( v1 v2 a a a )
-*
-* where d denotes a diagonal element of the reduced matrix, a denotes
-* an element of the original matrix that is unchanged, and vi denotes
-* an element of the vector defining H(i).
-*
-* =====================================================================
-*
-* .. Parameters ..
- DOUBLE PRECISION ZERO, ONE, HALF
- PARAMETER ( ZERO = 0.0D+0, ONE = 1.0D+0, HALF = 0.5D+0 )
-* ..
-* .. Local Scalars ..
- INTEGER I, IW
- DOUBLE PRECISION ALPHA
-* ..
-* .. External Subroutines ..
- EXTERNAL DAXPY, DGEMV, DLARFG, DSCAL, DSYMV
-* ..
-* .. External Functions ..
- LOGICAL LSAME
- DOUBLE PRECISION DDOT
- EXTERNAL LSAME, DDOT
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC MIN
-* ..
-* .. Executable Statements ..
-*
-* Quick return if possible
-*
- IF( N.LE.0 )
- $ RETURN
-*
- IF( LSAME( UPLO, 'U' ) ) THEN
-*
-* Reduce last NB columns of upper triangle
-*
- DO 10 I = N, N - NB + 1, -1
- IW = I - N + NB
- IF( I.LT.N ) THEN
-*
-* Update A(1:i,i)
-*
- CALL DGEMV( 'No transpose', I, N-I, -ONE, A( 1, I+1 ),
- $ LDA, W( I, IW+1 ), LDW, ONE, A( 1, I ), 1 )
- CALL DGEMV( 'No transpose', I, N-I, -ONE, W( 1, IW+1 ),
- $ LDW, A( I, I+1 ), LDA, ONE, A( 1, I ), 1 )
- END IF
- IF( I.GT.1 ) THEN
-*
-* Generate elementary reflector H(i) to annihilate
-* A(1:i-2,i)
-*
- CALL DLARFG( I-1, A( I-1, I ), A( 1, I ), 1, TAU( I-1 ) )
- E( I-1 ) = A( I-1, I )
- A( I-1, I ) = ONE
-*
-* Compute W(1:i-1,i)
-*
- CALL DSYMV( 'Upper', I-1, ONE, A, LDA, A( 1, I ), 1,
- $ ZERO, W( 1, IW ), 1 )
- IF( I.LT.N ) THEN
- CALL DGEMV( 'Transpose', I-1, N-I, ONE, W( 1, IW+1 ),
- $ LDW, A( 1, I ), 1, ZERO, W( I+1, IW ), 1 )
- CALL DGEMV( 'No transpose', I-1, N-I, -ONE,
- $ A( 1, I+1 ), LDA, W( I+1, IW ), 1, ONE,
- $ W( 1, IW ), 1 )
- CALL DGEMV( 'Transpose', I-1, N-I, ONE, A( 1, I+1 ),
- $ LDA, A( 1, I ), 1, ZERO, W( I+1, IW ), 1 )
- CALL DGEMV( 'No transpose', I-1, N-I, -ONE,
- $ W( 1, IW+1 ), LDW, W( I+1, IW ), 1, ONE,
- $ W( 1, IW ), 1 )
- END IF
- CALL DSCAL( I-1, TAU( I-1 ), W( 1, IW ), 1 )
- ALPHA = -HALF*TAU( I-1 )*DDOT( I-1, W( 1, IW ), 1,
- $ A( 1, I ), 1 )
- CALL DAXPY( I-1, ALPHA, A( 1, I ), 1, W( 1, IW ), 1 )
- END IF
-*
- 10 CONTINUE
- ELSE
-*
-* Reduce first NB columns of lower triangle
-*
- DO 20 I = 1, NB
-*
-* Update A(i:n,i)
-*
- CALL DGEMV( 'No transpose', N-I+1, I-1, -ONE, A( I, 1 ),
- $ LDA, W( I, 1 ), LDW, ONE, A( I, I ), 1 )
- CALL DGEMV( 'No transpose', N-I+1, I-1, -ONE, W( I, 1 ),
- $ LDW, A( I, 1 ), LDA, ONE, A( I, I ), 1 )
- IF( I.LT.N ) THEN
-*
-* Generate elementary reflector H(i) to annihilate
-* A(i+2:n,i)
-*
- CALL DLARFG( N-I, A( I+1, I ), A( MIN( I+2, N ), I ), 1,
- $ TAU( I ) )
- E( I ) = A( I+1, I )
- A( I+1, I ) = ONE
-*
-* Compute W(i+1:n,i)
-*
- CALL DSYMV( 'Lower', N-I, ONE, A( I+1, I+1 ), LDA,
- $ A( I+1, I ), 1, ZERO, W( I+1, I ), 1 )
- CALL DGEMV( 'Transpose', N-I, I-1, ONE, W( I+1, 1 ), LDW,
- $ A( I+1, I ), 1, ZERO, W( 1, I ), 1 )
- CALL DGEMV( 'No transpose', N-I, I-1, -ONE, A( I+1, 1 ),
- $ LDA, W( 1, I ), 1, ONE, W( I+1, I ), 1 )
- CALL DGEMV( 'Transpose', N-I, I-1, ONE, A( I+1, 1 ), LDA,
- $ A( I+1, I ), 1, ZERO, W( 1, I ), 1 )
- CALL DGEMV( 'No transpose', N-I, I-1, -ONE, W( I+1, 1 ),
- $ LDW, W( 1, I ), 1, ONE, W( I+1, I ), 1 )
- CALL DSCAL( N-I, TAU( I ), W( I+1, I ), 1 )
- ALPHA = -HALF*TAU( I )*DDOT( N-I, W( I+1, I ), 1,
- $ A( I+1, I ), 1 )
- CALL DAXPY( N-I, ALPHA, A( I+1, I ), 1, W( I+1, I ), 1 )
- END IF
-*
- 20 CONTINUE
- END IF
-*
- RETURN
-*
-* End of DLATRD
-*
- END
diff --git a/src/lib/lapack/dlatrs.f b/src/lib/lapack/dlatrs.f
deleted file mode 100644
index bbd3a9e4..00000000
--- a/src/lib/lapack/dlatrs.f
+++ /dev/null
@@ -1,701 +0,0 @@
- SUBROUTINE DLATRS( UPLO, TRANS, DIAG, NORMIN, N, A, LDA, X, SCALE,
- $ CNORM, INFO )
-*
-* -- LAPACK auxiliary routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- CHARACTER DIAG, NORMIN, TRANS, UPLO
- INTEGER INFO, LDA, N
- DOUBLE PRECISION SCALE
-* ..
-* .. Array Arguments ..
- DOUBLE PRECISION A( LDA, * ), CNORM( * ), X( * )
-* ..
-*
-* Purpose
-* =======
-*
-* DLATRS solves one of the triangular systems
-*
-* A *x = s*b or A'*x = s*b
-*
-* with scaling to prevent overflow. Here A is an upper or lower
-* triangular matrix, A' denotes the transpose of A, x and b are
-* n-element vectors, and s is a scaling factor, usually less than
-* or equal to 1, chosen so that the components of x will be less than
-* the overflow threshold. If the unscaled problem will not cause
-* overflow, the Level 2 BLAS routine DTRSV is called. If the matrix A
-* is singular (A(j,j) = 0 for some j), then s is set to 0 and a
-* non-trivial solution to A*x = 0 is returned.
-*
-* Arguments
-* =========
-*
-* UPLO (input) CHARACTER*1
-* Specifies whether the matrix A is upper or lower triangular.
-* = 'U': Upper triangular
-* = 'L': Lower triangular
-*
-* TRANS (input) CHARACTER*1
-* Specifies the operation applied to A.
-* = 'N': Solve A * x = s*b (No transpose)
-* = 'T': Solve A'* x = s*b (Transpose)
-* = 'C': Solve A'* x = s*b (Conjugate transpose = Transpose)
-*
-* DIAG (input) CHARACTER*1
-* Specifies whether or not the matrix A is unit triangular.
-* = 'N': Non-unit triangular
-* = 'U': Unit triangular
-*
-* NORMIN (input) CHARACTER*1
-* Specifies whether CNORM has been set or not.
-* = 'Y': CNORM contains the column norms on entry
-* = 'N': CNORM is not set on entry. On exit, the norms will
-* be computed and stored in CNORM.
-*
-* N (input) INTEGER
-* The order of the matrix A. N >= 0.
-*
-* A (input) DOUBLE PRECISION array, dimension (LDA,N)
-* The triangular matrix A. If UPLO = 'U', the leading n by n
-* upper triangular part of the array A contains the upper
-* triangular matrix, and the strictly lower triangular part of
-* A is not referenced. If UPLO = 'L', the leading n by n lower
-* triangular part of the array A contains the lower triangular
-* matrix, and the strictly upper triangular part of A is not
-* referenced. If DIAG = 'U', the diagonal elements of A are
-* also not referenced and are assumed to be 1.
-*
-* LDA (input) INTEGER
-* The leading dimension of the array A. LDA >= max (1,N).
-*
-* X (input/output) DOUBLE PRECISION array, dimension (N)
-* On entry, the right hand side b of the triangular system.
-* On exit, X is overwritten by the solution vector x.
-*
-* SCALE (output) DOUBLE PRECISION
-* The scaling factor s for the triangular system
-* A * x = s*b or A'* x = s*b.
-* If SCALE = 0, the matrix A is singular or badly scaled, and
-* the vector x is an exact or approximate solution to A*x = 0.
-*
-* CNORM (input or output) DOUBLE PRECISION array, dimension (N)
-*
-* If NORMIN = 'Y', CNORM is an input argument and CNORM(j)
-* contains the norm of the off-diagonal part of the j-th column
-* of A. If TRANS = 'N', CNORM(j) must be greater than or equal
-* to the infinity-norm, and if TRANS = 'T' or 'C', CNORM(j)
-* must be greater than or equal to the 1-norm.
-*
-* If NORMIN = 'N', CNORM is an output argument and CNORM(j)
-* returns the 1-norm of the offdiagonal part of the j-th column
-* of A.
-*
-* INFO (output) INTEGER
-* = 0: successful exit
-* < 0: if INFO = -k, the k-th argument had an illegal value
-*
-* Further Details
-* ======= =======
-*
-* A rough bound on x is computed; if that is less than overflow, DTRSV
-* is called, otherwise, specific code is used which checks for possible
-* overflow or divide-by-zero at every operation.
-*
-* A columnwise scheme is used for solving A*x = b. The basic algorithm
-* if A is lower triangular is
-*
-* x[1:n] := b[1:n]
-* for j = 1, ..., n
-* x(j) := x(j) / A(j,j)
-* x[j+1:n] := x[j+1:n] - x(j) * A[j+1:n,j]
-* end
-*
-* Define bounds on the components of x after j iterations of the loop:
-* M(j) = bound on x[1:j]
-* G(j) = bound on x[j+1:n]
-* Initially, let M(0) = 0 and G(0) = max{x(i), i=1,...,n}.
-*
-* Then for iteration j+1 we have
-* M(j+1) <= G(j) / | A(j+1,j+1) |
-* G(j+1) <= G(j) + M(j+1) * | A[j+2:n,j+1] |
-* <= G(j) ( 1 + CNORM(j+1) / | A(j+1,j+1) | )
-*
-* where CNORM(j+1) is greater than or equal to the infinity-norm of
-* column j+1 of A, not counting the diagonal. Hence
-*
-* G(j) <= G(0) product ( 1 + CNORM(i) / | A(i,i) | )
-* 1<=i<=j
-* and
-*
-* |x(j)| <= ( G(0) / |A(j,j)| ) product ( 1 + CNORM(i) / |A(i,i)| )
-* 1<=i< j
-*
-* Since |x(j)| <= M(j), we use the Level 2 BLAS routine DTRSV if the
-* reciprocal of the largest M(j), j=1,..,n, is larger than
-* max(underflow, 1/overflow).
-*
-* The bound on x(j) is also used to determine when a step in the
-* columnwise method can be performed without fear of overflow. If
-* the computed bound is greater than a large constant, x is scaled to
-* prevent overflow, but if the bound overflows, x is set to 0, x(j) to
-* 1, and scale to 0, and a non-trivial solution to A*x = 0 is found.
-*
-* Similarly, a row-wise scheme is used to solve A'*x = b. The basic
-* algorithm for A upper triangular is
-*
-* for j = 1, ..., n
-* x(j) := ( b(j) - A[1:j-1,j]' * x[1:j-1] ) / A(j,j)
-* end
-*
-* We simultaneously compute two bounds
-* G(j) = bound on ( b(i) - A[1:i-1,i]' * x[1:i-1] ), 1<=i<=j
-* M(j) = bound on x(i), 1<=i<=j
-*
-* The initial values are G(0) = 0, M(0) = max{b(i), i=1,..,n}, and we
-* add the constraint G(j) >= G(j-1) and M(j) >= M(j-1) for j >= 1.
-* Then the bound on x(j) is
-*
-* M(j) <= M(j-1) * ( 1 + CNORM(j) ) / | A(j,j) |
-*
-* <= M(0) * product ( ( 1 + CNORM(i) ) / |A(i,i)| )
-* 1<=i<=j
-*
-* and we can safely call DTRSV if 1/M(n) and 1/G(n) are both greater
-* than max(underflow, 1/overflow).
-*
-* =====================================================================
-*
-* .. Parameters ..
- DOUBLE PRECISION ZERO, HALF, ONE
- PARAMETER ( ZERO = 0.0D+0, HALF = 0.5D+0, ONE = 1.0D+0 )
-* ..
-* .. Local Scalars ..
- LOGICAL NOTRAN, NOUNIT, UPPER
- INTEGER I, IMAX, J, JFIRST, JINC, JLAST
- DOUBLE PRECISION BIGNUM, GROW, REC, SMLNUM, SUMJ, TJJ, TJJS,
- $ TMAX, TSCAL, USCAL, XBND, XJ, XMAX
-* ..
-* .. External Functions ..
- LOGICAL LSAME
- INTEGER IDAMAX
- DOUBLE PRECISION DASUM, DDOT, DLAMCH
- EXTERNAL LSAME, IDAMAX, DASUM, DDOT, DLAMCH
-* ..
-* .. External Subroutines ..
- EXTERNAL DAXPY, DSCAL, DTRSV, XERBLA
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC ABS, MAX, MIN
-* ..
-* .. Executable Statements ..
-*
- INFO = 0
- UPPER = LSAME( UPLO, 'U' )
- NOTRAN = LSAME( TRANS, 'N' )
- NOUNIT = LSAME( DIAG, 'N' )
-*
-* Test the input parameters.
-*
- IF( .NOT.UPPER .AND. .NOT.LSAME( UPLO, 'L' ) ) THEN
- INFO = -1
- ELSE IF( .NOT.NOTRAN .AND. .NOT.LSAME( TRANS, 'T' ) .AND. .NOT.
- $ LSAME( TRANS, 'C' ) ) THEN
- INFO = -2
- ELSE IF( .NOT.NOUNIT .AND. .NOT.LSAME( DIAG, 'U' ) ) THEN
- INFO = -3
- ELSE IF( .NOT.LSAME( NORMIN, 'Y' ) .AND. .NOT.
- $ LSAME( NORMIN, 'N' ) ) THEN
- INFO = -4
- ELSE IF( N.LT.0 ) THEN
- INFO = -5
- ELSE IF( LDA.LT.MAX( 1, N ) ) THEN
- INFO = -7
- END IF
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'DLATRS', -INFO )
- RETURN
- END IF
-*
-* Quick return if possible
-*
- IF( N.EQ.0 )
- $ RETURN
-*
-* Determine machine dependent parameters to control overflow.
-*
- SMLNUM = DLAMCH( 'Safe minimum' ) / DLAMCH( 'Precision' )
- BIGNUM = ONE / SMLNUM
- SCALE = ONE
-*
- IF( LSAME( NORMIN, 'N' ) ) THEN
-*
-* Compute the 1-norm of each column, not including the diagonal.
-*
- IF( UPPER ) THEN
-*
-* A is upper triangular.
-*
- DO 10 J = 1, N
- CNORM( J ) = DASUM( J-1, A( 1, J ), 1 )
- 10 CONTINUE
- ELSE
-*
-* A is lower triangular.
-*
- DO 20 J = 1, N - 1
- CNORM( J ) = DASUM( N-J, A( J+1, J ), 1 )
- 20 CONTINUE
- CNORM( N ) = ZERO
- END IF
- END IF
-*
-* Scale the column norms by TSCAL if the maximum element in CNORM is
-* greater than BIGNUM.
-*
- IMAX = IDAMAX( N, CNORM, 1 )
- TMAX = CNORM( IMAX )
- IF( TMAX.LE.BIGNUM ) THEN
- TSCAL = ONE
- ELSE
- TSCAL = ONE / ( SMLNUM*TMAX )
- CALL DSCAL( N, TSCAL, CNORM, 1 )
- END IF
-*
-* Compute a bound on the computed solution vector to see if the
-* Level 2 BLAS routine DTRSV can be used.
-*
- J = IDAMAX( N, X, 1 )
- XMAX = ABS( X( J ) )
- XBND = XMAX
- IF( NOTRAN ) THEN
-*
-* Compute the growth in A * x = b.
-*
- IF( UPPER ) THEN
- JFIRST = N
- JLAST = 1
- JINC = -1
- ELSE
- JFIRST = 1
- JLAST = N
- JINC = 1
- END IF
-*
- IF( TSCAL.NE.ONE ) THEN
- GROW = ZERO
- GO TO 50
- END IF
-*
- IF( NOUNIT ) THEN
-*
-* A is non-unit triangular.
-*
-* Compute GROW = 1/G(j) and XBND = 1/M(j).
-* Initially, G(0) = max{x(i), i=1,...,n}.
-*
- GROW = ONE / MAX( XBND, SMLNUM )
- XBND = GROW
- DO 30 J = JFIRST, JLAST, JINC
-*
-* Exit the loop if the growth factor is too small.
-*
- IF( GROW.LE.SMLNUM )
- $ GO TO 50
-*
-* M(j) = G(j-1) / abs(A(j,j))
-*
- TJJ = ABS( A( J, J ) )
- XBND = MIN( XBND, MIN( ONE, TJJ )*GROW )
- IF( TJJ+CNORM( J ).GE.SMLNUM ) THEN
-*
-* G(j) = G(j-1)*( 1 + CNORM(j) / abs(A(j,j)) )
-*
- GROW = GROW*( TJJ / ( TJJ+CNORM( J ) ) )
- ELSE
-*
-* G(j) could overflow, set GROW to 0.
-*
- GROW = ZERO
- END IF
- 30 CONTINUE
- GROW = XBND
- ELSE
-*
-* A is unit triangular.
-*
-* Compute GROW = 1/G(j), where G(0) = max{x(i), i=1,...,n}.
-*
- GROW = MIN( ONE, ONE / MAX( XBND, SMLNUM ) )
- DO 40 J = JFIRST, JLAST, JINC
-*
-* Exit the loop if the growth factor is too small.
-*
- IF( GROW.LE.SMLNUM )
- $ GO TO 50
-*
-* G(j) = G(j-1)*( 1 + CNORM(j) )
-*
- GROW = GROW*( ONE / ( ONE+CNORM( J ) ) )
- 40 CONTINUE
- END IF
- 50 CONTINUE
-*
- ELSE
-*
-* Compute the growth in A' * x = b.
-*
- IF( UPPER ) THEN
- JFIRST = 1
- JLAST = N
- JINC = 1
- ELSE
- JFIRST = N
- JLAST = 1
- JINC = -1
- END IF
-*
- IF( TSCAL.NE.ONE ) THEN
- GROW = ZERO
- GO TO 80
- END IF
-*
- IF( NOUNIT ) THEN
-*
-* A is non-unit triangular.
-*
-* Compute GROW = 1/G(j) and XBND = 1/M(j).
-* Initially, M(0) = max{x(i), i=1,...,n}.
-*
- GROW = ONE / MAX( XBND, SMLNUM )
- XBND = GROW
- DO 60 J = JFIRST, JLAST, JINC
-*
-* Exit the loop if the growth factor is too small.
-*
- IF( GROW.LE.SMLNUM )
- $ GO TO 80
-*
-* G(j) = max( G(j-1), M(j-1)*( 1 + CNORM(j) ) )
-*
- XJ = ONE + CNORM( J )
- GROW = MIN( GROW, XBND / XJ )
-*
-* M(j) = M(j-1)*( 1 + CNORM(j) ) / abs(A(j,j))
-*
- TJJ = ABS( A( J, J ) )
- IF( XJ.GT.TJJ )
- $ XBND = XBND*( TJJ / XJ )
- 60 CONTINUE
- GROW = MIN( GROW, XBND )
- ELSE
-*
-* A is unit triangular.
-*
-* Compute GROW = 1/G(j), where G(0) = max{x(i), i=1,...,n}.
-*
- GROW = MIN( ONE, ONE / MAX( XBND, SMLNUM ) )
- DO 70 J = JFIRST, JLAST, JINC
-*
-* Exit the loop if the growth factor is too small.
-*
- IF( GROW.LE.SMLNUM )
- $ GO TO 80
-*
-* G(j) = ( 1 + CNORM(j) )*G(j-1)
-*
- XJ = ONE + CNORM( J )
- GROW = GROW / XJ
- 70 CONTINUE
- END IF
- 80 CONTINUE
- END IF
-*
- IF( ( GROW*TSCAL ).GT.SMLNUM ) THEN
-*
-* Use the Level 2 BLAS solve if the reciprocal of the bound on
-* elements of X is not too small.
-*
- CALL DTRSV( UPLO, TRANS, DIAG, N, A, LDA, X, 1 )
- ELSE
-*
-* Use a Level 1 BLAS solve, scaling intermediate results.
-*
- IF( XMAX.GT.BIGNUM ) THEN
-*
-* Scale X so that its components are less than or equal to
-* BIGNUM in absolute value.
-*
- SCALE = BIGNUM / XMAX
- CALL DSCAL( N, SCALE, X, 1 )
- XMAX = BIGNUM
- END IF
-*
- IF( NOTRAN ) THEN
-*
-* Solve A * x = b
-*
- DO 110 J = JFIRST, JLAST, JINC
-*
-* Compute x(j) = b(j) / A(j,j), scaling x if necessary.
-*
- XJ = ABS( X( J ) )
- IF( NOUNIT ) THEN
- TJJS = A( J, J )*TSCAL
- ELSE
- TJJS = TSCAL
- IF( TSCAL.EQ.ONE )
- $ GO TO 100
- END IF
- TJJ = ABS( TJJS )
- IF( TJJ.GT.SMLNUM ) THEN
-*
-* abs(A(j,j)) > SMLNUM:
-*
- IF( TJJ.LT.ONE ) THEN
- IF( XJ.GT.TJJ*BIGNUM ) THEN
-*
-* Scale x by 1/b(j).
-*
- REC = ONE / XJ
- CALL DSCAL( N, REC, X, 1 )
- SCALE = SCALE*REC
- XMAX = XMAX*REC
- END IF
- END IF
- X( J ) = X( J ) / TJJS
- XJ = ABS( X( J ) )
- ELSE IF( TJJ.GT.ZERO ) THEN
-*
-* 0 < abs(A(j,j)) <= SMLNUM:
-*
- IF( XJ.GT.TJJ*BIGNUM ) THEN
-*
-* Scale x by (1/abs(x(j)))*abs(A(j,j))*BIGNUM
-* to avoid overflow when dividing by A(j,j).
-*
- REC = ( TJJ*BIGNUM ) / XJ
- IF( CNORM( J ).GT.ONE ) THEN
-*
-* Scale by 1/CNORM(j) to avoid overflow when
-* multiplying x(j) times column j.
-*
- REC = REC / CNORM( J )
- END IF
- CALL DSCAL( N, REC, X, 1 )
- SCALE = SCALE*REC
- XMAX = XMAX*REC
- END IF
- X( J ) = X( J ) / TJJS
- XJ = ABS( X( J ) )
- ELSE
-*
-* A(j,j) = 0: Set x(1:n) = 0, x(j) = 1, and
-* scale = 0, and compute a solution to A*x = 0.
-*
- DO 90 I = 1, N
- X( I ) = ZERO
- 90 CONTINUE
- X( J ) = ONE
- XJ = ONE
- SCALE = ZERO
- XMAX = ZERO
- END IF
- 100 CONTINUE
-*
-* Scale x if necessary to avoid overflow when adding a
-* multiple of column j of A.
-*
- IF( XJ.GT.ONE ) THEN
- REC = ONE / XJ
- IF( CNORM( J ).GT.( BIGNUM-XMAX )*REC ) THEN
-*
-* Scale x by 1/(2*abs(x(j))).
-*
- REC = REC*HALF
- CALL DSCAL( N, REC, X, 1 )
- SCALE = SCALE*REC
- END IF
- ELSE IF( XJ*CNORM( J ).GT.( BIGNUM-XMAX ) ) THEN
-*
-* Scale x by 1/2.
-*
- CALL DSCAL( N, HALF, X, 1 )
- SCALE = SCALE*HALF
- END IF
-*
- IF( UPPER ) THEN
- IF( J.GT.1 ) THEN
-*
-* Compute the update
-* x(1:j-1) := x(1:j-1) - x(j) * A(1:j-1,j)
-*
- CALL DAXPY( J-1, -X( J )*TSCAL, A( 1, J ), 1, X,
- $ 1 )
- I = IDAMAX( J-1, X, 1 )
- XMAX = ABS( X( I ) )
- END IF
- ELSE
- IF( J.LT.N ) THEN
-*
-* Compute the update
-* x(j+1:n) := x(j+1:n) - x(j) * A(j+1:n,j)
-*
- CALL DAXPY( N-J, -X( J )*TSCAL, A( J+1, J ), 1,
- $ X( J+1 ), 1 )
- I = J + IDAMAX( N-J, X( J+1 ), 1 )
- XMAX = ABS( X( I ) )
- END IF
- END IF
- 110 CONTINUE
-*
- ELSE
-*
-* Solve A' * x = b
-*
- DO 160 J = JFIRST, JLAST, JINC
-*
-* Compute x(j) = b(j) - sum A(k,j)*x(k).
-* k<>j
-*
- XJ = ABS( X( J ) )
- USCAL = TSCAL
- REC = ONE / MAX( XMAX, ONE )
- IF( CNORM( J ).GT.( BIGNUM-XJ )*REC ) THEN
-*
-* If x(j) could overflow, scale x by 1/(2*XMAX).
-*
- REC = REC*HALF
- IF( NOUNIT ) THEN
- TJJS = A( J, J )*TSCAL
- ELSE
- TJJS = TSCAL
- END IF
- TJJ = ABS( TJJS )
- IF( TJJ.GT.ONE ) THEN
-*
-* Divide by A(j,j) when scaling x if A(j,j) > 1.
-*
- REC = MIN( ONE, REC*TJJ )
- USCAL = USCAL / TJJS
- END IF
- IF( REC.LT.ONE ) THEN
- CALL DSCAL( N, REC, X, 1 )
- SCALE = SCALE*REC
- XMAX = XMAX*REC
- END IF
- END IF
-*
- SUMJ = ZERO
- IF( USCAL.EQ.ONE ) THEN
-*
-* If the scaling needed for A in the dot product is 1,
-* call DDOT to perform the dot product.
-*
- IF( UPPER ) THEN
- SUMJ = DDOT( J-1, A( 1, J ), 1, X, 1 )
- ELSE IF( J.LT.N ) THEN
- SUMJ = DDOT( N-J, A( J+1, J ), 1, X( J+1 ), 1 )
- END IF
- ELSE
-*
-* Otherwise, use in-line code for the dot product.
-*
- IF( UPPER ) THEN
- DO 120 I = 1, J - 1
- SUMJ = SUMJ + ( A( I, J )*USCAL )*X( I )
- 120 CONTINUE
- ELSE IF( J.LT.N ) THEN
- DO 130 I = J + 1, N
- SUMJ = SUMJ + ( A( I, J )*USCAL )*X( I )
- 130 CONTINUE
- END IF
- END IF
-*
- IF( USCAL.EQ.TSCAL ) THEN
-*
-* Compute x(j) := ( x(j) - sumj ) / A(j,j) if 1/A(j,j)
-* was not used to scale the dotproduct.
-*
- X( J ) = X( J ) - SUMJ
- XJ = ABS( X( J ) )
- IF( NOUNIT ) THEN
- TJJS = A( J, J )*TSCAL
- ELSE
- TJJS = TSCAL
- IF( TSCAL.EQ.ONE )
- $ GO TO 150
- END IF
-*
-* Compute x(j) = x(j) / A(j,j), scaling if necessary.
-*
- TJJ = ABS( TJJS )
- IF( TJJ.GT.SMLNUM ) THEN
-*
-* abs(A(j,j)) > SMLNUM:
-*
- IF( TJJ.LT.ONE ) THEN
- IF( XJ.GT.TJJ*BIGNUM ) THEN
-*
-* Scale X by 1/abs(x(j)).
-*
- REC = ONE / XJ
- CALL DSCAL( N, REC, X, 1 )
- SCALE = SCALE*REC
- XMAX = XMAX*REC
- END IF
- END IF
- X( J ) = X( J ) / TJJS
- ELSE IF( TJJ.GT.ZERO ) THEN
-*
-* 0 < abs(A(j,j)) <= SMLNUM:
-*
- IF( XJ.GT.TJJ*BIGNUM ) THEN
-*
-* Scale x by (1/abs(x(j)))*abs(A(j,j))*BIGNUM.
-*
- REC = ( TJJ*BIGNUM ) / XJ
- CALL DSCAL( N, REC, X, 1 )
- SCALE = SCALE*REC
- XMAX = XMAX*REC
- END IF
- X( J ) = X( J ) / TJJS
- ELSE
-*
-* A(j,j) = 0: Set x(1:n) = 0, x(j) = 1, and
-* scale = 0, and compute a solution to A'*x = 0.
-*
- DO 140 I = 1, N
- X( I ) = ZERO
- 140 CONTINUE
- X( J ) = ONE
- SCALE = ZERO
- XMAX = ZERO
- END IF
- 150 CONTINUE
- ELSE
-*
-* Compute x(j) := x(j) / A(j,j) - sumj if the dot
-* product has already been divided by 1/A(j,j).
-*
- X( J ) = X( J ) / TJJS - SUMJ
- END IF
- XMAX = MAX( XMAX, ABS( X( J ) ) )
- 160 CONTINUE
- END IF
- SCALE = SCALE / TSCAL
- END IF
-*
-* Scale the column norms by 1/TSCAL for return.
-*
- IF( TSCAL.NE.ONE ) THEN
- CALL DSCAL( N, ONE / TSCAL, CNORM, 1 )
- END IF
-*
- RETURN
-*
-* End of DLATRS
-*
- END
diff --git a/src/lib/lapack/dlatrz.f b/src/lib/lapack/dlatrz.f
deleted file mode 100644
index e1a2cf97..00000000
--- a/src/lib/lapack/dlatrz.f
+++ /dev/null
@@ -1,127 +0,0 @@
- SUBROUTINE DLATRZ( M, N, L, A, LDA, TAU, WORK )
-*
-* -- LAPACK routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- INTEGER L, LDA, M, N
-* ..
-* .. Array Arguments ..
- DOUBLE PRECISION A( LDA, * ), TAU( * ), WORK( * )
-* ..
-*
-* Purpose
-* =======
-*
-* DLATRZ factors the M-by-(M+L) real upper trapezoidal matrix
-* [ A1 A2 ] = [ A(1:M,1:M) A(1:M,N-L+1:N) ] as ( R 0 ) * Z, by means
-* of orthogonal transformations. Z is an (M+L)-by-(M+L) orthogonal
-* matrix and, R and A1 are M-by-M upper triangular matrices.
-*
-* Arguments
-* =========
-*
-* M (input) INTEGER
-* The number of rows of the matrix A. M >= 0.
-*
-* N (input) INTEGER
-* The number of columns of the matrix A. N >= 0.
-*
-* L (input) INTEGER
-* The number of columns of the matrix A containing the
-* meaningful part of the Householder vectors. N-M >= L >= 0.
-*
-* A (input/output) DOUBLE PRECISION array, dimension (LDA,N)
-* On entry, the leading M-by-N upper trapezoidal part of the
-* array A must contain the matrix to be factorized.
-* On exit, the leading M-by-M upper triangular part of A
-* contains the upper triangular matrix R, and elements N-L+1 to
-* N of the first M rows of A, with the array TAU, represent the
-* orthogonal matrix Z as a product of M elementary reflectors.
-*
-* LDA (input) INTEGER
-* The leading dimension of the array A. LDA >= max(1,M).
-*
-* TAU (output) DOUBLE PRECISION array, dimension (M)
-* The scalar factors of the elementary reflectors.
-*
-* WORK (workspace) DOUBLE PRECISION array, dimension (M)
-*
-* Further Details
-* ===============
-*
-* Based on contributions by
-* A. Petitet, Computer Science Dept., Univ. of Tenn., Knoxville, USA
-*
-* The factorization is obtained by Householder's method. The kth
-* transformation matrix, Z( k ), which is used to introduce zeros into
-* the ( m - k + 1 )th row of A, is given in the form
-*
-* Z( k ) = ( I 0 ),
-* ( 0 T( k ) )
-*
-* where
-*
-* T( k ) = I - tau*u( k )*u( k )', u( k ) = ( 1 ),
-* ( 0 )
-* ( z( k ) )
-*
-* tau is a scalar and z( k ) is an l element vector. tau and z( k )
-* are chosen to annihilate the elements of the kth row of A2.
-*
-* The scalar tau is returned in the kth element of TAU and the vector
-* u( k ) in the kth row of A2, such that the elements of z( k ) are
-* in a( k, l + 1 ), ..., a( k, n ). The elements of R are returned in
-* the upper triangular part of A1.
-*
-* Z is given by
-*
-* Z = Z( 1 ) * Z( 2 ) * ... * Z( m ).
-*
-* =====================================================================
-*
-* .. Parameters ..
- DOUBLE PRECISION ZERO
- PARAMETER ( ZERO = 0.0D+0 )
-* ..
-* .. Local Scalars ..
- INTEGER I
-* ..
-* .. External Subroutines ..
- EXTERNAL DLARFG, DLARZ
-* ..
-* .. Executable Statements ..
-*
-* Test the input arguments
-*
-* Quick return if possible
-*
- IF( M.EQ.0 ) THEN
- RETURN
- ELSE IF( M.EQ.N ) THEN
- DO 10 I = 1, N
- TAU( I ) = ZERO
- 10 CONTINUE
- RETURN
- END IF
-*
- DO 20 I = M, 1, -1
-*
-* Generate elementary reflector H(i) to annihilate
-* [ A(i,i) A(i,n-l+1:n) ]
-*
- CALL DLARFG( L+1, A( I, I ), A( I, N-L+1 ), LDA, TAU( I ) )
-*
-* Apply H(i) to A(1:i-1,i:n) from the right
-*
- CALL DLARZ( 'Right', I-1, N-I+1, L, A( I, N-L+1 ), LDA,
- $ TAU( I ), A( 1, I ), LDA, WORK )
-*
- 20 CONTINUE
-*
- RETURN
-*
-* End of DLATRZ
-*
- END
diff --git a/src/lib/lapack/dlatzm.f b/src/lib/lapack/dlatzm.f
deleted file mode 100644
index 2467ab60..00000000
--- a/src/lib/lapack/dlatzm.f
+++ /dev/null
@@ -1,142 +0,0 @@
- SUBROUTINE DLATZM( SIDE, M, N, V, INCV, TAU, C1, C2, LDC, WORK )
-*
-* -- LAPACK routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- CHARACTER SIDE
- INTEGER INCV, LDC, M, N
- DOUBLE PRECISION TAU
-* ..
-* .. Array Arguments ..
- DOUBLE PRECISION C1( LDC, * ), C2( LDC, * ), V( * ), WORK( * )
-* ..
-*
-* Purpose
-* =======
-*
-* This routine is deprecated and has been replaced by routine DORMRZ.
-*
-* DLATZM applies a Householder matrix generated by DTZRQF to a matrix.
-*
-* Let P = I - tau*u*u', u = ( 1 ),
-* ( v )
-* where v is an (m-1) vector if SIDE = 'L', or a (n-1) vector if
-* SIDE = 'R'.
-*
-* If SIDE equals 'L', let
-* C = [ C1 ] 1
-* [ C2 ] m-1
-* n
-* Then C is overwritten by P*C.
-*
-* If SIDE equals 'R', let
-* C = [ C1, C2 ] m
-* 1 n-1
-* Then C is overwritten by C*P.
-*
-* Arguments
-* =========
-*
-* SIDE (input) CHARACTER*1
-* = 'L': form P * C
-* = 'R': form C * P
-*
-* M (input) INTEGER
-* The number of rows of the matrix C.
-*
-* N (input) INTEGER
-* The number of columns of the matrix C.
-*
-* V (input) DOUBLE PRECISION array, dimension
-* (1 + (M-1)*abs(INCV)) if SIDE = 'L'
-* (1 + (N-1)*abs(INCV)) if SIDE = 'R'
-* The vector v in the representation of P. V is not used
-* if TAU = 0.
-*
-* INCV (input) INTEGER
-* The increment between elements of v. INCV <> 0
-*
-* TAU (input) DOUBLE PRECISION
-* The value tau in the representation of P.
-*
-* C1 (input/output) DOUBLE PRECISION array, dimension
-* (LDC,N) if SIDE = 'L'
-* (M,1) if SIDE = 'R'
-* On entry, the n-vector C1 if SIDE = 'L', or the m-vector C1
-* if SIDE = 'R'.
-*
-* On exit, the first row of P*C if SIDE = 'L', or the first
-* column of C*P if SIDE = 'R'.
-*
-* C2 (input/output) DOUBLE PRECISION array, dimension
-* (LDC, N) if SIDE = 'L'
-* (LDC, N-1) if SIDE = 'R'
-* On entry, the (m - 1) x n matrix C2 if SIDE = 'L', or the
-* m x (n - 1) matrix C2 if SIDE = 'R'.
-*
-* On exit, rows 2:m of P*C if SIDE = 'L', or columns 2:m of C*P
-* if SIDE = 'R'.
-*
-* LDC (input) INTEGER
-* The leading dimension of the arrays C1 and C2. LDC >= (1,M).
-*
-* WORK (workspace) DOUBLE PRECISION array, dimension
-* (N) if SIDE = 'L'
-* (M) if SIDE = 'R'
-*
-* =====================================================================
-*
-* .. Parameters ..
- DOUBLE PRECISION ONE, ZERO
- PARAMETER ( ONE = 1.0D+0, ZERO = 0.0D+0 )
-* ..
-* .. External Subroutines ..
- EXTERNAL DAXPY, DCOPY, DGEMV, DGER
-* ..
-* .. External Functions ..
- LOGICAL LSAME
- EXTERNAL LSAME
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC MIN
-* ..
-* .. Executable Statements ..
-*
- IF( ( MIN( M, N ).EQ.0 ) .OR. ( TAU.EQ.ZERO ) )
- $ RETURN
-*
- IF( LSAME( SIDE, 'L' ) ) THEN
-*
-* w := C1 + v' * C2
-*
- CALL DCOPY( N, C1, LDC, WORK, 1 )
- CALL DGEMV( 'Transpose', M-1, N, ONE, C2, LDC, V, INCV, ONE,
- $ WORK, 1 )
-*
-* [ C1 ] := [ C1 ] - tau* [ 1 ] * w'
-* [ C2 ] [ C2 ] [ v ]
-*
- CALL DAXPY( N, -TAU, WORK, 1, C1, LDC )
- CALL DGER( M-1, N, -TAU, V, INCV, WORK, 1, C2, LDC )
-*
- ELSE IF( LSAME( SIDE, 'R' ) ) THEN
-*
-* w := C1 + C2 * v
-*
- CALL DCOPY( M, C1, 1, WORK, 1 )
- CALL DGEMV( 'No transpose', M, N-1, ONE, C2, LDC, V, INCV, ONE,
- $ WORK, 1 )
-*
-* [ C1, C2 ] := [ C1, C2 ] - tau* w * [ 1 , v']
-*
- CALL DAXPY( M, -TAU, WORK, 1, C1, 1 )
- CALL DGER( M, N-1, -TAU, WORK, 1, V, INCV, C2, LDC )
- END IF
-*
- RETURN
-*
-* End of DLATZM
-*
- END
diff --git a/src/lib/lapack/dlazq3.f b/src/lib/lapack/dlazq3.f
deleted file mode 100644
index 784248f7..00000000
--- a/src/lib/lapack/dlazq3.f
+++ /dev/null
@@ -1,302 +0,0 @@
- SUBROUTINE DLAZQ3( I0, N0, Z, PP, DMIN, SIGMA, DESIG, QMAX, NFAIL,
- $ ITER, NDIV, IEEE, TTYPE, DMIN1, DMIN2, DN, DN1,
- $ DN2, TAU )
-*
-* -- LAPACK auxiliary routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- LOGICAL IEEE
- INTEGER I0, ITER, N0, NDIV, NFAIL, PP, TTYPE
- DOUBLE PRECISION DESIG, DMIN, DMIN1, DMIN2, DN, DN1, DN2, QMAX,
- $ SIGMA, TAU
-* ..
-* .. Array Arguments ..
- DOUBLE PRECISION Z( * )
-* ..
-*
-* Purpose
-* =======
-*
-* DLAZQ3 checks for deflation, computes a shift (TAU) and calls dqds.
-* In case of failure it changes shifts, and tries again until output
-* is positive.
-*
-* Arguments
-* =========
-*
-* I0 (input) INTEGER
-* First index.
-*
-* N0 (input) INTEGER
-* Last index.
-*
-* Z (input) DOUBLE PRECISION array, dimension ( 4*N )
-* Z holds the qd array.
-*
-* PP (input) INTEGER
-* PP=0 for ping, PP=1 for pong.
-*
-* DMIN (output) DOUBLE PRECISION
-* Minimum value of d.
-*
-* SIGMA (output) DOUBLE PRECISION
-* Sum of shifts used in current segment.
-*
-* DESIG (input/output) DOUBLE PRECISION
-* Lower order part of SIGMA
-*
-* QMAX (input) DOUBLE PRECISION
-* Maximum value of q.
-*
-* NFAIL (output) INTEGER
-* Number of times shift was too big.
-*
-* ITER (output) INTEGER
-* Number of iterations.
-*
-* NDIV (output) INTEGER
-* Number of divisions.
-*
-* IEEE (input) LOGICAL
-* Flag for IEEE or non IEEE arithmetic (passed to DLASQ5).
-*
-* TTYPE (input/output) INTEGER
-* Shift type. TTYPE is passed as an argument in order to save
-* its value between calls to DLAZQ3
-*
-* DMIN1 (input/output) REAL
-* DMIN2 (input/output) REAL
-* DN (input/output) REAL
-* DN1 (input/output) REAL
-* DN2 (input/output) REAL
-* TAU (input/output) REAL
-* These are passed as arguments in order to save their values
-* between calls to DLAZQ3
-*
-* This is a thread safe version of DLASQ3, which passes TTYPE, DMIN1,
-* DMIN2, DN, DN1. DN2 and TAU through the argument list in place of
-* declaring them in a SAVE statment.
-*
-* =====================================================================
-*
-* .. Parameters ..
- DOUBLE PRECISION CBIAS
- PARAMETER ( CBIAS = 1.50D0 )
- DOUBLE PRECISION ZERO, QURTR, HALF, ONE, TWO, HUNDRD
- PARAMETER ( ZERO = 0.0D0, QURTR = 0.250D0, HALF = 0.5D0,
- $ ONE = 1.0D0, TWO = 2.0D0, HUNDRD = 100.0D0 )
-* ..
-* .. Local Scalars ..
- INTEGER IPN4, J4, N0IN, NN
- DOUBLE PRECISION EPS, G, S, SAFMIN, T, TEMP, TOL, TOL2
-* ..
-* .. External Subroutines ..
- EXTERNAL DLASQ5, DLASQ6, DLAZQ4
-* ..
-* .. External Function ..
- DOUBLE PRECISION DLAMCH
- EXTERNAL DLAMCH
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC ABS, MIN, SQRT
-* ..
-* .. Executable Statements ..
-*
- N0IN = N0
- EPS = DLAMCH( 'Precision' )
- SAFMIN = DLAMCH( 'Safe minimum' )
- TOL = EPS*HUNDRD
- TOL2 = TOL**2
- G = ZERO
-*
-* Check for deflation.
-*
- 10 CONTINUE
-*
- IF( N0.LT.I0 )
- $ RETURN
- IF( N0.EQ.I0 )
- $ GO TO 20
- NN = 4*N0 + PP
- IF( N0.EQ.( I0+1 ) )
- $ GO TO 40
-*
-* Check whether E(N0-1) is negligible, 1 eigenvalue.
-*
- IF( Z( NN-5 ).GT.TOL2*( SIGMA+Z( NN-3 ) ) .AND.
- $ Z( NN-2*PP-4 ).GT.TOL2*Z( NN-7 ) )
- $ GO TO 30
-*
- 20 CONTINUE
-*
- Z( 4*N0-3 ) = Z( 4*N0+PP-3 ) + SIGMA
- N0 = N0 - 1
- GO TO 10
-*
-* Check whether E(N0-2) is negligible, 2 eigenvalues.
-*
- 30 CONTINUE
-*
- IF( Z( NN-9 ).GT.TOL2*SIGMA .AND.
- $ Z( NN-2*PP-8 ).GT.TOL2*Z( NN-11 ) )
- $ GO TO 50
-*
- 40 CONTINUE
-*
- IF( Z( NN-3 ).GT.Z( NN-7 ) ) THEN
- S = Z( NN-3 )
- Z( NN-3 ) = Z( NN-7 )
- Z( NN-7 ) = S
- END IF
- IF( Z( NN-5 ).GT.Z( NN-3 )*TOL2 ) THEN
- T = HALF*( ( Z( NN-7 )-Z( NN-3 ) )+Z( NN-5 ) )
- S = Z( NN-3 )*( Z( NN-5 ) / T )
- IF( S.LE.T ) THEN
- S = Z( NN-3 )*( Z( NN-5 ) /
- $ ( T*( ONE+SQRT( ONE+S / T ) ) ) )
- ELSE
- S = Z( NN-3 )*( Z( NN-5 ) / ( T+SQRT( T )*SQRT( T+S ) ) )
- END IF
- T = Z( NN-7 ) + ( S+Z( NN-5 ) )
- Z( NN-3 ) = Z( NN-3 )*( Z( NN-7 ) / T )
- Z( NN-7 ) = T
- END IF
- Z( 4*N0-7 ) = Z( NN-7 ) + SIGMA
- Z( 4*N0-3 ) = Z( NN-3 ) + SIGMA
- N0 = N0 - 2
- GO TO 10
-*
- 50 CONTINUE
-*
-* Reverse the qd-array, if warranted.
-*
- IF( DMIN.LE.ZERO .OR. N0.LT.N0IN ) THEN
- IF( CBIAS*Z( 4*I0+PP-3 ).LT.Z( 4*N0+PP-3 ) ) THEN
- IPN4 = 4*( I0+N0 )
- DO 60 J4 = 4*I0, 2*( I0+N0-1 ), 4
- TEMP = Z( J4-3 )
- Z( J4-3 ) = Z( IPN4-J4-3 )
- Z( IPN4-J4-3 ) = TEMP
- TEMP = Z( J4-2 )
- Z( J4-2 ) = Z( IPN4-J4-2 )
- Z( IPN4-J4-2 ) = TEMP
- TEMP = Z( J4-1 )
- Z( J4-1 ) = Z( IPN4-J4-5 )
- Z( IPN4-J4-5 ) = TEMP
- TEMP = Z( J4 )
- Z( J4 ) = Z( IPN4-J4-4 )
- Z( IPN4-J4-4 ) = TEMP
- 60 CONTINUE
- IF( N0-I0.LE.4 ) THEN
- Z( 4*N0+PP-1 ) = Z( 4*I0+PP-1 )
- Z( 4*N0-PP ) = Z( 4*I0-PP )
- END IF
- DMIN2 = MIN( DMIN2, Z( 4*N0+PP-1 ) )
- Z( 4*N0+PP-1 ) = MIN( Z( 4*N0+PP-1 ), Z( 4*I0+PP-1 ),
- $ Z( 4*I0+PP+3 ) )
- Z( 4*N0-PP ) = MIN( Z( 4*N0-PP ), Z( 4*I0-PP ),
- $ Z( 4*I0-PP+4 ) )
- QMAX = MAX( QMAX, Z( 4*I0+PP-3 ), Z( 4*I0+PP+1 ) )
- DMIN = -ZERO
- END IF
- END IF
-*
- IF( DMIN.LT.ZERO .OR. SAFMIN*QMAX.LT.MIN( Z( 4*N0+PP-1 ),
- $ Z( 4*N0+PP-9 ), DMIN2+Z( 4*N0-PP ) ) ) THEN
-*
-* Choose a shift.
-*
- CALL DLAZQ4( I0, N0, Z, PP, N0IN, DMIN, DMIN1, DMIN2, DN, DN1,
- $ DN2, TAU, TTYPE, G )
-*
-* Call dqds until DMIN > 0.
-*
- 80 CONTINUE
-*
- CALL DLASQ5( I0, N0, Z, PP, TAU, DMIN, DMIN1, DMIN2, DN,
- $ DN1, DN2, IEEE )
-*
- NDIV = NDIV + ( N0-I0+2 )
- ITER = ITER + 1
-*
-* Check status.
-*
- IF( DMIN.GE.ZERO .AND. DMIN1.GT.ZERO ) THEN
-*
-* Success.
-*
- GO TO 100
-*
- ELSE IF( DMIN.LT.ZERO .AND. DMIN1.GT.ZERO .AND.
- $ Z( 4*( N0-1 )-PP ).LT.TOL*( SIGMA+DN1 ) .AND.
- $ ABS( DN ).LT.TOL*SIGMA ) THEN
-*
-* Convergence hidden by negative DN.
-*
- Z( 4*( N0-1 )-PP+2 ) = ZERO
- DMIN = ZERO
- GO TO 100
- ELSE IF( DMIN.LT.ZERO ) THEN
-*
-* TAU too big. Select new TAU and try again.
-*
- NFAIL = NFAIL + 1
- IF( TTYPE.LT.-22 ) THEN
-*
-* Failed twice. Play it safe.
-*
- TAU = ZERO
- ELSE IF( DMIN1.GT.ZERO ) THEN
-*
-* Late failure. Gives excellent shift.
-*
- TAU = ( TAU+DMIN )*( ONE-TWO*EPS )
- TTYPE = TTYPE - 11
- ELSE
-*
-* Early failure. Divide by 4.
-*
- TAU = QURTR*TAU
- TTYPE = TTYPE - 12
- END IF
- GO TO 80
- ELSE IF( DMIN.NE.DMIN ) THEN
-*
-* NaN.
-*
- TAU = ZERO
- GO TO 80
- ELSE
-*
-* Possible underflow. Play it safe.
-*
- GO TO 90
- END IF
- END IF
-*
-* Risk of underflow.
-*
- 90 CONTINUE
- CALL DLASQ6( I0, N0, Z, PP, DMIN, DMIN1, DMIN2, DN, DN1, DN2 )
- NDIV = NDIV + ( N0-I0+2 )
- ITER = ITER + 1
- TAU = ZERO
-*
- 100 CONTINUE
- IF( TAU.LT.SIGMA ) THEN
- DESIG = DESIG + TAU
- T = SIGMA + DESIG
- DESIG = DESIG - ( T-SIGMA )
- ELSE
- T = SIGMA + TAU
- DESIG = SIGMA - ( T-TAU ) + DESIG
- END IF
- SIGMA = T
-*
- RETURN
-*
-* End of DLAZQ3
-*
- END
diff --git a/src/lib/lapack/dlazq4.f b/src/lib/lapack/dlazq4.f
deleted file mode 100644
index 7c257f8d..00000000
--- a/src/lib/lapack/dlazq4.f
+++ /dev/null
@@ -1,330 +0,0 @@
- SUBROUTINE DLAZQ4( I0, N0, Z, PP, N0IN, DMIN, DMIN1, DMIN2, DN,
- $ DN1, DN2, TAU, TTYPE, G )
-*
-* -- LAPACK auxiliary routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- INTEGER I0, N0, N0IN, PP, TTYPE
- DOUBLE PRECISION DMIN, DMIN1, DMIN2, DN, DN1, DN2, G, TAU
-* ..
-* .. Array Arguments ..
- DOUBLE PRECISION Z( * )
-* ..
-*
-* Purpose
-* =======
-*
-* DLAZQ4 computes an approximation TAU to the smallest eigenvalue
-* using values of d from the previous transform.
-*
-* I0 (input) INTEGER
-* First index.
-*
-* N0 (input) INTEGER
-* Last index.
-*
-* Z (input) DOUBLE PRECISION array, dimension ( 4*N )
-* Z holds the qd array.
-*
-* PP (input) INTEGER
-* PP=0 for ping, PP=1 for pong.
-*
-* N0IN (input) INTEGER
-* The value of N0 at start of EIGTEST.
-*
-* DMIN (input) DOUBLE PRECISION
-* Minimum value of d.
-*
-* DMIN1 (input) DOUBLE PRECISION
-* Minimum value of d, excluding D( N0 ).
-*
-* DMIN2 (input) DOUBLE PRECISION
-* Minimum value of d, excluding D( N0 ) and D( N0-1 ).
-*
-* DN (input) DOUBLE PRECISION
-* d(N)
-*
-* DN1 (input) DOUBLE PRECISION
-* d(N-1)
-*
-* DN2 (input) DOUBLE PRECISION
-* d(N-2)
-*
-* TAU (output) DOUBLE PRECISION
-* This is the shift.
-*
-* TTYPE (output) INTEGER
-* Shift type.
-*
-* G (input/output) DOUBLE PRECISION
-* G is passed as an argument in order to save its value between
-* calls to DLAZQ4
-*
-* Further Details
-* ===============
-* CNST1 = 9/16
-*
-* This is a thread safe version of DLASQ4, which passes G through the
-* argument list in place of declaring G in a SAVE statment.
-*
-* =====================================================================
-*
-* .. Parameters ..
- DOUBLE PRECISION CNST1, CNST2, CNST3
- PARAMETER ( CNST1 = 0.5630D0, CNST2 = 1.010D0,
- $ CNST3 = 1.050D0 )
- DOUBLE PRECISION QURTR, THIRD, HALF, ZERO, ONE, TWO, HUNDRD
- PARAMETER ( QURTR = 0.250D0, THIRD = 0.3330D0,
- $ HALF = 0.50D0, ZERO = 0.0D0, ONE = 1.0D0,
- $ TWO = 2.0D0, HUNDRD = 100.0D0 )
-* ..
-* .. Local Scalars ..
- INTEGER I4, NN, NP
- DOUBLE PRECISION A2, B1, B2, GAM, GAP1, GAP2, S
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC MAX, MIN, SQRT
-* ..
-* .. Executable Statements ..
-*
-* A negative DMIN forces the shift to take that absolute value
-* TTYPE records the type of shift.
-*
- IF( DMIN.LE.ZERO ) THEN
- TAU = -DMIN
- TTYPE = -1
- RETURN
- END IF
-*
- NN = 4*N0 + PP
- IF( N0IN.EQ.N0 ) THEN
-*
-* No eigenvalues deflated.
-*
- IF( DMIN.EQ.DN .OR. DMIN.EQ.DN1 ) THEN
-*
- B1 = SQRT( Z( NN-3 ) )*SQRT( Z( NN-5 ) )
- B2 = SQRT( Z( NN-7 ) )*SQRT( Z( NN-9 ) )
- A2 = Z( NN-7 ) + Z( NN-5 )
-*
-* Cases 2 and 3.
-*
- IF( DMIN.EQ.DN .AND. DMIN1.EQ.DN1 ) THEN
- GAP2 = DMIN2 - A2 - DMIN2*QURTR
- IF( GAP2.GT.ZERO .AND. GAP2.GT.B2 ) THEN
- GAP1 = A2 - DN - ( B2 / GAP2 )*B2
- ELSE
- GAP1 = A2 - DN - ( B1+B2 )
- END IF
- IF( GAP1.GT.ZERO .AND. GAP1.GT.B1 ) THEN
- S = MAX( DN-( B1 / GAP1 )*B1, HALF*DMIN )
- TTYPE = -2
- ELSE
- S = ZERO
- IF( DN.GT.B1 )
- $ S = DN - B1
- IF( A2.GT.( B1+B2 ) )
- $ S = MIN( S, A2-( B1+B2 ) )
- S = MAX( S, THIRD*DMIN )
- TTYPE = -3
- END IF
- ELSE
-*
-* Case 4.
-*
- TTYPE = -4
- S = QURTR*DMIN
- IF( DMIN.EQ.DN ) THEN
- GAM = DN
- A2 = ZERO
- IF( Z( NN-5 ) .GT. Z( NN-7 ) )
- $ RETURN
- B2 = Z( NN-5 ) / Z( NN-7 )
- NP = NN - 9
- ELSE
- NP = NN - 2*PP
- B2 = Z( NP-2 )
- GAM = DN1
- IF( Z( NP-4 ) .GT. Z( NP-2 ) )
- $ RETURN
- A2 = Z( NP-4 ) / Z( NP-2 )
- IF( Z( NN-9 ) .GT. Z( NN-11 ) )
- $ RETURN
- B2 = Z( NN-9 ) / Z( NN-11 )
- NP = NN - 13
- END IF
-*
-* Approximate contribution to norm squared from I < NN-1.
-*
- A2 = A2 + B2
- DO 10 I4 = NP, 4*I0 - 1 + PP, -4
- IF( B2.EQ.ZERO )
- $ GO TO 20
- B1 = B2
- IF( Z( I4 ) .GT. Z( I4-2 ) )
- $ RETURN
- B2 = B2*( Z( I4 ) / Z( I4-2 ) )
- A2 = A2 + B2
- IF( HUNDRD*MAX( B2, B1 ).LT.A2 .OR. CNST1.LT.A2 )
- $ GO TO 20
- 10 CONTINUE
- 20 CONTINUE
- A2 = CNST3*A2
-*
-* Rayleigh quotient residual bound.
-*
- IF( A2.LT.CNST1 )
- $ S = GAM*( ONE-SQRT( A2 ) ) / ( ONE+A2 )
- END IF
- ELSE IF( DMIN.EQ.DN2 ) THEN
-*
-* Case 5.
-*
- TTYPE = -5
- S = QURTR*DMIN
-*
-* Compute contribution to norm squared from I > NN-2.
-*
- NP = NN - 2*PP
- B1 = Z( NP-2 )
- B2 = Z( NP-6 )
- GAM = DN2
- IF( Z( NP-8 ).GT.B2 .OR. Z( NP-4 ).GT.B1 )
- $ RETURN
- A2 = ( Z( NP-8 ) / B2 )*( ONE+Z( NP-4 ) / B1 )
-*
-* Approximate contribution to norm squared from I < NN-2.
-*
- IF( N0-I0.GT.2 ) THEN
- B2 = Z( NN-13 ) / Z( NN-15 )
- A2 = A2 + B2
- DO 30 I4 = NN - 17, 4*I0 - 1 + PP, -4
- IF( B2.EQ.ZERO )
- $ GO TO 40
- B1 = B2
- IF( Z( I4 ) .GT. Z( I4-2 ) )
- $ RETURN
- B2 = B2*( Z( I4 ) / Z( I4-2 ) )
- A2 = A2 + B2
- IF( HUNDRD*MAX( B2, B1 ).LT.A2 .OR. CNST1.LT.A2 )
- $ GO TO 40
- 30 CONTINUE
- 40 CONTINUE
- A2 = CNST3*A2
- END IF
-*
- IF( A2.LT.CNST1 )
- $ S = GAM*( ONE-SQRT( A2 ) ) / ( ONE+A2 )
- ELSE
-*
-* Case 6, no information to guide us.
-*
- IF( TTYPE.EQ.-6 ) THEN
- G = G + THIRD*( ONE-G )
- ELSE IF( TTYPE.EQ.-18 ) THEN
- G = QURTR*THIRD
- ELSE
- G = QURTR
- END IF
- S = G*DMIN
- TTYPE = -6
- END IF
-*
- ELSE IF( N0IN.EQ.( N0+1 ) ) THEN
-*
-* One eigenvalue just deflated. Use DMIN1, DN1 for DMIN and DN.
-*
- IF( DMIN1.EQ.DN1 .AND. DMIN2.EQ.DN2 ) THEN
-*
-* Cases 7 and 8.
-*
- TTYPE = -7
- S = THIRD*DMIN1
- IF( Z( NN-5 ).GT.Z( NN-7 ) )
- $ RETURN
- B1 = Z( NN-5 ) / Z( NN-7 )
- B2 = B1
- IF( B2.EQ.ZERO )
- $ GO TO 60
- DO 50 I4 = 4*N0 - 9 + PP, 4*I0 - 1 + PP, -4
- A2 = B1
- IF( Z( I4 ).GT.Z( I4-2 ) )
- $ RETURN
- B1 = B1*( Z( I4 ) / Z( I4-2 ) )
- B2 = B2 + B1
- IF( HUNDRD*MAX( B1, A2 ).LT.B2 )
- $ GO TO 60
- 50 CONTINUE
- 60 CONTINUE
- B2 = SQRT( CNST3*B2 )
- A2 = DMIN1 / ( ONE+B2**2 )
- GAP2 = HALF*DMIN2 - A2
- IF( GAP2.GT.ZERO .AND. GAP2.GT.B2*A2 ) THEN
- S = MAX( S, A2*( ONE-CNST2*A2*( B2 / GAP2 )*B2 ) )
- ELSE
- S = MAX( S, A2*( ONE-CNST2*B2 ) )
- TTYPE = -8
- END IF
- ELSE
-*
-* Case 9.
-*
- S = QURTR*DMIN1
- IF( DMIN1.EQ.DN1 )
- $ S = HALF*DMIN1
- TTYPE = -9
- END IF
-*
- ELSE IF( N0IN.EQ.( N0+2 ) ) THEN
-*
-* Two eigenvalues deflated. Use DMIN2, DN2 for DMIN and DN.
-*
-* Cases 10 and 11.
-*
- IF( DMIN2.EQ.DN2 .AND. TWO*Z( NN-5 ).LT.Z( NN-7 ) ) THEN
- TTYPE = -10
- S = THIRD*DMIN2
- IF( Z( NN-5 ).GT.Z( NN-7 ) )
- $ RETURN
- B1 = Z( NN-5 ) / Z( NN-7 )
- B2 = B1
- IF( B2.EQ.ZERO )
- $ GO TO 80
- DO 70 I4 = 4*N0 - 9 + PP, 4*I0 - 1 + PP, -4
- IF( Z( I4 ).GT.Z( I4-2 ) )
- $ RETURN
- B1 = B1*( Z( I4 ) / Z( I4-2 ) )
- B2 = B2 + B1
- IF( HUNDRD*B1.LT.B2 )
- $ GO TO 80
- 70 CONTINUE
- 80 CONTINUE
- B2 = SQRT( CNST3*B2 )
- A2 = DMIN2 / ( ONE+B2**2 )
- GAP2 = Z( NN-7 ) + Z( NN-9 ) -
- $ SQRT( Z( NN-11 ) )*SQRT( Z( NN-9 ) ) - A2
- IF( GAP2.GT.ZERO .AND. GAP2.GT.B2*A2 ) THEN
- S = MAX( S, A2*( ONE-CNST2*A2*( B2 / GAP2 )*B2 ) )
- ELSE
- S = MAX( S, A2*( ONE-CNST2*B2 ) )
- END IF
- ELSE
- S = QURTR*DMIN2
- TTYPE = -11
- END IF
- ELSE IF( N0IN.GT.( N0+2 ) ) THEN
-*
-* Case 12, more than two eigenvalues deflated. No information.
-*
- S = ZERO
- TTYPE = -12
- END IF
-*
- TAU = S
- RETURN
-*
-* End of DLAZQ4
-*
- END
diff --git a/src/lib/lapack/dopgtr.f b/src/lib/lapack/dopgtr.f
deleted file mode 100644
index cf0901ff..00000000
--- a/src/lib/lapack/dopgtr.f
+++ /dev/null
@@ -1,160 +0,0 @@
- SUBROUTINE DOPGTR( UPLO, N, AP, TAU, Q, LDQ, WORK, INFO )
-*
-* -- LAPACK routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- CHARACTER UPLO
- INTEGER INFO, LDQ, N
-* ..
-* .. Array Arguments ..
- DOUBLE PRECISION AP( * ), Q( LDQ, * ), TAU( * ), WORK( * )
-* ..
-*
-* Purpose
-* =======
-*
-* DOPGTR generates a real orthogonal matrix Q which is defined as the
-* product of n-1 elementary reflectors H(i) of order n, as returned by
-* DSPTRD using packed storage:
-*
-* if UPLO = 'U', Q = H(n-1) . . . H(2) H(1),
-*
-* if UPLO = 'L', Q = H(1) H(2) . . . H(n-1).
-*
-* Arguments
-* =========
-*
-* UPLO (input) CHARACTER*1
-* = 'U': Upper triangular packed storage used in previous
-* call to DSPTRD;
-* = 'L': Lower triangular packed storage used in previous
-* call to DSPTRD.
-*
-* N (input) INTEGER
-* The order of the matrix Q. N >= 0.
-*
-* AP (input) DOUBLE PRECISION array, dimension (N*(N+1)/2)
-* The vectors which define the elementary reflectors, as
-* returned by DSPTRD.
-*
-* TAU (input) DOUBLE PRECISION array, dimension (N-1)
-* TAU(i) must contain the scalar factor of the elementary
-* reflector H(i), as returned by DSPTRD.
-*
-* Q (output) DOUBLE PRECISION array, dimension (LDQ,N)
-* The N-by-N orthogonal matrix Q.
-*
-* LDQ (input) INTEGER
-* The leading dimension of the array Q. LDQ >= max(1,N).
-*
-* WORK (workspace) DOUBLE PRECISION array, dimension (N-1)
-*
-* INFO (output) INTEGER
-* = 0: successful exit
-* < 0: if INFO = -i, the i-th argument had an illegal value
-*
-* =====================================================================
-*
-* .. Parameters ..
- DOUBLE PRECISION ZERO, ONE
- PARAMETER ( ZERO = 0.0D+0, ONE = 1.0D+0 )
-* ..
-* .. Local Scalars ..
- LOGICAL UPPER
- INTEGER I, IINFO, IJ, J
-* ..
-* .. External Functions ..
- LOGICAL LSAME
- EXTERNAL LSAME
-* ..
-* .. External Subroutines ..
- EXTERNAL DORG2L, DORG2R, XERBLA
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC MAX
-* ..
-* .. Executable Statements ..
-*
-* Test the input arguments
-*
- INFO = 0
- UPPER = LSAME( UPLO, 'U' )
- IF( .NOT.UPPER .AND. .NOT.LSAME( UPLO, 'L' ) ) THEN
- INFO = -1
- ELSE IF( N.LT.0 ) THEN
- INFO = -2
- ELSE IF( LDQ.LT.MAX( 1, N ) ) THEN
- INFO = -6
- END IF
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'DOPGTR', -INFO )
- RETURN
- END IF
-*
-* Quick return if possible
-*
- IF( N.EQ.0 )
- $ RETURN
-*
- IF( UPPER ) THEN
-*
-* Q was determined by a call to DSPTRD with UPLO = 'U'
-*
-* Unpack the vectors which define the elementary reflectors and
-* set the last row and column of Q equal to those of the unit
-* matrix
-*
- IJ = 2
- DO 20 J = 1, N - 1
- DO 10 I = 1, J - 1
- Q( I, J ) = AP( IJ )
- IJ = IJ + 1
- 10 CONTINUE
- IJ = IJ + 2
- Q( N, J ) = ZERO
- 20 CONTINUE
- DO 30 I = 1, N - 1
- Q( I, N ) = ZERO
- 30 CONTINUE
- Q( N, N ) = ONE
-*
-* Generate Q(1:n-1,1:n-1)
-*
- CALL DORG2L( N-1, N-1, N-1, Q, LDQ, TAU, WORK, IINFO )
-*
- ELSE
-*
-* Q was determined by a call to DSPTRD with UPLO = 'L'.
-*
-* Unpack the vectors which define the elementary reflectors and
-* set the first row and column of Q equal to those of the unit
-* matrix
-*
- Q( 1, 1 ) = ONE
- DO 40 I = 2, N
- Q( I, 1 ) = ZERO
- 40 CONTINUE
- IJ = 3
- DO 60 J = 2, N
- Q( 1, J ) = ZERO
- DO 50 I = J + 1, N
- Q( I, J ) = AP( IJ )
- IJ = IJ + 1
- 50 CONTINUE
- IJ = IJ + 2
- 60 CONTINUE
- IF( N.GT.1 ) THEN
-*
-* Generate Q(2:n,2:n)
-*
- CALL DORG2R( N-1, N-1, N-1, Q( 2, 2 ), LDQ, TAU, WORK,
- $ IINFO )
- END IF
- END IF
- RETURN
-*
-* End of DOPGTR
-*
- END
diff --git a/src/lib/lapack/dorg2l.f b/src/lib/lapack/dorg2l.f
deleted file mode 100644
index a20965fd..00000000
--- a/src/lib/lapack/dorg2l.f
+++ /dev/null
@@ -1,127 +0,0 @@
- SUBROUTINE DORG2L( M, N, K, A, LDA, TAU, WORK, INFO )
-*
-* -- LAPACK routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- INTEGER INFO, K, LDA, M, N
-* ..
-* .. Array Arguments ..
- DOUBLE PRECISION A( LDA, * ), TAU( * ), WORK( * )
-* ..
-*
-* Purpose
-* =======
-*
-* DORG2L generates an m by n real matrix Q with orthonormal columns,
-* which is defined as the last n columns of a product of k elementary
-* reflectors of order m
-*
-* Q = H(k) . . . H(2) H(1)
-*
-* as returned by DGEQLF.
-*
-* Arguments
-* =========
-*
-* M (input) INTEGER
-* The number of rows of the matrix Q. M >= 0.
-*
-* N (input) INTEGER
-* The number of columns of the matrix Q. M >= N >= 0.
-*
-* K (input) INTEGER
-* The number of elementary reflectors whose product defines the
-* matrix Q. N >= K >= 0.
-*
-* A (input/output) DOUBLE PRECISION array, dimension (LDA,N)
-* On entry, the (n-k+i)-th column must contain the vector which
-* defines the elementary reflector H(i), for i = 1,2,...,k, as
-* returned by DGEQLF in the last k columns of its array
-* argument A.
-* On exit, the m by n matrix Q.
-*
-* LDA (input) INTEGER
-* The first dimension of the array A. LDA >= max(1,M).
-*
-* TAU (input) DOUBLE PRECISION array, dimension (K)
-* TAU(i) must contain the scalar factor of the elementary
-* reflector H(i), as returned by DGEQLF.
-*
-* WORK (workspace) DOUBLE PRECISION array, dimension (N)
-*
-* INFO (output) INTEGER
-* = 0: successful exit
-* < 0: if INFO = -i, the i-th argument has an illegal value
-*
-* =====================================================================
-*
-* .. Parameters ..
- DOUBLE PRECISION ONE, ZERO
- PARAMETER ( ONE = 1.0D+0, ZERO = 0.0D+0 )
-* ..
-* .. Local Scalars ..
- INTEGER I, II, J, L
-* ..
-* .. External Subroutines ..
- EXTERNAL DLARF, DSCAL, XERBLA
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC MAX
-* ..
-* .. Executable Statements ..
-*
-* Test the input arguments
-*
- INFO = 0
- IF( M.LT.0 ) THEN
- INFO = -1
- ELSE IF( N.LT.0 .OR. N.GT.M ) THEN
- INFO = -2
- ELSE IF( K.LT.0 .OR. K.GT.N ) THEN
- INFO = -3
- ELSE IF( LDA.LT.MAX( 1, M ) ) THEN
- INFO = -5
- END IF
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'DORG2L', -INFO )
- RETURN
- END IF
-*
-* Quick return if possible
-*
- IF( N.LE.0 )
- $ RETURN
-*
-* Initialise columns 1:n-k to columns of the unit matrix
-*
- DO 20 J = 1, N - K
- DO 10 L = 1, M
- A( L, J ) = ZERO
- 10 CONTINUE
- A( M-N+J, J ) = ONE
- 20 CONTINUE
-*
- DO 40 I = 1, K
- II = N - K + I
-*
-* Apply H(i) to A(1:m-k+i,1:n-k+i) from the left
-*
- A( M-N+II, II ) = ONE
- CALL DLARF( 'Left', M-N+II, II-1, A( 1, II ), 1, TAU( I ), A,
- $ LDA, WORK )
- CALL DSCAL( M-N+II-1, -TAU( I ), A( 1, II ), 1 )
- A( M-N+II, II ) = ONE - TAU( I )
-*
-* Set A(m-k+i+1:m,n-k+i) to zero
-*
- DO 30 L = M - N + II + 1, M
- A( L, II ) = ZERO
- 30 CONTINUE
- 40 CONTINUE
- RETURN
-*
-* End of DORG2L
-*
- END
diff --git a/src/lib/lapack/dorg2r.f b/src/lib/lapack/dorg2r.f
deleted file mode 100644
index 476e9f70..00000000
--- a/src/lib/lapack/dorg2r.f
+++ /dev/null
@@ -1,129 +0,0 @@
- SUBROUTINE DORG2R( M, N, K, A, LDA, TAU, WORK, INFO )
-*
-* -- LAPACK routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- INTEGER INFO, K, LDA, M, N
-* ..
-* .. Array Arguments ..
- DOUBLE PRECISION A( LDA, * ), TAU( * ), WORK( * )
-* ..
-*
-* Purpose
-* =======
-*
-* DORG2R generates an m by n real matrix Q with orthonormal columns,
-* which is defined as the first n columns of a product of k elementary
-* reflectors of order m
-*
-* Q = H(1) H(2) . . . H(k)
-*
-* as returned by DGEQRF.
-*
-* Arguments
-* =========
-*
-* M (input) INTEGER
-* The number of rows of the matrix Q. M >= 0.
-*
-* N (input) INTEGER
-* The number of columns of the matrix Q. M >= N >= 0.
-*
-* K (input) INTEGER
-* The number of elementary reflectors whose product defines the
-* matrix Q. N >= K >= 0.
-*
-* A (input/output) DOUBLE PRECISION array, dimension (LDA,N)
-* On entry, the i-th column must contain the vector which
-* defines the elementary reflector H(i), for i = 1,2,...,k, as
-* returned by DGEQRF in the first k columns of its array
-* argument A.
-* On exit, the m-by-n matrix Q.
-*
-* LDA (input) INTEGER
-* The first dimension of the array A. LDA >= max(1,M).
-*
-* TAU (input) DOUBLE PRECISION array, dimension (K)
-* TAU(i) must contain the scalar factor of the elementary
-* reflector H(i), as returned by DGEQRF.
-*
-* WORK (workspace) DOUBLE PRECISION array, dimension (N)
-*
-* INFO (output) INTEGER
-* = 0: successful exit
-* < 0: if INFO = -i, the i-th argument has an illegal value
-*
-* =====================================================================
-*
-* .. Parameters ..
- DOUBLE PRECISION ONE, ZERO
- PARAMETER ( ONE = 1.0D+0, ZERO = 0.0D+0 )
-* ..
-* .. Local Scalars ..
- INTEGER I, J, L
-* ..
-* .. External Subroutines ..
- EXTERNAL DLARF, DSCAL, XERBLA
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC MAX
-* ..
-* .. Executable Statements ..
-*
-* Test the input arguments
-*
- INFO = 0
- IF( M.LT.0 ) THEN
- INFO = -1
- ELSE IF( N.LT.0 .OR. N.GT.M ) THEN
- INFO = -2
- ELSE IF( K.LT.0 .OR. K.GT.N ) THEN
- INFO = -3
- ELSE IF( LDA.LT.MAX( 1, M ) ) THEN
- INFO = -5
- END IF
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'DORG2R', -INFO )
- RETURN
- END IF
-*
-* Quick return if possible
-*
- IF( N.LE.0 )
- $ RETURN
-*
-* Initialise columns k+1:n to columns of the unit matrix
-*
- DO 20 J = K + 1, N
- DO 10 L = 1, M
- A( L, J ) = ZERO
- 10 CONTINUE
- A( J, J ) = ONE
- 20 CONTINUE
-*
- DO 40 I = K, 1, -1
-*
-* Apply H(i) to A(i:m,i:n) from the left
-*
- IF( I.LT.N ) THEN
- A( I, I ) = ONE
- CALL DLARF( 'Left', M-I+1, N-I, A( I, I ), 1, TAU( I ),
- $ A( I, I+1 ), LDA, WORK )
- END IF
- IF( I.LT.M )
- $ CALL DSCAL( M-I, -TAU( I ), A( I+1, I ), 1 )
- A( I, I ) = ONE - TAU( I )
-*
-* Set A(1:i-1,i) to zero
-*
- DO 30 L = 1, I - 1
- A( L, I ) = ZERO
- 30 CONTINUE
- 40 CONTINUE
- RETURN
-*
-* End of DORG2R
-*
- END
diff --git a/src/lib/lapack/dorgbr.f b/src/lib/lapack/dorgbr.f
deleted file mode 100644
index dc882990..00000000
--- a/src/lib/lapack/dorgbr.f
+++ /dev/null
@@ -1,244 +0,0 @@
- SUBROUTINE DORGBR( VECT, M, N, K, A, LDA, TAU, WORK, LWORK, INFO )
-*
-* -- LAPACK routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- CHARACTER VECT
- INTEGER INFO, K, LDA, LWORK, M, N
-* ..
-* .. Array Arguments ..
- DOUBLE PRECISION A( LDA, * ), TAU( * ), WORK( * )
-* ..
-*
-* Purpose
-* =======
-*
-* DORGBR generates one of the real orthogonal matrices Q or P**T
-* determined by DGEBRD when reducing a real matrix A to bidiagonal
-* form: A = Q * B * P**T. Q and P**T are defined as products of
-* elementary reflectors H(i) or G(i) respectively.
-*
-* If VECT = 'Q', A is assumed to have been an M-by-K matrix, and Q
-* is of order M:
-* if m >= k, Q = H(1) H(2) . . . H(k) and DORGBR returns the first n
-* columns of Q, where m >= n >= k;
-* if m < k, Q = H(1) H(2) . . . H(m-1) and DORGBR returns Q as an
-* M-by-M matrix.
-*
-* If VECT = 'P', A is assumed to have been a K-by-N matrix, and P**T
-* is of order N:
-* if k < n, P**T = G(k) . . . G(2) G(1) and DORGBR returns the first m
-* rows of P**T, where n >= m >= k;
-* if k >= n, P**T = G(n-1) . . . G(2) G(1) and DORGBR returns P**T as
-* an N-by-N matrix.
-*
-* Arguments
-* =========
-*
-* VECT (input) CHARACTER*1
-* Specifies whether the matrix Q or the matrix P**T is
-* required, as defined in the transformation applied by DGEBRD:
-* = 'Q': generate Q;
-* = 'P': generate P**T.
-*
-* M (input) INTEGER
-* The number of rows of the matrix Q or P**T to be returned.
-* M >= 0.
-*
-* N (input) INTEGER
-* The number of columns of the matrix Q or P**T to be returned.
-* N >= 0.
-* If VECT = 'Q', M >= N >= min(M,K);
-* if VECT = 'P', N >= M >= min(N,K).
-*
-* K (input) INTEGER
-* If VECT = 'Q', the number of columns in the original M-by-K
-* matrix reduced by DGEBRD.
-* If VECT = 'P', the number of rows in the original K-by-N
-* matrix reduced by DGEBRD.
-* K >= 0.
-*
-* A (input/output) DOUBLE PRECISION array, dimension (LDA,N)
-* On entry, the vectors which define the elementary reflectors,
-* as returned by DGEBRD.
-* On exit, the M-by-N matrix Q or P**T.
-*
-* LDA (input) INTEGER
-* The leading dimension of the array A. LDA >= max(1,M).
-*
-* TAU (input) DOUBLE PRECISION array, dimension
-* (min(M,K)) if VECT = 'Q'
-* (min(N,K)) if VECT = 'P'
-* TAU(i) must contain the scalar factor of the elementary
-* reflector H(i) or G(i), which determines Q or P**T, as
-* returned by DGEBRD in its array argument TAUQ or TAUP.
-*
-* WORK (workspace/output) DOUBLE PRECISION array, dimension (MAX(1,LWORK))
-* On exit, if INFO = 0, WORK(1) returns the optimal LWORK.
-*
-* LWORK (input) INTEGER
-* The dimension of the array WORK. LWORK >= max(1,min(M,N)).
-* For optimum performance LWORK >= min(M,N)*NB, where NB
-* is the optimal blocksize.
-*
-* If LWORK = -1, then a workspace query is assumed; the routine
-* only calculates the optimal size of the WORK array, returns
-* this value as the first entry of the WORK array, and no error
-* message related to LWORK is issued by XERBLA.
-*
-* INFO (output) INTEGER
-* = 0: successful exit
-* < 0: if INFO = -i, the i-th argument had an illegal value
-*
-* =====================================================================
-*
-* .. Parameters ..
- DOUBLE PRECISION ZERO, ONE
- PARAMETER ( ZERO = 0.0D+0, ONE = 1.0D+0 )
-* ..
-* .. Local Scalars ..
- LOGICAL LQUERY, WANTQ
- INTEGER I, IINFO, J, LWKOPT, MN, NB
-* ..
-* .. External Functions ..
- LOGICAL LSAME
- INTEGER ILAENV
- EXTERNAL LSAME, ILAENV
-* ..
-* .. External Subroutines ..
- EXTERNAL DORGLQ, DORGQR, XERBLA
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC MAX, MIN
-* ..
-* .. Executable Statements ..
-*
-* Test the input arguments
-*
- INFO = 0
- WANTQ = LSAME( VECT, 'Q' )
- MN = MIN( M, N )
- LQUERY = ( LWORK.EQ.-1 )
- IF( .NOT.WANTQ .AND. .NOT.LSAME( VECT, 'P' ) ) THEN
- INFO = -1
- ELSE IF( M.LT.0 ) THEN
- INFO = -2
- ELSE IF( N.LT.0 .OR. ( WANTQ .AND. ( N.GT.M .OR. N.LT.MIN( M,
- $ K ) ) ) .OR. ( .NOT.WANTQ .AND. ( M.GT.N .OR. M.LT.
- $ MIN( N, K ) ) ) ) THEN
- INFO = -3
- ELSE IF( K.LT.0 ) THEN
- INFO = -4
- ELSE IF( LDA.LT.MAX( 1, M ) ) THEN
- INFO = -6
- ELSE IF( LWORK.LT.MAX( 1, MN ) .AND. .NOT.LQUERY ) THEN
- INFO = -9
- END IF
-*
- IF( INFO.EQ.0 ) THEN
- IF( WANTQ ) THEN
- NB = ILAENV( 1, 'DORGQR', ' ', M, N, K, -1 )
- ELSE
- NB = ILAENV( 1, 'DORGLQ', ' ', M, N, K, -1 )
- END IF
- LWKOPT = MAX( 1, MN )*NB
- WORK( 1 ) = LWKOPT
- END IF
-*
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'DORGBR', -INFO )
- RETURN
- ELSE IF( LQUERY ) THEN
- RETURN
- END IF
-*
-* Quick return if possible
-*
- IF( M.EQ.0 .OR. N.EQ.0 ) THEN
- WORK( 1 ) = 1
- RETURN
- END IF
-*
- IF( WANTQ ) THEN
-*
-* Form Q, determined by a call to DGEBRD to reduce an m-by-k
-* matrix
-*
- IF( M.GE.K ) THEN
-*
-* If m >= k, assume m >= n >= k
-*
- CALL DORGQR( M, N, K, A, LDA, TAU, WORK, LWORK, IINFO )
-*
- ELSE
-*
-* If m < k, assume m = n
-*
-* Shift the vectors which define the elementary reflectors one
-* column to the right, and set the first row and column of Q
-* to those of the unit matrix
-*
- DO 20 J = M, 2, -1
- A( 1, J ) = ZERO
- DO 10 I = J + 1, M
- A( I, J ) = A( I, J-1 )
- 10 CONTINUE
- 20 CONTINUE
- A( 1, 1 ) = ONE
- DO 30 I = 2, M
- A( I, 1 ) = ZERO
- 30 CONTINUE
- IF( M.GT.1 ) THEN
-*
-* Form Q(2:m,2:m)
-*
- CALL DORGQR( M-1, M-1, M-1, A( 2, 2 ), LDA, TAU, WORK,
- $ LWORK, IINFO )
- END IF
- END IF
- ELSE
-*
-* Form P', determined by a call to DGEBRD to reduce a k-by-n
-* matrix
-*
- IF( K.LT.N ) THEN
-*
-* If k < n, assume k <= m <= n
-*
- CALL DORGLQ( M, N, K, A, LDA, TAU, WORK, LWORK, IINFO )
-*
- ELSE
-*
-* If k >= n, assume m = n
-*
-* Shift the vectors which define the elementary reflectors one
-* row downward, and set the first row and column of P' to
-* those of the unit matrix
-*
- A( 1, 1 ) = ONE
- DO 40 I = 2, N
- A( I, 1 ) = ZERO
- 40 CONTINUE
- DO 60 J = 2, N
- DO 50 I = J - 1, 2, -1
- A( I, J ) = A( I-1, J )
- 50 CONTINUE
- A( 1, J ) = ZERO
- 60 CONTINUE
- IF( N.GT.1 ) THEN
-*
-* Form P'(2:n,2:n)
-*
- CALL DORGLQ( N-1, N-1, N-1, A( 2, 2 ), LDA, TAU, WORK,
- $ LWORK, IINFO )
- END IF
- END IF
- END IF
- WORK( 1 ) = LWKOPT
- RETURN
-*
-* End of DORGBR
-*
- END
diff --git a/src/lib/lapack/dorghr.f b/src/lib/lapack/dorghr.f
deleted file mode 100644
index 1283aece..00000000
--- a/src/lib/lapack/dorghr.f
+++ /dev/null
@@ -1,164 +0,0 @@
- SUBROUTINE DORGHR( N, ILO, IHI, A, LDA, TAU, WORK, LWORK, INFO )
-*
-* -- LAPACK routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- INTEGER IHI, ILO, INFO, LDA, LWORK, N
-* ..
-* .. Array Arguments ..
- DOUBLE PRECISION A( LDA, * ), TAU( * ), WORK( * )
-* ..
-*
-* Purpose
-* =======
-*
-* DORGHR generates a real orthogonal matrix Q which is defined as the
-* product of IHI-ILO elementary reflectors of order N, as returned by
-* DGEHRD:
-*
-* Q = H(ilo) H(ilo+1) . . . H(ihi-1).
-*
-* Arguments
-* =========
-*
-* N (input) INTEGER
-* The order of the matrix Q. N >= 0.
-*
-* ILO (input) INTEGER
-* IHI (input) INTEGER
-* ILO and IHI must have the same values as in the previous call
-* of DGEHRD. Q is equal to the unit matrix except in the
-* submatrix Q(ilo+1:ihi,ilo+1:ihi).
-* 1 <= ILO <= IHI <= N, if N > 0; ILO=1 and IHI=0, if N=0.
-*
-* A (input/output) DOUBLE PRECISION array, dimension (LDA,N)
-* On entry, the vectors which define the elementary reflectors,
-* as returned by DGEHRD.
-* On exit, the N-by-N orthogonal matrix Q.
-*
-* LDA (input) INTEGER
-* The leading dimension of the array A. LDA >= max(1,N).
-*
-* TAU (input) DOUBLE PRECISION array, dimension (N-1)
-* TAU(i) must contain the scalar factor of the elementary
-* reflector H(i), as returned by DGEHRD.
-*
-* WORK (workspace/output) DOUBLE PRECISION array, dimension (MAX(1,LWORK))
-* On exit, if INFO = 0, WORK(1) returns the optimal LWORK.
-*
-* LWORK (input) INTEGER
-* The dimension of the array WORK. LWORK >= IHI-ILO.
-* For optimum performance LWORK >= (IHI-ILO)*NB, where NB is
-* the optimal blocksize.
-*
-* If LWORK = -1, then a workspace query is assumed; the routine
-* only calculates the optimal size of the WORK array, returns
-* this value as the first entry of the WORK array, and no error
-* message related to LWORK is issued by XERBLA.
-*
-* INFO (output) INTEGER
-* = 0: successful exit
-* < 0: if INFO = -i, the i-th argument had an illegal value
-*
-* =====================================================================
-*
-* .. Parameters ..
- DOUBLE PRECISION ZERO, ONE
- PARAMETER ( ZERO = 0.0D+0, ONE = 1.0D+0 )
-* ..
-* .. Local Scalars ..
- LOGICAL LQUERY
- INTEGER I, IINFO, J, LWKOPT, NB, NH
-* ..
-* .. External Subroutines ..
- EXTERNAL DORGQR, XERBLA
-* ..
-* .. External Functions ..
- INTEGER ILAENV
- EXTERNAL ILAENV
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC MAX, MIN
-* ..
-* .. Executable Statements ..
-*
-* Test the input arguments
-*
- INFO = 0
- NH = IHI - ILO
- LQUERY = ( LWORK.EQ.-1 )
- IF( N.LT.0 ) THEN
- INFO = -1
- ELSE IF( ILO.LT.1 .OR. ILO.GT.MAX( 1, N ) ) THEN
- INFO = -2
- ELSE IF( IHI.LT.MIN( ILO, N ) .OR. IHI.GT.N ) THEN
- INFO = -3
- ELSE IF( LDA.LT.MAX( 1, N ) ) THEN
- INFO = -5
- ELSE IF( LWORK.LT.MAX( 1, NH ) .AND. .NOT.LQUERY ) THEN
- INFO = -8
- END IF
-*
- IF( INFO.EQ.0 ) THEN
- NB = ILAENV( 1, 'DORGQR', ' ', NH, NH, NH, -1 )
- LWKOPT = MAX( 1, NH )*NB
- WORK( 1 ) = LWKOPT
- END IF
-*
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'DORGHR', -INFO )
- RETURN
- ELSE IF( LQUERY ) THEN
- RETURN
- END IF
-*
-* Quick return if possible
-*
- IF( N.EQ.0 ) THEN
- WORK( 1 ) = 1
- RETURN
- END IF
-*
-* Shift the vectors which define the elementary reflectors one
-* column to the right, and set the first ilo and the last n-ihi
-* rows and columns to those of the unit matrix
-*
- DO 40 J = IHI, ILO + 1, -1
- DO 10 I = 1, J - 1
- A( I, J ) = ZERO
- 10 CONTINUE
- DO 20 I = J + 1, IHI
- A( I, J ) = A( I, J-1 )
- 20 CONTINUE
- DO 30 I = IHI + 1, N
- A( I, J ) = ZERO
- 30 CONTINUE
- 40 CONTINUE
- DO 60 J = 1, ILO
- DO 50 I = 1, N
- A( I, J ) = ZERO
- 50 CONTINUE
- A( J, J ) = ONE
- 60 CONTINUE
- DO 80 J = IHI + 1, N
- DO 70 I = 1, N
- A( I, J ) = ZERO
- 70 CONTINUE
- A( J, J ) = ONE
- 80 CONTINUE
-*
- IF( NH.GT.0 ) THEN
-*
-* Generate Q(ilo+1:ihi,ilo+1:ihi)
-*
- CALL DORGQR( NH, NH, NH, A( ILO+1, ILO+1 ), LDA, TAU( ILO ),
- $ WORK, LWORK, IINFO )
- END IF
- WORK( 1 ) = LWKOPT
- RETURN
-*
-* End of DORGHR
-*
- END
diff --git a/src/lib/lapack/dorgl2.f b/src/lib/lapack/dorgl2.f
deleted file mode 100644
index 1e08344d..00000000
--- a/src/lib/lapack/dorgl2.f
+++ /dev/null
@@ -1,133 +0,0 @@
- SUBROUTINE DORGL2( M, N, K, A, LDA, TAU, WORK, INFO )
-*
-* -- LAPACK routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- INTEGER INFO, K, LDA, M, N
-* ..
-* .. Array Arguments ..
- DOUBLE PRECISION A( LDA, * ), TAU( * ), WORK( * )
-* ..
-*
-* Purpose
-* =======
-*
-* DORGL2 generates an m by n real matrix Q with orthonormal rows,
-* which is defined as the first m rows of a product of k elementary
-* reflectors of order n
-*
-* Q = H(k) . . . H(2) H(1)
-*
-* as returned by DGELQF.
-*
-* Arguments
-* =========
-*
-* M (input) INTEGER
-* The number of rows of the matrix Q. M >= 0.
-*
-* N (input) INTEGER
-* The number of columns of the matrix Q. N >= M.
-*
-* K (input) INTEGER
-* The number of elementary reflectors whose product defines the
-* matrix Q. M >= K >= 0.
-*
-* A (input/output) DOUBLE PRECISION array, dimension (LDA,N)
-* On entry, the i-th row must contain the vector which defines
-* the elementary reflector H(i), for i = 1,2,...,k, as returned
-* by DGELQF in the first k rows of its array argument A.
-* On exit, the m-by-n matrix Q.
-*
-* LDA (input) INTEGER
-* The first dimension of the array A. LDA >= max(1,M).
-*
-* TAU (input) DOUBLE PRECISION array, dimension (K)
-* TAU(i) must contain the scalar factor of the elementary
-* reflector H(i), as returned by DGELQF.
-*
-* WORK (workspace) DOUBLE PRECISION array, dimension (M)
-*
-* INFO (output) INTEGER
-* = 0: successful exit
-* < 0: if INFO = -i, the i-th argument has an illegal value
-*
-* =====================================================================
-*
-* .. Parameters ..
- DOUBLE PRECISION ONE, ZERO
- PARAMETER ( ONE = 1.0D+0, ZERO = 0.0D+0 )
-* ..
-* .. Local Scalars ..
- INTEGER I, J, L
-* ..
-* .. External Subroutines ..
- EXTERNAL DLARF, DSCAL, XERBLA
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC MAX
-* ..
-* .. Executable Statements ..
-*
-* Test the input arguments
-*
- INFO = 0
- IF( M.LT.0 ) THEN
- INFO = -1
- ELSE IF( N.LT.M ) THEN
- INFO = -2
- ELSE IF( K.LT.0 .OR. K.GT.M ) THEN
- INFO = -3
- ELSE IF( LDA.LT.MAX( 1, M ) ) THEN
- INFO = -5
- END IF
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'DORGL2', -INFO )
- RETURN
- END IF
-*
-* Quick return if possible
-*
- IF( M.LE.0 )
- $ RETURN
-*
- IF( K.LT.M ) THEN
-*
-* Initialise rows k+1:m to rows of the unit matrix
-*
- DO 20 J = 1, N
- DO 10 L = K + 1, M
- A( L, J ) = ZERO
- 10 CONTINUE
- IF( J.GT.K .AND. J.LE.M )
- $ A( J, J ) = ONE
- 20 CONTINUE
- END IF
-*
- DO 40 I = K, 1, -1
-*
-* Apply H(i) to A(i:m,i:n) from the right
-*
- IF( I.LT.N ) THEN
- IF( I.LT.M ) THEN
- A( I, I ) = ONE
- CALL DLARF( 'Right', M-I, N-I+1, A( I, I ), LDA,
- $ TAU( I ), A( I+1, I ), LDA, WORK )
- END IF
- CALL DSCAL( N-I, -TAU( I ), A( I, I+1 ), LDA )
- END IF
- A( I, I ) = ONE - TAU( I )
-*
-* Set A(i,1:i-1) to zero
-*
- DO 30 L = 1, I - 1
- A( I, L ) = ZERO
- 30 CONTINUE
- 40 CONTINUE
- RETURN
-*
-* End of DORGL2
-*
- END
diff --git a/src/lib/lapack/dorglq.f b/src/lib/lapack/dorglq.f
deleted file mode 100644
index e4f58c96..00000000
--- a/src/lib/lapack/dorglq.f
+++ /dev/null
@@ -1,215 +0,0 @@
- SUBROUTINE DORGLQ( M, N, K, A, LDA, TAU, WORK, LWORK, INFO )
-*
-* -- LAPACK routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- INTEGER INFO, K, LDA, LWORK, M, N
-* ..
-* .. Array Arguments ..
- DOUBLE PRECISION A( LDA, * ), TAU( * ), WORK( * )
-* ..
-*
-* Purpose
-* =======
-*
-* DORGLQ generates an M-by-N real matrix Q with orthonormal rows,
-* which is defined as the first M rows of a product of K elementary
-* reflectors of order N
-*
-* Q = H(k) . . . H(2) H(1)
-*
-* as returned by DGELQF.
-*
-* Arguments
-* =========
-*
-* M (input) INTEGER
-* The number of rows of the matrix Q. M >= 0.
-*
-* N (input) INTEGER
-* The number of columns of the matrix Q. N >= M.
-*
-* K (input) INTEGER
-* The number of elementary reflectors whose product defines the
-* matrix Q. M >= K >= 0.
-*
-* A (input/output) DOUBLE PRECISION array, dimension (LDA,N)
-* On entry, the i-th row must contain the vector which defines
-* the elementary reflector H(i), for i = 1,2,...,k, as returned
-* by DGELQF in the first k rows of its array argument A.
-* On exit, the M-by-N matrix Q.
-*
-* LDA (input) INTEGER
-* The first dimension of the array A. LDA >= max(1,M).
-*
-* TAU (input) DOUBLE PRECISION array, dimension (K)
-* TAU(i) must contain the scalar factor of the elementary
-* reflector H(i), as returned by DGELQF.
-*
-* WORK (workspace/output) DOUBLE PRECISION array, dimension (MAX(1,LWORK))
-* On exit, if INFO = 0, WORK(1) returns the optimal LWORK.
-*
-* LWORK (input) INTEGER
-* The dimension of the array WORK. LWORK >= max(1,M).
-* For optimum performance LWORK >= M*NB, where NB is
-* the optimal blocksize.
-*
-* If LWORK = -1, then a workspace query is assumed; the routine
-* only calculates the optimal size of the WORK array, returns
-* this value as the first entry of the WORK array, and no error
-* message related to LWORK is issued by XERBLA.
-*
-* INFO (output) INTEGER
-* = 0: successful exit
-* < 0: if INFO = -i, the i-th argument has an illegal value
-*
-* =====================================================================
-*
-* .. Parameters ..
- DOUBLE PRECISION ZERO
- PARAMETER ( ZERO = 0.0D+0 )
-* ..
-* .. Local Scalars ..
- LOGICAL LQUERY
- INTEGER I, IB, IINFO, IWS, J, KI, KK, L, LDWORK,
- $ LWKOPT, NB, NBMIN, NX
-* ..
-* .. External Subroutines ..
- EXTERNAL DLARFB, DLARFT, DORGL2, XERBLA
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC MAX, MIN
-* ..
-* .. External Functions ..
- INTEGER ILAENV
- EXTERNAL ILAENV
-* ..
-* .. Executable Statements ..
-*
-* Test the input arguments
-*
- INFO = 0
- NB = ILAENV( 1, 'DORGLQ', ' ', M, N, K, -1 )
- LWKOPT = MAX( 1, M )*NB
- WORK( 1 ) = LWKOPT
- LQUERY = ( LWORK.EQ.-1 )
- IF( M.LT.0 ) THEN
- INFO = -1
- ELSE IF( N.LT.M ) THEN
- INFO = -2
- ELSE IF( K.LT.0 .OR. K.GT.M ) THEN
- INFO = -3
- ELSE IF( LDA.LT.MAX( 1, M ) ) THEN
- INFO = -5
- ELSE IF( LWORK.LT.MAX( 1, M ) .AND. .NOT.LQUERY ) THEN
- INFO = -8
- END IF
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'DORGLQ', -INFO )
- RETURN
- ELSE IF( LQUERY ) THEN
- RETURN
- END IF
-*
-* Quick return if possible
-*
- IF( M.LE.0 ) THEN
- WORK( 1 ) = 1
- RETURN
- END IF
-*
- NBMIN = 2
- NX = 0
- IWS = M
- IF( NB.GT.1 .AND. NB.LT.K ) THEN
-*
-* Determine when to cross over from blocked to unblocked code.
-*
- NX = MAX( 0, ILAENV( 3, 'DORGLQ', ' ', M, N, K, -1 ) )
- IF( NX.LT.K ) THEN
-*
-* Determine if workspace is large enough for blocked code.
-*
- LDWORK = M
- IWS = LDWORK*NB
- IF( LWORK.LT.IWS ) THEN
-*
-* Not enough workspace to use optimal NB: reduce NB and
-* determine the minimum value of NB.
-*
- NB = LWORK / LDWORK
- NBMIN = MAX( 2, ILAENV( 2, 'DORGLQ', ' ', M, N, K, -1 ) )
- END IF
- END IF
- END IF
-*
- IF( NB.GE.NBMIN .AND. NB.LT.K .AND. NX.LT.K ) THEN
-*
-* Use blocked code after the last block.
-* The first kk rows are handled by the block method.
-*
- KI = ( ( K-NX-1 ) / NB )*NB
- KK = MIN( K, KI+NB )
-*
-* Set A(kk+1:m,1:kk) to zero.
-*
- DO 20 J = 1, KK
- DO 10 I = KK + 1, M
- A( I, J ) = ZERO
- 10 CONTINUE
- 20 CONTINUE
- ELSE
- KK = 0
- END IF
-*
-* Use unblocked code for the last or only block.
-*
- IF( KK.LT.M )
- $ CALL DORGL2( M-KK, N-KK, K-KK, A( KK+1, KK+1 ), LDA,
- $ TAU( KK+1 ), WORK, IINFO )
-*
- IF( KK.GT.0 ) THEN
-*
-* Use blocked code
-*
- DO 50 I = KI + 1, 1, -NB
- IB = MIN( NB, K-I+1 )
- IF( I+IB.LE.M ) THEN
-*
-* Form the triangular factor of the block reflector
-* H = H(i) H(i+1) . . . H(i+ib-1)
-*
- CALL DLARFT( 'Forward', 'Rowwise', N-I+1, IB, A( I, I ),
- $ LDA, TAU( I ), WORK, LDWORK )
-*
-* Apply H' to A(i+ib:m,i:n) from the right
-*
- CALL DLARFB( 'Right', 'Transpose', 'Forward', 'Rowwise',
- $ M-I-IB+1, N-I+1, IB, A( I, I ), LDA, WORK,
- $ LDWORK, A( I+IB, I ), LDA, WORK( IB+1 ),
- $ LDWORK )
- END IF
-*
-* Apply H' to columns i:n of current block
-*
- CALL DORGL2( IB, N-I+1, IB, A( I, I ), LDA, TAU( I ), WORK,
- $ IINFO )
-*
-* Set columns 1:i-1 of current block to zero
-*
- DO 40 J = 1, I - 1
- DO 30 L = I, I + IB - 1
- A( L, J ) = ZERO
- 30 CONTINUE
- 40 CONTINUE
- 50 CONTINUE
- END IF
-*
- WORK( 1 ) = IWS
- RETURN
-*
-* End of DORGLQ
-*
- END
diff --git a/src/lib/lapack/dorgql.f b/src/lib/lapack/dorgql.f
deleted file mode 100644
index 1c4896e9..00000000
--- a/src/lib/lapack/dorgql.f
+++ /dev/null
@@ -1,222 +0,0 @@
- SUBROUTINE DORGQL( M, N, K, A, LDA, TAU, WORK, LWORK, INFO )
-*
-* -- LAPACK routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- INTEGER INFO, K, LDA, LWORK, M, N
-* ..
-* .. Array Arguments ..
- DOUBLE PRECISION A( LDA, * ), TAU( * ), WORK( * )
-* ..
-*
-* Purpose
-* =======
-*
-* DORGQL generates an M-by-N real matrix Q with orthonormal columns,
-* which is defined as the last N columns of a product of K elementary
-* reflectors of order M
-*
-* Q = H(k) . . . H(2) H(1)
-*
-* as returned by DGEQLF.
-*
-* Arguments
-* =========
-*
-* M (input) INTEGER
-* The number of rows of the matrix Q. M >= 0.
-*
-* N (input) INTEGER
-* The number of columns of the matrix Q. M >= N >= 0.
-*
-* K (input) INTEGER
-* The number of elementary reflectors whose product defines the
-* matrix Q. N >= K >= 0.
-*
-* A (input/output) DOUBLE PRECISION array, dimension (LDA,N)
-* On entry, the (n-k+i)-th column must contain the vector which
-* defines the elementary reflector H(i), for i = 1,2,...,k, as
-* returned by DGEQLF in the last k columns of its array
-* argument A.
-* On exit, the M-by-N matrix Q.
-*
-* LDA (input) INTEGER
-* The first dimension of the array A. LDA >= max(1,M).
-*
-* TAU (input) DOUBLE PRECISION array, dimension (K)
-* TAU(i) must contain the scalar factor of the elementary
-* reflector H(i), as returned by DGEQLF.
-*
-* WORK (workspace/output) DOUBLE PRECISION array, dimension (MAX(1,LWORK))
-* On exit, if INFO = 0, WORK(1) returns the optimal LWORK.
-*
-* LWORK (input) INTEGER
-* The dimension of the array WORK. LWORK >= max(1,N).
-* For optimum performance LWORK >= N*NB, where NB is the
-* optimal blocksize.
-*
-* If LWORK = -1, then a workspace query is assumed; the routine
-* only calculates the optimal size of the WORK array, returns
-* this value as the first entry of the WORK array, and no error
-* message related to LWORK is issued by XERBLA.
-*
-* INFO (output) INTEGER
-* = 0: successful exit
-* < 0: if INFO = -i, the i-th argument has an illegal value
-*
-* =====================================================================
-*
-* .. Parameters ..
- DOUBLE PRECISION ZERO
- PARAMETER ( ZERO = 0.0D+0 )
-* ..
-* .. Local Scalars ..
- LOGICAL LQUERY
- INTEGER I, IB, IINFO, IWS, J, KK, L, LDWORK, LWKOPT,
- $ NB, NBMIN, NX
-* ..
-* .. External Subroutines ..
- EXTERNAL DLARFB, DLARFT, DORG2L, XERBLA
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC MAX, MIN
-* ..
-* .. External Functions ..
- INTEGER ILAENV
- EXTERNAL ILAENV
-* ..
-* .. Executable Statements ..
-*
-* Test the input arguments
-*
- INFO = 0
- LQUERY = ( LWORK.EQ.-1 )
- IF( M.LT.0 ) THEN
- INFO = -1
- ELSE IF( N.LT.0 .OR. N.GT.M ) THEN
- INFO = -2
- ELSE IF( K.LT.0 .OR. K.GT.N ) THEN
- INFO = -3
- ELSE IF( LDA.LT.MAX( 1, M ) ) THEN
- INFO = -5
- END IF
-*
- IF( INFO.EQ.0 ) THEN
- IF( N.EQ.0 ) THEN
- LWKOPT = 1
- ELSE
- NB = ILAENV( 1, 'DORGQL', ' ', M, N, K, -1 )
- LWKOPT = N*NB
- END IF
- WORK( 1 ) = LWKOPT
-*
- IF( LWORK.LT.MAX( 1, N ) .AND. .NOT.LQUERY ) THEN
- INFO = -8
- END IF
- END IF
-*
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'DORGQL', -INFO )
- RETURN
- ELSE IF( LQUERY ) THEN
- RETURN
- END IF
-*
-* Quick return if possible
-*
- IF( N.LE.0 ) THEN
- RETURN
- END IF
-*
- NBMIN = 2
- NX = 0
- IWS = N
- IF( NB.GT.1 .AND. NB.LT.K ) THEN
-*
-* Determine when to cross over from blocked to unblocked code.
-*
- NX = MAX( 0, ILAENV( 3, 'DORGQL', ' ', M, N, K, -1 ) )
- IF( NX.LT.K ) THEN
-*
-* Determine if workspace is large enough for blocked code.
-*
- LDWORK = N
- IWS = LDWORK*NB
- IF( LWORK.LT.IWS ) THEN
-*
-* Not enough workspace to use optimal NB: reduce NB and
-* determine the minimum value of NB.
-*
- NB = LWORK / LDWORK
- NBMIN = MAX( 2, ILAENV( 2, 'DORGQL', ' ', M, N, K, -1 ) )
- END IF
- END IF
- END IF
-*
- IF( NB.GE.NBMIN .AND. NB.LT.K .AND. NX.LT.K ) THEN
-*
-* Use blocked code after the first block.
-* The last kk columns are handled by the block method.
-*
- KK = MIN( K, ( ( K-NX+NB-1 ) / NB )*NB )
-*
-* Set A(m-kk+1:m,1:n-kk) to zero.
-*
- DO 20 J = 1, N - KK
- DO 10 I = M - KK + 1, M
- A( I, J ) = ZERO
- 10 CONTINUE
- 20 CONTINUE
- ELSE
- KK = 0
- END IF
-*
-* Use unblocked code for the first or only block.
-*
- CALL DORG2L( M-KK, N-KK, K-KK, A, LDA, TAU, WORK, IINFO )
-*
- IF( KK.GT.0 ) THEN
-*
-* Use blocked code
-*
- DO 50 I = K - KK + 1, K, NB
- IB = MIN( NB, K-I+1 )
- IF( N-K+I.GT.1 ) THEN
-*
-* Form the triangular factor of the block reflector
-* H = H(i+ib-1) . . . H(i+1) H(i)
-*
- CALL DLARFT( 'Backward', 'Columnwise', M-K+I+IB-1, IB,
- $ A( 1, N-K+I ), LDA, TAU( I ), WORK, LDWORK )
-*
-* Apply H to A(1:m-k+i+ib-1,1:n-k+i-1) from the left
-*
- CALL DLARFB( 'Left', 'No transpose', 'Backward',
- $ 'Columnwise', M-K+I+IB-1, N-K+I-1, IB,
- $ A( 1, N-K+I ), LDA, WORK, LDWORK, A, LDA,
- $ WORK( IB+1 ), LDWORK )
- END IF
-*
-* Apply H to rows 1:m-k+i+ib-1 of current block
-*
- CALL DORG2L( M-K+I+IB-1, IB, IB, A( 1, N-K+I ), LDA,
- $ TAU( I ), WORK, IINFO )
-*
-* Set rows m-k+i+ib:m of current block to zero
-*
- DO 40 J = N - K + I, N - K + I + IB - 1
- DO 30 L = M - K + I + IB, M
- A( L, J ) = ZERO
- 30 CONTINUE
- 40 CONTINUE
- 50 CONTINUE
- END IF
-*
- WORK( 1 ) = IWS
- RETURN
-*
-* End of DORGQL
-*
- END
diff --git a/src/lib/lapack/dorgqr.f b/src/lib/lapack/dorgqr.f
deleted file mode 100644
index 4db0ef5a..00000000
--- a/src/lib/lapack/dorgqr.f
+++ /dev/null
@@ -1,216 +0,0 @@
- SUBROUTINE DORGQR( M, N, K, A, LDA, TAU, WORK, LWORK, INFO )
-*
-* -- LAPACK routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- INTEGER INFO, K, LDA, LWORK, M, N
-* ..
-* .. Array Arguments ..
- DOUBLE PRECISION A( LDA, * ), TAU( * ), WORK( * )
-* ..
-*
-* Purpose
-* =======
-*
-* DORGQR generates an M-by-N real matrix Q with orthonormal columns,
-* which is defined as the first N columns of a product of K elementary
-* reflectors of order M
-*
-* Q = H(1) H(2) . . . H(k)
-*
-* as returned by DGEQRF.
-*
-* Arguments
-* =========
-*
-* M (input) INTEGER
-* The number of rows of the matrix Q. M >= 0.
-*
-* N (input) INTEGER
-* The number of columns of the matrix Q. M >= N >= 0.
-*
-* K (input) INTEGER
-* The number of elementary reflectors whose product defines the
-* matrix Q. N >= K >= 0.
-*
-* A (input/output) DOUBLE PRECISION array, dimension (LDA,N)
-* On entry, the i-th column must contain the vector which
-* defines the elementary reflector H(i), for i = 1,2,...,k, as
-* returned by DGEQRF in the first k columns of its array
-* argument A.
-* On exit, the M-by-N matrix Q.
-*
-* LDA (input) INTEGER
-* The first dimension of the array A. LDA >= max(1,M).
-*
-* TAU (input) DOUBLE PRECISION array, dimension (K)
-* TAU(i) must contain the scalar factor of the elementary
-* reflector H(i), as returned by DGEQRF.
-*
-* WORK (workspace/output) DOUBLE PRECISION array, dimension (MAX(1,LWORK))
-* On exit, if INFO = 0, WORK(1) returns the optimal LWORK.
-*
-* LWORK (input) INTEGER
-* The dimension of the array WORK. LWORK >= max(1,N).
-* For optimum performance LWORK >= N*NB, where NB is the
-* optimal blocksize.
-*
-* If LWORK = -1, then a workspace query is assumed; the routine
-* only calculates the optimal size of the WORK array, returns
-* this value as the first entry of the WORK array, and no error
-* message related to LWORK is issued by XERBLA.
-*
-* INFO (output) INTEGER
-* = 0: successful exit
-* < 0: if INFO = -i, the i-th argument has an illegal value
-*
-* =====================================================================
-*
-* .. Parameters ..
- DOUBLE PRECISION ZERO
- PARAMETER ( ZERO = 0.0D+0 )
-* ..
-* .. Local Scalars ..
- LOGICAL LQUERY
- INTEGER I, IB, IINFO, IWS, J, KI, KK, L, LDWORK,
- $ LWKOPT, NB, NBMIN, NX
-* ..
-* .. External Subroutines ..
- EXTERNAL DLARFB, DLARFT, DORG2R, XERBLA
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC MAX, MIN
-* ..
-* .. External Functions ..
- INTEGER ILAENV
- EXTERNAL ILAENV
-* ..
-* .. Executable Statements ..
-*
-* Test the input arguments
-*
- INFO = 0
- NB = ILAENV( 1, 'DORGQR', ' ', M, N, K, -1 )
- LWKOPT = MAX( 1, N )*NB
- WORK( 1 ) = LWKOPT
- LQUERY = ( LWORK.EQ.-1 )
- IF( M.LT.0 ) THEN
- INFO = -1
- ELSE IF( N.LT.0 .OR. N.GT.M ) THEN
- INFO = -2
- ELSE IF( K.LT.0 .OR. K.GT.N ) THEN
- INFO = -3
- ELSE IF( LDA.LT.MAX( 1, M ) ) THEN
- INFO = -5
- ELSE IF( LWORK.LT.MAX( 1, N ) .AND. .NOT.LQUERY ) THEN
- INFO = -8
- END IF
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'DORGQR', -INFO )
- RETURN
- ELSE IF( LQUERY ) THEN
- RETURN
- END IF
-*
-* Quick return if possible
-*
- IF( N.LE.0 ) THEN
- WORK( 1 ) = 1
- RETURN
- END IF
-*
- NBMIN = 2
- NX = 0
- IWS = N
- IF( NB.GT.1 .AND. NB.LT.K ) THEN
-*
-* Determine when to cross over from blocked to unblocked code.
-*
- NX = MAX( 0, ILAENV( 3, 'DORGQR', ' ', M, N, K, -1 ) )
- IF( NX.LT.K ) THEN
-*
-* Determine if workspace is large enough for blocked code.
-*
- LDWORK = N
- IWS = LDWORK*NB
- IF( LWORK.LT.IWS ) THEN
-*
-* Not enough workspace to use optimal NB: reduce NB and
-* determine the minimum value of NB.
-*
- NB = LWORK / LDWORK
- NBMIN = MAX( 2, ILAENV( 2, 'DORGQR', ' ', M, N, K, -1 ) )
- END IF
- END IF
- END IF
-*
- IF( NB.GE.NBMIN .AND. NB.LT.K .AND. NX.LT.K ) THEN
-*
-* Use blocked code after the last block.
-* The first kk columns are handled by the block method.
-*
- KI = ( ( K-NX-1 ) / NB )*NB
- KK = MIN( K, KI+NB )
-*
-* Set A(1:kk,kk+1:n) to zero.
-*
- DO 20 J = KK + 1, N
- DO 10 I = 1, KK
- A( I, J ) = ZERO
- 10 CONTINUE
- 20 CONTINUE
- ELSE
- KK = 0
- END IF
-*
-* Use unblocked code for the last or only block.
-*
- IF( KK.LT.N )
- $ CALL DORG2R( M-KK, N-KK, K-KK, A( KK+1, KK+1 ), LDA,
- $ TAU( KK+1 ), WORK, IINFO )
-*
- IF( KK.GT.0 ) THEN
-*
-* Use blocked code
-*
- DO 50 I = KI + 1, 1, -NB
- IB = MIN( NB, K-I+1 )
- IF( I+IB.LE.N ) THEN
-*
-* Form the triangular factor of the block reflector
-* H = H(i) H(i+1) . . . H(i+ib-1)
-*
- CALL DLARFT( 'Forward', 'Columnwise', M-I+1, IB,
- $ A( I, I ), LDA, TAU( I ), WORK, LDWORK )
-*
-* Apply H to A(i:m,i+ib:n) from the left
-*
- CALL DLARFB( 'Left', 'No transpose', 'Forward',
- $ 'Columnwise', M-I+1, N-I-IB+1, IB,
- $ A( I, I ), LDA, WORK, LDWORK, A( I, I+IB ),
- $ LDA, WORK( IB+1 ), LDWORK )
- END IF
-*
-* Apply H to rows i:m of current block
-*
- CALL DORG2R( M-I+1, IB, IB, A( I, I ), LDA, TAU( I ), WORK,
- $ IINFO )
-*
-* Set rows 1:i-1 of current block to zero
-*
- DO 40 J = I, I + IB - 1
- DO 30 L = 1, I - 1
- A( L, J ) = ZERO
- 30 CONTINUE
- 40 CONTINUE
- 50 CONTINUE
- END IF
-*
- WORK( 1 ) = IWS
- RETURN
-*
-* End of DORGQR
-*
- END
diff --git a/src/lib/lapack/dorgr2.f b/src/lib/lapack/dorgr2.f
deleted file mode 100644
index 9da45c5f..00000000
--- a/src/lib/lapack/dorgr2.f
+++ /dev/null
@@ -1,131 +0,0 @@
- SUBROUTINE DORGR2( M, N, K, A, LDA, TAU, WORK, INFO )
-*
-* -- LAPACK routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- INTEGER INFO, K, LDA, M, N
-* ..
-* .. Array Arguments ..
- DOUBLE PRECISION A( LDA, * ), TAU( * ), WORK( * )
-* ..
-*
-* Purpose
-* =======
-*
-* DORGR2 generates an m by n real matrix Q with orthonormal rows,
-* which is defined as the last m rows of a product of k elementary
-* reflectors of order n
-*
-* Q = H(1) H(2) . . . H(k)
-*
-* as returned by DGERQF.
-*
-* Arguments
-* =========
-*
-* M (input) INTEGER
-* The number of rows of the matrix Q. M >= 0.
-*
-* N (input) INTEGER
-* The number of columns of the matrix Q. N >= M.
-*
-* K (input) INTEGER
-* The number of elementary reflectors whose product defines the
-* matrix Q. M >= K >= 0.
-*
-* A (input/output) DOUBLE PRECISION array, dimension (LDA,N)
-* On entry, the (m-k+i)-th row must contain the vector which
-* defines the elementary reflector H(i), for i = 1,2,...,k, as
-* returned by DGERQF in the last k rows of its array argument
-* A.
-* On exit, the m by n matrix Q.
-*
-* LDA (input) INTEGER
-* The first dimension of the array A. LDA >= max(1,M).
-*
-* TAU (input) DOUBLE PRECISION array, dimension (K)
-* TAU(i) must contain the scalar factor of the elementary
-* reflector H(i), as returned by DGERQF.
-*
-* WORK (workspace) DOUBLE PRECISION array, dimension (M)
-*
-* INFO (output) INTEGER
-* = 0: successful exit
-* < 0: if INFO = -i, the i-th argument has an illegal value
-*
-* =====================================================================
-*
-* .. Parameters ..
- DOUBLE PRECISION ONE, ZERO
- PARAMETER ( ONE = 1.0D+0, ZERO = 0.0D+0 )
-* ..
-* .. Local Scalars ..
- INTEGER I, II, J, L
-* ..
-* .. External Subroutines ..
- EXTERNAL DLARF, DSCAL, XERBLA
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC MAX
-* ..
-* .. Executable Statements ..
-*
-* Test the input arguments
-*
- INFO = 0
- IF( M.LT.0 ) THEN
- INFO = -1
- ELSE IF( N.LT.M ) THEN
- INFO = -2
- ELSE IF( K.LT.0 .OR. K.GT.M ) THEN
- INFO = -3
- ELSE IF( LDA.LT.MAX( 1, M ) ) THEN
- INFO = -5
- END IF
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'DORGR2', -INFO )
- RETURN
- END IF
-*
-* Quick return if possible
-*
- IF( M.LE.0 )
- $ RETURN
-*
- IF( K.LT.M ) THEN
-*
-* Initialise rows 1:m-k to rows of the unit matrix
-*
- DO 20 J = 1, N
- DO 10 L = 1, M - K
- A( L, J ) = ZERO
- 10 CONTINUE
- IF( J.GT.N-M .AND. J.LE.N-K )
- $ A( M-N+J, J ) = ONE
- 20 CONTINUE
- END IF
-*
- DO 40 I = 1, K
- II = M - K + I
-*
-* Apply H(i) to A(1:m-k+i,1:n-k+i) from the right
-*
- A( II, N-M+II ) = ONE
- CALL DLARF( 'Right', II-1, N-M+II, A( II, 1 ), LDA, TAU( I ),
- $ A, LDA, WORK )
- CALL DSCAL( N-M+II-1, -TAU( I ), A( II, 1 ), LDA )
- A( II, N-M+II ) = ONE - TAU( I )
-*
-* Set A(m-k+i,n-k+i+1:n) to zero
-*
- DO 30 L = N - M + II + 1, N
- A( II, L ) = ZERO
- 30 CONTINUE
- 40 CONTINUE
- RETURN
-*
-* End of DORGR2
-*
- END
diff --git a/src/lib/lapack/dorgrq.f b/src/lib/lapack/dorgrq.f
deleted file mode 100644
index 11633403..00000000
--- a/src/lib/lapack/dorgrq.f
+++ /dev/null
@@ -1,222 +0,0 @@
- SUBROUTINE DORGRQ( M, N, K, A, LDA, TAU, WORK, LWORK, INFO )
-*
-* -- LAPACK routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- INTEGER INFO, K, LDA, LWORK, M, N
-* ..
-* .. Array Arguments ..
- DOUBLE PRECISION A( LDA, * ), TAU( * ), WORK( * )
-* ..
-*
-* Purpose
-* =======
-*
-* DORGRQ generates an M-by-N real matrix Q with orthonormal rows,
-* which is defined as the last M rows of a product of K elementary
-* reflectors of order N
-*
-* Q = H(1) H(2) . . . H(k)
-*
-* as returned by DGERQF.
-*
-* Arguments
-* =========
-*
-* M (input) INTEGER
-* The number of rows of the matrix Q. M >= 0.
-*
-* N (input) INTEGER
-* The number of columns of the matrix Q. N >= M.
-*
-* K (input) INTEGER
-* The number of elementary reflectors whose product defines the
-* matrix Q. M >= K >= 0.
-*
-* A (input/output) DOUBLE PRECISION array, dimension (LDA,N)
-* On entry, the (m-k+i)-th row must contain the vector which
-* defines the elementary reflector H(i), for i = 1,2,...,k, as
-* returned by DGERQF in the last k rows of its array argument
-* A.
-* On exit, the M-by-N matrix Q.
-*
-* LDA (input) INTEGER
-* The first dimension of the array A. LDA >= max(1,M).
-*
-* TAU (input) DOUBLE PRECISION array, dimension (K)
-* TAU(i) must contain the scalar factor of the elementary
-* reflector H(i), as returned by DGERQF.
-*
-* WORK (workspace/output) DOUBLE PRECISION array, dimension (MAX(1,LWORK))
-* On exit, if INFO = 0, WORK(1) returns the optimal LWORK.
-*
-* LWORK (input) INTEGER
-* The dimension of the array WORK. LWORK >= max(1,M).
-* For optimum performance LWORK >= M*NB, where NB is the
-* optimal blocksize.
-*
-* If LWORK = -1, then a workspace query is assumed; the routine
-* only calculates the optimal size of the WORK array, returns
-* this value as the first entry of the WORK array, and no error
-* message related to LWORK is issued by XERBLA.
-*
-* INFO (output) INTEGER
-* = 0: successful exit
-* < 0: if INFO = -i, the i-th argument has an illegal value
-*
-* =====================================================================
-*
-* .. Parameters ..
- DOUBLE PRECISION ZERO
- PARAMETER ( ZERO = 0.0D+0 )
-* ..
-* .. Local Scalars ..
- LOGICAL LQUERY
- INTEGER I, IB, II, IINFO, IWS, J, KK, L, LDWORK,
- $ LWKOPT, NB, NBMIN, NX
-* ..
-* .. External Subroutines ..
- EXTERNAL DLARFB, DLARFT, DORGR2, XERBLA
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC MAX, MIN
-* ..
-* .. External Functions ..
- INTEGER ILAENV
- EXTERNAL ILAENV
-* ..
-* .. Executable Statements ..
-*
-* Test the input arguments
-*
- INFO = 0
- LQUERY = ( LWORK.EQ.-1 )
- IF( M.LT.0 ) THEN
- INFO = -1
- ELSE IF( N.LT.M ) THEN
- INFO = -2
- ELSE IF( K.LT.0 .OR. K.GT.M ) THEN
- INFO = -3
- ELSE IF( LDA.LT.MAX( 1, M ) ) THEN
- INFO = -5
- END IF
-*
- IF( INFO.EQ.0 ) THEN
- IF( M.LE.0 ) THEN
- LWKOPT = 1
- ELSE
- NB = ILAENV( 1, 'DORGRQ', ' ', M, N, K, -1 )
- LWKOPT = M*NB
- END IF
- WORK( 1 ) = LWKOPT
-*
- IF( LWORK.LT.MAX( 1, M ) .AND. .NOT.LQUERY ) THEN
- INFO = -8
- END IF
- END IF
-*
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'DORGRQ', -INFO )
- RETURN
- ELSE IF( LQUERY ) THEN
- RETURN
- END IF
-*
-* Quick return if possible
-*
- IF( M.LE.0 ) THEN
- RETURN
- END IF
-*
- NBMIN = 2
- NX = 0
- IWS = M
- IF( NB.GT.1 .AND. NB.LT.K ) THEN
-*
-* Determine when to cross over from blocked to unblocked code.
-*
- NX = MAX( 0, ILAENV( 3, 'DORGRQ', ' ', M, N, K, -1 ) )
- IF( NX.LT.K ) THEN
-*
-* Determine if workspace is large enough for blocked code.
-*
- LDWORK = M
- IWS = LDWORK*NB
- IF( LWORK.LT.IWS ) THEN
-*
-* Not enough workspace to use optimal NB: reduce NB and
-* determine the minimum value of NB.
-*
- NB = LWORK / LDWORK
- NBMIN = MAX( 2, ILAENV( 2, 'DORGRQ', ' ', M, N, K, -1 ) )
- END IF
- END IF
- END IF
-*
- IF( NB.GE.NBMIN .AND. NB.LT.K .AND. NX.LT.K ) THEN
-*
-* Use blocked code after the first block.
-* The last kk rows are handled by the block method.
-*
- KK = MIN( K, ( ( K-NX+NB-1 ) / NB )*NB )
-*
-* Set A(1:m-kk,n-kk+1:n) to zero.
-*
- DO 20 J = N - KK + 1, N
- DO 10 I = 1, M - KK
- A( I, J ) = ZERO
- 10 CONTINUE
- 20 CONTINUE
- ELSE
- KK = 0
- END IF
-*
-* Use unblocked code for the first or only block.
-*
- CALL DORGR2( M-KK, N-KK, K-KK, A, LDA, TAU, WORK, IINFO )
-*
- IF( KK.GT.0 ) THEN
-*
-* Use blocked code
-*
- DO 50 I = K - KK + 1, K, NB
- IB = MIN( NB, K-I+1 )
- II = M - K + I
- IF( II.GT.1 ) THEN
-*
-* Form the triangular factor of the block reflector
-* H = H(i+ib-1) . . . H(i+1) H(i)
-*
- CALL DLARFT( 'Backward', 'Rowwise', N-K+I+IB-1, IB,
- $ A( II, 1 ), LDA, TAU( I ), WORK, LDWORK )
-*
-* Apply H' to A(1:m-k+i-1,1:n-k+i+ib-1) from the right
-*
- CALL DLARFB( 'Right', 'Transpose', 'Backward', 'Rowwise',
- $ II-1, N-K+I+IB-1, IB, A( II, 1 ), LDA, WORK,
- $ LDWORK, A, LDA, WORK( IB+1 ), LDWORK )
- END IF
-*
-* Apply H' to columns 1:n-k+i+ib-1 of current block
-*
- CALL DORGR2( IB, N-K+I+IB-1, IB, A( II, 1 ), LDA, TAU( I ),
- $ WORK, IINFO )
-*
-* Set columns n-k+i+ib:n of current block to zero
-*
- DO 40 L = N - K + I + IB, N
- DO 30 J = II, II + IB - 1
- A( J, L ) = ZERO
- 30 CONTINUE
- 40 CONTINUE
- 50 CONTINUE
- END IF
-*
- WORK( 1 ) = IWS
- RETURN
-*
-* End of DORGRQ
-*
- END
diff --git a/src/lib/lapack/dorgtr.f b/src/lib/lapack/dorgtr.f
deleted file mode 100644
index 4c72d031..00000000
--- a/src/lib/lapack/dorgtr.f
+++ /dev/null
@@ -1,183 +0,0 @@
- SUBROUTINE DORGTR( UPLO, N, A, LDA, TAU, WORK, LWORK, INFO )
-*
-* -- LAPACK routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- CHARACTER UPLO
- INTEGER INFO, LDA, LWORK, N
-* ..
-* .. Array Arguments ..
- DOUBLE PRECISION A( LDA, * ), TAU( * ), WORK( * )
-* ..
-*
-* Purpose
-* =======
-*
-* DORGTR generates a real orthogonal matrix Q which is defined as the
-* product of n-1 elementary reflectors of order N, as returned by
-* DSYTRD:
-*
-* if UPLO = 'U', Q = H(n-1) . . . H(2) H(1),
-*
-* if UPLO = 'L', Q = H(1) H(2) . . . H(n-1).
-*
-* Arguments
-* =========
-*
-* UPLO (input) CHARACTER*1
-* = 'U': Upper triangle of A contains elementary reflectors
-* from DSYTRD;
-* = 'L': Lower triangle of A contains elementary reflectors
-* from DSYTRD.
-*
-* N (input) INTEGER
-* The order of the matrix Q. N >= 0.
-*
-* A (input/output) DOUBLE PRECISION array, dimension (LDA,N)
-* On entry, the vectors which define the elementary reflectors,
-* as returned by DSYTRD.
-* On exit, the N-by-N orthogonal matrix Q.
-*
-* LDA (input) INTEGER
-* The leading dimension of the array A. LDA >= max(1,N).
-*
-* TAU (input) DOUBLE PRECISION array, dimension (N-1)
-* TAU(i) must contain the scalar factor of the elementary
-* reflector H(i), as returned by DSYTRD.
-*
-* WORK (workspace/output) DOUBLE PRECISION array, dimension (MAX(1,LWORK))
-* On exit, if INFO = 0, WORK(1) returns the optimal LWORK.
-*
-* LWORK (input) INTEGER
-* The dimension of the array WORK. LWORK >= max(1,N-1).
-* For optimum performance LWORK >= (N-1)*NB, where NB is
-* the optimal blocksize.
-*
-* If LWORK = -1, then a workspace query is assumed; the routine
-* only calculates the optimal size of the WORK array, returns
-* this value as the first entry of the WORK array, and no error
-* message related to LWORK is issued by XERBLA.
-*
-* INFO (output) INTEGER
-* = 0: successful exit
-* < 0: if INFO = -i, the i-th argument had an illegal value
-*
-* =====================================================================
-*
-* .. Parameters ..
- DOUBLE PRECISION ZERO, ONE
- PARAMETER ( ZERO = 0.0D+0, ONE = 1.0D+0 )
-* ..
-* .. Local Scalars ..
- LOGICAL LQUERY, UPPER
- INTEGER I, IINFO, J, LWKOPT, NB
-* ..
-* .. External Functions ..
- LOGICAL LSAME
- INTEGER ILAENV
- EXTERNAL LSAME, ILAENV
-* ..
-* .. External Subroutines ..
- EXTERNAL DORGQL, DORGQR, XERBLA
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC MAX
-* ..
-* .. Executable Statements ..
-*
-* Test the input arguments
-*
- INFO = 0
- LQUERY = ( LWORK.EQ.-1 )
- UPPER = LSAME( UPLO, 'U' )
- IF( .NOT.UPPER .AND. .NOT.LSAME( UPLO, 'L' ) ) THEN
- INFO = -1
- ELSE IF( N.LT.0 ) THEN
- INFO = -2
- ELSE IF( LDA.LT.MAX( 1, N ) ) THEN
- INFO = -4
- ELSE IF( LWORK.LT.MAX( 1, N-1 ) .AND. .NOT.LQUERY ) THEN
- INFO = -7
- END IF
-*
- IF( INFO.EQ.0 ) THEN
- IF( UPPER ) THEN
- NB = ILAENV( 1, 'DORGQL', ' ', N-1, N-1, N-1, -1 )
- ELSE
- NB = ILAENV( 1, 'DORGQR', ' ', N-1, N-1, N-1, -1 )
- END IF
- LWKOPT = MAX( 1, N-1 )*NB
- WORK( 1 ) = LWKOPT
- END IF
-*
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'DORGTR', -INFO )
- RETURN
- ELSE IF( LQUERY ) THEN
- RETURN
- END IF
-*
-* Quick return if possible
-*
- IF( N.EQ.0 ) THEN
- WORK( 1 ) = 1
- RETURN
- END IF
-*
- IF( UPPER ) THEN
-*
-* Q was determined by a call to DSYTRD with UPLO = 'U'
-*
-* Shift the vectors which define the elementary reflectors one
-* column to the left, and set the last row and column of Q to
-* those of the unit matrix
-*
- DO 20 J = 1, N - 1
- DO 10 I = 1, J - 1
- A( I, J ) = A( I, J+1 )
- 10 CONTINUE
- A( N, J ) = ZERO
- 20 CONTINUE
- DO 30 I = 1, N - 1
- A( I, N ) = ZERO
- 30 CONTINUE
- A( N, N ) = ONE
-*
-* Generate Q(1:n-1,1:n-1)
-*
- CALL DORGQL( N-1, N-1, N-1, A, LDA, TAU, WORK, LWORK, IINFO )
-*
- ELSE
-*
-* Q was determined by a call to DSYTRD with UPLO = 'L'.
-*
-* Shift the vectors which define the elementary reflectors one
-* column to the right, and set the first row and column of Q to
-* those of the unit matrix
-*
- DO 50 J = N, 2, -1
- A( 1, J ) = ZERO
- DO 40 I = J + 1, N
- A( I, J ) = A( I, J-1 )
- 40 CONTINUE
- 50 CONTINUE
- A( 1, 1 ) = ONE
- DO 60 I = 2, N
- A( I, 1 ) = ZERO
- 60 CONTINUE
- IF( N.GT.1 ) THEN
-*
-* Generate Q(2:n,2:n)
-*
- CALL DORGQR( N-1, N-1, N-1, A( 2, 2 ), LDA, TAU, WORK,
- $ LWORK, IINFO )
- END IF
- END IF
- WORK( 1 ) = LWKOPT
- RETURN
-*
-* End of DORGTR
-*
- END
diff --git a/src/lib/lapack/dorm2l.f b/src/lib/lapack/dorm2l.f
deleted file mode 100644
index 27120075..00000000
--- a/src/lib/lapack/dorm2l.f
+++ /dev/null
@@ -1,193 +0,0 @@
- SUBROUTINE DORM2L( SIDE, TRANS, M, N, K, A, LDA, TAU, C, LDC,
- $ WORK, INFO )
-*
-* -- LAPACK routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- CHARACTER SIDE, TRANS
- INTEGER INFO, K, LDA, LDC, M, N
-* ..
-* .. Array Arguments ..
- DOUBLE PRECISION A( LDA, * ), C( LDC, * ), TAU( * ), WORK( * )
-* ..
-*
-* Purpose
-* =======
-*
-* DORM2L overwrites the general real m by n matrix C with
-*
-* Q * C if SIDE = 'L' and TRANS = 'N', or
-*
-* Q'* C if SIDE = 'L' and TRANS = 'T', or
-*
-* C * Q if SIDE = 'R' and TRANS = 'N', or
-*
-* C * Q' if SIDE = 'R' and TRANS = 'T',
-*
-* where Q is a real orthogonal matrix defined as the product of k
-* elementary reflectors
-*
-* Q = H(k) . . . H(2) H(1)
-*
-* as returned by DGEQLF. Q is of order m if SIDE = 'L' and of order n
-* if SIDE = 'R'.
-*
-* Arguments
-* =========
-*
-* SIDE (input) CHARACTER*1
-* = 'L': apply Q or Q' from the Left
-* = 'R': apply Q or Q' from the Right
-*
-* TRANS (input) CHARACTER*1
-* = 'N': apply Q (No transpose)
-* = 'T': apply Q' (Transpose)
-*
-* M (input) INTEGER
-* The number of rows of the matrix C. M >= 0.
-*
-* N (input) INTEGER
-* The number of columns of the matrix C. N >= 0.
-*
-* K (input) INTEGER
-* The number of elementary reflectors whose product defines
-* the matrix Q.
-* If SIDE = 'L', M >= K >= 0;
-* if SIDE = 'R', N >= K >= 0.
-*
-* A (input) DOUBLE PRECISION array, dimension (LDA,K)
-* The i-th column must contain the vector which defines the
-* elementary reflector H(i), for i = 1,2,...,k, as returned by
-* DGEQLF in the last k columns of its array argument A.
-* A is modified by the routine but restored on exit.
-*
-* LDA (input) INTEGER
-* The leading dimension of the array A.
-* If SIDE = 'L', LDA >= max(1,M);
-* if SIDE = 'R', LDA >= max(1,N).
-*
-* TAU (input) DOUBLE PRECISION array, dimension (K)
-* TAU(i) must contain the scalar factor of the elementary
-* reflector H(i), as returned by DGEQLF.
-*
-* C (input/output) DOUBLE PRECISION array, dimension (LDC,N)
-* On entry, the m by n matrix C.
-* On exit, C is overwritten by Q*C or Q'*C or C*Q' or C*Q.
-*
-* LDC (input) INTEGER
-* The leading dimension of the array C. LDC >= max(1,M).
-*
-* WORK (workspace) DOUBLE PRECISION array, dimension
-* (N) if SIDE = 'L',
-* (M) if SIDE = 'R'
-*
-* INFO (output) INTEGER
-* = 0: successful exit
-* < 0: if INFO = -i, the i-th argument had an illegal value
-*
-* =====================================================================
-*
-* .. Parameters ..
- DOUBLE PRECISION ONE
- PARAMETER ( ONE = 1.0D+0 )
-* ..
-* .. Local Scalars ..
- LOGICAL LEFT, NOTRAN
- INTEGER I, I1, I2, I3, MI, NI, NQ
- DOUBLE PRECISION AII
-* ..
-* .. External Functions ..
- LOGICAL LSAME
- EXTERNAL LSAME
-* ..
-* .. External Subroutines ..
- EXTERNAL DLARF, XERBLA
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC MAX
-* ..
-* .. Executable Statements ..
-*
-* Test the input arguments
-*
- INFO = 0
- LEFT = LSAME( SIDE, 'L' )
- NOTRAN = LSAME( TRANS, 'N' )
-*
-* NQ is the order of Q
-*
- IF( LEFT ) THEN
- NQ = M
- ELSE
- NQ = N
- END IF
- IF( .NOT.LEFT .AND. .NOT.LSAME( SIDE, 'R' ) ) THEN
- INFO = -1
- ELSE IF( .NOT.NOTRAN .AND. .NOT.LSAME( TRANS, 'T' ) ) THEN
- INFO = -2
- ELSE IF( M.LT.0 ) THEN
- INFO = -3
- ELSE IF( N.LT.0 ) THEN
- INFO = -4
- ELSE IF( K.LT.0 .OR. K.GT.NQ ) THEN
- INFO = -5
- ELSE IF( LDA.LT.MAX( 1, NQ ) ) THEN
- INFO = -7
- ELSE IF( LDC.LT.MAX( 1, M ) ) THEN
- INFO = -10
- END IF
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'DORM2L', -INFO )
- RETURN
- END IF
-*
-* Quick return if possible
-*
- IF( M.EQ.0 .OR. N.EQ.0 .OR. K.EQ.0 )
- $ RETURN
-*
- IF( ( LEFT .AND. NOTRAN ) .OR. ( .NOT.LEFT .AND. .NOT.NOTRAN ) )
- $ THEN
- I1 = 1
- I2 = K
- I3 = 1
- ELSE
- I1 = K
- I2 = 1
- I3 = -1
- END IF
-*
- IF( LEFT ) THEN
- NI = N
- ELSE
- MI = M
- END IF
-*
- DO 10 I = I1, I2, I3
- IF( LEFT ) THEN
-*
-* H(i) is applied to C(1:m-k+i,1:n)
-*
- MI = M - K + I
- ELSE
-*
-* H(i) is applied to C(1:m,1:n-k+i)
-*
- NI = N - K + I
- END IF
-*
-* Apply H(i)
-*
- AII = A( NQ-K+I, I )
- A( NQ-K+I, I ) = ONE
- CALL DLARF( SIDE, MI, NI, A( 1, I ), 1, TAU( I ), C, LDC,
- $ WORK )
- A( NQ-K+I, I ) = AII
- 10 CONTINUE
- RETURN
-*
-* End of DORM2L
-*
- END
diff --git a/src/lib/lapack/dorm2r.f b/src/lib/lapack/dorm2r.f
deleted file mode 100644
index 79c9ef35..00000000
--- a/src/lib/lapack/dorm2r.f
+++ /dev/null
@@ -1,197 +0,0 @@
- SUBROUTINE DORM2R( SIDE, TRANS, M, N, K, A, LDA, TAU, C, LDC,
- $ WORK, INFO )
-*
-* -- LAPACK routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- CHARACTER SIDE, TRANS
- INTEGER INFO, K, LDA, LDC, M, N
-* ..
-* .. Array Arguments ..
- DOUBLE PRECISION A( LDA, * ), C( LDC, * ), TAU( * ), WORK( * )
-* ..
-*
-* Purpose
-* =======
-*
-* DORM2R overwrites the general real m by n matrix C with
-*
-* Q * C if SIDE = 'L' and TRANS = 'N', or
-*
-* Q'* C if SIDE = 'L' and TRANS = 'T', or
-*
-* C * Q if SIDE = 'R' and TRANS = 'N', or
-*
-* C * Q' if SIDE = 'R' and TRANS = 'T',
-*
-* where Q is a real orthogonal matrix defined as the product of k
-* elementary reflectors
-*
-* Q = H(1) H(2) . . . H(k)
-*
-* as returned by DGEQRF. Q is of order m if SIDE = 'L' and of order n
-* if SIDE = 'R'.
-*
-* Arguments
-* =========
-*
-* SIDE (input) CHARACTER*1
-* = 'L': apply Q or Q' from the Left
-* = 'R': apply Q or Q' from the Right
-*
-* TRANS (input) CHARACTER*1
-* = 'N': apply Q (No transpose)
-* = 'T': apply Q' (Transpose)
-*
-* M (input) INTEGER
-* The number of rows of the matrix C. M >= 0.
-*
-* N (input) INTEGER
-* The number of columns of the matrix C. N >= 0.
-*
-* K (input) INTEGER
-* The number of elementary reflectors whose product defines
-* the matrix Q.
-* If SIDE = 'L', M >= K >= 0;
-* if SIDE = 'R', N >= K >= 0.
-*
-* A (input) DOUBLE PRECISION array, dimension (LDA,K)
-* The i-th column must contain the vector which defines the
-* elementary reflector H(i), for i = 1,2,...,k, as returned by
-* DGEQRF in the first k columns of its array argument A.
-* A is modified by the routine but restored on exit.
-*
-* LDA (input) INTEGER
-* The leading dimension of the array A.
-* If SIDE = 'L', LDA >= max(1,M);
-* if SIDE = 'R', LDA >= max(1,N).
-*
-* TAU (input) DOUBLE PRECISION array, dimension (K)
-* TAU(i) must contain the scalar factor of the elementary
-* reflector H(i), as returned by DGEQRF.
-*
-* C (input/output) DOUBLE PRECISION array, dimension (LDC,N)
-* On entry, the m by n matrix C.
-* On exit, C is overwritten by Q*C or Q'*C or C*Q' or C*Q.
-*
-* LDC (input) INTEGER
-* The leading dimension of the array C. LDC >= max(1,M).
-*
-* WORK (workspace) DOUBLE PRECISION array, dimension
-* (N) if SIDE = 'L',
-* (M) if SIDE = 'R'
-*
-* INFO (output) INTEGER
-* = 0: successful exit
-* < 0: if INFO = -i, the i-th argument had an illegal value
-*
-* =====================================================================
-*
-* .. Parameters ..
- DOUBLE PRECISION ONE
- PARAMETER ( ONE = 1.0D+0 )
-* ..
-* .. Local Scalars ..
- LOGICAL LEFT, NOTRAN
- INTEGER I, I1, I2, I3, IC, JC, MI, NI, NQ
- DOUBLE PRECISION AII
-* ..
-* .. External Functions ..
- LOGICAL LSAME
- EXTERNAL LSAME
-* ..
-* .. External Subroutines ..
- EXTERNAL DLARF, XERBLA
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC MAX
-* ..
-* .. Executable Statements ..
-*
-* Test the input arguments
-*
- INFO = 0
- LEFT = LSAME( SIDE, 'L' )
- NOTRAN = LSAME( TRANS, 'N' )
-*
-* NQ is the order of Q
-*
- IF( LEFT ) THEN
- NQ = M
- ELSE
- NQ = N
- END IF
- IF( .NOT.LEFT .AND. .NOT.LSAME( SIDE, 'R' ) ) THEN
- INFO = -1
- ELSE IF( .NOT.NOTRAN .AND. .NOT.LSAME( TRANS, 'T' ) ) THEN
- INFO = -2
- ELSE IF( M.LT.0 ) THEN
- INFO = -3
- ELSE IF( N.LT.0 ) THEN
- INFO = -4
- ELSE IF( K.LT.0 .OR. K.GT.NQ ) THEN
- INFO = -5
- ELSE IF( LDA.LT.MAX( 1, NQ ) ) THEN
- INFO = -7
- ELSE IF( LDC.LT.MAX( 1, M ) ) THEN
- INFO = -10
- END IF
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'DORM2R', -INFO )
- RETURN
- END IF
-*
-* Quick return if possible
-*
- IF( M.EQ.0 .OR. N.EQ.0 .OR. K.EQ.0 )
- $ RETURN
-*
- IF( ( LEFT .AND. .NOT.NOTRAN ) .OR. ( .NOT.LEFT .AND. NOTRAN ) )
- $ THEN
- I1 = 1
- I2 = K
- I3 = 1
- ELSE
- I1 = K
- I2 = 1
- I3 = -1
- END IF
-*
- IF( LEFT ) THEN
- NI = N
- JC = 1
- ELSE
- MI = M
- IC = 1
- END IF
-*
- DO 10 I = I1, I2, I3
- IF( LEFT ) THEN
-*
-* H(i) is applied to C(i:m,1:n)
-*
- MI = M - I + 1
- IC = I
- ELSE
-*
-* H(i) is applied to C(1:m,i:n)
-*
- NI = N - I + 1
- JC = I
- END IF
-*
-* Apply H(i)
-*
- AII = A( I, I )
- A( I, I ) = ONE
- CALL DLARF( SIDE, MI, NI, A( I, I ), 1, TAU( I ), C( IC, JC ),
- $ LDC, WORK )
- A( I, I ) = AII
- 10 CONTINUE
- RETURN
-*
-* End of DORM2R
-*
- END
diff --git a/src/lib/lapack/dormbr.f b/src/lib/lapack/dormbr.f
deleted file mode 100644
index 8066b893..00000000
--- a/src/lib/lapack/dormbr.f
+++ /dev/null
@@ -1,281 +0,0 @@
- SUBROUTINE DORMBR( VECT, SIDE, TRANS, M, N, K, A, LDA, TAU, C,
- $ LDC, WORK, LWORK, INFO )
-*
-* -- LAPACK routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- CHARACTER SIDE, TRANS, VECT
- INTEGER INFO, K, LDA, LDC, LWORK, M, N
-* ..
-* .. Array Arguments ..
- DOUBLE PRECISION A( LDA, * ), C( LDC, * ), TAU( * ), WORK( * )
-* ..
-*
-* Purpose
-* =======
-*
-* If VECT = 'Q', DORMBR overwrites the general real M-by-N matrix C
-* with
-* SIDE = 'L' SIDE = 'R'
-* TRANS = 'N': Q * C C * Q
-* TRANS = 'T': Q**T * C C * Q**T
-*
-* If VECT = 'P', DORMBR overwrites the general real M-by-N matrix C
-* with
-* SIDE = 'L' SIDE = 'R'
-* TRANS = 'N': P * C C * P
-* TRANS = 'T': P**T * C C * P**T
-*
-* Here Q and P**T are the orthogonal matrices determined by DGEBRD when
-* reducing a real matrix A to bidiagonal form: A = Q * B * P**T. Q and
-* P**T are defined as products of elementary reflectors H(i) and G(i)
-* respectively.
-*
-* Let nq = m if SIDE = 'L' and nq = n if SIDE = 'R'. Thus nq is the
-* order of the orthogonal matrix Q or P**T that is applied.
-*
-* If VECT = 'Q', A is assumed to have been an NQ-by-K matrix:
-* if nq >= k, Q = H(1) H(2) . . . H(k);
-* if nq < k, Q = H(1) H(2) . . . H(nq-1).
-*
-* If VECT = 'P', A is assumed to have been a K-by-NQ matrix:
-* if k < nq, P = G(1) G(2) . . . G(k);
-* if k >= nq, P = G(1) G(2) . . . G(nq-1).
-*
-* Arguments
-* =========
-*
-* VECT (input) CHARACTER*1
-* = 'Q': apply Q or Q**T;
-* = 'P': apply P or P**T.
-*
-* SIDE (input) CHARACTER*1
-* = 'L': apply Q, Q**T, P or P**T from the Left;
-* = 'R': apply Q, Q**T, P or P**T from the Right.
-*
-* TRANS (input) CHARACTER*1
-* = 'N': No transpose, apply Q or P;
-* = 'T': Transpose, apply Q**T or P**T.
-*
-* M (input) INTEGER
-* The number of rows of the matrix C. M >= 0.
-*
-* N (input) INTEGER
-* The number of columns of the matrix C. N >= 0.
-*
-* K (input) INTEGER
-* If VECT = 'Q', the number of columns in the original
-* matrix reduced by DGEBRD.
-* If VECT = 'P', the number of rows in the original
-* matrix reduced by DGEBRD.
-* K >= 0.
-*
-* A (input) DOUBLE PRECISION array, dimension
-* (LDA,min(nq,K)) if VECT = 'Q'
-* (LDA,nq) if VECT = 'P'
-* The vectors which define the elementary reflectors H(i) and
-* G(i), whose products determine the matrices Q and P, as
-* returned by DGEBRD.
-*
-* LDA (input) INTEGER
-* The leading dimension of the array A.
-* If VECT = 'Q', LDA >= max(1,nq);
-* if VECT = 'P', LDA >= max(1,min(nq,K)).
-*
-* TAU (input) DOUBLE PRECISION array, dimension (min(nq,K))
-* TAU(i) must contain the scalar factor of the elementary
-* reflector H(i) or G(i) which determines Q or P, as returned
-* by DGEBRD in the array argument TAUQ or TAUP.
-*
-* C (input/output) DOUBLE PRECISION array, dimension (LDC,N)
-* On entry, the M-by-N matrix C.
-* On exit, C is overwritten by Q*C or Q**T*C or C*Q**T or C*Q
-* or P*C or P**T*C or C*P or C*P**T.
-*
-* LDC (input) INTEGER
-* The leading dimension of the array C. LDC >= max(1,M).
-*
-* WORK (workspace/output) DOUBLE PRECISION array, dimension (MAX(1,LWORK))
-* On exit, if INFO = 0, WORK(1) returns the optimal LWORK.
-*
-* LWORK (input) INTEGER
-* The dimension of the array WORK.
-* If SIDE = 'L', LWORK >= max(1,N);
-* if SIDE = 'R', LWORK >= max(1,M).
-* For optimum performance LWORK >= N*NB if SIDE = 'L', and
-* LWORK >= M*NB if SIDE = 'R', where NB is the optimal
-* blocksize.
-*
-* If LWORK = -1, then a workspace query is assumed; the routine
-* only calculates the optimal size of the WORK array, returns
-* this value as the first entry of the WORK array, and no error
-* message related to LWORK is issued by XERBLA.
-*
-* INFO (output) INTEGER
-* = 0: successful exit
-* < 0: if INFO = -i, the i-th argument had an illegal value
-*
-* =====================================================================
-*
-* .. Local Scalars ..
- LOGICAL APPLYQ, LEFT, LQUERY, NOTRAN
- CHARACTER TRANST
- INTEGER I1, I2, IINFO, LWKOPT, MI, NB, NI, NQ, NW
-* ..
-* .. External Functions ..
- LOGICAL LSAME
- INTEGER ILAENV
- EXTERNAL LSAME, ILAENV
-* ..
-* .. External Subroutines ..
- EXTERNAL DORMLQ, DORMQR, XERBLA
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC MAX, MIN
-* ..
-* .. Executable Statements ..
-*
-* Test the input arguments
-*
- INFO = 0
- APPLYQ = LSAME( VECT, 'Q' )
- LEFT = LSAME( SIDE, 'L' )
- NOTRAN = LSAME( TRANS, 'N' )
- LQUERY = ( LWORK.EQ.-1 )
-*
-* NQ is the order of Q or P and NW is the minimum dimension of WORK
-*
- IF( LEFT ) THEN
- NQ = M
- NW = N
- ELSE
- NQ = N
- NW = M
- END IF
- IF( .NOT.APPLYQ .AND. .NOT.LSAME( VECT, 'P' ) ) THEN
- INFO = -1
- ELSE IF( .NOT.LEFT .AND. .NOT.LSAME( SIDE, 'R' ) ) THEN
- INFO = -2
- ELSE IF( .NOT.NOTRAN .AND. .NOT.LSAME( TRANS, 'T' ) ) THEN
- INFO = -3
- ELSE IF( M.LT.0 ) THEN
- INFO = -4
- ELSE IF( N.LT.0 ) THEN
- INFO = -5
- ELSE IF( K.LT.0 ) THEN
- INFO = -6
- ELSE IF( ( APPLYQ .AND. LDA.LT.MAX( 1, NQ ) ) .OR.
- $ ( .NOT.APPLYQ .AND. LDA.LT.MAX( 1, MIN( NQ, K ) ) ) )
- $ THEN
- INFO = -8
- ELSE IF( LDC.LT.MAX( 1, M ) ) THEN
- INFO = -11
- ELSE IF( LWORK.LT.MAX( 1, NW ) .AND. .NOT.LQUERY ) THEN
- INFO = -13
- END IF
-*
- IF( INFO.EQ.0 ) THEN
- IF( APPLYQ ) THEN
- IF( LEFT ) THEN
- NB = ILAENV( 1, 'DORMQR', SIDE // TRANS, M-1, N, M-1,
- $ -1 )
- ELSE
- NB = ILAENV( 1, 'DORMQR', SIDE // TRANS, M, N-1, N-1,
- $ -1 )
- END IF
- ELSE
- IF( LEFT ) THEN
- NB = ILAENV( 1, 'DORMLQ', SIDE // TRANS, M-1, N, M-1,
- $ -1 )
- ELSE
- NB = ILAENV( 1, 'DORMLQ', SIDE // TRANS, M, N-1, N-1,
- $ -1 )
- END IF
- END IF
- LWKOPT = MAX( 1, NW )*NB
- WORK( 1 ) = LWKOPT
- END IF
-*
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'DORMBR', -INFO )
- RETURN
- ELSE IF( LQUERY ) THEN
- RETURN
- END IF
-*
-* Quick return if possible
-*
- WORK( 1 ) = 1
- IF( M.EQ.0 .OR. N.EQ.0 )
- $ RETURN
-*
- IF( APPLYQ ) THEN
-*
-* Apply Q
-*
- IF( NQ.GE.K ) THEN
-*
-* Q was determined by a call to DGEBRD with nq >= k
-*
- CALL DORMQR( SIDE, TRANS, M, N, K, A, LDA, TAU, C, LDC,
- $ WORK, LWORK, IINFO )
- ELSE IF( NQ.GT.1 ) THEN
-*
-* Q was determined by a call to DGEBRD with nq < k
-*
- IF( LEFT ) THEN
- MI = M - 1
- NI = N
- I1 = 2
- I2 = 1
- ELSE
- MI = M
- NI = N - 1
- I1 = 1
- I2 = 2
- END IF
- CALL DORMQR( SIDE, TRANS, MI, NI, NQ-1, A( 2, 1 ), LDA, TAU,
- $ C( I1, I2 ), LDC, WORK, LWORK, IINFO )
- END IF
- ELSE
-*
-* Apply P
-*
- IF( NOTRAN ) THEN
- TRANST = 'T'
- ELSE
- TRANST = 'N'
- END IF
- IF( NQ.GT.K ) THEN
-*
-* P was determined by a call to DGEBRD with nq > k
-*
- CALL DORMLQ( SIDE, TRANST, M, N, K, A, LDA, TAU, C, LDC,
- $ WORK, LWORK, IINFO )
- ELSE IF( NQ.GT.1 ) THEN
-*
-* P was determined by a call to DGEBRD with nq <= k
-*
- IF( LEFT ) THEN
- MI = M - 1
- NI = N
- I1 = 2
- I2 = 1
- ELSE
- MI = M
- NI = N - 1
- I1 = 1
- I2 = 2
- END IF
- CALL DORMLQ( SIDE, TRANST, MI, NI, NQ-1, A( 1, 2 ), LDA,
- $ TAU, C( I1, I2 ), LDC, WORK, LWORK, IINFO )
- END IF
- END IF
- WORK( 1 ) = LWKOPT
- RETURN
-*
-* End of DORMBR
-*
- END
diff --git a/src/lib/lapack/dormhr.f b/src/lib/lapack/dormhr.f
deleted file mode 100644
index 5862538e..00000000
--- a/src/lib/lapack/dormhr.f
+++ /dev/null
@@ -1,201 +0,0 @@
- SUBROUTINE DORMHR( SIDE, TRANS, M, N, ILO, IHI, A, LDA, TAU, C,
- $ LDC, WORK, LWORK, INFO )
-*
-* -- LAPACK routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- CHARACTER SIDE, TRANS
- INTEGER IHI, ILO, INFO, LDA, LDC, LWORK, M, N
-* ..
-* .. Array Arguments ..
- DOUBLE PRECISION A( LDA, * ), C( LDC, * ), TAU( * ), WORK( * )
-* ..
-*
-* Purpose
-* =======
-*
-* DORMHR overwrites the general real M-by-N matrix C with
-*
-* SIDE = 'L' SIDE = 'R'
-* TRANS = 'N': Q * C C * Q
-* TRANS = 'T': Q**T * C C * Q**T
-*
-* where Q is a real orthogonal matrix of order nq, with nq = m if
-* SIDE = 'L' and nq = n if SIDE = 'R'. Q is defined as the product of
-* IHI-ILO elementary reflectors, as returned by DGEHRD:
-*
-* Q = H(ilo) H(ilo+1) . . . H(ihi-1).
-*
-* Arguments
-* =========
-*
-* SIDE (input) CHARACTER*1
-* = 'L': apply Q or Q**T from the Left;
-* = 'R': apply Q or Q**T from the Right.
-*
-* TRANS (input) CHARACTER*1
-* = 'N': No transpose, apply Q;
-* = 'T': Transpose, apply Q**T.
-*
-* M (input) INTEGER
-* The number of rows of the matrix C. M >= 0.
-*
-* N (input) INTEGER
-* The number of columns of the matrix C. N >= 0.
-*
-* ILO (input) INTEGER
-* IHI (input) INTEGER
-* ILO and IHI must have the same values as in the previous call
-* of DGEHRD. Q is equal to the unit matrix except in the
-* submatrix Q(ilo+1:ihi,ilo+1:ihi).
-* If SIDE = 'L', then 1 <= ILO <= IHI <= M, if M > 0, and
-* ILO = 1 and IHI = 0, if M = 0;
-* if SIDE = 'R', then 1 <= ILO <= IHI <= N, if N > 0, and
-* ILO = 1 and IHI = 0, if N = 0.
-*
-* A (input) DOUBLE PRECISION array, dimension
-* (LDA,M) if SIDE = 'L'
-* (LDA,N) if SIDE = 'R'
-* The vectors which define the elementary reflectors, as
-* returned by DGEHRD.
-*
-* LDA (input) INTEGER
-* The leading dimension of the array A.
-* LDA >= max(1,M) if SIDE = 'L'; LDA >= max(1,N) if SIDE = 'R'.
-*
-* TAU (input) DOUBLE PRECISION array, dimension
-* (M-1) if SIDE = 'L'
-* (N-1) if SIDE = 'R'
-* TAU(i) must contain the scalar factor of the elementary
-* reflector H(i), as returned by DGEHRD.
-*
-* C (input/output) DOUBLE PRECISION array, dimension (LDC,N)
-* On entry, the M-by-N matrix C.
-* On exit, C is overwritten by Q*C or Q**T*C or C*Q**T or C*Q.
-*
-* LDC (input) INTEGER
-* The leading dimension of the array C. LDC >= max(1,M).
-*
-* WORK (workspace/output) DOUBLE PRECISION array, dimension (MAX(1,LWORK))
-* On exit, if INFO = 0, WORK(1) returns the optimal LWORK.
-*
-* LWORK (input) INTEGER
-* The dimension of the array WORK.
-* If SIDE = 'L', LWORK >= max(1,N);
-* if SIDE = 'R', LWORK >= max(1,M).
-* For optimum performance LWORK >= N*NB if SIDE = 'L', and
-* LWORK >= M*NB if SIDE = 'R', where NB is the optimal
-* blocksize.
-*
-* If LWORK = -1, then a workspace query is assumed; the routine
-* only calculates the optimal size of the WORK array, returns
-* this value as the first entry of the WORK array, and no error
-* message related to LWORK is issued by XERBLA.
-*
-* INFO (output) INTEGER
-* = 0: successful exit
-* < 0: if INFO = -i, the i-th argument had an illegal value
-*
-* =====================================================================
-*
-* .. Local Scalars ..
- LOGICAL LEFT, LQUERY
- INTEGER I1, I2, IINFO, LWKOPT, MI, NB, NH, NI, NQ, NW
-* ..
-* .. External Functions ..
- LOGICAL LSAME
- INTEGER ILAENV
- EXTERNAL LSAME, ILAENV
-* ..
-* .. External Subroutines ..
- EXTERNAL DORMQR, XERBLA
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC MAX, MIN
-* ..
-* .. Executable Statements ..
-*
-* Test the input arguments
-*
- INFO = 0
- NH = IHI - ILO
- LEFT = LSAME( SIDE, 'L' )
- LQUERY = ( LWORK.EQ.-1 )
-*
-* NQ is the order of Q and NW is the minimum dimension of WORK
-*
- IF( LEFT ) THEN
- NQ = M
- NW = N
- ELSE
- NQ = N
- NW = M
- END IF
- IF( .NOT.LEFT .AND. .NOT.LSAME( SIDE, 'R' ) ) THEN
- INFO = -1
- ELSE IF( .NOT.LSAME( TRANS, 'N' ) .AND. .NOT.LSAME( TRANS, 'T' ) )
- $ THEN
- INFO = -2
- ELSE IF( M.LT.0 ) THEN
- INFO = -3
- ELSE IF( N.LT.0 ) THEN
- INFO = -4
- ELSE IF( ILO.LT.1 .OR. ILO.GT.MAX( 1, NQ ) ) THEN
- INFO = -5
- ELSE IF( IHI.LT.MIN( ILO, NQ ) .OR. IHI.GT.NQ ) THEN
- INFO = -6
- ELSE IF( LDA.LT.MAX( 1, NQ ) ) THEN
- INFO = -8
- ELSE IF( LDC.LT.MAX( 1, M ) ) THEN
- INFO = -11
- ELSE IF( LWORK.LT.MAX( 1, NW ) .AND. .NOT.LQUERY ) THEN
- INFO = -13
- END IF
-*
- IF( INFO.EQ.0 ) THEN
- IF( LEFT ) THEN
- NB = ILAENV( 1, 'DORMQR', SIDE // TRANS, NH, N, NH, -1 )
- ELSE
- NB = ILAENV( 1, 'DORMQR', SIDE // TRANS, M, NH, NH, -1 )
- END IF
- LWKOPT = MAX( 1, NW )*NB
- WORK( 1 ) = LWKOPT
- END IF
-*
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'DORMHR', -INFO )
- RETURN
- ELSE IF( LQUERY ) THEN
- RETURN
- END IF
-*
-* Quick return if possible
-*
- IF( M.EQ.0 .OR. N.EQ.0 .OR. NH.EQ.0 ) THEN
- WORK( 1 ) = 1
- RETURN
- END IF
-*
- IF( LEFT ) THEN
- MI = NH
- NI = N
- I1 = ILO + 1
- I2 = 1
- ELSE
- MI = M
- NI = NH
- I1 = 1
- I2 = ILO + 1
- END IF
-*
- CALL DORMQR( SIDE, TRANS, MI, NI, NH, A( ILO+1, ILO ), LDA,
- $ TAU( ILO ), C( I1, I2 ), LDC, WORK, LWORK, IINFO )
-*
- WORK( 1 ) = LWKOPT
- RETURN
-*
-* End of DORMHR
-*
- END
diff --git a/src/lib/lapack/dorml2.f b/src/lib/lapack/dorml2.f
deleted file mode 100644
index d3941c9a..00000000
--- a/src/lib/lapack/dorml2.f
+++ /dev/null
@@ -1,197 +0,0 @@
- SUBROUTINE DORML2( SIDE, TRANS, M, N, K, A, LDA, TAU, C, LDC,
- $ WORK, INFO )
-*
-* -- LAPACK routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- CHARACTER SIDE, TRANS
- INTEGER INFO, K, LDA, LDC, M, N
-* ..
-* .. Array Arguments ..
- DOUBLE PRECISION A( LDA, * ), C( LDC, * ), TAU( * ), WORK( * )
-* ..
-*
-* Purpose
-* =======
-*
-* DORML2 overwrites the general real m by n matrix C with
-*
-* Q * C if SIDE = 'L' and TRANS = 'N', or
-*
-* Q'* C if SIDE = 'L' and TRANS = 'T', or
-*
-* C * Q if SIDE = 'R' and TRANS = 'N', or
-*
-* C * Q' if SIDE = 'R' and TRANS = 'T',
-*
-* where Q is a real orthogonal matrix defined as the product of k
-* elementary reflectors
-*
-* Q = H(k) . . . H(2) H(1)
-*
-* as returned by DGELQF. Q is of order m if SIDE = 'L' and of order n
-* if SIDE = 'R'.
-*
-* Arguments
-* =========
-*
-* SIDE (input) CHARACTER*1
-* = 'L': apply Q or Q' from the Left
-* = 'R': apply Q or Q' from the Right
-*
-* TRANS (input) CHARACTER*1
-* = 'N': apply Q (No transpose)
-* = 'T': apply Q' (Transpose)
-*
-* M (input) INTEGER
-* The number of rows of the matrix C. M >= 0.
-*
-* N (input) INTEGER
-* The number of columns of the matrix C. N >= 0.
-*
-* K (input) INTEGER
-* The number of elementary reflectors whose product defines
-* the matrix Q.
-* If SIDE = 'L', M >= K >= 0;
-* if SIDE = 'R', N >= K >= 0.
-*
-* A (input) DOUBLE PRECISION array, dimension
-* (LDA,M) if SIDE = 'L',
-* (LDA,N) if SIDE = 'R'
-* The i-th row must contain the vector which defines the
-* elementary reflector H(i), for i = 1,2,...,k, as returned by
-* DGELQF in the first k rows of its array argument A.
-* A is modified by the routine but restored on exit.
-*
-* LDA (input) INTEGER
-* The leading dimension of the array A. LDA >= max(1,K).
-*
-* TAU (input) DOUBLE PRECISION array, dimension (K)
-* TAU(i) must contain the scalar factor of the elementary
-* reflector H(i), as returned by DGELQF.
-*
-* C (input/output) DOUBLE PRECISION array, dimension (LDC,N)
-* On entry, the m by n matrix C.
-* On exit, C is overwritten by Q*C or Q'*C or C*Q' or C*Q.
-*
-* LDC (input) INTEGER
-* The leading dimension of the array C. LDC >= max(1,M).
-*
-* WORK (workspace) DOUBLE PRECISION array, dimension
-* (N) if SIDE = 'L',
-* (M) if SIDE = 'R'
-*
-* INFO (output) INTEGER
-* = 0: successful exit
-* < 0: if INFO = -i, the i-th argument had an illegal value
-*
-* =====================================================================
-*
-* .. Parameters ..
- DOUBLE PRECISION ONE
- PARAMETER ( ONE = 1.0D+0 )
-* ..
-* .. Local Scalars ..
- LOGICAL LEFT, NOTRAN
- INTEGER I, I1, I2, I3, IC, JC, MI, NI, NQ
- DOUBLE PRECISION AII
-* ..
-* .. External Functions ..
- LOGICAL LSAME
- EXTERNAL LSAME
-* ..
-* .. External Subroutines ..
- EXTERNAL DLARF, XERBLA
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC MAX
-* ..
-* .. Executable Statements ..
-*
-* Test the input arguments
-*
- INFO = 0
- LEFT = LSAME( SIDE, 'L' )
- NOTRAN = LSAME( TRANS, 'N' )
-*
-* NQ is the order of Q
-*
- IF( LEFT ) THEN
- NQ = M
- ELSE
- NQ = N
- END IF
- IF( .NOT.LEFT .AND. .NOT.LSAME( SIDE, 'R' ) ) THEN
- INFO = -1
- ELSE IF( .NOT.NOTRAN .AND. .NOT.LSAME( TRANS, 'T' ) ) THEN
- INFO = -2
- ELSE IF( M.LT.0 ) THEN
- INFO = -3
- ELSE IF( N.LT.0 ) THEN
- INFO = -4
- ELSE IF( K.LT.0 .OR. K.GT.NQ ) THEN
- INFO = -5
- ELSE IF( LDA.LT.MAX( 1, K ) ) THEN
- INFO = -7
- ELSE IF( LDC.LT.MAX( 1, M ) ) THEN
- INFO = -10
- END IF
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'DORML2', -INFO )
- RETURN
- END IF
-*
-* Quick return if possible
-*
- IF( M.EQ.0 .OR. N.EQ.0 .OR. K.EQ.0 )
- $ RETURN
-*
- IF( ( LEFT .AND. NOTRAN ) .OR. ( .NOT.LEFT .AND. .NOT.NOTRAN ) )
- $ THEN
- I1 = 1
- I2 = K
- I3 = 1
- ELSE
- I1 = K
- I2 = 1
- I3 = -1
- END IF
-*
- IF( LEFT ) THEN
- NI = N
- JC = 1
- ELSE
- MI = M
- IC = 1
- END IF
-*
- DO 10 I = I1, I2, I3
- IF( LEFT ) THEN
-*
-* H(i) is applied to C(i:m,1:n)
-*
- MI = M - I + 1
- IC = I
- ELSE
-*
-* H(i) is applied to C(1:m,i:n)
-*
- NI = N - I + 1
- JC = I
- END IF
-*
-* Apply H(i)
-*
- AII = A( I, I )
- A( I, I ) = ONE
- CALL DLARF( SIDE, MI, NI, A( I, I ), LDA, TAU( I ),
- $ C( IC, JC ), LDC, WORK )
- A( I, I ) = AII
- 10 CONTINUE
- RETURN
-*
-* End of DORML2
-*
- END
diff --git a/src/lib/lapack/dormlq.f b/src/lib/lapack/dormlq.f
deleted file mode 100644
index f0c68ef2..00000000
--- a/src/lib/lapack/dormlq.f
+++ /dev/null
@@ -1,267 +0,0 @@
- SUBROUTINE DORMLQ( SIDE, TRANS, M, N, K, A, LDA, TAU, C, LDC,
- $ WORK, LWORK, INFO )
-*
-* -- LAPACK routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- CHARACTER SIDE, TRANS
- INTEGER INFO, K, LDA, LDC, LWORK, M, N
-* ..
-* .. Array Arguments ..
- DOUBLE PRECISION A( LDA, * ), C( LDC, * ), TAU( * ), WORK( * )
-* ..
-*
-* Purpose
-* =======
-*
-* DORMLQ overwrites the general real M-by-N matrix C with
-*
-* SIDE = 'L' SIDE = 'R'
-* TRANS = 'N': Q * C C * Q
-* TRANS = 'T': Q**T * C C * Q**T
-*
-* where Q is a real orthogonal matrix defined as the product of k
-* elementary reflectors
-*
-* Q = H(k) . . . H(2) H(1)
-*
-* as returned by DGELQF. Q is of order M if SIDE = 'L' and of order N
-* if SIDE = 'R'.
-*
-* Arguments
-* =========
-*
-* SIDE (input) CHARACTER*1
-* = 'L': apply Q or Q**T from the Left;
-* = 'R': apply Q or Q**T from the Right.
-*
-* TRANS (input) CHARACTER*1
-* = 'N': No transpose, apply Q;
-* = 'T': Transpose, apply Q**T.
-*
-* M (input) INTEGER
-* The number of rows of the matrix C. M >= 0.
-*
-* N (input) INTEGER
-* The number of columns of the matrix C. N >= 0.
-*
-* K (input) INTEGER
-* The number of elementary reflectors whose product defines
-* the matrix Q.
-* If SIDE = 'L', M >= K >= 0;
-* if SIDE = 'R', N >= K >= 0.
-*
-* A (input) DOUBLE PRECISION array, dimension
-* (LDA,M) if SIDE = 'L',
-* (LDA,N) if SIDE = 'R'
-* The i-th row must contain the vector which defines the
-* elementary reflector H(i), for i = 1,2,...,k, as returned by
-* DGELQF in the first k rows of its array argument A.
-* A is modified by the routine but restored on exit.
-*
-* LDA (input) INTEGER
-* The leading dimension of the array A. LDA >= max(1,K).
-*
-* TAU (input) DOUBLE PRECISION array, dimension (K)
-* TAU(i) must contain the scalar factor of the elementary
-* reflector H(i), as returned by DGELQF.
-*
-* C (input/output) DOUBLE PRECISION array, dimension (LDC,N)
-* On entry, the M-by-N matrix C.
-* On exit, C is overwritten by Q*C or Q**T*C or C*Q**T or C*Q.
-*
-* LDC (input) INTEGER
-* The leading dimension of the array C. LDC >= max(1,M).
-*
-* WORK (workspace/output) DOUBLE PRECISION array, dimension (MAX(1,LWORK))
-* On exit, if INFO = 0, WORK(1) returns the optimal LWORK.
-*
-* LWORK (input) INTEGER
-* The dimension of the array WORK.
-* If SIDE = 'L', LWORK >= max(1,N);
-* if SIDE = 'R', LWORK >= max(1,M).
-* For optimum performance LWORK >= N*NB if SIDE = 'L', and
-* LWORK >= M*NB if SIDE = 'R', where NB is the optimal
-* blocksize.
-*
-* If LWORK = -1, then a workspace query is assumed; the routine
-* only calculates the optimal size of the WORK array, returns
-* this value as the first entry of the WORK array, and no error
-* message related to LWORK is issued by XERBLA.
-*
-* INFO (output) INTEGER
-* = 0: successful exit
-* < 0: if INFO = -i, the i-th argument had an illegal value
-*
-* =====================================================================
-*
-* .. Parameters ..
- INTEGER NBMAX, LDT
- PARAMETER ( NBMAX = 64, LDT = NBMAX+1 )
-* ..
-* .. Local Scalars ..
- LOGICAL LEFT, LQUERY, NOTRAN
- CHARACTER TRANST
- INTEGER I, I1, I2, I3, IB, IC, IINFO, IWS, JC, LDWORK,
- $ LWKOPT, MI, NB, NBMIN, NI, NQ, NW
-* ..
-* .. Local Arrays ..
- DOUBLE PRECISION T( LDT, NBMAX )
-* ..
-* .. External Functions ..
- LOGICAL LSAME
- INTEGER ILAENV
- EXTERNAL LSAME, ILAENV
-* ..
-* .. External Subroutines ..
- EXTERNAL DLARFB, DLARFT, DORML2, XERBLA
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC MAX, MIN
-* ..
-* .. Executable Statements ..
-*
-* Test the input arguments
-*
- INFO = 0
- LEFT = LSAME( SIDE, 'L' )
- NOTRAN = LSAME( TRANS, 'N' )
- LQUERY = ( LWORK.EQ.-1 )
-*
-* NQ is the order of Q and NW is the minimum dimension of WORK
-*
- IF( LEFT ) THEN
- NQ = M
- NW = N
- ELSE
- NQ = N
- NW = M
- END IF
- IF( .NOT.LEFT .AND. .NOT.LSAME( SIDE, 'R' ) ) THEN
- INFO = -1
- ELSE IF( .NOT.NOTRAN .AND. .NOT.LSAME( TRANS, 'T' ) ) THEN
- INFO = -2
- ELSE IF( M.LT.0 ) THEN
- INFO = -3
- ELSE IF( N.LT.0 ) THEN
- INFO = -4
- ELSE IF( K.LT.0 .OR. K.GT.NQ ) THEN
- INFO = -5
- ELSE IF( LDA.LT.MAX( 1, K ) ) THEN
- INFO = -7
- ELSE IF( LDC.LT.MAX( 1, M ) ) THEN
- INFO = -10
- ELSE IF( LWORK.LT.MAX( 1, NW ) .AND. .NOT.LQUERY ) THEN
- INFO = -12
- END IF
-*
- IF( INFO.EQ.0 ) THEN
-*
-* Determine the block size. NB may be at most NBMAX, where NBMAX
-* is used to define the local array T.
-*
- NB = MIN( NBMAX, ILAENV( 1, 'DORMLQ', SIDE // TRANS, M, N, K,
- $ -1 ) )
- LWKOPT = MAX( 1, NW )*NB
- WORK( 1 ) = LWKOPT
- END IF
-*
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'DORMLQ', -INFO )
- RETURN
- ELSE IF( LQUERY ) THEN
- RETURN
- END IF
-*
-* Quick return if possible
-*
- IF( M.EQ.0 .OR. N.EQ.0 .OR. K.EQ.0 ) THEN
- WORK( 1 ) = 1
- RETURN
- END IF
-*
- NBMIN = 2
- LDWORK = NW
- IF( NB.GT.1 .AND. NB.LT.K ) THEN
- IWS = NW*NB
- IF( LWORK.LT.IWS ) THEN
- NB = LWORK / LDWORK
- NBMIN = MAX( 2, ILAENV( 2, 'DORMLQ', SIDE // TRANS, M, N, K,
- $ -1 ) )
- END IF
- ELSE
- IWS = NW
- END IF
-*
- IF( NB.LT.NBMIN .OR. NB.GE.K ) THEN
-*
-* Use unblocked code
-*
- CALL DORML2( SIDE, TRANS, M, N, K, A, LDA, TAU, C, LDC, WORK,
- $ IINFO )
- ELSE
-*
-* Use blocked code
-*
- IF( ( LEFT .AND. NOTRAN ) .OR.
- $ ( .NOT.LEFT .AND. .NOT.NOTRAN ) ) THEN
- I1 = 1
- I2 = K
- I3 = NB
- ELSE
- I1 = ( ( K-1 ) / NB )*NB + 1
- I2 = 1
- I3 = -NB
- END IF
-*
- IF( LEFT ) THEN
- NI = N
- JC = 1
- ELSE
- MI = M
- IC = 1
- END IF
-*
- IF( NOTRAN ) THEN
- TRANST = 'T'
- ELSE
- TRANST = 'N'
- END IF
-*
- DO 10 I = I1, I2, I3
- IB = MIN( NB, K-I+1 )
-*
-* Form the triangular factor of the block reflector
-* H = H(i) H(i+1) . . . H(i+ib-1)
-*
- CALL DLARFT( 'Forward', 'Rowwise', NQ-I+1, IB, A( I, I ),
- $ LDA, TAU( I ), T, LDT )
- IF( LEFT ) THEN
-*
-* H or H' is applied to C(i:m,1:n)
-*
- MI = M - I + 1
- IC = I
- ELSE
-*
-* H or H' is applied to C(1:m,i:n)
-*
- NI = N - I + 1
- JC = I
- END IF
-*
-* Apply H or H'
-*
- CALL DLARFB( SIDE, TRANST, 'Forward', 'Rowwise', MI, NI, IB,
- $ A( I, I ), LDA, T, LDT, C( IC, JC ), LDC, WORK,
- $ LDWORK )
- 10 CONTINUE
- END IF
- WORK( 1 ) = LWKOPT
- RETURN
-*
-* End of DORMLQ
-*
- END
diff --git a/src/lib/lapack/dormql.f b/src/lib/lapack/dormql.f
deleted file mode 100644
index f3370f10..00000000
--- a/src/lib/lapack/dormql.f
+++ /dev/null
@@ -1,261 +0,0 @@
- SUBROUTINE DORMQL( SIDE, TRANS, M, N, K, A, LDA, TAU, C, LDC,
- $ WORK, LWORK, INFO )
-*
-* -- LAPACK routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- CHARACTER SIDE, TRANS
- INTEGER INFO, K, LDA, LDC, LWORK, M, N
-* ..
-* .. Array Arguments ..
- DOUBLE PRECISION A( LDA, * ), C( LDC, * ), TAU( * ), WORK( * )
-* ..
-*
-* Purpose
-* =======
-*
-* DORMQL overwrites the general real M-by-N matrix C with
-*
-* SIDE = 'L' SIDE = 'R'
-* TRANS = 'N': Q * C C * Q
-* TRANS = 'T': Q**T * C C * Q**T
-*
-* where Q is a real orthogonal matrix defined as the product of k
-* elementary reflectors
-*
-* Q = H(k) . . . H(2) H(1)
-*
-* as returned by DGEQLF. Q is of order M if SIDE = 'L' and of order N
-* if SIDE = 'R'.
-*
-* Arguments
-* =========
-*
-* SIDE (input) CHARACTER*1
-* = 'L': apply Q or Q**T from the Left;
-* = 'R': apply Q or Q**T from the Right.
-*
-* TRANS (input) CHARACTER*1
-* = 'N': No transpose, apply Q;
-* = 'T': Transpose, apply Q**T.
-*
-* M (input) INTEGER
-* The number of rows of the matrix C. M >= 0.
-*
-* N (input) INTEGER
-* The number of columns of the matrix C. N >= 0.
-*
-* K (input) INTEGER
-* The number of elementary reflectors whose product defines
-* the matrix Q.
-* If SIDE = 'L', M >= K >= 0;
-* if SIDE = 'R', N >= K >= 0.
-*
-* A (input) DOUBLE PRECISION array, dimension (LDA,K)
-* The i-th column must contain the vector which defines the
-* elementary reflector H(i), for i = 1,2,...,k, as returned by
-* DGEQLF in the last k columns of its array argument A.
-* A is modified by the routine but restored on exit.
-*
-* LDA (input) INTEGER
-* The leading dimension of the array A.
-* If SIDE = 'L', LDA >= max(1,M);
-* if SIDE = 'R', LDA >= max(1,N).
-*
-* TAU (input) DOUBLE PRECISION array, dimension (K)
-* TAU(i) must contain the scalar factor of the elementary
-* reflector H(i), as returned by DGEQLF.
-*
-* C (input/output) DOUBLE PRECISION array, dimension (LDC,N)
-* On entry, the M-by-N matrix C.
-* On exit, C is overwritten by Q*C or Q**T*C or C*Q**T or C*Q.
-*
-* LDC (input) INTEGER
-* The leading dimension of the array C. LDC >= max(1,M).
-*
-* WORK (workspace/output) DOUBLE PRECISION array, dimension (MAX(1,LWORK))
-* On exit, if INFO = 0, WORK(1) returns the optimal LWORK.
-*
-* LWORK (input) INTEGER
-* The dimension of the array WORK.
-* If SIDE = 'L', LWORK >= max(1,N);
-* if SIDE = 'R', LWORK >= max(1,M).
-* For optimum performance LWORK >= N*NB if SIDE = 'L', and
-* LWORK >= M*NB if SIDE = 'R', where NB is the optimal
-* blocksize.
-*
-* If LWORK = -1, then a workspace query is assumed; the routine
-* only calculates the optimal size of the WORK array, returns
-* this value as the first entry of the WORK array, and no error
-* message related to LWORK is issued by XERBLA.
-*
-* INFO (output) INTEGER
-* = 0: successful exit
-* < 0: if INFO = -i, the i-th argument had an illegal value
-*
-* =====================================================================
-*
-* .. Parameters ..
- INTEGER NBMAX, LDT
- PARAMETER ( NBMAX = 64, LDT = NBMAX+1 )
-* ..
-* .. Local Scalars ..
- LOGICAL LEFT, LQUERY, NOTRAN
- INTEGER I, I1, I2, I3, IB, IINFO, IWS, LDWORK, LWKOPT,
- $ MI, NB, NBMIN, NI, NQ, NW
-* ..
-* .. Local Arrays ..
- DOUBLE PRECISION T( LDT, NBMAX )
-* ..
-* .. External Functions ..
- LOGICAL LSAME
- INTEGER ILAENV
- EXTERNAL LSAME, ILAENV
-* ..
-* .. External Subroutines ..
- EXTERNAL DLARFB, DLARFT, DORM2L, XERBLA
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC MAX, MIN
-* ..
-* .. Executable Statements ..
-*
-* Test the input arguments
-*
- INFO = 0
- LEFT = LSAME( SIDE, 'L' )
- NOTRAN = LSAME( TRANS, 'N' )
- LQUERY = ( LWORK.EQ.-1 )
-*
-* NQ is the order of Q and NW is the minimum dimension of WORK
-*
- IF( LEFT ) THEN
- NQ = M
- NW = MAX( 1, N )
- ELSE
- NQ = N
- NW = MAX( 1, M )
- END IF
- IF( .NOT.LEFT .AND. .NOT.LSAME( SIDE, 'R' ) ) THEN
- INFO = -1
- ELSE IF( .NOT.NOTRAN .AND. .NOT.LSAME( TRANS, 'T' ) ) THEN
- INFO = -2
- ELSE IF( M.LT.0 ) THEN
- INFO = -3
- ELSE IF( N.LT.0 ) THEN
- INFO = -4
- ELSE IF( K.LT.0 .OR. K.GT.NQ ) THEN
- INFO = -5
- ELSE IF( LDA.LT.MAX( 1, NQ ) ) THEN
- INFO = -7
- ELSE IF( LDC.LT.MAX( 1, M ) ) THEN
- INFO = -10
- END IF
-*
- IF( INFO.EQ.0 ) THEN
- IF( M.EQ.0 .OR. N.EQ.0 ) THEN
- LWKOPT = 1
- ELSE
-*
-* Determine the block size. NB may be at most NBMAX, where
-* NBMAX is used to define the local array T.
-*
- NB = MIN( NBMAX, ILAENV( 1, 'DORMQL', SIDE // TRANS, M, N,
- $ K, -1 ) )
- LWKOPT = NW*NB
- END IF
- WORK( 1 ) = LWKOPT
-*
- IF( LWORK.LT.NW .AND. .NOT.LQUERY ) THEN
- INFO = -12
- END IF
- END IF
-*
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'DORMQL', -INFO )
- RETURN
- ELSE IF( LQUERY ) THEN
- RETURN
- END IF
-*
-* Quick return if possible
-*
- IF( M.EQ.0 .OR. N.EQ.0 ) THEN
- RETURN
- END IF
-*
- NBMIN = 2
- LDWORK = NW
- IF( NB.GT.1 .AND. NB.LT.K ) THEN
- IWS = NW*NB
- IF( LWORK.LT.IWS ) THEN
- NB = LWORK / LDWORK
- NBMIN = MAX( 2, ILAENV( 2, 'DORMQL', SIDE // TRANS, M, N, K,
- $ -1 ) )
- END IF
- ELSE
- IWS = NW
- END IF
-*
- IF( NB.LT.NBMIN .OR. NB.GE.K ) THEN
-*
-* Use unblocked code
-*
- CALL DORM2L( SIDE, TRANS, M, N, K, A, LDA, TAU, C, LDC, WORK,
- $ IINFO )
- ELSE
-*
-* Use blocked code
-*
- IF( ( LEFT .AND. NOTRAN ) .OR.
- $ ( .NOT.LEFT .AND. .NOT.NOTRAN ) ) THEN
- I1 = 1
- I2 = K
- I3 = NB
- ELSE
- I1 = ( ( K-1 ) / NB )*NB + 1
- I2 = 1
- I3 = -NB
- END IF
-*
- IF( LEFT ) THEN
- NI = N
- ELSE
- MI = M
- END IF
-*
- DO 10 I = I1, I2, I3
- IB = MIN( NB, K-I+1 )
-*
-* Form the triangular factor of the block reflector
-* H = H(i+ib-1) . . . H(i+1) H(i)
-*
- CALL DLARFT( 'Backward', 'Columnwise', NQ-K+I+IB-1, IB,
- $ A( 1, I ), LDA, TAU( I ), T, LDT )
- IF( LEFT ) THEN
-*
-* H or H' is applied to C(1:m-k+i+ib-1,1:n)
-*
- MI = M - K + I + IB - 1
- ELSE
-*
-* H or H' is applied to C(1:m,1:n-k+i+ib-1)
-*
- NI = N - K + I + IB - 1
- END IF
-*
-* Apply H or H'
-*
- CALL DLARFB( SIDE, TRANS, 'Backward', 'Columnwise', MI, NI,
- $ IB, A( 1, I ), LDA, T, LDT, C, LDC, WORK,
- $ LDWORK )
- 10 CONTINUE
- END IF
- WORK( 1 ) = LWKOPT
- RETURN
-*
-* End of DORMQL
-*
- END
diff --git a/src/lib/lapack/dormqr.f b/src/lib/lapack/dormqr.f
deleted file mode 100644
index ee372695..00000000
--- a/src/lib/lapack/dormqr.f
+++ /dev/null
@@ -1,260 +0,0 @@
- SUBROUTINE DORMQR( SIDE, TRANS, M, N, K, A, LDA, TAU, C, LDC,
- $ WORK, LWORK, INFO )
-*
-* -- LAPACK routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- CHARACTER SIDE, TRANS
- INTEGER INFO, K, LDA, LDC, LWORK, M, N
-* ..
-* .. Array Arguments ..
- DOUBLE PRECISION A( LDA, * ), C( LDC, * ), TAU( * ), WORK( * )
-* ..
-*
-* Purpose
-* =======
-*
-* DORMQR overwrites the general real M-by-N matrix C with
-*
-* SIDE = 'L' SIDE = 'R'
-* TRANS = 'N': Q * C C * Q
-* TRANS = 'T': Q**T * C C * Q**T
-*
-* where Q is a real orthogonal matrix defined as the product of k
-* elementary reflectors
-*
-* Q = H(1) H(2) . . . H(k)
-*
-* as returned by DGEQRF. Q is of order M if SIDE = 'L' and of order N
-* if SIDE = 'R'.
-*
-* Arguments
-* =========
-*
-* SIDE (input) CHARACTER*1
-* = 'L': apply Q or Q**T from the Left;
-* = 'R': apply Q or Q**T from the Right.
-*
-* TRANS (input) CHARACTER*1
-* = 'N': No transpose, apply Q;
-* = 'T': Transpose, apply Q**T.
-*
-* M (input) INTEGER
-* The number of rows of the matrix C. M >= 0.
-*
-* N (input) INTEGER
-* The number of columns of the matrix C. N >= 0.
-*
-* K (input) INTEGER
-* The number of elementary reflectors whose product defines
-* the matrix Q.
-* If SIDE = 'L', M >= K >= 0;
-* if SIDE = 'R', N >= K >= 0.
-*
-* A (input) DOUBLE PRECISION array, dimension (LDA,K)
-* The i-th column must contain the vector which defines the
-* elementary reflector H(i), for i = 1,2,...,k, as returned by
-* DGEQRF in the first k columns of its array argument A.
-* A is modified by the routine but restored on exit.
-*
-* LDA (input) INTEGER
-* The leading dimension of the array A.
-* If SIDE = 'L', LDA >= max(1,M);
-* if SIDE = 'R', LDA >= max(1,N).
-*
-* TAU (input) DOUBLE PRECISION array, dimension (K)
-* TAU(i) must contain the scalar factor of the elementary
-* reflector H(i), as returned by DGEQRF.
-*
-* C (input/output) DOUBLE PRECISION array, dimension (LDC,N)
-* On entry, the M-by-N matrix C.
-* On exit, C is overwritten by Q*C or Q**T*C or C*Q**T or C*Q.
-*
-* LDC (input) INTEGER
-* The leading dimension of the array C. LDC >= max(1,M).
-*
-* WORK (workspace/output) DOUBLE PRECISION array, dimension (MAX(1,LWORK))
-* On exit, if INFO = 0, WORK(1) returns the optimal LWORK.
-*
-* LWORK (input) INTEGER
-* The dimension of the array WORK.
-* If SIDE = 'L', LWORK >= max(1,N);
-* if SIDE = 'R', LWORK >= max(1,M).
-* For optimum performance LWORK >= N*NB if SIDE = 'L', and
-* LWORK >= M*NB if SIDE = 'R', where NB is the optimal
-* blocksize.
-*
-* If LWORK = -1, then a workspace query is assumed; the routine
-* only calculates the optimal size of the WORK array, returns
-* this value as the first entry of the WORK array, and no error
-* message related to LWORK is issued by XERBLA.
-*
-* INFO (output) INTEGER
-* = 0: successful exit
-* < 0: if INFO = -i, the i-th argument had an illegal value
-*
-* =====================================================================
-*
-* .. Parameters ..
- INTEGER NBMAX, LDT
- PARAMETER ( NBMAX = 64, LDT = NBMAX+1 )
-* ..
-* .. Local Scalars ..
- LOGICAL LEFT, LQUERY, NOTRAN
- INTEGER I, I1, I2, I3, IB, IC, IINFO, IWS, JC, LDWORK,
- $ LWKOPT, MI, NB, NBMIN, NI, NQ, NW
-* ..
-* .. Local Arrays ..
- DOUBLE PRECISION T( LDT, NBMAX )
-* ..
-* .. External Functions ..
- LOGICAL LSAME
- INTEGER ILAENV
- EXTERNAL LSAME, ILAENV
-* ..
-* .. External Subroutines ..
- EXTERNAL DLARFB, DLARFT, DORM2R, XERBLA
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC MAX, MIN
-* ..
-* .. Executable Statements ..
-*
-* Test the input arguments
-*
- INFO = 0
- LEFT = LSAME( SIDE, 'L' )
- NOTRAN = LSAME( TRANS, 'N' )
- LQUERY = ( LWORK.EQ.-1 )
-*
-* NQ is the order of Q and NW is the minimum dimension of WORK
-*
- IF( LEFT ) THEN
- NQ = M
- NW = N
- ELSE
- NQ = N
- NW = M
- END IF
- IF( .NOT.LEFT .AND. .NOT.LSAME( SIDE, 'R' ) ) THEN
- INFO = -1
- ELSE IF( .NOT.NOTRAN .AND. .NOT.LSAME( TRANS, 'T' ) ) THEN
- INFO = -2
- ELSE IF( M.LT.0 ) THEN
- INFO = -3
- ELSE IF( N.LT.0 ) THEN
- INFO = -4
- ELSE IF( K.LT.0 .OR. K.GT.NQ ) THEN
- INFO = -5
- ELSE IF( LDA.LT.MAX( 1, NQ ) ) THEN
- INFO = -7
- ELSE IF( LDC.LT.MAX( 1, M ) ) THEN
- INFO = -10
- ELSE IF( LWORK.LT.MAX( 1, NW ) .AND. .NOT.LQUERY ) THEN
- INFO = -12
- END IF
-*
- IF( INFO.EQ.0 ) THEN
-*
-* Determine the block size. NB may be at most NBMAX, where NBMAX
-* is used to define the local array T.
-*
- NB = MIN( NBMAX, ILAENV( 1, 'DORMQR', SIDE // TRANS, M, N, K,
- $ -1 ) )
- LWKOPT = MAX( 1, NW )*NB
- WORK( 1 ) = LWKOPT
- END IF
-*
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'DORMQR', -INFO )
- RETURN
- ELSE IF( LQUERY ) THEN
- RETURN
- END IF
-*
-* Quick return if possible
-*
- IF( M.EQ.0 .OR. N.EQ.0 .OR. K.EQ.0 ) THEN
- WORK( 1 ) = 1
- RETURN
- END IF
-*
- NBMIN = 2
- LDWORK = NW
- IF( NB.GT.1 .AND. NB.LT.K ) THEN
- IWS = NW*NB
- IF( LWORK.LT.IWS ) THEN
- NB = LWORK / LDWORK
- NBMIN = MAX( 2, ILAENV( 2, 'DORMQR', SIDE // TRANS, M, N, K,
- $ -1 ) )
- END IF
- ELSE
- IWS = NW
- END IF
-*
- IF( NB.LT.NBMIN .OR. NB.GE.K ) THEN
-*
-* Use unblocked code
-*
- CALL DORM2R( SIDE, TRANS, M, N, K, A, LDA, TAU, C, LDC, WORK,
- $ IINFO )
- ELSE
-*
-* Use blocked code
-*
- IF( ( LEFT .AND. .NOT.NOTRAN ) .OR.
- $ ( .NOT.LEFT .AND. NOTRAN ) ) THEN
- I1 = 1
- I2 = K
- I3 = NB
- ELSE
- I1 = ( ( K-1 ) / NB )*NB + 1
- I2 = 1
- I3 = -NB
- END IF
-*
- IF( LEFT ) THEN
- NI = N
- JC = 1
- ELSE
- MI = M
- IC = 1
- END IF
-*
- DO 10 I = I1, I2, I3
- IB = MIN( NB, K-I+1 )
-*
-* Form the triangular factor of the block reflector
-* H = H(i) H(i+1) . . . H(i+ib-1)
-*
- CALL DLARFT( 'Forward', 'Columnwise', NQ-I+1, IB, A( I, I ),
- $ LDA, TAU( I ), T, LDT )
- IF( LEFT ) THEN
-*
-* H or H' is applied to C(i:m,1:n)
-*
- MI = M - I + 1
- IC = I
- ELSE
-*
-* H or H' is applied to C(1:m,i:n)
-*
- NI = N - I + 1
- JC = I
- END IF
-*
-* Apply H or H'
-*
- CALL DLARFB( SIDE, TRANS, 'Forward', 'Columnwise', MI, NI,
- $ IB, A( I, I ), LDA, T, LDT, C( IC, JC ), LDC,
- $ WORK, LDWORK )
- 10 CONTINUE
- END IF
- WORK( 1 ) = LWKOPT
- RETURN
-*
-* End of DORMQR
-*
- END
diff --git a/src/lib/lapack/dormr2.f b/src/lib/lapack/dormr2.f
deleted file mode 100644
index 994552fb..00000000
--- a/src/lib/lapack/dormr2.f
+++ /dev/null
@@ -1,193 +0,0 @@
- SUBROUTINE DORMR2( SIDE, TRANS, M, N, K, A, LDA, TAU, C, LDC,
- $ WORK, INFO )
-*
-* -- LAPACK routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- CHARACTER SIDE, TRANS
- INTEGER INFO, K, LDA, LDC, M, N
-* ..
-* .. Array Arguments ..
- DOUBLE PRECISION A( LDA, * ), C( LDC, * ), TAU( * ), WORK( * )
-* ..
-*
-* Purpose
-* =======
-*
-* DORMR2 overwrites the general real m by n matrix C with
-*
-* Q * C if SIDE = 'L' and TRANS = 'N', or
-*
-* Q'* C if SIDE = 'L' and TRANS = 'T', or
-*
-* C * Q if SIDE = 'R' and TRANS = 'N', or
-*
-* C * Q' if SIDE = 'R' and TRANS = 'T',
-*
-* where Q is a real orthogonal matrix defined as the product of k
-* elementary reflectors
-*
-* Q = H(1) H(2) . . . H(k)
-*
-* as returned by DGERQF. Q is of order m if SIDE = 'L' and of order n
-* if SIDE = 'R'.
-*
-* Arguments
-* =========
-*
-* SIDE (input) CHARACTER*1
-* = 'L': apply Q or Q' from the Left
-* = 'R': apply Q or Q' from the Right
-*
-* TRANS (input) CHARACTER*1
-* = 'N': apply Q (No transpose)
-* = 'T': apply Q' (Transpose)
-*
-* M (input) INTEGER
-* The number of rows of the matrix C. M >= 0.
-*
-* N (input) INTEGER
-* The number of columns of the matrix C. N >= 0.
-*
-* K (input) INTEGER
-* The number of elementary reflectors whose product defines
-* the matrix Q.
-* If SIDE = 'L', M >= K >= 0;
-* if SIDE = 'R', N >= K >= 0.
-*
-* A (input) DOUBLE PRECISION array, dimension
-* (LDA,M) if SIDE = 'L',
-* (LDA,N) if SIDE = 'R'
-* The i-th row must contain the vector which defines the
-* elementary reflector H(i), for i = 1,2,...,k, as returned by
-* DGERQF in the last k rows of its array argument A.
-* A is modified by the routine but restored on exit.
-*
-* LDA (input) INTEGER
-* The leading dimension of the array A. LDA >= max(1,K).
-*
-* TAU (input) DOUBLE PRECISION array, dimension (K)
-* TAU(i) must contain the scalar factor of the elementary
-* reflector H(i), as returned by DGERQF.
-*
-* C (input/output) DOUBLE PRECISION array, dimension (LDC,N)
-* On entry, the m by n matrix C.
-* On exit, C is overwritten by Q*C or Q'*C or C*Q' or C*Q.
-*
-* LDC (input) INTEGER
-* The leading dimension of the array C. LDC >= max(1,M).
-*
-* WORK (workspace) DOUBLE PRECISION array, dimension
-* (N) if SIDE = 'L',
-* (M) if SIDE = 'R'
-*
-* INFO (output) INTEGER
-* = 0: successful exit
-* < 0: if INFO = -i, the i-th argument had an illegal value
-*
-* =====================================================================
-*
-* .. Parameters ..
- DOUBLE PRECISION ONE
- PARAMETER ( ONE = 1.0D+0 )
-* ..
-* .. Local Scalars ..
- LOGICAL LEFT, NOTRAN
- INTEGER I, I1, I2, I3, MI, NI, NQ
- DOUBLE PRECISION AII
-* ..
-* .. External Functions ..
- LOGICAL LSAME
- EXTERNAL LSAME
-* ..
-* .. External Subroutines ..
- EXTERNAL DLARF, XERBLA
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC MAX
-* ..
-* .. Executable Statements ..
-*
-* Test the input arguments
-*
- INFO = 0
- LEFT = LSAME( SIDE, 'L' )
- NOTRAN = LSAME( TRANS, 'N' )
-*
-* NQ is the order of Q
-*
- IF( LEFT ) THEN
- NQ = M
- ELSE
- NQ = N
- END IF
- IF( .NOT.LEFT .AND. .NOT.LSAME( SIDE, 'R' ) ) THEN
- INFO = -1
- ELSE IF( .NOT.NOTRAN .AND. .NOT.LSAME( TRANS, 'T' ) ) THEN
- INFO = -2
- ELSE IF( M.LT.0 ) THEN
- INFO = -3
- ELSE IF( N.LT.0 ) THEN
- INFO = -4
- ELSE IF( K.LT.0 .OR. K.GT.NQ ) THEN
- INFO = -5
- ELSE IF( LDA.LT.MAX( 1, K ) ) THEN
- INFO = -7
- ELSE IF( LDC.LT.MAX( 1, M ) ) THEN
- INFO = -10
- END IF
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'DORMR2', -INFO )
- RETURN
- END IF
-*
-* Quick return if possible
-*
- IF( M.EQ.0 .OR. N.EQ.0 .OR. K.EQ.0 )
- $ RETURN
-*
- IF( ( LEFT .AND. .NOT.NOTRAN ) .OR. ( .NOT.LEFT .AND. NOTRAN ) )
- $ THEN
- I1 = 1
- I2 = K
- I3 = 1
- ELSE
- I1 = K
- I2 = 1
- I3 = -1
- END IF
-*
- IF( LEFT ) THEN
- NI = N
- ELSE
- MI = M
- END IF
-*
- DO 10 I = I1, I2, I3
- IF( LEFT ) THEN
-*
-* H(i) is applied to C(1:m-k+i,1:n)
-*
- MI = M - K + I
- ELSE
-*
-* H(i) is applied to C(1:m,1:n-k+i)
-*
- NI = N - K + I
- END IF
-*
-* Apply H(i)
-*
- AII = A( I, NQ-K+I )
- A( I, NQ-K+I ) = ONE
- CALL DLARF( SIDE, MI, NI, A( I, 1 ), LDA, TAU( I ), C, LDC,
- $ WORK )
- A( I, NQ-K+I ) = AII
- 10 CONTINUE
- RETURN
-*
-* End of DORMR2
-*
- END
diff --git a/src/lib/lapack/dormr3.f b/src/lib/lapack/dormr3.f
deleted file mode 100644
index 7bdcb856..00000000
--- a/src/lib/lapack/dormr3.f
+++ /dev/null
@@ -1,206 +0,0 @@
- SUBROUTINE DORMR3( SIDE, TRANS, M, N, K, L, A, LDA, TAU, C, LDC,
- $ WORK, INFO )
-*
-* -- LAPACK routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- CHARACTER SIDE, TRANS
- INTEGER INFO, K, L, LDA, LDC, M, N
-* ..
-* .. Array Arguments ..
- DOUBLE PRECISION A( LDA, * ), C( LDC, * ), TAU( * ), WORK( * )
-* ..
-*
-* Purpose
-* =======
-*
-* DORMR3 overwrites the general real m by n matrix C with
-*
-* Q * C if SIDE = 'L' and TRANS = 'N', or
-*
-* Q'* C if SIDE = 'L' and TRANS = 'T', or
-*
-* C * Q if SIDE = 'R' and TRANS = 'N', or
-*
-* C * Q' if SIDE = 'R' and TRANS = 'T',
-*
-* where Q is a real orthogonal matrix defined as the product of k
-* elementary reflectors
-*
-* Q = H(1) H(2) . . . H(k)
-*
-* as returned by DTZRZF. Q is of order m if SIDE = 'L' and of order n
-* if SIDE = 'R'.
-*
-* Arguments
-* =========
-*
-* SIDE (input) CHARACTER*1
-* = 'L': apply Q or Q' from the Left
-* = 'R': apply Q or Q' from the Right
-*
-* TRANS (input) CHARACTER*1
-* = 'N': apply Q (No transpose)
-* = 'T': apply Q' (Transpose)
-*
-* M (input) INTEGER
-* The number of rows of the matrix C. M >= 0.
-*
-* N (input) INTEGER
-* The number of columns of the matrix C. N >= 0.
-*
-* K (input) INTEGER
-* The number of elementary reflectors whose product defines
-* the matrix Q.
-* If SIDE = 'L', M >= K >= 0;
-* if SIDE = 'R', N >= K >= 0.
-*
-* L (input) INTEGER
-* The number of columns of the matrix A containing
-* the meaningful part of the Householder reflectors.
-* If SIDE = 'L', M >= L >= 0, if SIDE = 'R', N >= L >= 0.
-*
-* A (input) DOUBLE PRECISION array, dimension
-* (LDA,M) if SIDE = 'L',
-* (LDA,N) if SIDE = 'R'
-* The i-th row must contain the vector which defines the
-* elementary reflector H(i), for i = 1,2,...,k, as returned by
-* DTZRZF in the last k rows of its array argument A.
-* A is modified by the routine but restored on exit.
-*
-* LDA (input) INTEGER
-* The leading dimension of the array A. LDA >= max(1,K).
-*
-* TAU (input) DOUBLE PRECISION array, dimension (K)
-* TAU(i) must contain the scalar factor of the elementary
-* reflector H(i), as returned by DTZRZF.
-*
-* C (input/output) DOUBLE PRECISION array, dimension (LDC,N)
-* On entry, the m-by-n matrix C.
-* On exit, C is overwritten by Q*C or Q'*C or C*Q' or C*Q.
-*
-* LDC (input) INTEGER
-* The leading dimension of the array C. LDC >= max(1,M).
-*
-* WORK (workspace) DOUBLE PRECISION array, dimension
-* (N) if SIDE = 'L',
-* (M) if SIDE = 'R'
-*
-* INFO (output) INTEGER
-* = 0: successful exit
-* < 0: if INFO = -i, the i-th argument had an illegal value
-*
-* Further Details
-* ===============
-*
-* Based on contributions by
-* A. Petitet, Computer Science Dept., Univ. of Tenn., Knoxville, USA
-*
-* =====================================================================
-*
-* .. Local Scalars ..
- LOGICAL LEFT, NOTRAN
- INTEGER I, I1, I2, I3, IC, JA, JC, MI, NI, NQ
-* ..
-* .. External Functions ..
- LOGICAL LSAME
- EXTERNAL LSAME
-* ..
-* .. External Subroutines ..
- EXTERNAL DLARZ, XERBLA
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC MAX
-* ..
-* .. Executable Statements ..
-*
-* Test the input arguments
-*
- INFO = 0
- LEFT = LSAME( SIDE, 'L' )
- NOTRAN = LSAME( TRANS, 'N' )
-*
-* NQ is the order of Q
-*
- IF( LEFT ) THEN
- NQ = M
- ELSE
- NQ = N
- END IF
- IF( .NOT.LEFT .AND. .NOT.LSAME( SIDE, 'R' ) ) THEN
- INFO = -1
- ELSE IF( .NOT.NOTRAN .AND. .NOT.LSAME( TRANS, 'T' ) ) THEN
- INFO = -2
- ELSE IF( M.LT.0 ) THEN
- INFO = -3
- ELSE IF( N.LT.0 ) THEN
- INFO = -4
- ELSE IF( K.LT.0 .OR. K.GT.NQ ) THEN
- INFO = -5
- ELSE IF( L.LT.0 .OR. ( LEFT .AND. ( L.GT.M ) ) .OR.
- $ ( .NOT.LEFT .AND. ( L.GT.N ) ) ) THEN
- INFO = -6
- ELSE IF( LDA.LT.MAX( 1, K ) ) THEN
- INFO = -8
- ELSE IF( LDC.LT.MAX( 1, M ) ) THEN
- INFO = -11
- END IF
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'DORMR3', -INFO )
- RETURN
- END IF
-*
-* Quick return if possible
-*
- IF( M.EQ.0 .OR. N.EQ.0 .OR. K.EQ.0 )
- $ RETURN
-*
- IF( ( LEFT .AND. .NOT.NOTRAN .OR. .NOT.LEFT .AND. NOTRAN ) ) THEN
- I1 = 1
- I2 = K
- I3 = 1
- ELSE
- I1 = K
- I2 = 1
- I3 = -1
- END IF
-*
- IF( LEFT ) THEN
- NI = N
- JA = M - L + 1
- JC = 1
- ELSE
- MI = M
- JA = N - L + 1
- IC = 1
- END IF
-*
- DO 10 I = I1, I2, I3
- IF( LEFT ) THEN
-*
-* H(i) or H(i)' is applied to C(i:m,1:n)
-*
- MI = M - I + 1
- IC = I
- ELSE
-*
-* H(i) or H(i)' is applied to C(1:m,i:n)
-*
- NI = N - I + 1
- JC = I
- END IF
-*
-* Apply H(i) or H(i)'
-*
- CALL DLARZ( SIDE, MI, NI, L, A( I, JA ), LDA, TAU( I ),
- $ C( IC, JC ), LDC, WORK )
-*
- 10 CONTINUE
-*
- RETURN
-*
-* End of DORMR3
-*
- END
diff --git a/src/lib/lapack/dormrq.f b/src/lib/lapack/dormrq.f
deleted file mode 100644
index 522c1392..00000000
--- a/src/lib/lapack/dormrq.f
+++ /dev/null
@@ -1,268 +0,0 @@
- SUBROUTINE DORMRQ( SIDE, TRANS, M, N, K, A, LDA, TAU, C, LDC,
- $ WORK, LWORK, INFO )
-*
-* -- LAPACK routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- CHARACTER SIDE, TRANS
- INTEGER INFO, K, LDA, LDC, LWORK, M, N
-* ..
-* .. Array Arguments ..
- DOUBLE PRECISION A( LDA, * ), C( LDC, * ), TAU( * ), WORK( * )
-* ..
-*
-* Purpose
-* =======
-*
-* DORMRQ overwrites the general real M-by-N matrix C with
-*
-* SIDE = 'L' SIDE = 'R'
-* TRANS = 'N': Q * C C * Q
-* TRANS = 'T': Q**T * C C * Q**T
-*
-* where Q is a real orthogonal matrix defined as the product of k
-* elementary reflectors
-*
-* Q = H(1) H(2) . . . H(k)
-*
-* as returned by DGERQF. Q is of order M if SIDE = 'L' and of order N
-* if SIDE = 'R'.
-*
-* Arguments
-* =========
-*
-* SIDE (input) CHARACTER*1
-* = 'L': apply Q or Q**T from the Left;
-* = 'R': apply Q or Q**T from the Right.
-*
-* TRANS (input) CHARACTER*1
-* = 'N': No transpose, apply Q;
-* = 'T': Transpose, apply Q**T.
-*
-* M (input) INTEGER
-* The number of rows of the matrix C. M >= 0.
-*
-* N (input) INTEGER
-* The number of columns of the matrix C. N >= 0.
-*
-* K (input) INTEGER
-* The number of elementary reflectors whose product defines
-* the matrix Q.
-* If SIDE = 'L', M >= K >= 0;
-* if SIDE = 'R', N >= K >= 0.
-*
-* A (input) DOUBLE PRECISION array, dimension
-* (LDA,M) if SIDE = 'L',
-* (LDA,N) if SIDE = 'R'
-* The i-th row must contain the vector which defines the
-* elementary reflector H(i), for i = 1,2,...,k, as returned by
-* DGERQF in the last k rows of its array argument A.
-* A is modified by the routine but restored on exit.
-*
-* LDA (input) INTEGER
-* The leading dimension of the array A. LDA >= max(1,K).
-*
-* TAU (input) DOUBLE PRECISION array, dimension (K)
-* TAU(i) must contain the scalar factor of the elementary
-* reflector H(i), as returned by DGERQF.
-*
-* C (input/output) DOUBLE PRECISION array, dimension (LDC,N)
-* On entry, the M-by-N matrix C.
-* On exit, C is overwritten by Q*C or Q**T*C or C*Q**T or C*Q.
-*
-* LDC (input) INTEGER
-* The leading dimension of the array C. LDC >= max(1,M).
-*
-* WORK (workspace/output) DOUBLE PRECISION array, dimension (MAX(1,LWORK))
-* On exit, if INFO = 0, WORK(1) returns the optimal LWORK.
-*
-* LWORK (input) INTEGER
-* The dimension of the array WORK.
-* If SIDE = 'L', LWORK >= max(1,N);
-* if SIDE = 'R', LWORK >= max(1,M).
-* For optimum performance LWORK >= N*NB if SIDE = 'L', and
-* LWORK >= M*NB if SIDE = 'R', where NB is the optimal
-* blocksize.
-*
-* If LWORK = -1, then a workspace query is assumed; the routine
-* only calculates the optimal size of the WORK array, returns
-* this value as the first entry of the WORK array, and no error
-* message related to LWORK is issued by XERBLA.
-*
-* INFO (output) INTEGER
-* = 0: successful exit
-* < 0: if INFO = -i, the i-th argument had an illegal value
-*
-* =====================================================================
-*
-* .. Parameters ..
- INTEGER NBMAX, LDT
- PARAMETER ( NBMAX = 64, LDT = NBMAX+1 )
-* ..
-* .. Local Scalars ..
- LOGICAL LEFT, LQUERY, NOTRAN
- CHARACTER TRANST
- INTEGER I, I1, I2, I3, IB, IINFO, IWS, LDWORK, LWKOPT,
- $ MI, NB, NBMIN, NI, NQ, NW
-* ..
-* .. Local Arrays ..
- DOUBLE PRECISION T( LDT, NBMAX )
-* ..
-* .. External Functions ..
- LOGICAL LSAME
- INTEGER ILAENV
- EXTERNAL LSAME, ILAENV
-* ..
-* .. External Subroutines ..
- EXTERNAL DLARFB, DLARFT, DORMR2, XERBLA
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC MAX, MIN
-* ..
-* .. Executable Statements ..
-*
-* Test the input arguments
-*
- INFO = 0
- LEFT = LSAME( SIDE, 'L' )
- NOTRAN = LSAME( TRANS, 'N' )
- LQUERY = ( LWORK.EQ.-1 )
-*
-* NQ is the order of Q and NW is the minimum dimension of WORK
-*
- IF( LEFT ) THEN
- NQ = M
- NW = MAX( 1, N )
- ELSE
- NQ = N
- NW = MAX( 1, M )
- END IF
- IF( .NOT.LEFT .AND. .NOT.LSAME( SIDE, 'R' ) ) THEN
- INFO = -1
- ELSE IF( .NOT.NOTRAN .AND. .NOT.LSAME( TRANS, 'T' ) ) THEN
- INFO = -2
- ELSE IF( M.LT.0 ) THEN
- INFO = -3
- ELSE IF( N.LT.0 ) THEN
- INFO = -4
- ELSE IF( K.LT.0 .OR. K.GT.NQ ) THEN
- INFO = -5
- ELSE IF( LDA.LT.MAX( 1, K ) ) THEN
- INFO = -7
- ELSE IF( LDC.LT.MAX( 1, M ) ) THEN
- INFO = -10
- END IF
-*
- IF( INFO.EQ.0 ) THEN
- IF( M.EQ.0 .OR. N.EQ.0 ) THEN
- LWKOPT = 1
- ELSE
-*
-* Determine the block size. NB may be at most NBMAX, where
-* NBMAX is used to define the local array T.
-*
- NB = MIN( NBMAX, ILAENV( 1, 'DORMRQ', SIDE // TRANS, M, N,
- $ K, -1 ) )
- LWKOPT = NW*NB
- END IF
- WORK( 1 ) = LWKOPT
-*
- IF( LWORK.LT.NW .AND. .NOT.LQUERY ) THEN
- INFO = -12
- END IF
- END IF
-*
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'DORMRQ', -INFO )
- RETURN
- ELSE IF( LQUERY ) THEN
- RETURN
- END IF
-*
-* Quick return if possible
-*
- IF( M.EQ.0 .OR. N.EQ.0 ) THEN
- RETURN
- END IF
-*
- NBMIN = 2
- LDWORK = NW
- IF( NB.GT.1 .AND. NB.LT.K ) THEN
- IWS = NW*NB
- IF( LWORK.LT.IWS ) THEN
- NB = LWORK / LDWORK
- NBMIN = MAX( 2, ILAENV( 2, 'DORMRQ', SIDE // TRANS, M, N, K,
- $ -1 ) )
- END IF
- ELSE
- IWS = NW
- END IF
-*
- IF( NB.LT.NBMIN .OR. NB.GE.K ) THEN
-*
-* Use unblocked code
-*
- CALL DORMR2( SIDE, TRANS, M, N, K, A, LDA, TAU, C, LDC, WORK,
- $ IINFO )
- ELSE
-*
-* Use blocked code
-*
- IF( ( LEFT .AND. .NOT.NOTRAN ) .OR.
- $ ( .NOT.LEFT .AND. NOTRAN ) ) THEN
- I1 = 1
- I2 = K
- I3 = NB
- ELSE
- I1 = ( ( K-1 ) / NB )*NB + 1
- I2 = 1
- I3 = -NB
- END IF
-*
- IF( LEFT ) THEN
- NI = N
- ELSE
- MI = M
- END IF
-*
- IF( NOTRAN ) THEN
- TRANST = 'T'
- ELSE
- TRANST = 'N'
- END IF
-*
- DO 10 I = I1, I2, I3
- IB = MIN( NB, K-I+1 )
-*
-* Form the triangular factor of the block reflector
-* H = H(i+ib-1) . . . H(i+1) H(i)
-*
- CALL DLARFT( 'Backward', 'Rowwise', NQ-K+I+IB-1, IB,
- $ A( I, 1 ), LDA, TAU( I ), T, LDT )
- IF( LEFT ) THEN
-*
-* H or H' is applied to C(1:m-k+i+ib-1,1:n)
-*
- MI = M - K + I + IB - 1
- ELSE
-*
-* H or H' is applied to C(1:m,1:n-k+i+ib-1)
-*
- NI = N - K + I + IB - 1
- END IF
-*
-* Apply H or H'
-*
- CALL DLARFB( SIDE, TRANST, 'Backward', 'Rowwise', MI, NI,
- $ IB, A( I, 1 ), LDA, T, LDT, C, LDC, WORK,
- $ LDWORK )
- 10 CONTINUE
- END IF
- WORK( 1 ) = LWKOPT
- RETURN
-*
-* End of DORMRQ
-*
- END
diff --git a/src/lib/lapack/dormrz.f b/src/lib/lapack/dormrz.f
deleted file mode 100644
index 9e14acce..00000000
--- a/src/lib/lapack/dormrz.f
+++ /dev/null
@@ -1,292 +0,0 @@
- SUBROUTINE DORMRZ( SIDE, TRANS, M, N, K, L, A, LDA, TAU, C, LDC,
- $ WORK, LWORK, INFO )
-*
-* -- LAPACK routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- CHARACTER SIDE, TRANS
- INTEGER INFO, K, L, LDA, LDC, LWORK, M, N
-* ..
-* .. Array Arguments ..
- DOUBLE PRECISION A( LDA, * ), C( LDC, * ), TAU( * ), WORK( * )
-* ..
-*
-* Purpose
-* =======
-*
-* DORMRZ overwrites the general real M-by-N matrix C with
-*
-* SIDE = 'L' SIDE = 'R'
-* TRANS = 'N': Q * C C * Q
-* TRANS = 'T': Q**T * C C * Q**T
-*
-* where Q is a real orthogonal matrix defined as the product of k
-* elementary reflectors
-*
-* Q = H(1) H(2) . . . H(k)
-*
-* as returned by DTZRZF. Q is of order M if SIDE = 'L' and of order N
-* if SIDE = 'R'.
-*
-* Arguments
-* =========
-*
-* SIDE (input) CHARACTER*1
-* = 'L': apply Q or Q**T from the Left;
-* = 'R': apply Q or Q**T from the Right.
-*
-* TRANS (input) CHARACTER*1
-* = 'N': No transpose, apply Q;
-* = 'T': Transpose, apply Q**T.
-*
-* M (input) INTEGER
-* The number of rows of the matrix C. M >= 0.
-*
-* N (input) INTEGER
-* The number of columns of the matrix C. N >= 0.
-*
-* K (input) INTEGER
-* The number of elementary reflectors whose product defines
-* the matrix Q.
-* If SIDE = 'L', M >= K >= 0;
-* if SIDE = 'R', N >= K >= 0.
-*
-* L (input) INTEGER
-* The number of columns of the matrix A containing
-* the meaningful part of the Householder reflectors.
-* If SIDE = 'L', M >= L >= 0, if SIDE = 'R', N >= L >= 0.
-*
-* A (input) DOUBLE PRECISION array, dimension
-* (LDA,M) if SIDE = 'L',
-* (LDA,N) if SIDE = 'R'
-* The i-th row must contain the vector which defines the
-* elementary reflector H(i), for i = 1,2,...,k, as returned by
-* DTZRZF in the last k rows of its array argument A.
-* A is modified by the routine but restored on exit.
-*
-* LDA (input) INTEGER
-* The leading dimension of the array A. LDA >= max(1,K).
-*
-* TAU (input) DOUBLE PRECISION array, dimension (K)
-* TAU(i) must contain the scalar factor of the elementary
-* reflector H(i), as returned by DTZRZF.
-*
-* C (input/output) DOUBLE PRECISION array, dimension (LDC,N)
-* On entry, the M-by-N matrix C.
-* On exit, C is overwritten by Q*C or Q**H*C or C*Q**H or C*Q.
-*
-* LDC (input) INTEGER
-* The leading dimension of the array C. LDC >= max(1,M).
-*
-* WORK (workspace/output) DOUBLE PRECISION array, dimension (MAX(1,LWORK))
-* On exit, if INFO = 0, WORK(1) returns the optimal LWORK.
-*
-* LWORK (input) INTEGER
-* The dimension of the array WORK.
-* If SIDE = 'L', LWORK >= max(1,N);
-* if SIDE = 'R', LWORK >= max(1,M).
-* For optimum performance LWORK >= N*NB if SIDE = 'L', and
-* LWORK >= M*NB if SIDE = 'R', where NB is the optimal
-* blocksize.
-*
-* If LWORK = -1, then a workspace query is assumed; the routine
-* only calculates the optimal size of the WORK array, returns
-* this value as the first entry of the WORK array, and no error
-* message related to LWORK is issued by XERBLA.
-*
-* INFO (output) INTEGER
-* = 0: successful exit
-* < 0: if INFO = -i, the i-th argument had an illegal value
-*
-* Further Details
-* ===============
-*
-* Based on contributions by
-* A. Petitet, Computer Science Dept., Univ. of Tenn., Knoxville, USA
-*
-* =====================================================================
-*
-* .. Parameters ..
- INTEGER NBMAX, LDT
- PARAMETER ( NBMAX = 64, LDT = NBMAX+1 )
-* ..
-* .. Local Scalars ..
- LOGICAL LEFT, LQUERY, NOTRAN
- CHARACTER TRANST
- INTEGER I, I1, I2, I3, IB, IC, IINFO, IWS, JA, JC,
- $ LDWORK, LWKOPT, MI, NB, NBMIN, NI, NQ, NW
-* ..
-* .. Local Arrays ..
- DOUBLE PRECISION T( LDT, NBMAX )
-* ..
-* .. External Functions ..
- LOGICAL LSAME
- INTEGER ILAENV
- EXTERNAL LSAME, ILAENV
-* ..
-* .. External Subroutines ..
- EXTERNAL DLARZB, DLARZT, DORMR3, XERBLA
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC MAX, MIN
-* ..
-* .. Executable Statements ..
-*
-* Test the input arguments
-*
- INFO = 0
- LEFT = LSAME( SIDE, 'L' )
- NOTRAN = LSAME( TRANS, 'N' )
- LQUERY = ( LWORK.EQ.-1 )
-*
-* NQ is the order of Q and NW is the minimum dimension of WORK
-*
- IF( LEFT ) THEN
- NQ = M
- NW = MAX( 1, N )
- ELSE
- NQ = N
- NW = MAX( 1, M )
- END IF
- IF( .NOT.LEFT .AND. .NOT.LSAME( SIDE, 'R' ) ) THEN
- INFO = -1
- ELSE IF( .NOT.NOTRAN .AND. .NOT.LSAME( TRANS, 'T' ) ) THEN
- INFO = -2
- ELSE IF( M.LT.0 ) THEN
- INFO = -3
- ELSE IF( N.LT.0 ) THEN
- INFO = -4
- ELSE IF( K.LT.0 .OR. K.GT.NQ ) THEN
- INFO = -5
- ELSE IF( L.LT.0 .OR. ( LEFT .AND. ( L.GT.M ) ) .OR.
- $ ( .NOT.LEFT .AND. ( L.GT.N ) ) ) THEN
- INFO = -6
- ELSE IF( LDA.LT.MAX( 1, K ) ) THEN
- INFO = -8
- ELSE IF( LDC.LT.MAX( 1, M ) ) THEN
- INFO = -11
- END IF
-*
- IF( INFO.EQ.0 ) THEN
- IF( M.EQ.0 .OR. N.EQ.0 ) THEN
- LWKOPT = 1
-*
-* Determine the block size. NB may be at most NBMAX, where
-* NBMAX is used to define the local array T.
-*
- NB = MIN( NBMAX, ILAENV( 1, 'DORMRQ', SIDE // TRANS, M, N,
- $ K, -1 ) )
- LWKOPT = NW*NB
- END IF
- WORK( 1 ) = LWKOPT
-*
- IF( LWORK.LT.MAX( 1, NW ) .AND. .NOT.LQUERY ) THEN
- INFO = -13
- END IF
- END IF
-*
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'DORMRZ', -INFO )
- RETURN
- ELSE IF( LQUERY ) THEN
- RETURN
- END IF
-*
-* Quick return if possible
-*
- IF( M.EQ.0 .OR. N.EQ.0 ) THEN
- WORK( 1 ) = 1
- RETURN
- END IF
-*
- NBMIN = 2
- LDWORK = NW
- IF( NB.GT.1 .AND. NB.LT.K ) THEN
- IWS = NW*NB
- IF( LWORK.LT.IWS ) THEN
- NB = LWORK / LDWORK
- NBMIN = MAX( 2, ILAENV( 2, 'DORMRQ', SIDE // TRANS, M, N, K,
- $ -1 ) )
- END IF
- ELSE
- IWS = NW
- END IF
-*
- IF( NB.LT.NBMIN .OR. NB.GE.K ) THEN
-*
-* Use unblocked code
-*
- CALL DORMR3( SIDE, TRANS, M, N, K, L, A, LDA, TAU, C, LDC,
- $ WORK, IINFO )
- ELSE
-*
-* Use blocked code
-*
- IF( ( LEFT .AND. .NOT.NOTRAN ) .OR.
- $ ( .NOT.LEFT .AND. NOTRAN ) ) THEN
- I1 = 1
- I2 = K
- I3 = NB
- ELSE
- I1 = ( ( K-1 ) / NB )*NB + 1
- I2 = 1
- I3 = -NB
- END IF
-*
- IF( LEFT ) THEN
- NI = N
- JC = 1
- JA = M - L + 1
- ELSE
- MI = M
- IC = 1
- JA = N - L + 1
- END IF
-*
- IF( NOTRAN ) THEN
- TRANST = 'T'
- ELSE
- TRANST = 'N'
- END IF
-*
- DO 10 I = I1, I2, I3
- IB = MIN( NB, K-I+1 )
-*
-* Form the triangular factor of the block reflector
-* H = H(i+ib-1) . . . H(i+1) H(i)
-*
- CALL DLARZT( 'Backward', 'Rowwise', L, IB, A( I, JA ), LDA,
- $ TAU( I ), T, LDT )
-*
- IF( LEFT ) THEN
-*
-* H or H' is applied to C(i:m,1:n)
-*
- MI = M - I + 1
- IC = I
- ELSE
-*
-* H or H' is applied to C(1:m,i:n)
-*
- NI = N - I + 1
- JC = I
- END IF
-*
-* Apply H or H'
-*
- CALL DLARZB( SIDE, TRANST, 'Backward', 'Rowwise', MI, NI,
- $ IB, L, A( I, JA ), LDA, T, LDT, C( IC, JC ),
- $ LDC, WORK, LDWORK )
- 10 CONTINUE
-*
- END IF
-*
- WORK( 1 ) = LWKOPT
-*
- RETURN
-*
-* End of DORMRZ
-*
- END
diff --git a/src/lib/lapack/dpocon.f b/src/lib/lapack/dpocon.f
deleted file mode 100644
index c28af374..00000000
--- a/src/lib/lapack/dpocon.f
+++ /dev/null
@@ -1,177 +0,0 @@
- SUBROUTINE DPOCON( UPLO, N, A, LDA, ANORM, RCOND, WORK, IWORK,
- $ INFO )
-*
-* -- LAPACK routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* Modified to call DLACN2 in place of DLACON, 5 Feb 03, SJH.
-*
-* .. Scalar Arguments ..
- CHARACTER UPLO
- INTEGER INFO, LDA, N
- DOUBLE PRECISION ANORM, RCOND
-* ..
-* .. Array Arguments ..
- INTEGER IWORK( * )
- DOUBLE PRECISION A( LDA, * ), WORK( * )
-* ..
-*
-* Purpose
-* =======
-*
-* DPOCON estimates the reciprocal of the condition number (in the
-* 1-norm) of a real symmetric positive definite matrix using the
-* Cholesky factorization A = U**T*U or A = L*L**T computed by DPOTRF.
-*
-* An estimate is obtained for norm(inv(A)), and the reciprocal of the
-* condition number is computed as RCOND = 1 / (ANORM * norm(inv(A))).
-*
-* Arguments
-* =========
-*
-* UPLO (input) CHARACTER*1
-* = 'U': Upper triangle of A is stored;
-* = 'L': Lower triangle of A is stored.
-*
-* N (input) INTEGER
-* The order of the matrix A. N >= 0.
-*
-* A (input) DOUBLE PRECISION array, dimension (LDA,N)
-* The triangular factor U or L from the Cholesky factorization
-* A = U**T*U or A = L*L**T, as computed by DPOTRF.
-*
-* LDA (input) INTEGER
-* The leading dimension of the array A. LDA >= max(1,N).
-*
-* ANORM (input) DOUBLE PRECISION
-* The 1-norm (or infinity-norm) of the symmetric matrix A.
-*
-* RCOND (output) DOUBLE PRECISION
-* The reciprocal of the condition number of the matrix A,
-* computed as RCOND = 1/(ANORM * AINVNM), where AINVNM is an
-* estimate of the 1-norm of inv(A) computed in this routine.
-*
-* WORK (workspace) DOUBLE PRECISION array, dimension (3*N)
-*
-* IWORK (workspace) INTEGER array, dimension (N)
-*
-* INFO (output) INTEGER
-* = 0: successful exit
-* < 0: if INFO = -i, the i-th argument had an illegal value
-*
-* =====================================================================
-*
-* .. Parameters ..
- DOUBLE PRECISION ONE, ZERO
- PARAMETER ( ONE = 1.0D+0, ZERO = 0.0D+0 )
-* ..
-* .. Local Scalars ..
- LOGICAL UPPER
- CHARACTER NORMIN
- INTEGER IX, KASE
- DOUBLE PRECISION AINVNM, SCALE, SCALEL, SCALEU, SMLNUM
-* ..
-* .. Local Arrays ..
- INTEGER ISAVE( 3 )
-* ..
-* .. External Functions ..
- LOGICAL LSAME
- INTEGER IDAMAX
- DOUBLE PRECISION DLAMCH
- EXTERNAL LSAME, IDAMAX, DLAMCH
-* ..
-* .. External Subroutines ..
- EXTERNAL DLACN2, DLATRS, DRSCL, XERBLA
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC ABS, MAX
-* ..
-* .. Executable Statements ..
-*
-* Test the input parameters.
-*
- INFO = 0
- UPPER = LSAME( UPLO, 'U' )
- IF( .NOT.UPPER .AND. .NOT.LSAME( UPLO, 'L' ) ) THEN
- INFO = -1
- ELSE IF( N.LT.0 ) THEN
- INFO = -2
- ELSE IF( LDA.LT.MAX( 1, N ) ) THEN
- INFO = -4
- ELSE IF( ANORM.LT.ZERO ) THEN
- INFO = -5
- END IF
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'DPOCON', -INFO )
- RETURN
- END IF
-*
-* Quick return if possible
-*
- RCOND = ZERO
- IF( N.EQ.0 ) THEN
- RCOND = ONE
- RETURN
- ELSE IF( ANORM.EQ.ZERO ) THEN
- RETURN
- END IF
-*
- SMLNUM = DLAMCH( 'Safe minimum' )
-*
-* Estimate the 1-norm of inv(A).
-*
- KASE = 0
- NORMIN = 'N'
- 10 CONTINUE
- CALL DLACN2( N, WORK( N+1 ), WORK, IWORK, AINVNM, KASE, ISAVE )
- IF( KASE.NE.0 ) THEN
- IF( UPPER ) THEN
-*
-* Multiply by inv(U').
-*
- CALL DLATRS( 'Upper', 'Transpose', 'Non-unit', NORMIN, N, A,
- $ LDA, WORK, SCALEL, WORK( 2*N+1 ), INFO )
- NORMIN = 'Y'
-*
-* Multiply by inv(U).
-*
- CALL DLATRS( 'Upper', 'No transpose', 'Non-unit', NORMIN, N,
- $ A, LDA, WORK, SCALEU, WORK( 2*N+1 ), INFO )
- ELSE
-*
-* Multiply by inv(L).
-*
- CALL DLATRS( 'Lower', 'No transpose', 'Non-unit', NORMIN, N,
- $ A, LDA, WORK, SCALEL, WORK( 2*N+1 ), INFO )
- NORMIN = 'Y'
-*
-* Multiply by inv(L').
-*
- CALL DLATRS( 'Lower', 'Transpose', 'Non-unit', NORMIN, N, A,
- $ LDA, WORK, SCALEU, WORK( 2*N+1 ), INFO )
- END IF
-*
-* Multiply by 1/SCALE if doing so will not cause overflow.
-*
- SCALE = SCALEL*SCALEU
- IF( SCALE.NE.ONE ) THEN
- IX = IDAMAX( N, WORK, 1 )
- IF( SCALE.LT.ABS( WORK( IX ) )*SMLNUM .OR. SCALE.EQ.ZERO )
- $ GO TO 20
- CALL DRSCL( N, SCALE, WORK, 1 )
- END IF
- GO TO 10
- END IF
-*
-* Compute the estimate of the reciprocal condition number.
-*
- IF( AINVNM.NE.ZERO )
- $ RCOND = ( ONE / AINVNM ) / ANORM
-*
- 20 CONTINUE
- RETURN
-*
-* End of DPOCON
-*
- END
diff --git a/src/lib/lapack/dpotf2.f b/src/lib/lapack/dpotf2.f
deleted file mode 100644
index b7d65e91..00000000
--- a/src/lib/lapack/dpotf2.f
+++ /dev/null
@@ -1,167 +0,0 @@
- SUBROUTINE DPOTF2( UPLO, N, A, LDA, INFO )
-*
-* -- LAPACK routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- CHARACTER UPLO
- INTEGER INFO, LDA, N
-* ..
-* .. Array Arguments ..
- DOUBLE PRECISION A( LDA, * )
-* ..
-*
-* Purpose
-* =======
-*
-* DPOTF2 computes the Cholesky factorization of a real symmetric
-* positive definite matrix A.
-*
-* The factorization has the form
-* A = U' * U , if UPLO = 'U', or
-* A = L * L', if UPLO = 'L',
-* where U is an upper triangular matrix and L is lower triangular.
-*
-* This is the unblocked version of the algorithm, calling Level 2 BLAS.
-*
-* Arguments
-* =========
-*
-* UPLO (input) CHARACTER*1
-* Specifies whether the upper or lower triangular part of the
-* symmetric matrix A is stored.
-* = 'U': Upper triangular
-* = 'L': Lower triangular
-*
-* N (input) INTEGER
-* The order of the matrix A. N >= 0.
-*
-* A (input/output) DOUBLE PRECISION array, dimension (LDA,N)
-* On entry, the symmetric matrix A. If UPLO = 'U', the leading
-* n by n upper triangular part of A contains the upper
-* triangular part of the matrix A, and the strictly lower
-* triangular part of A is not referenced. If UPLO = 'L', the
-* leading n by n lower triangular part of A contains the lower
-* triangular part of the matrix A, and the strictly upper
-* triangular part of A is not referenced.
-*
-* On exit, if INFO = 0, the factor U or L from the Cholesky
-* factorization A = U'*U or A = L*L'.
-*
-* LDA (input) INTEGER
-* The leading dimension of the array A. LDA >= max(1,N).
-*
-* INFO (output) INTEGER
-* = 0: successful exit
-* < 0: if INFO = -k, the k-th argument had an illegal value
-* > 0: if INFO = k, the leading minor of order k is not
-* positive definite, and the factorization could not be
-* completed.
-*
-* =====================================================================
-*
-* .. Parameters ..
- DOUBLE PRECISION ONE, ZERO
- PARAMETER ( ONE = 1.0D+0, ZERO = 0.0D+0 )
-* ..
-* .. Local Scalars ..
- LOGICAL UPPER
- INTEGER J
- DOUBLE PRECISION AJJ
-* ..
-* .. External Functions ..
- LOGICAL LSAME
- DOUBLE PRECISION DDOT
- EXTERNAL LSAME, DDOT
-* ..
-* .. External Subroutines ..
- EXTERNAL DGEMV, DSCAL, XERBLA
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC MAX, SQRT
-* ..
-* .. Executable Statements ..
-*
-* Test the input parameters.
-*
- INFO = 0
- UPPER = LSAME( UPLO, 'U' )
- IF( .NOT.UPPER .AND. .NOT.LSAME( UPLO, 'L' ) ) THEN
- INFO = -1
- ELSE IF( N.LT.0 ) THEN
- INFO = -2
- ELSE IF( LDA.LT.MAX( 1, N ) ) THEN
- INFO = -4
- END IF
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'DPOTF2', -INFO )
- RETURN
- END IF
-*
-* Quick return if possible
-*
- IF( N.EQ.0 )
- $ RETURN
-*
- IF( UPPER ) THEN
-*
-* Compute the Cholesky factorization A = U'*U.
-*
- DO 10 J = 1, N
-*
-* Compute U(J,J) and test for non-positive-definiteness.
-*
- AJJ = A( J, J ) - DDOT( J-1, A( 1, J ), 1, A( 1, J ), 1 )
- IF( AJJ.LE.ZERO ) THEN
- A( J, J ) = AJJ
- GO TO 30
- END IF
- AJJ = SQRT( AJJ )
- A( J, J ) = AJJ
-*
-* Compute elements J+1:N of row J.
-*
- IF( J.LT.N ) THEN
- CALL DGEMV( 'Transpose', J-1, N-J, -ONE, A( 1, J+1 ),
- $ LDA, A( 1, J ), 1, ONE, A( J, J+1 ), LDA )
- CALL DSCAL( N-J, ONE / AJJ, A( J, J+1 ), LDA )
- END IF
- 10 CONTINUE
- ELSE
-*
-* Compute the Cholesky factorization A = L*L'.
-*
- DO 20 J = 1, N
-*
-* Compute L(J,J) and test for non-positive-definiteness.
-*
- AJJ = A( J, J ) - DDOT( J-1, A( J, 1 ), LDA, A( J, 1 ),
- $ LDA )
- IF( AJJ.LE.ZERO ) THEN
- A( J, J ) = AJJ
- GO TO 30
- END IF
- AJJ = SQRT( AJJ )
- A( J, J ) = AJJ
-*
-* Compute elements J+1:N of column J.
-*
- IF( J.LT.N ) THEN
- CALL DGEMV( 'No transpose', N-J, J-1, -ONE, A( J+1, 1 ),
- $ LDA, A( J, 1 ), LDA, ONE, A( J+1, J ), 1 )
- CALL DSCAL( N-J, ONE / AJJ, A( J+1, J ), 1 )
- END IF
- 20 CONTINUE
- END IF
- GO TO 40
-*
- 30 CONTINUE
- INFO = J
-*
- 40 CONTINUE
- RETURN
-*
-* End of DPOTF2
-*
- END
diff --git a/src/lib/lapack/dpotrf.f b/src/lib/lapack/dpotrf.f
deleted file mode 100644
index 8449df6d..00000000
--- a/src/lib/lapack/dpotrf.f
+++ /dev/null
@@ -1,183 +0,0 @@
- SUBROUTINE DPOTRF( UPLO, N, A, LDA, INFO )
-*
-* -- LAPACK routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- CHARACTER UPLO
- INTEGER INFO, LDA, N
-* ..
-* .. Array Arguments ..
- DOUBLE PRECISION A( LDA, * )
-* ..
-*
-* Purpose
-* =======
-*
-* DPOTRF computes the Cholesky factorization of a real symmetric
-* positive definite matrix A.
-*
-* The factorization has the form
-* A = U**T * U, if UPLO = 'U', or
-* A = L * L**T, if UPLO = 'L',
-* where U is an upper triangular matrix and L is lower triangular.
-*
-* This is the block version of the algorithm, calling Level 3 BLAS.
-*
-* Arguments
-* =========
-*
-* UPLO (input) CHARACTER*1
-* = 'U': Upper triangle of A is stored;
-* = 'L': Lower triangle of A is stored.
-*
-* N (input) INTEGER
-* The order of the matrix A. N >= 0.
-*
-* A (input/output) DOUBLE PRECISION array, dimension (LDA,N)
-* On entry, the symmetric matrix A. If UPLO = 'U', the leading
-* N-by-N upper triangular part of A contains the upper
-* triangular part of the matrix A, and the strictly lower
-* triangular part of A is not referenced. If UPLO = 'L', the
-* leading N-by-N lower triangular part of A contains the lower
-* triangular part of the matrix A, and the strictly upper
-* triangular part of A is not referenced.
-*
-* On exit, if INFO = 0, the factor U or L from the Cholesky
-* factorization A = U**T*U or A = L*L**T.
-*
-* LDA (input) INTEGER
-* The leading dimension of the array A. LDA >= max(1,N).
-*
-* INFO (output) INTEGER
-* = 0: successful exit
-* < 0: if INFO = -i, the i-th argument had an illegal value
-* > 0: if INFO = i, the leading minor of order i is not
-* positive definite, and the factorization could not be
-* completed.
-*
-* =====================================================================
-*
-* .. Parameters ..
- DOUBLE PRECISION ONE
- PARAMETER ( ONE = 1.0D+0 )
-* ..
-* .. Local Scalars ..
- LOGICAL UPPER
- INTEGER J, JB, NB
-* ..
-* .. External Functions ..
- LOGICAL LSAME
- INTEGER ILAENV
- EXTERNAL LSAME, ILAENV
-* ..
-* .. External Subroutines ..
- EXTERNAL DGEMM, DPOTF2, DSYRK, DTRSM, XERBLA
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC MAX, MIN
-* ..
-* .. Executable Statements ..
-*
-* Test the input parameters.
-*
- INFO = 0
- UPPER = LSAME( UPLO, 'U' )
- IF( .NOT.UPPER .AND. .NOT.LSAME( UPLO, 'L' ) ) THEN
- INFO = -1
- ELSE IF( N.LT.0 ) THEN
- INFO = -2
- ELSE IF( LDA.LT.MAX( 1, N ) ) THEN
- INFO = -4
- END IF
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'DPOTRF', -INFO )
- RETURN
- END IF
-*
-* Quick return if possible
-*
- IF( N.EQ.0 )
- $ RETURN
-*
-* Determine the block size for this environment.
-*
- NB = ILAENV( 1, 'DPOTRF', UPLO, N, -1, -1, -1 )
- IF( NB.LE.1 .OR. NB.GE.N ) THEN
-*
-* Use unblocked code.
-*
- CALL DPOTF2( UPLO, N, A, LDA, INFO )
- ELSE
-*
-* Use blocked code.
-*
- IF( UPPER ) THEN
-*
-* Compute the Cholesky factorization A = U'*U.
-*
- DO 10 J = 1, N, NB
-*
-* Update and factorize the current diagonal block and test
-* for non-positive-definiteness.
-*
- JB = MIN( NB, N-J+1 )
- CALL DSYRK( 'Upper', 'Transpose', JB, J-1, -ONE,
- $ A( 1, J ), LDA, ONE, A( J, J ), LDA )
- CALL DPOTF2( 'Upper', JB, A( J, J ), LDA, INFO )
- IF( INFO.NE.0 )
- $ GO TO 30
- IF( J+JB.LE.N ) THEN
-*
-* Compute the current block row.
-*
- CALL DGEMM( 'Transpose', 'No transpose', JB, N-J-JB+1,
- $ J-1, -ONE, A( 1, J ), LDA, A( 1, J+JB ),
- $ LDA, ONE, A( J, J+JB ), LDA )
- CALL DTRSM( 'Left', 'Upper', 'Transpose', 'Non-unit',
- $ JB, N-J-JB+1, ONE, A( J, J ), LDA,
- $ A( J, J+JB ), LDA )
- END IF
- 10 CONTINUE
-*
- ELSE
-*
-* Compute the Cholesky factorization A = L*L'.
-*
- DO 20 J = 1, N, NB
-*
-* Update and factorize the current diagonal block and test
-* for non-positive-definiteness.
-*
- JB = MIN( NB, N-J+1 )
- CALL DSYRK( 'Lower', 'No transpose', JB, J-1, -ONE,
- $ A( J, 1 ), LDA, ONE, A( J, J ), LDA )
- CALL DPOTF2( 'Lower', JB, A( J, J ), LDA, INFO )
- IF( INFO.NE.0 )
- $ GO TO 30
- IF( J+JB.LE.N ) THEN
-*
-* Compute the current block column.
-*
- CALL DGEMM( 'No transpose', 'Transpose', N-J-JB+1, JB,
- $ J-1, -ONE, A( J+JB, 1 ), LDA, A( J, 1 ),
- $ LDA, ONE, A( J+JB, J ), LDA )
- CALL DTRSM( 'Right', 'Lower', 'Transpose', 'Non-unit',
- $ N-J-JB+1, JB, ONE, A( J, J ), LDA,
- $ A( J+JB, J ), LDA )
- END IF
- 20 CONTINUE
- END IF
- END IF
- GO TO 40
-*
- 30 CONTINUE
- INFO = INFO + J - 1
-*
- 40 CONTINUE
- RETURN
-*
-* End of DPOTRF
-*
- END
diff --git a/src/lib/lapack/dpotrs.f b/src/lib/lapack/dpotrs.f
deleted file mode 100644
index 0273655e..00000000
--- a/src/lib/lapack/dpotrs.f
+++ /dev/null
@@ -1,132 +0,0 @@
- SUBROUTINE DPOTRS( UPLO, N, NRHS, A, LDA, B, LDB, INFO )
-*
-* -- LAPACK routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- CHARACTER UPLO
- INTEGER INFO, LDA, LDB, N, NRHS
-* ..
-* .. Array Arguments ..
- DOUBLE PRECISION A( LDA, * ), B( LDB, * )
-* ..
-*
-* Purpose
-* =======
-*
-* DPOTRS solves a system of linear equations A*X = B with a symmetric
-* positive definite matrix A using the Cholesky factorization
-* A = U**T*U or A = L*L**T computed by DPOTRF.
-*
-* Arguments
-* =========
-*
-* UPLO (input) CHARACTER*1
-* = 'U': Upper triangle of A is stored;
-* = 'L': Lower triangle of A is stored.
-*
-* N (input) INTEGER
-* The order of the matrix A. N >= 0.
-*
-* NRHS (input) INTEGER
-* The number of right hand sides, i.e., the number of columns
-* of the matrix B. NRHS >= 0.
-*
-* A (input) DOUBLE PRECISION array, dimension (LDA,N)
-* The triangular factor U or L from the Cholesky factorization
-* A = U**T*U or A = L*L**T, as computed by DPOTRF.
-*
-* LDA (input) INTEGER
-* The leading dimension of the array A. LDA >= max(1,N).
-*
-* B (input/output) DOUBLE PRECISION array, dimension (LDB,NRHS)
-* On entry, the right hand side matrix B.
-* On exit, the solution matrix X.
-*
-* LDB (input) INTEGER
-* The leading dimension of the array B. LDB >= max(1,N).
-*
-* INFO (output) INTEGER
-* = 0: successful exit
-* < 0: if INFO = -i, the i-th argument had an illegal value
-*
-* =====================================================================
-*
-* .. Parameters ..
- DOUBLE PRECISION ONE
- PARAMETER ( ONE = 1.0D+0 )
-* ..
-* .. Local Scalars ..
- LOGICAL UPPER
-* ..
-* .. External Functions ..
- LOGICAL LSAME
- EXTERNAL LSAME
-* ..
-* .. External Subroutines ..
- EXTERNAL DTRSM, XERBLA
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC MAX
-* ..
-* .. Executable Statements ..
-*
-* Test the input parameters.
-*
- INFO = 0
- UPPER = LSAME( UPLO, 'U' )
- IF( .NOT.UPPER .AND. .NOT.LSAME( UPLO, 'L' ) ) THEN
- INFO = -1
- ELSE IF( N.LT.0 ) THEN
- INFO = -2
- ELSE IF( NRHS.LT.0 ) THEN
- INFO = -3
- ELSE IF( LDA.LT.MAX( 1, N ) ) THEN
- INFO = -5
- ELSE IF( LDB.LT.MAX( 1, N ) ) THEN
- INFO = -7
- END IF
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'DPOTRS', -INFO )
- RETURN
- END IF
-*
-* Quick return if possible
-*
- IF( N.EQ.0 .OR. NRHS.EQ.0 )
- $ RETURN
-*
- IF( UPPER ) THEN
-*
-* Solve A*X = B where A = U'*U.
-*
-* Solve U'*X = B, overwriting B with X.
-*
- CALL DTRSM( 'Left', 'Upper', 'Transpose', 'Non-unit', N, NRHS,
- $ ONE, A, LDA, B, LDB )
-*
-* Solve U*X = B, overwriting B with X.
-*
- CALL DTRSM( 'Left', 'Upper', 'No transpose', 'Non-unit', N,
- $ NRHS, ONE, A, LDA, B, LDB )
- ELSE
-*
-* Solve A*X = B where A = L*L'.
-*
-* Solve L*X = B, overwriting B with X.
-*
- CALL DTRSM( 'Left', 'Lower', 'No transpose', 'Non-unit', N,
- $ NRHS, ONE, A, LDA, B, LDB )
-*
-* Solve L'*X = B, overwriting B with X.
-*
- CALL DTRSM( 'Left', 'Lower', 'Transpose', 'Non-unit', N, NRHS,
- $ ONE, A, LDA, B, LDB )
- END IF
-*
- RETURN
-*
-* End of DPOTRS
-*
- END
diff --git a/src/lib/lapack/dpptrf.f b/src/lib/lapack/dpptrf.f
deleted file mode 100644
index a5e2a596..00000000
--- a/src/lib/lapack/dpptrf.f
+++ /dev/null
@@ -1,177 +0,0 @@
- SUBROUTINE DPPTRF( UPLO, N, AP, INFO )
-*
-* -- LAPACK routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- CHARACTER UPLO
- INTEGER INFO, N
-* ..
-* .. Array Arguments ..
- DOUBLE PRECISION AP( * )
-* ..
-*
-* Purpose
-* =======
-*
-* DPPTRF computes the Cholesky factorization of a real symmetric
-* positive definite matrix A stored in packed format.
-*
-* The factorization has the form
-* A = U**T * U, if UPLO = 'U', or
-* A = L * L**T, if UPLO = 'L',
-* where U is an upper triangular matrix and L is lower triangular.
-*
-* Arguments
-* =========
-*
-* UPLO (input) CHARACTER*1
-* = 'U': Upper triangle of A is stored;
-* = 'L': Lower triangle of A is stored.
-*
-* N (input) INTEGER
-* The order of the matrix A. N >= 0.
-*
-* AP (input/output) DOUBLE PRECISION array, dimension (N*(N+1)/2)
-* On entry, the upper or lower triangle of the symmetric matrix
-* A, packed columnwise in a linear array. The j-th column of A
-* is stored in the array AP as follows:
-* if UPLO = 'U', AP(i + (j-1)*j/2) = A(i,j) for 1<=i<=j;
-* if UPLO = 'L', AP(i + (j-1)*(2n-j)/2) = A(i,j) for j<=i<=n.
-* See below for further details.
-*
-* On exit, if INFO = 0, the triangular factor U or L from the
-* Cholesky factorization A = U**T*U or A = L*L**T, in the same
-* storage format as A.
-*
-* INFO (output) INTEGER
-* = 0: successful exit
-* < 0: if INFO = -i, the i-th argument had an illegal value
-* > 0: if INFO = i, the leading minor of order i is not
-* positive definite, and the factorization could not be
-* completed.
-*
-* Further Details
-* ======= =======
-*
-* The packed storage scheme is illustrated by the following example
-* when N = 4, UPLO = 'U':
-*
-* Two-dimensional storage of the symmetric matrix A:
-*
-* a11 a12 a13 a14
-* a22 a23 a24
-* a33 a34 (aij = aji)
-* a44
-*
-* Packed storage of the upper triangle of A:
-*
-* AP = [ a11, a12, a22, a13, a23, a33, a14, a24, a34, a44 ]
-*
-* =====================================================================
-*
-* .. Parameters ..
- DOUBLE PRECISION ONE, ZERO
- PARAMETER ( ONE = 1.0D+0, ZERO = 0.0D+0 )
-* ..
-* .. Local Scalars ..
- LOGICAL UPPER
- INTEGER J, JC, JJ
- DOUBLE PRECISION AJJ
-* ..
-* .. External Functions ..
- LOGICAL LSAME
- DOUBLE PRECISION DDOT
- EXTERNAL LSAME, DDOT
-* ..
-* .. External Subroutines ..
- EXTERNAL DSCAL, DSPR, DTPSV, XERBLA
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC SQRT
-* ..
-* .. Executable Statements ..
-*
-* Test the input parameters.
-*
- INFO = 0
- UPPER = LSAME( UPLO, 'U' )
- IF( .NOT.UPPER .AND. .NOT.LSAME( UPLO, 'L' ) ) THEN
- INFO = -1
- ELSE IF( N.LT.0 ) THEN
- INFO = -2
- END IF
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'DPPTRF', -INFO )
- RETURN
- END IF
-*
-* Quick return if possible
-*
- IF( N.EQ.0 )
- $ RETURN
-*
- IF( UPPER ) THEN
-*
-* Compute the Cholesky factorization A = U'*U.
-*
- JJ = 0
- DO 10 J = 1, N
- JC = JJ + 1
- JJ = JJ + J
-*
-* Compute elements 1:J-1 of column J.
-*
- IF( J.GT.1 )
- $ CALL DTPSV( 'Upper', 'Transpose', 'Non-unit', J-1, AP,
- $ AP( JC ), 1 )
-*
-* Compute U(J,J) and test for non-positive-definiteness.
-*
- AJJ = AP( JJ ) - DDOT( J-1, AP( JC ), 1, AP( JC ), 1 )
- IF( AJJ.LE.ZERO ) THEN
- AP( JJ ) = AJJ
- GO TO 30
- END IF
- AP( JJ ) = SQRT( AJJ )
- 10 CONTINUE
- ELSE
-*
-* Compute the Cholesky factorization A = L*L'.
-*
- JJ = 1
- DO 20 J = 1, N
-*
-* Compute L(J,J) and test for non-positive-definiteness.
-*
- AJJ = AP( JJ )
- IF( AJJ.LE.ZERO ) THEN
- AP( JJ ) = AJJ
- GO TO 30
- END IF
- AJJ = SQRT( AJJ )
- AP( JJ ) = AJJ
-*
-* Compute elements J+1:N of column J and update the trailing
-* submatrix.
-*
- IF( J.LT.N ) THEN
- CALL DSCAL( N-J, ONE / AJJ, AP( JJ+1 ), 1 )
- CALL DSPR( 'Lower', N-J, -ONE, AP( JJ+1 ), 1,
- $ AP( JJ+N-J+1 ) )
- JJ = JJ + N - J + 1
- END IF
- 20 CONTINUE
- END IF
- GO TO 40
-*
- 30 CONTINUE
- INFO = J
-*
- 40 CONTINUE
- RETURN
-*
-* End of DPPTRF
-*
- END
diff --git a/src/lib/lapack/drscl.f b/src/lib/lapack/drscl.f
deleted file mode 100644
index a13e96d8..00000000
--- a/src/lib/lapack/drscl.f
+++ /dev/null
@@ -1,114 +0,0 @@
- SUBROUTINE DRSCL( N, SA, SX, INCX )
-*
-* -- LAPACK auxiliary routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- INTEGER INCX, N
- DOUBLE PRECISION SA
-* ..
-* .. Array Arguments ..
- DOUBLE PRECISION SX( * )
-* ..
-*
-* Purpose
-* =======
-*
-* DRSCL multiplies an n-element real vector x by the real scalar 1/a.
-* This is done without overflow or underflow as long as
-* the final result x/a does not overflow or underflow.
-*
-* Arguments
-* =========
-*
-* N (input) INTEGER
-* The number of components of the vector x.
-*
-* SA (input) DOUBLE PRECISION
-* The scalar a which is used to divide each component of x.
-* SA must be >= 0, or the subroutine will divide by zero.
-*
-* SX (input/output) DOUBLE PRECISION array, dimension
-* (1+(N-1)*abs(INCX))
-* The n-element vector x.
-*
-* INCX (input) INTEGER
-* The increment between successive values of the vector SX.
-* > 0: SX(1) = X(1) and SX(1+(i-1)*INCX) = x(i), 1< i<= n
-*
-* =====================================================================
-*
-* .. Parameters ..
- DOUBLE PRECISION ONE, ZERO
- PARAMETER ( ONE = 1.0D+0, ZERO = 0.0D+0 )
-* ..
-* .. Local Scalars ..
- LOGICAL DONE
- DOUBLE PRECISION BIGNUM, CDEN, CDEN1, CNUM, CNUM1, MUL, SMLNUM
-* ..
-* .. External Functions ..
- DOUBLE PRECISION DLAMCH
- EXTERNAL DLAMCH
-* ..
-* .. External Subroutines ..
- EXTERNAL DSCAL
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC ABS
-* ..
-* .. Executable Statements ..
-*
-* Quick return if possible
-*
- IF( N.LE.0 )
- $ RETURN
-*
-* Get machine parameters
-*
- SMLNUM = DLAMCH( 'S' )
- BIGNUM = ONE / SMLNUM
- CALL DLABAD( SMLNUM, BIGNUM )
-*
-* Initialize the denominator to SA and the numerator to 1.
-*
- CDEN = SA
- CNUM = ONE
-*
- 10 CONTINUE
- CDEN1 = CDEN*SMLNUM
- CNUM1 = CNUM / BIGNUM
- IF( ABS( CDEN1 ).GT.ABS( CNUM ) .AND. CNUM.NE.ZERO ) THEN
-*
-* Pre-multiply X by SMLNUM if CDEN is large compared to CNUM.
-*
- MUL = SMLNUM
- DONE = .FALSE.
- CDEN = CDEN1
- ELSE IF( ABS( CNUM1 ).GT.ABS( CDEN ) ) THEN
-*
-* Pre-multiply X by BIGNUM if CDEN is small compared to CNUM.
-*
- MUL = BIGNUM
- DONE = .FALSE.
- CNUM = CNUM1
- ELSE
-*
-* Multiply X by CNUM / CDEN and return.
-*
- MUL = CNUM / CDEN
- DONE = .TRUE.
- END IF
-*
-* Scale the vector X by MUL
-*
- CALL DSCAL( N, MUL, SX, INCX )
-*
- IF( .NOT.DONE )
- $ GO TO 10
-*
- RETURN
-*
-* End of DRSCL
-*
- END
diff --git a/src/lib/lapack/dspev.f b/src/lib/lapack/dspev.f
deleted file mode 100644
index 64582c99..00000000
--- a/src/lib/lapack/dspev.f
+++ /dev/null
@@ -1,187 +0,0 @@
- SUBROUTINE DSPEV( JOBZ, UPLO, N, AP, W, Z, LDZ, WORK, INFO )
-*
-* -- LAPACK driver routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- CHARACTER JOBZ, UPLO
- INTEGER INFO, LDZ, N
-* ..
-* .. Array Arguments ..
- DOUBLE PRECISION AP( * ), W( * ), WORK( * ), Z( LDZ, * )
-* ..
-*
-* Purpose
-* =======
-*
-* DSPEV computes all the eigenvalues and, optionally, eigenvectors of a
-* real symmetric matrix A in packed storage.
-*
-* Arguments
-* =========
-*
-* JOBZ (input) CHARACTER*1
-* = 'N': Compute eigenvalues only;
-* = 'V': Compute eigenvalues and eigenvectors.
-*
-* UPLO (input) CHARACTER*1
-* = 'U': Upper triangle of A is stored;
-* = 'L': Lower triangle of A is stored.
-*
-* N (input) INTEGER
-* The order of the matrix A. N >= 0.
-*
-* AP (input/output) DOUBLE PRECISION array, dimension (N*(N+1)/2)
-* On entry, the upper or lower triangle of the symmetric matrix
-* A, packed columnwise in a linear array. The j-th column of A
-* is stored in the array AP as follows:
-* if UPLO = 'U', AP(i + (j-1)*j/2) = A(i,j) for 1<=i<=j;
-* if UPLO = 'L', AP(i + (j-1)*(2*n-j)/2) = A(i,j) for j<=i<=n.
-*
-* On exit, AP is overwritten by values generated during the
-* reduction to tridiagonal form. If UPLO = 'U', the diagonal
-* and first superdiagonal of the tridiagonal matrix T overwrite
-* the corresponding elements of A, and if UPLO = 'L', the
-* diagonal and first subdiagonal of T overwrite the
-* corresponding elements of A.
-*
-* W (output) DOUBLE PRECISION array, dimension (N)
-* If INFO = 0, the eigenvalues in ascending order.
-*
-* Z (output) DOUBLE PRECISION array, dimension (LDZ, N)
-* If JOBZ = 'V', then if INFO = 0, Z contains the orthonormal
-* eigenvectors of the matrix A, with the i-th column of Z
-* holding the eigenvector associated with W(i).
-* If JOBZ = 'N', then Z is not referenced.
-*
-* LDZ (input) INTEGER
-* The leading dimension of the array Z. LDZ >= 1, and if
-* JOBZ = 'V', LDZ >= max(1,N).
-*
-* WORK (workspace) DOUBLE PRECISION array, dimension (3*N)
-*
-* INFO (output) INTEGER
-* = 0: successful exit.
-* < 0: if INFO = -i, the i-th argument had an illegal value.
-* > 0: if INFO = i, the algorithm failed to converge; i
-* off-diagonal elements of an intermediate tridiagonal
-* form did not converge to zero.
-*
-* =====================================================================
-*
-* .. Parameters ..
- DOUBLE PRECISION ZERO, ONE
- PARAMETER ( ZERO = 0.0D0, ONE = 1.0D0 )
-* ..
-* .. Local Scalars ..
- LOGICAL WANTZ
- INTEGER IINFO, IMAX, INDE, INDTAU, INDWRK, ISCALE
- DOUBLE PRECISION ANRM, BIGNUM, EPS, RMAX, RMIN, SAFMIN, SIGMA,
- $ SMLNUM
-* ..
-* .. External Functions ..
- LOGICAL LSAME
- DOUBLE PRECISION DLAMCH, DLANSP
- EXTERNAL LSAME, DLAMCH, DLANSP
-* ..
-* .. External Subroutines ..
- EXTERNAL DOPGTR, DSCAL, DSPTRD, DSTEQR, DSTERF, XERBLA
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC SQRT
-* ..
-* .. Executable Statements ..
-*
-* Test the input parameters.
-*
- WANTZ = LSAME( JOBZ, 'V' )
-*
- INFO = 0
- IF( .NOT.( WANTZ .OR. LSAME( JOBZ, 'N' ) ) ) THEN
- INFO = -1
- ELSE IF( .NOT.( LSAME( UPLO, 'U' ) .OR. LSAME( UPLO, 'L' ) ) )
- $ THEN
- INFO = -2
- ELSE IF( N.LT.0 ) THEN
- INFO = -3
- ELSE IF( LDZ.LT.1 .OR. ( WANTZ .AND. LDZ.LT.N ) ) THEN
- INFO = -7
- END IF
-*
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'DSPEV ', -INFO )
- RETURN
- END IF
-*
-* Quick return if possible
-*
- IF( N.EQ.0 )
- $ RETURN
-*
- IF( N.EQ.1 ) THEN
- W( 1 ) = AP( 1 )
- IF( WANTZ )
- $ Z( 1, 1 ) = ONE
- RETURN
- END IF
-*
-* Get machine constants.
-*
- SAFMIN = DLAMCH( 'Safe minimum' )
- EPS = DLAMCH( 'Precision' )
- SMLNUM = SAFMIN / EPS
- BIGNUM = ONE / SMLNUM
- RMIN = SQRT( SMLNUM )
- RMAX = SQRT( BIGNUM )
-*
-* Scale matrix to allowable range, if necessary.
-*
- ANRM = DLANSP( 'M', UPLO, N, AP, WORK )
- ISCALE = 0
- IF( ANRM.GT.ZERO .AND. ANRM.LT.RMIN ) THEN
- ISCALE = 1
- SIGMA = RMIN / ANRM
- ELSE IF( ANRM.GT.RMAX ) THEN
- ISCALE = 1
- SIGMA = RMAX / ANRM
- END IF
- IF( ISCALE.EQ.1 ) THEN
- CALL DSCAL( ( N*( N+1 ) ) / 2, SIGMA, AP, 1 )
- END IF
-*
-* Call DSPTRD to reduce symmetric packed matrix to tridiagonal form.
-*
- INDE = 1
- INDTAU = INDE + N
- CALL DSPTRD( UPLO, N, AP, W, WORK( INDE ), WORK( INDTAU ), IINFO )
-*
-* For eigenvalues only, call DSTERF. For eigenvectors, first call
-* DOPGTR to generate the orthogonal matrix, then call DSTEQR.
-*
- IF( .NOT.WANTZ ) THEN
- CALL DSTERF( N, W, WORK( INDE ), INFO )
- ELSE
- INDWRK = INDTAU + N
- CALL DOPGTR( UPLO, N, AP, WORK( INDTAU ), Z, LDZ,
- $ WORK( INDWRK ), IINFO )
- CALL DSTEQR( JOBZ, N, W, WORK( INDE ), Z, LDZ, WORK( INDTAU ),
- $ INFO )
- END IF
-*
-* If matrix was scaled, then rescale eigenvalues appropriately.
-*
- IF( ISCALE.EQ.1 ) THEN
- IF( INFO.EQ.0 ) THEN
- IMAX = N
- ELSE
- IMAX = INFO - 1
- END IF
- CALL DSCAL( IMAX, ONE / SIGMA, W, 1 )
- END IF
-*
- RETURN
-*
-* End of DSPEV
-*
- END
diff --git a/src/lib/lapack/dspgst.f b/src/lib/lapack/dspgst.f
deleted file mode 100644
index 8e121a94..00000000
--- a/src/lib/lapack/dspgst.f
+++ /dev/null
@@ -1,208 +0,0 @@
- SUBROUTINE DSPGST( ITYPE, UPLO, N, AP, BP, INFO )
-*
-* -- LAPACK routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- CHARACTER UPLO
- INTEGER INFO, ITYPE, N
-* ..
-* .. Array Arguments ..
- DOUBLE PRECISION AP( * ), BP( * )
-* ..
-*
-* Purpose
-* =======
-*
-* DSPGST reduces a real symmetric-definite generalized eigenproblem
-* to standard form, using packed storage.
-*
-* If ITYPE = 1, the problem is A*x = lambda*B*x,
-* and A is overwritten by inv(U**T)*A*inv(U) or inv(L)*A*inv(L**T)
-*
-* If ITYPE = 2 or 3, the problem is A*B*x = lambda*x or
-* B*A*x = lambda*x, and A is overwritten by U*A*U**T or L**T*A*L.
-*
-* B must have been previously factorized as U**T*U or L*L**T by DPPTRF.
-*
-* Arguments
-* =========
-*
-* ITYPE (input) INTEGER
-* = 1: compute inv(U**T)*A*inv(U) or inv(L)*A*inv(L**T);
-* = 2 or 3: compute U*A*U**T or L**T*A*L.
-*
-* UPLO (input) CHARACTER*1
-* = 'U': Upper triangle of A is stored and B is factored as
-* U**T*U;
-* = 'L': Lower triangle of A is stored and B is factored as
-* L*L**T.
-*
-* N (input) INTEGER
-* The order of the matrices A and B. N >= 0.
-*
-* AP (input/output) DOUBLE PRECISION array, dimension (N*(N+1)/2)
-* On entry, the upper or lower triangle of the symmetric matrix
-* A, packed columnwise in a linear array. The j-th column of A
-* is stored in the array AP as follows:
-* if UPLO = 'U', AP(i + (j-1)*j/2) = A(i,j) for 1<=i<=j;
-* if UPLO = 'L', AP(i + (j-1)*(2n-j)/2) = A(i,j) for j<=i<=n.
-*
-* On exit, if INFO = 0, the transformed matrix, stored in the
-* same format as A.
-*
-* BP (input) DOUBLE PRECISION array, dimension (N*(N+1)/2)
-* The triangular factor from the Cholesky factorization of B,
-* stored in the same format as A, as returned by DPPTRF.
-*
-* INFO (output) INTEGER
-* = 0: successful exit
-* < 0: if INFO = -i, the i-th argument had an illegal value
-*
-* =====================================================================
-*
-* .. Parameters ..
- DOUBLE PRECISION ONE, HALF
- PARAMETER ( ONE = 1.0D0, HALF = 0.5D0 )
-* ..
-* .. Local Scalars ..
- LOGICAL UPPER
- INTEGER J, J1, J1J1, JJ, K, K1, K1K1, KK
- DOUBLE PRECISION AJJ, AKK, BJJ, BKK, CT
-* ..
-* .. External Subroutines ..
- EXTERNAL DAXPY, DSCAL, DSPMV, DSPR2, DTPMV, DTPSV,
- $ XERBLA
-* ..
-* .. External Functions ..
- LOGICAL LSAME
- DOUBLE PRECISION DDOT
- EXTERNAL LSAME, DDOT
-* ..
-* .. Executable Statements ..
-*
-* Test the input parameters.
-*
- INFO = 0
- UPPER = LSAME( UPLO, 'U' )
- IF( ITYPE.LT.1 .OR. ITYPE.GT.3 ) THEN
- INFO = -1
- ELSE IF( .NOT.UPPER .AND. .NOT.LSAME( UPLO, 'L' ) ) THEN
- INFO = -2
- ELSE IF( N.LT.0 ) THEN
- INFO = -3
- END IF
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'DSPGST', -INFO )
- RETURN
- END IF
-*
- IF( ITYPE.EQ.1 ) THEN
- IF( UPPER ) THEN
-*
-* Compute inv(U')*A*inv(U)
-*
-* J1 and JJ are the indices of A(1,j) and A(j,j)
-*
- JJ = 0
- DO 10 J = 1, N
- J1 = JJ + 1
- JJ = JJ + J
-*
-* Compute the j-th column of the upper triangle of A
-*
- BJJ = BP( JJ )
- CALL DTPSV( UPLO, 'Transpose', 'Nonunit', J, BP,
- $ AP( J1 ), 1 )
- CALL DSPMV( UPLO, J-1, -ONE, AP, BP( J1 ), 1, ONE,
- $ AP( J1 ), 1 )
- CALL DSCAL( J-1, ONE / BJJ, AP( J1 ), 1 )
- AP( JJ ) = ( AP( JJ )-DDOT( J-1, AP( J1 ), 1, BP( J1 ),
- $ 1 ) ) / BJJ
- 10 CONTINUE
- ELSE
-*
-* Compute inv(L)*A*inv(L')
-*
-* KK and K1K1 are the indices of A(k,k) and A(k+1,k+1)
-*
- KK = 1
- DO 20 K = 1, N
- K1K1 = KK + N - K + 1
-*
-* Update the lower triangle of A(k:n,k:n)
-*
- AKK = AP( KK )
- BKK = BP( KK )
- AKK = AKK / BKK**2
- AP( KK ) = AKK
- IF( K.LT.N ) THEN
- CALL DSCAL( N-K, ONE / BKK, AP( KK+1 ), 1 )
- CT = -HALF*AKK
- CALL DAXPY( N-K, CT, BP( KK+1 ), 1, AP( KK+1 ), 1 )
- CALL DSPR2( UPLO, N-K, -ONE, AP( KK+1 ), 1,
- $ BP( KK+1 ), 1, AP( K1K1 ) )
- CALL DAXPY( N-K, CT, BP( KK+1 ), 1, AP( KK+1 ), 1 )
- CALL DTPSV( UPLO, 'No transpose', 'Non-unit', N-K,
- $ BP( K1K1 ), AP( KK+1 ), 1 )
- END IF
- KK = K1K1
- 20 CONTINUE
- END IF
- ELSE
- IF( UPPER ) THEN
-*
-* Compute U*A*U'
-*
-* K1 and KK are the indices of A(1,k) and A(k,k)
-*
- KK = 0
- DO 30 K = 1, N
- K1 = KK + 1
- KK = KK + K
-*
-* Update the upper triangle of A(1:k,1:k)
-*
- AKK = AP( KK )
- BKK = BP( KK )
- CALL DTPMV( UPLO, 'No transpose', 'Non-unit', K-1, BP,
- $ AP( K1 ), 1 )
- CT = HALF*AKK
- CALL DAXPY( K-1, CT, BP( K1 ), 1, AP( K1 ), 1 )
- CALL DSPR2( UPLO, K-1, ONE, AP( K1 ), 1, BP( K1 ), 1,
- $ AP )
- CALL DAXPY( K-1, CT, BP( K1 ), 1, AP( K1 ), 1 )
- CALL DSCAL( K-1, BKK, AP( K1 ), 1 )
- AP( KK ) = AKK*BKK**2
- 30 CONTINUE
- ELSE
-*
-* Compute L'*A*L
-*
-* JJ and J1J1 are the indices of A(j,j) and A(j+1,j+1)
-*
- JJ = 1
- DO 40 J = 1, N
- J1J1 = JJ + N - J + 1
-*
-* Compute the j-th column of the lower triangle of A
-*
- AJJ = AP( JJ )
- BJJ = BP( JJ )
- AP( JJ ) = AJJ*BJJ + DDOT( N-J, AP( JJ+1 ), 1,
- $ BP( JJ+1 ), 1 )
- CALL DSCAL( N-J, BJJ, AP( JJ+1 ), 1 )
- CALL DSPMV( UPLO, N-J, ONE, AP( J1J1 ), BP( JJ+1 ), 1,
- $ ONE, AP( JJ+1 ), 1 )
- CALL DTPMV( UPLO, 'Transpose', 'Non-unit', N-J+1,
- $ BP( JJ ), AP( JJ ), 1 )
- JJ = J1J1
- 40 CONTINUE
- END IF
- END IF
- RETURN
-*
-* End of DSPGST
-*
- END
diff --git a/src/lib/lapack/dspgv.f b/src/lib/lapack/dspgv.f
deleted file mode 100644
index 737a1ee3..00000000
--- a/src/lib/lapack/dspgv.f
+++ /dev/null
@@ -1,195 +0,0 @@
- SUBROUTINE DSPGV( ITYPE, JOBZ, UPLO, N, AP, BP, W, Z, LDZ, WORK,
- $ INFO )
-*
-* -- LAPACK driver routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- CHARACTER JOBZ, UPLO
- INTEGER INFO, ITYPE, LDZ, N
-* ..
-* .. Array Arguments ..
- DOUBLE PRECISION AP( * ), BP( * ), W( * ), WORK( * ),
- $ Z( LDZ, * )
-* ..
-*
-* Purpose
-* =======
-*
-* DSPGV computes all the eigenvalues and, optionally, the eigenvectors
-* of a real generalized symmetric-definite eigenproblem, of the form
-* A*x=(lambda)*B*x, A*Bx=(lambda)*x, or B*A*x=(lambda)*x.
-* Here A and B are assumed to be symmetric, stored in packed format,
-* and B is also positive definite.
-*
-* Arguments
-* =========
-*
-* ITYPE (input) INTEGER
-* Specifies the problem type to be solved:
-* = 1: A*x = (lambda)*B*x
-* = 2: A*B*x = (lambda)*x
-* = 3: B*A*x = (lambda)*x
-*
-* JOBZ (input) CHARACTER*1
-* = 'N': Compute eigenvalues only;
-* = 'V': Compute eigenvalues and eigenvectors.
-*
-* UPLO (input) CHARACTER*1
-* = 'U': Upper triangles of A and B are stored;
-* = 'L': Lower triangles of A and B are stored.
-*
-* N (input) INTEGER
-* The order of the matrices A and B. N >= 0.
-*
-* AP (input/output) DOUBLE PRECISION array, dimension
-* (N*(N+1)/2)
-* On entry, the upper or lower triangle of the symmetric matrix
-* A, packed columnwise in a linear array. The j-th column of A
-* is stored in the array AP as follows:
-* if UPLO = 'U', AP(i + (j-1)*j/2) = A(i,j) for 1<=i<=j;
-* if UPLO = 'L', AP(i + (j-1)*(2*n-j)/2) = A(i,j) for j<=i<=n.
-*
-* On exit, the contents of AP are destroyed.
-*
-* BP (input/output) DOUBLE PRECISION array, dimension (N*(N+1)/2)
-* On entry, the upper or lower triangle of the symmetric matrix
-* B, packed columnwise in a linear array. The j-th column of B
-* is stored in the array BP as follows:
-* if UPLO = 'U', BP(i + (j-1)*j/2) = B(i,j) for 1<=i<=j;
-* if UPLO = 'L', BP(i + (j-1)*(2*n-j)/2) = B(i,j) for j<=i<=n.
-*
-* On exit, the triangular factor U or L from the Cholesky
-* factorization B = U**T*U or B = L*L**T, in the same storage
-* format as B.
-*
-* W (output) DOUBLE PRECISION array, dimension (N)
-* If INFO = 0, the eigenvalues in ascending order.
-*
-* Z (output) DOUBLE PRECISION array, dimension (LDZ, N)
-* If JOBZ = 'V', then if INFO = 0, Z contains the matrix Z of
-* eigenvectors. The eigenvectors are normalized as follows:
-* if ITYPE = 1 or 2, Z**T*B*Z = I;
-* if ITYPE = 3, Z**T*inv(B)*Z = I.
-* If JOBZ = 'N', then Z is not referenced.
-*
-* LDZ (input) INTEGER
-* The leading dimension of the array Z. LDZ >= 1, and if
-* JOBZ = 'V', LDZ >= max(1,N).
-*
-* WORK (workspace) DOUBLE PRECISION array, dimension (3*N)
-*
-* INFO (output) INTEGER
-* = 0: successful exit
-* < 0: if INFO = -i, the i-th argument had an illegal value
-* > 0: DPPTRF or DSPEV returned an error code:
-* <= N: if INFO = i, DSPEV failed to converge;
-* i off-diagonal elements of an intermediate
-* tridiagonal form did not converge to zero.
-* > N: if INFO = n + i, for 1 <= i <= n, then the leading
-* minor of order i of B is not positive definite.
-* The factorization of B could not be completed and
-* no eigenvalues or eigenvectors were computed.
-*
-* =====================================================================
-*
-* .. Local Scalars ..
- LOGICAL UPPER, WANTZ
- CHARACTER TRANS
- INTEGER J, NEIG
-* ..
-* .. External Functions ..
- LOGICAL LSAME
- EXTERNAL LSAME
-* ..
-* .. External Subroutines ..
- EXTERNAL DPPTRF, DSPEV, DSPGST, DTPMV, DTPSV, XERBLA
-* ..
-* .. Executable Statements ..
-*
-* Test the input parameters.
-*
- WANTZ = LSAME( JOBZ, 'V' )
- UPPER = LSAME( UPLO, 'U' )
-*
- INFO = 0
- IF( ITYPE.LT.1 .OR. ITYPE.GT.3 ) THEN
- INFO = -1
- ELSE IF( .NOT.( WANTZ .OR. LSAME( JOBZ, 'N' ) ) ) THEN
- INFO = -2
- ELSE IF( .NOT.( UPPER .OR. LSAME( UPLO, 'L' ) ) ) THEN
- INFO = -3
- ELSE IF( N.LT.0 ) THEN
- INFO = -4
- ELSE IF( LDZ.LT.1 .OR. ( WANTZ .AND. LDZ.LT.N ) ) THEN
- INFO = -9
- END IF
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'DSPGV ', -INFO )
- RETURN
- END IF
-*
-* Quick return if possible
-*
- IF( N.EQ.0 )
- $ RETURN
-*
-* Form a Cholesky factorization of B.
-*
- CALL DPPTRF( UPLO, N, BP, INFO )
- IF( INFO.NE.0 ) THEN
- INFO = N + INFO
- RETURN
- END IF
-*
-* Transform problem to standard eigenvalue problem and solve.
-*
- CALL DSPGST( ITYPE, UPLO, N, AP, BP, INFO )
- CALL DSPEV( JOBZ, UPLO, N, AP, W, Z, LDZ, WORK, INFO )
-*
- IF( WANTZ ) THEN
-*
-* Backtransform eigenvectors to the original problem.
-*
- NEIG = N
- IF( INFO.GT.0 )
- $ NEIG = INFO - 1
- IF( ITYPE.EQ.1 .OR. ITYPE.EQ.2 ) THEN
-*
-* For A*x=(lambda)*B*x and A*B*x=(lambda)*x;
-* backtransform eigenvectors: x = inv(L)'*y or inv(U)*y
-*
- IF( UPPER ) THEN
- TRANS = 'N'
- ELSE
- TRANS = 'T'
- END IF
-*
- DO 10 J = 1, NEIG
- CALL DTPSV( UPLO, TRANS, 'Non-unit', N, BP, Z( 1, J ),
- $ 1 )
- 10 CONTINUE
-*
- ELSE IF( ITYPE.EQ.3 ) THEN
-*
-* For B*A*x=(lambda)*x;
-* backtransform eigenvectors: x = L*y or U'*y
-*
- IF( UPPER ) THEN
- TRANS = 'T'
- ELSE
- TRANS = 'N'
- END IF
-*
- DO 20 J = 1, NEIG
- CALL DTPMV( UPLO, TRANS, 'Non-unit', N, BP, Z( 1, J ),
- $ 1 )
- 20 CONTINUE
- END IF
- END IF
- RETURN
-*
-* End of DSPGV
-*
- END
diff --git a/src/lib/lapack/dsptrd.f b/src/lib/lapack/dsptrd.f
deleted file mode 100644
index 6d3390e3..00000000
--- a/src/lib/lapack/dsptrd.f
+++ /dev/null
@@ -1,228 +0,0 @@
- SUBROUTINE DSPTRD( UPLO, N, AP, D, E, TAU, INFO )
-*
-* -- LAPACK routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- CHARACTER UPLO
- INTEGER INFO, N
-* ..
-* .. Array Arguments ..
- DOUBLE PRECISION AP( * ), D( * ), E( * ), TAU( * )
-* ..
-*
-* Purpose
-* =======
-*
-* DSPTRD reduces a real symmetric matrix A stored in packed form to
-* symmetric tridiagonal form T by an orthogonal similarity
-* transformation: Q**T * A * Q = T.
-*
-* Arguments
-* =========
-*
-* UPLO (input) CHARACTER*1
-* = 'U': Upper triangle of A is stored;
-* = 'L': Lower triangle of A is stored.
-*
-* N (input) INTEGER
-* The order of the matrix A. N >= 0.
-*
-* AP (input/output) DOUBLE PRECISION array, dimension (N*(N+1)/2)
-* On entry, the upper or lower triangle of the symmetric matrix
-* A, packed columnwise in a linear array. The j-th column of A
-* is stored in the array AP as follows:
-* if UPLO = 'U', AP(i + (j-1)*j/2) = A(i,j) for 1<=i<=j;
-* if UPLO = 'L', AP(i + (j-1)*(2*n-j)/2) = A(i,j) for j<=i<=n.
-* On exit, if UPLO = 'U', the diagonal and first superdiagonal
-* of A are overwritten by the corresponding elements of the
-* tridiagonal matrix T, and the elements above the first
-* superdiagonal, with the array TAU, represent the orthogonal
-* matrix Q as a product of elementary reflectors; if UPLO
-* = 'L', the diagonal and first subdiagonal of A are over-
-* written by the corresponding elements of the tridiagonal
-* matrix T, and the elements below the first subdiagonal, with
-* the array TAU, represent the orthogonal matrix Q as a product
-* of elementary reflectors. See Further Details.
-*
-* D (output) DOUBLE PRECISION array, dimension (N)
-* The diagonal elements of the tridiagonal matrix T:
-* D(i) = A(i,i).
-*
-* E (output) DOUBLE PRECISION array, dimension (N-1)
-* The off-diagonal elements of the tridiagonal matrix T:
-* E(i) = A(i,i+1) if UPLO = 'U', E(i) = A(i+1,i) if UPLO = 'L'.
-*
-* TAU (output) DOUBLE PRECISION array, dimension (N-1)
-* The scalar factors of the elementary reflectors (see Further
-* Details).
-*
-* INFO (output) INTEGER
-* = 0: successful exit
-* < 0: if INFO = -i, the i-th argument had an illegal value
-*
-* Further Details
-* ===============
-*
-* If UPLO = 'U', the matrix Q is represented as a product of elementary
-* reflectors
-*
-* Q = H(n-1) . . . H(2) H(1).
-*
-* Each H(i) has the form
-*
-* H(i) = I - tau * v * v'
-*
-* where tau is a real scalar, and v is a real vector with
-* v(i+1:n) = 0 and v(i) = 1; v(1:i-1) is stored on exit in AP,
-* overwriting A(1:i-1,i+1), and tau is stored in TAU(i).
-*
-* If UPLO = 'L', the matrix Q is represented as a product of elementary
-* reflectors
-*
-* Q = H(1) H(2) . . . H(n-1).
-*
-* Each H(i) has the form
-*
-* H(i) = I - tau * v * v'
-*
-* where tau is a real scalar, and v is a real vector with
-* v(1:i) = 0 and v(i+1) = 1; v(i+2:n) is stored on exit in AP,
-* overwriting A(i+2:n,i), and tau is stored in TAU(i).
-*
-* =====================================================================
-*
-* .. Parameters ..
- DOUBLE PRECISION ONE, ZERO, HALF
- PARAMETER ( ONE = 1.0D0, ZERO = 0.0D0,
- $ HALF = 1.0D0 / 2.0D0 )
-* ..
-* .. Local Scalars ..
- LOGICAL UPPER
- INTEGER I, I1, I1I1, II
- DOUBLE PRECISION ALPHA, TAUI
-* ..
-* .. External Subroutines ..
- EXTERNAL DAXPY, DLARFG, DSPMV, DSPR2, XERBLA
-* ..
-* .. External Functions ..
- LOGICAL LSAME
- DOUBLE PRECISION DDOT
- EXTERNAL LSAME, DDOT
-* ..
-* .. Executable Statements ..
-*
-* Test the input parameters
-*
- INFO = 0
- UPPER = LSAME( UPLO, 'U' )
- IF( .NOT.UPPER .AND. .NOT.LSAME( UPLO, 'L' ) ) THEN
- INFO = -1
- ELSE IF( N.LT.0 ) THEN
- INFO = -2
- END IF
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'DSPTRD', -INFO )
- RETURN
- END IF
-*
-* Quick return if possible
-*
- IF( N.LE.0 )
- $ RETURN
-*
- IF( UPPER ) THEN
-*
-* Reduce the upper triangle of A.
-* I1 is the index in AP of A(1,I+1).
-*
- I1 = N*( N-1 ) / 2 + 1
- DO 10 I = N - 1, 1, -1
-*
-* Generate elementary reflector H(i) = I - tau * v * v'
-* to annihilate A(1:i-1,i+1)
-*
- CALL DLARFG( I, AP( I1+I-1 ), AP( I1 ), 1, TAUI )
- E( I ) = AP( I1+I-1 )
-*
- IF( TAUI.NE.ZERO ) THEN
-*
-* Apply H(i) from both sides to A(1:i,1:i)
-*
- AP( I1+I-1 ) = ONE
-*
-* Compute y := tau * A * v storing y in TAU(1:i)
-*
- CALL DSPMV( UPLO, I, TAUI, AP, AP( I1 ), 1, ZERO, TAU,
- $ 1 )
-*
-* Compute w := y - 1/2 * tau * (y'*v) * v
-*
- ALPHA = -HALF*TAUI*DDOT( I, TAU, 1, AP( I1 ), 1 )
- CALL DAXPY( I, ALPHA, AP( I1 ), 1, TAU, 1 )
-*
-* Apply the transformation as a rank-2 update:
-* A := A - v * w' - w * v'
-*
- CALL DSPR2( UPLO, I, -ONE, AP( I1 ), 1, TAU, 1, AP )
-*
- AP( I1+I-1 ) = E( I )
- END IF
- D( I+1 ) = AP( I1+I )
- TAU( I ) = TAUI
- I1 = I1 - I
- 10 CONTINUE
- D( 1 ) = AP( 1 )
- ELSE
-*
-* Reduce the lower triangle of A. II is the index in AP of
-* A(i,i) and I1I1 is the index of A(i+1,i+1).
-*
- II = 1
- DO 20 I = 1, N - 1
- I1I1 = II + N - I + 1
-*
-* Generate elementary reflector H(i) = I - tau * v * v'
-* to annihilate A(i+2:n,i)
-*
- CALL DLARFG( N-I, AP( II+1 ), AP( II+2 ), 1, TAUI )
- E( I ) = AP( II+1 )
-*
- IF( TAUI.NE.ZERO ) THEN
-*
-* Apply H(i) from both sides to A(i+1:n,i+1:n)
-*
- AP( II+1 ) = ONE
-*
-* Compute y := tau * A * v storing y in TAU(i:n-1)
-*
- CALL DSPMV( UPLO, N-I, TAUI, AP( I1I1 ), AP( II+1 ), 1,
- $ ZERO, TAU( I ), 1 )
-*
-* Compute w := y - 1/2 * tau * (y'*v) * v
-*
- ALPHA = -HALF*TAUI*DDOT( N-I, TAU( I ), 1, AP( II+1 ),
- $ 1 )
- CALL DAXPY( N-I, ALPHA, AP( II+1 ), 1, TAU( I ), 1 )
-*
-* Apply the transformation as a rank-2 update:
-* A := A - v * w' - w * v'
-*
- CALL DSPR2( UPLO, N-I, -ONE, AP( II+1 ), 1, TAU( I ), 1,
- $ AP( I1I1 ) )
-*
- AP( II+1 ) = E( I )
- END IF
- D( I ) = AP( II )
- TAU( I ) = TAUI
- II = I1I1
- 20 CONTINUE
- D( N ) = AP( II )
- END IF
-*
- RETURN
-*
-* End of DSPTRD
-*
- END
diff --git a/src/lib/lapack/dsptrf.f b/src/lib/lapack/dsptrf.f
deleted file mode 100644
index 8b8a9185..00000000
--- a/src/lib/lapack/dsptrf.f
+++ /dev/null
@@ -1,547 +0,0 @@
- SUBROUTINE DSPTRF( UPLO, N, AP, IPIV, INFO )
-*
-* -- LAPACK routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- CHARACTER UPLO
- INTEGER INFO, N
-* ..
-* .. Array Arguments ..
- INTEGER IPIV( * )
- DOUBLE PRECISION AP( * )
-* ..
-*
-* Purpose
-* =======
-*
-* DSPTRF computes the factorization of a real symmetric matrix A stored
-* in packed format using the Bunch-Kaufman diagonal pivoting method:
-*
-* A = U*D*U**T or A = L*D*L**T
-*
-* where U (or L) is a product of permutation and unit upper (lower)
-* triangular matrices, and D is symmetric and block diagonal with
-* 1-by-1 and 2-by-2 diagonal blocks.
-*
-* Arguments
-* =========
-*
-* UPLO (input) CHARACTER*1
-* = 'U': Upper triangle of A is stored;
-* = 'L': Lower triangle of A is stored.
-*
-* N (input) INTEGER
-* The order of the matrix A. N >= 0.
-*
-* AP (input/output) DOUBLE PRECISION array, dimension (N*(N+1)/2)
-* On entry, the upper or lower triangle of the symmetric matrix
-* A, packed columnwise in a linear array. The j-th column of A
-* is stored in the array AP as follows:
-* if UPLO = 'U', AP(i + (j-1)*j/2) = A(i,j) for 1<=i<=j;
-* if UPLO = 'L', AP(i + (j-1)*(2n-j)/2) = A(i,j) for j<=i<=n.
-*
-* On exit, the block diagonal matrix D and the multipliers used
-* to obtain the factor U or L, stored as a packed triangular
-* matrix overwriting A (see below for further details).
-*
-* IPIV (output) INTEGER array, dimension (N)
-* Details of the interchanges and the block structure of D.
-* If IPIV(k) > 0, then rows and columns k and IPIV(k) were
-* interchanged and D(k,k) is a 1-by-1 diagonal block.
-* If UPLO = 'U' and IPIV(k) = IPIV(k-1) < 0, then rows and
-* columns k-1 and -IPIV(k) were interchanged and D(k-1:k,k-1:k)
-* is a 2-by-2 diagonal block. If UPLO = 'L' and IPIV(k) =
-* IPIV(k+1) < 0, then rows and columns k+1 and -IPIV(k) were
-* interchanged and D(k:k+1,k:k+1) is a 2-by-2 diagonal block.
-*
-* INFO (output) INTEGER
-* = 0: successful exit
-* < 0: if INFO = -i, the i-th argument had an illegal value
-* > 0: if INFO = i, D(i,i) is exactly zero. The factorization
-* has been completed, but the block diagonal matrix D is
-* exactly singular, and division by zero will occur if it
-* is used to solve a system of equations.
-*
-* Further Details
-* ===============
-*
-* 5-96 - Based on modifications by J. Lewis, Boeing Computer Services
-* Company
-*
-* If UPLO = 'U', then A = U*D*U', where
-* U = P(n)*U(n)* ... *P(k)U(k)* ...,
-* i.e., U is a product of terms P(k)*U(k), where k decreases from n to
-* 1 in steps of 1 or 2, and D is a block diagonal matrix with 1-by-1
-* and 2-by-2 diagonal blocks D(k). P(k) is a permutation matrix as
-* defined by IPIV(k), and U(k) is a unit upper triangular matrix, such
-* that if the diagonal block D(k) is of order s (s = 1 or 2), then
-*
-* ( I v 0 ) k-s
-* U(k) = ( 0 I 0 ) s
-* ( 0 0 I ) n-k
-* k-s s n-k
-*
-* If s = 1, D(k) overwrites A(k,k), and v overwrites A(1:k-1,k).
-* If s = 2, the upper triangle of D(k) overwrites A(k-1,k-1), A(k-1,k),
-* and A(k,k), and v overwrites A(1:k-2,k-1:k).
-*
-* If UPLO = 'L', then A = L*D*L', where
-* L = P(1)*L(1)* ... *P(k)*L(k)* ...,
-* i.e., L is a product of terms P(k)*L(k), where k increases from 1 to
-* n in steps of 1 or 2, and D is a block diagonal matrix with 1-by-1
-* and 2-by-2 diagonal blocks D(k). P(k) is a permutation matrix as
-* defined by IPIV(k), and L(k) is a unit lower triangular matrix, such
-* that if the diagonal block D(k) is of order s (s = 1 or 2), then
-*
-* ( I 0 0 ) k-1
-* L(k) = ( 0 I 0 ) s
-* ( 0 v I ) n-k-s+1
-* k-1 s n-k-s+1
-*
-* If s = 1, D(k) overwrites A(k,k), and v overwrites A(k+1:n,k).
-* If s = 2, the lower triangle of D(k) overwrites A(k,k), A(k+1,k),
-* and A(k+1,k+1), and v overwrites A(k+2:n,k:k+1).
-*
-* =====================================================================
-*
-* .. Parameters ..
- DOUBLE PRECISION ZERO, ONE
- PARAMETER ( ZERO = 0.0D+0, ONE = 1.0D+0 )
- DOUBLE PRECISION EIGHT, SEVTEN
- PARAMETER ( EIGHT = 8.0D+0, SEVTEN = 17.0D+0 )
-* ..
-* .. Local Scalars ..
- LOGICAL UPPER
- INTEGER I, IMAX, J, JMAX, K, KC, KK, KNC, KP, KPC,
- $ KSTEP, KX, NPP
- DOUBLE PRECISION ABSAKK, ALPHA, COLMAX, D11, D12, D21, D22, R1,
- $ ROWMAX, T, WK, WKM1, WKP1
-* ..
-* .. External Functions ..
- LOGICAL LSAME
- INTEGER IDAMAX
- EXTERNAL LSAME, IDAMAX
-* ..
-* .. External Subroutines ..
- EXTERNAL DSCAL, DSPR, DSWAP, XERBLA
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC ABS, MAX, SQRT
-* ..
-* .. Executable Statements ..
-*
-* Test the input parameters.
-*
- INFO = 0
- UPPER = LSAME( UPLO, 'U' )
- IF( .NOT.UPPER .AND. .NOT.LSAME( UPLO, 'L' ) ) THEN
- INFO = -1
- ELSE IF( N.LT.0 ) THEN
- INFO = -2
- END IF
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'DSPTRF', -INFO )
- RETURN
- END IF
-*
-* Initialize ALPHA for use in choosing pivot block size.
-*
- ALPHA = ( ONE+SQRT( SEVTEN ) ) / EIGHT
-*
- IF( UPPER ) THEN
-*
-* Factorize A as U*D*U' using the upper triangle of A
-*
-* K is the main loop index, decreasing from N to 1 in steps of
-* 1 or 2
-*
- K = N
- KC = ( N-1 )*N / 2 + 1
- 10 CONTINUE
- KNC = KC
-*
-* If K < 1, exit from loop
-*
- IF( K.LT.1 )
- $ GO TO 110
- KSTEP = 1
-*
-* Determine rows and columns to be interchanged and whether
-* a 1-by-1 or 2-by-2 pivot block will be used
-*
- ABSAKK = ABS( AP( KC+K-1 ) )
-*
-* IMAX is the row-index of the largest off-diagonal element in
-* column K, and COLMAX is its absolute value
-*
- IF( K.GT.1 ) THEN
- IMAX = IDAMAX( K-1, AP( KC ), 1 )
- COLMAX = ABS( AP( KC+IMAX-1 ) )
- ELSE
- COLMAX = ZERO
- END IF
-*
- IF( MAX( ABSAKK, COLMAX ).EQ.ZERO ) THEN
-*
-* Column K is zero: set INFO and continue
-*
- IF( INFO.EQ.0 )
- $ INFO = K
- KP = K
- ELSE
- IF( ABSAKK.GE.ALPHA*COLMAX ) THEN
-*
-* no interchange, use 1-by-1 pivot block
-*
- KP = K
- ELSE
-*
-* JMAX is the column-index of the largest off-diagonal
-* element in row IMAX, and ROWMAX is its absolute value
-*
- ROWMAX = ZERO
- JMAX = IMAX
- KX = IMAX*( IMAX+1 ) / 2 + IMAX
- DO 20 J = IMAX + 1, K
- IF( ABS( AP( KX ) ).GT.ROWMAX ) THEN
- ROWMAX = ABS( AP( KX ) )
- JMAX = J
- END IF
- KX = KX + J
- 20 CONTINUE
- KPC = ( IMAX-1 )*IMAX / 2 + 1
- IF( IMAX.GT.1 ) THEN
- JMAX = IDAMAX( IMAX-1, AP( KPC ), 1 )
- ROWMAX = MAX( ROWMAX, ABS( AP( KPC+JMAX-1 ) ) )
- END IF
-*
- IF( ABSAKK.GE.ALPHA*COLMAX*( COLMAX / ROWMAX ) ) THEN
-*
-* no interchange, use 1-by-1 pivot block
-*
- KP = K
- ELSE IF( ABS( AP( KPC+IMAX-1 ) ).GE.ALPHA*ROWMAX ) THEN
-*
-* interchange rows and columns K and IMAX, use 1-by-1
-* pivot block
-*
- KP = IMAX
- ELSE
-*
-* interchange rows and columns K-1 and IMAX, use 2-by-2
-* pivot block
-*
- KP = IMAX
- KSTEP = 2
- END IF
- END IF
-*
- KK = K - KSTEP + 1
- IF( KSTEP.EQ.2 )
- $ KNC = KNC - K + 1
- IF( KP.NE.KK ) THEN
-*
-* Interchange rows and columns KK and KP in the leading
-* submatrix A(1:k,1:k)
-*
- CALL DSWAP( KP-1, AP( KNC ), 1, AP( KPC ), 1 )
- KX = KPC + KP - 1
- DO 30 J = KP + 1, KK - 1
- KX = KX + J - 1
- T = AP( KNC+J-1 )
- AP( KNC+J-1 ) = AP( KX )
- AP( KX ) = T
- 30 CONTINUE
- T = AP( KNC+KK-1 )
- AP( KNC+KK-1 ) = AP( KPC+KP-1 )
- AP( KPC+KP-1 ) = T
- IF( KSTEP.EQ.2 ) THEN
- T = AP( KC+K-2 )
- AP( KC+K-2 ) = AP( KC+KP-1 )
- AP( KC+KP-1 ) = T
- END IF
- END IF
-*
-* Update the leading submatrix
-*
- IF( KSTEP.EQ.1 ) THEN
-*
-* 1-by-1 pivot block D(k): column k now holds
-*
-* W(k) = U(k)*D(k)
-*
-* where U(k) is the k-th column of U
-*
-* Perform a rank-1 update of A(1:k-1,1:k-1) as
-*
-* A := A - U(k)*D(k)*U(k)' = A - W(k)*1/D(k)*W(k)'
-*
- R1 = ONE / AP( KC+K-1 )
- CALL DSPR( UPLO, K-1, -R1, AP( KC ), 1, AP )
-*
-* Store U(k) in column k
-*
- CALL DSCAL( K-1, R1, AP( KC ), 1 )
- ELSE
-*
-* 2-by-2 pivot block D(k): columns k and k-1 now hold
-*
-* ( W(k-1) W(k) ) = ( U(k-1) U(k) )*D(k)
-*
-* where U(k) and U(k-1) are the k-th and (k-1)-th columns
-* of U
-*
-* Perform a rank-2 update of A(1:k-2,1:k-2) as
-*
-* A := A - ( U(k-1) U(k) )*D(k)*( U(k-1) U(k) )'
-* = A - ( W(k-1) W(k) )*inv(D(k))*( W(k-1) W(k) )'
-*
- IF( K.GT.2 ) THEN
-*
- D12 = AP( K-1+( K-1 )*K / 2 )
- D22 = AP( K-1+( K-2 )*( K-1 ) / 2 ) / D12
- D11 = AP( K+( K-1 )*K / 2 ) / D12
- T = ONE / ( D11*D22-ONE )
- D12 = T / D12
-*
- DO 50 J = K - 2, 1, -1
- WKM1 = D12*( D11*AP( J+( K-2 )*( K-1 ) / 2 )-
- $ AP( J+( K-1 )*K / 2 ) )
- WK = D12*( D22*AP( J+( K-1 )*K / 2 )-
- $ AP( J+( K-2 )*( K-1 ) / 2 ) )
- DO 40 I = J, 1, -1
- AP( I+( J-1 )*J / 2 ) = AP( I+( J-1 )*J / 2 ) -
- $ AP( I+( K-1 )*K / 2 )*WK -
- $ AP( I+( K-2 )*( K-1 ) / 2 )*WKM1
- 40 CONTINUE
- AP( J+( K-1 )*K / 2 ) = WK
- AP( J+( K-2 )*( K-1 ) / 2 ) = WKM1
- 50 CONTINUE
-*
- END IF
-*
- END IF
- END IF
-*
-* Store details of the interchanges in IPIV
-*
- IF( KSTEP.EQ.1 ) THEN
- IPIV( K ) = KP
- ELSE
- IPIV( K ) = -KP
- IPIV( K-1 ) = -KP
- END IF
-*
-* Decrease K and return to the start of the main loop
-*
- K = K - KSTEP
- KC = KNC - K
- GO TO 10
-*
- ELSE
-*
-* Factorize A as L*D*L' using the lower triangle of A
-*
-* K is the main loop index, increasing from 1 to N in steps of
-* 1 or 2
-*
- K = 1
- KC = 1
- NPP = N*( N+1 ) / 2
- 60 CONTINUE
- KNC = KC
-*
-* If K > N, exit from loop
-*
- IF( K.GT.N )
- $ GO TO 110
- KSTEP = 1
-*
-* Determine rows and columns to be interchanged and whether
-* a 1-by-1 or 2-by-2 pivot block will be used
-*
- ABSAKK = ABS( AP( KC ) )
-*
-* IMAX is the row-index of the largest off-diagonal element in
-* column K, and COLMAX is its absolute value
-*
- IF( K.LT.N ) THEN
- IMAX = K + IDAMAX( N-K, AP( KC+1 ), 1 )
- COLMAX = ABS( AP( KC+IMAX-K ) )
- ELSE
- COLMAX = ZERO
- END IF
-*
- IF( MAX( ABSAKK, COLMAX ).EQ.ZERO ) THEN
-*
-* Column K is zero: set INFO and continue
-*
- IF( INFO.EQ.0 )
- $ INFO = K
- KP = K
- ELSE
- IF( ABSAKK.GE.ALPHA*COLMAX ) THEN
-*
-* no interchange, use 1-by-1 pivot block
-*
- KP = K
- ELSE
-*
-* JMAX is the column-index of the largest off-diagonal
-* element in row IMAX, and ROWMAX is its absolute value
-*
- ROWMAX = ZERO
- KX = KC + IMAX - K
- DO 70 J = K, IMAX - 1
- IF( ABS( AP( KX ) ).GT.ROWMAX ) THEN
- ROWMAX = ABS( AP( KX ) )
- JMAX = J
- END IF
- KX = KX + N - J
- 70 CONTINUE
- KPC = NPP - ( N-IMAX+1 )*( N-IMAX+2 ) / 2 + 1
- IF( IMAX.LT.N ) THEN
- JMAX = IMAX + IDAMAX( N-IMAX, AP( KPC+1 ), 1 )
- ROWMAX = MAX( ROWMAX, ABS( AP( KPC+JMAX-IMAX ) ) )
- END IF
-*
- IF( ABSAKK.GE.ALPHA*COLMAX*( COLMAX / ROWMAX ) ) THEN
-*
-* no interchange, use 1-by-1 pivot block
-*
- KP = K
- ELSE IF( ABS( AP( KPC ) ).GE.ALPHA*ROWMAX ) THEN
-*
-* interchange rows and columns K and IMAX, use 1-by-1
-* pivot block
-*
- KP = IMAX
- ELSE
-*
-* interchange rows and columns K+1 and IMAX, use 2-by-2
-* pivot block
-*
- KP = IMAX
- KSTEP = 2
- END IF
- END IF
-*
- KK = K + KSTEP - 1
- IF( KSTEP.EQ.2 )
- $ KNC = KNC + N - K + 1
- IF( KP.NE.KK ) THEN
-*
-* Interchange rows and columns KK and KP in the trailing
-* submatrix A(k:n,k:n)
-*
- IF( KP.LT.N )
- $ CALL DSWAP( N-KP, AP( KNC+KP-KK+1 ), 1, AP( KPC+1 ),
- $ 1 )
- KX = KNC + KP - KK
- DO 80 J = KK + 1, KP - 1
- KX = KX + N - J + 1
- T = AP( KNC+J-KK )
- AP( KNC+J-KK ) = AP( KX )
- AP( KX ) = T
- 80 CONTINUE
- T = AP( KNC )
- AP( KNC ) = AP( KPC )
- AP( KPC ) = T
- IF( KSTEP.EQ.2 ) THEN
- T = AP( KC+1 )
- AP( KC+1 ) = AP( KC+KP-K )
- AP( KC+KP-K ) = T
- END IF
- END IF
-*
-* Update the trailing submatrix
-*
- IF( KSTEP.EQ.1 ) THEN
-*
-* 1-by-1 pivot block D(k): column k now holds
-*
-* W(k) = L(k)*D(k)
-*
-* where L(k) is the k-th column of L
-*
- IF( K.LT.N ) THEN
-*
-* Perform a rank-1 update of A(k+1:n,k+1:n) as
-*
-* A := A - L(k)*D(k)*L(k)' = A - W(k)*(1/D(k))*W(k)'
-*
- R1 = ONE / AP( KC )
- CALL DSPR( UPLO, N-K, -R1, AP( KC+1 ), 1,
- $ AP( KC+N-K+1 ) )
-*
-* Store L(k) in column K
-*
- CALL DSCAL( N-K, R1, AP( KC+1 ), 1 )
- END IF
- ELSE
-*
-* 2-by-2 pivot block D(k): columns K and K+1 now hold
-*
-* ( W(k) W(k+1) ) = ( L(k) L(k+1) )*D(k)
-*
-* where L(k) and L(k+1) are the k-th and (k+1)-th columns
-* of L
-*
- IF( K.LT.N-1 ) THEN
-*
-* Perform a rank-2 update of A(k+2:n,k+2:n) as
-*
-* A := A - ( L(k) L(k+1) )*D(k)*( L(k) L(k+1) )'
-* = A - ( W(k) W(k+1) )*inv(D(k))*( W(k) W(k+1) )'
-*
- D21 = AP( K+1+( K-1 )*( 2*N-K ) / 2 )
- D11 = AP( K+1+K*( 2*N-K-1 ) / 2 ) / D21
- D22 = AP( K+( K-1 )*( 2*N-K ) / 2 ) / D21
- T = ONE / ( D11*D22-ONE )
- D21 = T / D21
-*
- DO 100 J = K + 2, N
- WK = D21*( D11*AP( J+( K-1 )*( 2*N-K ) / 2 )-
- $ AP( J+K*( 2*N-K-1 ) / 2 ) )
- WKP1 = D21*( D22*AP( J+K*( 2*N-K-1 ) / 2 )-
- $ AP( J+( K-1 )*( 2*N-K ) / 2 ) )
-*
- DO 90 I = J, N
- AP( I+( J-1 )*( 2*N-J ) / 2 ) = AP( I+( J-1 )*
- $ ( 2*N-J ) / 2 ) - AP( I+( K-1 )*( 2*N-K ) /
- $ 2 )*WK - AP( I+K*( 2*N-K-1 ) / 2 )*WKP1
- 90 CONTINUE
-*
- AP( J+( K-1 )*( 2*N-K ) / 2 ) = WK
- AP( J+K*( 2*N-K-1 ) / 2 ) = WKP1
-*
- 100 CONTINUE
- END IF
- END IF
- END IF
-*
-* Store details of the interchanges in IPIV
-*
- IF( KSTEP.EQ.1 ) THEN
- IPIV( K ) = KP
- ELSE
- IPIV( K ) = -KP
- IPIV( K+1 ) = -KP
- END IF
-*
-* Increase K and return to the start of the main loop
-*
- K = K + KSTEP
- KC = KNC + N - K + 2
- GO TO 60
-*
- END IF
-*
- 110 CONTINUE
- RETURN
-*
-* End of DSPTRF
-*
- END
diff --git a/src/lib/lapack/dsteqr.f b/src/lib/lapack/dsteqr.f
deleted file mode 100644
index 0afd7957..00000000
--- a/src/lib/lapack/dsteqr.f
+++ /dev/null
@@ -1,500 +0,0 @@
- SUBROUTINE DSTEQR( COMPZ, N, D, E, Z, LDZ, WORK, INFO )
-*
-* -- LAPACK routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- CHARACTER COMPZ
- INTEGER INFO, LDZ, N
-* ..
-* .. Array Arguments ..
- DOUBLE PRECISION D( * ), E( * ), WORK( * ), Z( LDZ, * )
-* ..
-*
-* Purpose
-* =======
-*
-* DSTEQR computes all eigenvalues and, optionally, eigenvectors of a
-* symmetric tridiagonal matrix using the implicit QL or QR method.
-* The eigenvectors of a full or band symmetric matrix can also be found
-* if DSYTRD or DSPTRD or DSBTRD has been used to reduce this matrix to
-* tridiagonal form.
-*
-* Arguments
-* =========
-*
-* COMPZ (input) CHARACTER*1
-* = 'N': Compute eigenvalues only.
-* = 'V': Compute eigenvalues and eigenvectors of the original
-* symmetric matrix. On entry, Z must contain the
-* orthogonal matrix used to reduce the original matrix
-* to tridiagonal form.
-* = 'I': Compute eigenvalues and eigenvectors of the
-* tridiagonal matrix. Z is initialized to the identity
-* matrix.
-*
-* N (input) INTEGER
-* The order of the matrix. N >= 0.
-*
-* D (input/output) DOUBLE PRECISION array, dimension (N)
-* On entry, the diagonal elements of the tridiagonal matrix.
-* On exit, if INFO = 0, the eigenvalues in ascending order.
-*
-* E (input/output) DOUBLE PRECISION array, dimension (N-1)
-* On entry, the (n-1) subdiagonal elements of the tridiagonal
-* matrix.
-* On exit, E has been destroyed.
-*
-* Z (input/output) DOUBLE PRECISION array, dimension (LDZ, N)
-* On entry, if COMPZ = 'V', then Z contains the orthogonal
-* matrix used in the reduction to tridiagonal form.
-* On exit, if INFO = 0, then if COMPZ = 'V', Z contains the
-* orthonormal eigenvectors of the original symmetric matrix,
-* and if COMPZ = 'I', Z contains the orthonormal eigenvectors
-* of the symmetric tridiagonal matrix.
-* If COMPZ = 'N', then Z is not referenced.
-*
-* LDZ (input) INTEGER
-* The leading dimension of the array Z. LDZ >= 1, and if
-* eigenvectors are desired, then LDZ >= max(1,N).
-*
-* WORK (workspace) DOUBLE PRECISION array, dimension (max(1,2*N-2))
-* If COMPZ = 'N', then WORK is not referenced.
-*
-* INFO (output) INTEGER
-* = 0: successful exit
-* < 0: if INFO = -i, the i-th argument had an illegal value
-* > 0: the algorithm has failed to find all the eigenvalues in
-* a total of 30*N iterations; if INFO = i, then i
-* elements of E have not converged to zero; on exit, D
-* and E contain the elements of a symmetric tridiagonal
-* matrix which is orthogonally similar to the original
-* matrix.
-*
-* =====================================================================
-*
-* .. Parameters ..
- DOUBLE PRECISION ZERO, ONE, TWO, THREE
- PARAMETER ( ZERO = 0.0D0, ONE = 1.0D0, TWO = 2.0D0,
- $ THREE = 3.0D0 )
- INTEGER MAXIT
- PARAMETER ( MAXIT = 30 )
-* ..
-* .. Local Scalars ..
- INTEGER I, ICOMPZ, II, ISCALE, J, JTOT, K, L, L1, LEND,
- $ LENDM1, LENDP1, LENDSV, LM1, LSV, M, MM, MM1,
- $ NM1, NMAXIT
- DOUBLE PRECISION ANORM, B, C, EPS, EPS2, F, G, P, R, RT1, RT2,
- $ S, SAFMAX, SAFMIN, SSFMAX, SSFMIN, TST
-* ..
-* .. External Functions ..
- LOGICAL LSAME
- DOUBLE PRECISION DLAMCH, DLANST, DLAPY2
- EXTERNAL LSAME, DLAMCH, DLANST, DLAPY2
-* ..
-* .. External Subroutines ..
- EXTERNAL DLAE2, DLAEV2, DLARTG, DLASCL, DLASET, DLASR,
- $ DLASRT, DSWAP, XERBLA
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC ABS, MAX, SIGN, SQRT
-* ..
-* .. Executable Statements ..
-*
-* Test the input parameters.
-*
- INFO = 0
-*
- IF( LSAME( COMPZ, 'N' ) ) THEN
- ICOMPZ = 0
- ELSE IF( LSAME( COMPZ, 'V' ) ) THEN
- ICOMPZ = 1
- ELSE IF( LSAME( COMPZ, 'I' ) ) THEN
- ICOMPZ = 2
- ELSE
- ICOMPZ = -1
- END IF
- IF( ICOMPZ.LT.0 ) THEN
- INFO = -1
- ELSE IF( N.LT.0 ) THEN
- INFO = -2
- ELSE IF( ( LDZ.LT.1 ) .OR. ( ICOMPZ.GT.0 .AND. LDZ.LT.MAX( 1,
- $ N ) ) ) THEN
- INFO = -6
- END IF
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'DSTEQR', -INFO )
- RETURN
- END IF
-*
-* Quick return if possible
-*
- IF( N.EQ.0 )
- $ RETURN
-*
- IF( N.EQ.1 ) THEN
- IF( ICOMPZ.EQ.2 )
- $ Z( 1, 1 ) = ONE
- RETURN
- END IF
-*
-* Determine the unit roundoff and over/underflow thresholds.
-*
- EPS = DLAMCH( 'E' )
- EPS2 = EPS**2
- SAFMIN = DLAMCH( 'S' )
- SAFMAX = ONE / SAFMIN
- SSFMAX = SQRT( SAFMAX ) / THREE
- SSFMIN = SQRT( SAFMIN ) / EPS2
-*
-* Compute the eigenvalues and eigenvectors of the tridiagonal
-* matrix.
-*
- IF( ICOMPZ.EQ.2 )
- $ CALL DLASET( 'Full', N, N, ZERO, ONE, Z, LDZ )
-*
- NMAXIT = N*MAXIT
- JTOT = 0
-*
-* Determine where the matrix splits and choose QL or QR iteration
-* for each block, according to whether top or bottom diagonal
-* element is smaller.
-*
- L1 = 1
- NM1 = N - 1
-*
- 10 CONTINUE
- IF( L1.GT.N )
- $ GO TO 160
- IF( L1.GT.1 )
- $ E( L1-1 ) = ZERO
- IF( L1.LE.NM1 ) THEN
- DO 20 M = L1, NM1
- TST = ABS( E( M ) )
- IF( TST.EQ.ZERO )
- $ GO TO 30
- IF( TST.LE.( SQRT( ABS( D( M ) ) )*SQRT( ABS( D( M+
- $ 1 ) ) ) )*EPS ) THEN
- E( M ) = ZERO
- GO TO 30
- END IF
- 20 CONTINUE
- END IF
- M = N
-*
- 30 CONTINUE
- L = L1
- LSV = L
- LEND = M
- LENDSV = LEND
- L1 = M + 1
- IF( LEND.EQ.L )
- $ GO TO 10
-*
-* Scale submatrix in rows and columns L to LEND
-*
- ANORM = DLANST( 'I', LEND-L+1, D( L ), E( L ) )
- ISCALE = 0
- IF( ANORM.EQ.ZERO )
- $ GO TO 10
- IF( ANORM.GT.SSFMAX ) THEN
- ISCALE = 1
- CALL DLASCL( 'G', 0, 0, ANORM, SSFMAX, LEND-L+1, 1, D( L ), N,
- $ INFO )
- CALL DLASCL( 'G', 0, 0, ANORM, SSFMAX, LEND-L, 1, E( L ), N,
- $ INFO )
- ELSE IF( ANORM.LT.SSFMIN ) THEN
- ISCALE = 2
- CALL DLASCL( 'G', 0, 0, ANORM, SSFMIN, LEND-L+1, 1, D( L ), N,
- $ INFO )
- CALL DLASCL( 'G', 0, 0, ANORM, SSFMIN, LEND-L, 1, E( L ), N,
- $ INFO )
- END IF
-*
-* Choose between QL and QR iteration
-*
- IF( ABS( D( LEND ) ).LT.ABS( D( L ) ) ) THEN
- LEND = LSV
- L = LENDSV
- END IF
-*
- IF( LEND.GT.L ) THEN
-*
-* QL Iteration
-*
-* Look for small subdiagonal element.
-*
- 40 CONTINUE
- IF( L.NE.LEND ) THEN
- LENDM1 = LEND - 1
- DO 50 M = L, LENDM1
- TST = ABS( E( M ) )**2
- IF( TST.LE.( EPS2*ABS( D( M ) ) )*ABS( D( M+1 ) )+
- $ SAFMIN )GO TO 60
- 50 CONTINUE
- END IF
-*
- M = LEND
-*
- 60 CONTINUE
- IF( M.LT.LEND )
- $ E( M ) = ZERO
- P = D( L )
- IF( M.EQ.L )
- $ GO TO 80
-*
-* If remaining matrix is 2-by-2, use DLAE2 or SLAEV2
-* to compute its eigensystem.
-*
- IF( M.EQ.L+1 ) THEN
- IF( ICOMPZ.GT.0 ) THEN
- CALL DLAEV2( D( L ), E( L ), D( L+1 ), RT1, RT2, C, S )
- WORK( L ) = C
- WORK( N-1+L ) = S
- CALL DLASR( 'R', 'V', 'B', N, 2, WORK( L ),
- $ WORK( N-1+L ), Z( 1, L ), LDZ )
- ELSE
- CALL DLAE2( D( L ), E( L ), D( L+1 ), RT1, RT2 )
- END IF
- D( L ) = RT1
- D( L+1 ) = RT2
- E( L ) = ZERO
- L = L + 2
- IF( L.LE.LEND )
- $ GO TO 40
- GO TO 140
- END IF
-*
- IF( JTOT.EQ.NMAXIT )
- $ GO TO 140
- JTOT = JTOT + 1
-*
-* Form shift.
-*
- G = ( D( L+1 )-P ) / ( TWO*E( L ) )
- R = DLAPY2( G, ONE )
- G = D( M ) - P + ( E( L ) / ( G+SIGN( R, G ) ) )
-*
- S = ONE
- C = ONE
- P = ZERO
-*
-* Inner loop
-*
- MM1 = M - 1
- DO 70 I = MM1, L, -1
- F = S*E( I )
- B = C*E( I )
- CALL DLARTG( G, F, C, S, R )
- IF( I.NE.M-1 )
- $ E( I+1 ) = R
- G = D( I+1 ) - P
- R = ( D( I )-G )*S + TWO*C*B
- P = S*R
- D( I+1 ) = G + P
- G = C*R - B
-*
-* If eigenvectors are desired, then save rotations.
-*
- IF( ICOMPZ.GT.0 ) THEN
- WORK( I ) = C
- WORK( N-1+I ) = -S
- END IF
-*
- 70 CONTINUE
-*
-* If eigenvectors are desired, then apply saved rotations.
-*
- IF( ICOMPZ.GT.0 ) THEN
- MM = M - L + 1
- CALL DLASR( 'R', 'V', 'B', N, MM, WORK( L ), WORK( N-1+L ),
- $ Z( 1, L ), LDZ )
- END IF
-*
- D( L ) = D( L ) - P
- E( L ) = G
- GO TO 40
-*
-* Eigenvalue found.
-*
- 80 CONTINUE
- D( L ) = P
-*
- L = L + 1
- IF( L.LE.LEND )
- $ GO TO 40
- GO TO 140
-*
- ELSE
-*
-* QR Iteration
-*
-* Look for small superdiagonal element.
-*
- 90 CONTINUE
- IF( L.NE.LEND ) THEN
- LENDP1 = LEND + 1
- DO 100 M = L, LENDP1, -1
- TST = ABS( E( M-1 ) )**2
- IF( TST.LE.( EPS2*ABS( D( M ) ) )*ABS( D( M-1 ) )+
- $ SAFMIN )GO TO 110
- 100 CONTINUE
- END IF
-*
- M = LEND
-*
- 110 CONTINUE
- IF( M.GT.LEND )
- $ E( M-1 ) = ZERO
- P = D( L )
- IF( M.EQ.L )
- $ GO TO 130
-*
-* If remaining matrix is 2-by-2, use DLAE2 or SLAEV2
-* to compute its eigensystem.
-*
- IF( M.EQ.L-1 ) THEN
- IF( ICOMPZ.GT.0 ) THEN
- CALL DLAEV2( D( L-1 ), E( L-1 ), D( L ), RT1, RT2, C, S )
- WORK( M ) = C
- WORK( N-1+M ) = S
- CALL DLASR( 'R', 'V', 'F', N, 2, WORK( M ),
- $ WORK( N-1+M ), Z( 1, L-1 ), LDZ )
- ELSE
- CALL DLAE2( D( L-1 ), E( L-1 ), D( L ), RT1, RT2 )
- END IF
- D( L-1 ) = RT1
- D( L ) = RT2
- E( L-1 ) = ZERO
- L = L - 2
- IF( L.GE.LEND )
- $ GO TO 90
- GO TO 140
- END IF
-*
- IF( JTOT.EQ.NMAXIT )
- $ GO TO 140
- JTOT = JTOT + 1
-*
-* Form shift.
-*
- G = ( D( L-1 )-P ) / ( TWO*E( L-1 ) )
- R = DLAPY2( G, ONE )
- G = D( M ) - P + ( E( L-1 ) / ( G+SIGN( R, G ) ) )
-*
- S = ONE
- C = ONE
- P = ZERO
-*
-* Inner loop
-*
- LM1 = L - 1
- DO 120 I = M, LM1
- F = S*E( I )
- B = C*E( I )
- CALL DLARTG( G, F, C, S, R )
- IF( I.NE.M )
- $ E( I-1 ) = R
- G = D( I ) - P
- R = ( D( I+1 )-G )*S + TWO*C*B
- P = S*R
- D( I ) = G + P
- G = C*R - B
-*
-* If eigenvectors are desired, then save rotations.
-*
- IF( ICOMPZ.GT.0 ) THEN
- WORK( I ) = C
- WORK( N-1+I ) = S
- END IF
-*
- 120 CONTINUE
-*
-* If eigenvectors are desired, then apply saved rotations.
-*
- IF( ICOMPZ.GT.0 ) THEN
- MM = L - M + 1
- CALL DLASR( 'R', 'V', 'F', N, MM, WORK( M ), WORK( N-1+M ),
- $ Z( 1, M ), LDZ )
- END IF
-*
- D( L ) = D( L ) - P
- E( LM1 ) = G
- GO TO 90
-*
-* Eigenvalue found.
-*
- 130 CONTINUE
- D( L ) = P
-*
- L = L - 1
- IF( L.GE.LEND )
- $ GO TO 90
- GO TO 140
-*
- END IF
-*
-* Undo scaling if necessary
-*
- 140 CONTINUE
- IF( ISCALE.EQ.1 ) THEN
- CALL DLASCL( 'G', 0, 0, SSFMAX, ANORM, LENDSV-LSV+1, 1,
- $ D( LSV ), N, INFO )
- CALL DLASCL( 'G', 0, 0, SSFMAX, ANORM, LENDSV-LSV, 1, E( LSV ),
- $ N, INFO )
- ELSE IF( ISCALE.EQ.2 ) THEN
- CALL DLASCL( 'G', 0, 0, SSFMIN, ANORM, LENDSV-LSV+1, 1,
- $ D( LSV ), N, INFO )
- CALL DLASCL( 'G', 0, 0, SSFMIN, ANORM, LENDSV-LSV, 1, E( LSV ),
- $ N, INFO )
- END IF
-*
-* Check for no convergence to an eigenvalue after a total
-* of N*MAXIT iterations.
-*
- IF( JTOT.LT.NMAXIT )
- $ GO TO 10
- DO 150 I = 1, N - 1
- IF( E( I ).NE.ZERO )
- $ INFO = INFO + 1
- 150 CONTINUE
- GO TO 190
-*
-* Order eigenvalues and eigenvectors.
-*
- 160 CONTINUE
- IF( ICOMPZ.EQ.0 ) THEN
-*
-* Use Quick Sort
-*
- CALL DLASRT( 'I', N, D, INFO )
-*
- ELSE
-*
-* Use Selection Sort to minimize swaps of eigenvectors
-*
- DO 180 II = 2, N
- I = II - 1
- K = I
- P = D( I )
- DO 170 J = II, N
- IF( D( J ).LT.P ) THEN
- K = J
- P = D( J )
- END IF
- 170 CONTINUE
- IF( K.NE.I ) THEN
- D( K ) = D( I )
- D( I ) = P
- CALL DSWAP( N, Z( 1, I ), 1, Z( 1, K ), 1 )
- END IF
- 180 CONTINUE
- END IF
-*
- 190 CONTINUE
- RETURN
-*
-* End of DSTEQR
-*
- END
diff --git a/src/lib/lapack/dsterf.f b/src/lib/lapack/dsterf.f
deleted file mode 100644
index c17ea23a..00000000
--- a/src/lib/lapack/dsterf.f
+++ /dev/null
@@ -1,364 +0,0 @@
- SUBROUTINE DSTERF( N, D, E, INFO )
-*
-* -- LAPACK routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- INTEGER INFO, N
-* ..
-* .. Array Arguments ..
- DOUBLE PRECISION D( * ), E( * )
-* ..
-*
-* Purpose
-* =======
-*
-* DSTERF computes all eigenvalues of a symmetric tridiagonal matrix
-* using the Pal-Walker-Kahan variant of the QL or QR algorithm.
-*
-* Arguments
-* =========
-*
-* N (input) INTEGER
-* The order of the matrix. N >= 0.
-*
-* D (input/output) DOUBLE PRECISION array, dimension (N)
-* On entry, the n diagonal elements of the tridiagonal matrix.
-* On exit, if INFO = 0, the eigenvalues in ascending order.
-*
-* E (input/output) DOUBLE PRECISION array, dimension (N-1)
-* On entry, the (n-1) subdiagonal elements of the tridiagonal
-* matrix.
-* On exit, E has been destroyed.
-*
-* INFO (output) INTEGER
-* = 0: successful exit
-* < 0: if INFO = -i, the i-th argument had an illegal value
-* > 0: the algorithm failed to find all of the eigenvalues in
-* a total of 30*N iterations; if INFO = i, then i
-* elements of E have not converged to zero.
-*
-* =====================================================================
-*
-* .. Parameters ..
- DOUBLE PRECISION ZERO, ONE, TWO, THREE
- PARAMETER ( ZERO = 0.0D0, ONE = 1.0D0, TWO = 2.0D0,
- $ THREE = 3.0D0 )
- INTEGER MAXIT
- PARAMETER ( MAXIT = 30 )
-* ..
-* .. Local Scalars ..
- INTEGER I, ISCALE, JTOT, L, L1, LEND, LENDSV, LSV, M,
- $ NMAXIT
- DOUBLE PRECISION ALPHA, ANORM, BB, C, EPS, EPS2, GAMMA, OLDC,
- $ OLDGAM, P, R, RT1, RT2, RTE, S, SAFMAX, SAFMIN,
- $ SIGMA, SSFMAX, SSFMIN
-* ..
-* .. External Functions ..
- DOUBLE PRECISION DLAMCH, DLANST, DLAPY2
- EXTERNAL DLAMCH, DLANST, DLAPY2
-* ..
-* .. External Subroutines ..
- EXTERNAL DLAE2, DLASCL, DLASRT, XERBLA
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC ABS, SIGN, SQRT
-* ..
-* .. Executable Statements ..
-*
-* Test the input parameters.
-*
- INFO = 0
-*
-* Quick return if possible
-*
- IF( N.LT.0 ) THEN
- INFO = -1
- CALL XERBLA( 'DSTERF', -INFO )
- RETURN
- END IF
- IF( N.LE.1 )
- $ RETURN
-*
-* Determine the unit roundoff for this environment.
-*
- EPS = DLAMCH( 'E' )
- EPS2 = EPS**2
- SAFMIN = DLAMCH( 'S' )
- SAFMAX = ONE / SAFMIN
- SSFMAX = SQRT( SAFMAX ) / THREE
- SSFMIN = SQRT( SAFMIN ) / EPS2
-*
-* Compute the eigenvalues of the tridiagonal matrix.
-*
- NMAXIT = N*MAXIT
- SIGMA = ZERO
- JTOT = 0
-*
-* Determine where the matrix splits and choose QL or QR iteration
-* for each block, according to whether top or bottom diagonal
-* element is smaller.
-*
- L1 = 1
-*
- 10 CONTINUE
- IF( L1.GT.N )
- $ GO TO 170
- IF( L1.GT.1 )
- $ E( L1-1 ) = ZERO
- DO 20 M = L1, N - 1
- IF( ABS( E( M ) ).LE.( SQRT( ABS( D( M ) ) )*SQRT( ABS( D( M+
- $ 1 ) ) ) )*EPS ) THEN
- E( M ) = ZERO
- GO TO 30
- END IF
- 20 CONTINUE
- M = N
-*
- 30 CONTINUE
- L = L1
- LSV = L
- LEND = M
- LENDSV = LEND
- L1 = M + 1
- IF( LEND.EQ.L )
- $ GO TO 10
-*
-* Scale submatrix in rows and columns L to LEND
-*
- ANORM = DLANST( 'I', LEND-L+1, D( L ), E( L ) )
- ISCALE = 0
- IF( ANORM.GT.SSFMAX ) THEN
- ISCALE = 1
- CALL DLASCL( 'G', 0, 0, ANORM, SSFMAX, LEND-L+1, 1, D( L ), N,
- $ INFO )
- CALL DLASCL( 'G', 0, 0, ANORM, SSFMAX, LEND-L, 1, E( L ), N,
- $ INFO )
- ELSE IF( ANORM.LT.SSFMIN ) THEN
- ISCALE = 2
- CALL DLASCL( 'G', 0, 0, ANORM, SSFMIN, LEND-L+1, 1, D( L ), N,
- $ INFO )
- CALL DLASCL( 'G', 0, 0, ANORM, SSFMIN, LEND-L, 1, E( L ), N,
- $ INFO )
- END IF
-*
- DO 40 I = L, LEND - 1
- E( I ) = E( I )**2
- 40 CONTINUE
-*
-* Choose between QL and QR iteration
-*
- IF( ABS( D( LEND ) ).LT.ABS( D( L ) ) ) THEN
- LEND = LSV
- L = LENDSV
- END IF
-*
- IF( LEND.GE.L ) THEN
-*
-* QL Iteration
-*
-* Look for small subdiagonal element.
-*
- 50 CONTINUE
- IF( L.NE.LEND ) THEN
- DO 60 M = L, LEND - 1
- IF( ABS( E( M ) ).LE.EPS2*ABS( D( M )*D( M+1 ) ) )
- $ GO TO 70
- 60 CONTINUE
- END IF
- M = LEND
-*
- 70 CONTINUE
- IF( M.LT.LEND )
- $ E( M ) = ZERO
- P = D( L )
- IF( M.EQ.L )
- $ GO TO 90
-*
-* If remaining matrix is 2 by 2, use DLAE2 to compute its
-* eigenvalues.
-*
- IF( M.EQ.L+1 ) THEN
- RTE = SQRT( E( L ) )
- CALL DLAE2( D( L ), RTE, D( L+1 ), RT1, RT2 )
- D( L ) = RT1
- D( L+1 ) = RT2
- E( L ) = ZERO
- L = L + 2
- IF( L.LE.LEND )
- $ GO TO 50
- GO TO 150
- END IF
-*
- IF( JTOT.EQ.NMAXIT )
- $ GO TO 150
- JTOT = JTOT + 1
-*
-* Form shift.
-*
- RTE = SQRT( E( L ) )
- SIGMA = ( D( L+1 )-P ) / ( TWO*RTE )
- R = DLAPY2( SIGMA, ONE )
- SIGMA = P - ( RTE / ( SIGMA+SIGN( R, SIGMA ) ) )
-*
- C = ONE
- S = ZERO
- GAMMA = D( M ) - SIGMA
- P = GAMMA*GAMMA
-*
-* Inner loop
-*
- DO 80 I = M - 1, L, -1
- BB = E( I )
- R = P + BB
- IF( I.NE.M-1 )
- $ E( I+1 ) = S*R
- OLDC = C
- C = P / R
- S = BB / R
- OLDGAM = GAMMA
- ALPHA = D( I )
- GAMMA = C*( ALPHA-SIGMA ) - S*OLDGAM
- D( I+1 ) = OLDGAM + ( ALPHA-GAMMA )
- IF( C.NE.ZERO ) THEN
- P = ( GAMMA*GAMMA ) / C
- ELSE
- P = OLDC*BB
- END IF
- 80 CONTINUE
-*
- E( L ) = S*P
- D( L ) = SIGMA + GAMMA
- GO TO 50
-*
-* Eigenvalue found.
-*
- 90 CONTINUE
- D( L ) = P
-*
- L = L + 1
- IF( L.LE.LEND )
- $ GO TO 50
- GO TO 150
-*
- ELSE
-*
-* QR Iteration
-*
-* Look for small superdiagonal element.
-*
- 100 CONTINUE
- DO 110 M = L, LEND + 1, -1
- IF( ABS( E( M-1 ) ).LE.EPS2*ABS( D( M )*D( M-1 ) ) )
- $ GO TO 120
- 110 CONTINUE
- M = LEND
-*
- 120 CONTINUE
- IF( M.GT.LEND )
- $ E( M-1 ) = ZERO
- P = D( L )
- IF( M.EQ.L )
- $ GO TO 140
-*
-* If remaining matrix is 2 by 2, use DLAE2 to compute its
-* eigenvalues.
-*
- IF( M.EQ.L-1 ) THEN
- RTE = SQRT( E( L-1 ) )
- CALL DLAE2( D( L ), RTE, D( L-1 ), RT1, RT2 )
- D( L ) = RT1
- D( L-1 ) = RT2
- E( L-1 ) = ZERO
- L = L - 2
- IF( L.GE.LEND )
- $ GO TO 100
- GO TO 150
- END IF
-*
- IF( JTOT.EQ.NMAXIT )
- $ GO TO 150
- JTOT = JTOT + 1
-*
-* Form shift.
-*
- RTE = SQRT( E( L-1 ) )
- SIGMA = ( D( L-1 )-P ) / ( TWO*RTE )
- R = DLAPY2( SIGMA, ONE )
- SIGMA = P - ( RTE / ( SIGMA+SIGN( R, SIGMA ) ) )
-*
- C = ONE
- S = ZERO
- GAMMA = D( M ) - SIGMA
- P = GAMMA*GAMMA
-*
-* Inner loop
-*
- DO 130 I = M, L - 1
- BB = E( I )
- R = P + BB
- IF( I.NE.M )
- $ E( I-1 ) = S*R
- OLDC = C
- C = P / R
- S = BB / R
- OLDGAM = GAMMA
- ALPHA = D( I+1 )
- GAMMA = C*( ALPHA-SIGMA ) - S*OLDGAM
- D( I ) = OLDGAM + ( ALPHA-GAMMA )
- IF( C.NE.ZERO ) THEN
- P = ( GAMMA*GAMMA ) / C
- ELSE
- P = OLDC*BB
- END IF
- 130 CONTINUE
-*
- E( L-1 ) = S*P
- D( L ) = SIGMA + GAMMA
- GO TO 100
-*
-* Eigenvalue found.
-*
- 140 CONTINUE
- D( L ) = P
-*
- L = L - 1
- IF( L.GE.LEND )
- $ GO TO 100
- GO TO 150
-*
- END IF
-*
-* Undo scaling if necessary
-*
- 150 CONTINUE
- IF( ISCALE.EQ.1 )
- $ CALL DLASCL( 'G', 0, 0, SSFMAX, ANORM, LENDSV-LSV+1, 1,
- $ D( LSV ), N, INFO )
- IF( ISCALE.EQ.2 )
- $ CALL DLASCL( 'G', 0, 0, SSFMIN, ANORM, LENDSV-LSV+1, 1,
- $ D( LSV ), N, INFO )
-*
-* Check for no convergence to an eigenvalue after a total
-* of N*MAXIT iterations.
-*
- IF( JTOT.LT.NMAXIT )
- $ GO TO 10
- DO 160 I = 1, N - 1
- IF( E( I ).NE.ZERO )
- $ INFO = INFO + 1
- 160 CONTINUE
- GO TO 180
-*
-* Sort eigenvalues in increasing order.
-*
- 170 CONTINUE
- CALL DLASRT( 'I', N, D, INFO )
-*
- 180 CONTINUE
- RETURN
-*
-* End of DSTERF
-*
- END
diff --git a/src/lib/lapack/dsycon.f b/src/lib/lapack/dsycon.f
deleted file mode 100644
index 711b48ca..00000000
--- a/src/lib/lapack/dsycon.f
+++ /dev/null
@@ -1,165 +0,0 @@
- SUBROUTINE DSYCON( UPLO, N, A, LDA, IPIV, ANORM, RCOND, WORK,
- $ IWORK, INFO )
-*
-* -- LAPACK routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* Modified to call DLACN2 in place of DLACON, 5 Feb 03, SJH.
-*
-* .. Scalar Arguments ..
- CHARACTER UPLO
- INTEGER INFO, LDA, N
- DOUBLE PRECISION ANORM, RCOND
-* ..
-* .. Array Arguments ..
- INTEGER IPIV( * ), IWORK( * )
- DOUBLE PRECISION A( LDA, * ), WORK( * )
-* ..
-*
-* Purpose
-* =======
-*
-* DSYCON estimates the reciprocal of the condition number (in the
-* 1-norm) of a real symmetric matrix A using the factorization
-* A = U*D*U**T or A = L*D*L**T computed by DSYTRF.
-*
-* An estimate is obtained for norm(inv(A)), and the reciprocal of the
-* condition number is computed as RCOND = 1 / (ANORM * norm(inv(A))).
-*
-* Arguments
-* =========
-*
-* UPLO (input) CHARACTER*1
-* Specifies whether the details of the factorization are stored
-* as an upper or lower triangular matrix.
-* = 'U': Upper triangular, form is A = U*D*U**T;
-* = 'L': Lower triangular, form is A = L*D*L**T.
-*
-* N (input) INTEGER
-* The order of the matrix A. N >= 0.
-*
-* A (input) DOUBLE PRECISION array, dimension (LDA,N)
-* The block diagonal matrix D and the multipliers used to
-* obtain the factor U or L as computed by DSYTRF.
-*
-* LDA (input) INTEGER
-* The leading dimension of the array A. LDA >= max(1,N).
-*
-* IPIV (input) INTEGER array, dimension (N)
-* Details of the interchanges and the block structure of D
-* as determined by DSYTRF.
-*
-* ANORM (input) DOUBLE PRECISION
-* The 1-norm of the original matrix A.
-*
-* RCOND (output) DOUBLE PRECISION
-* The reciprocal of the condition number of the matrix A,
-* computed as RCOND = 1/(ANORM * AINVNM), where AINVNM is an
-* estimate of the 1-norm of inv(A) computed in this routine.
-*
-* WORK (workspace) DOUBLE PRECISION array, dimension (2*N)
-*
-* IWORK (workspace) INTEGER array, dimension (N)
-*
-* INFO (output) INTEGER
-* = 0: successful exit
-* < 0: if INFO = -i, the i-th argument had an illegal value
-*
-* =====================================================================
-*
-* .. Parameters ..
- DOUBLE PRECISION ONE, ZERO
- PARAMETER ( ONE = 1.0D+0, ZERO = 0.0D+0 )
-* ..
-* .. Local Scalars ..
- LOGICAL UPPER
- INTEGER I, KASE
- DOUBLE PRECISION AINVNM
-* ..
-* .. Local Arrays ..
- INTEGER ISAVE( 3 )
-* ..
-* .. External Functions ..
- LOGICAL LSAME
- EXTERNAL LSAME
-* ..
-* .. External Subroutines ..
- EXTERNAL DLACN2, DSYTRS, XERBLA
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC MAX
-* ..
-* .. Executable Statements ..
-*
-* Test the input parameters.
-*
- INFO = 0
- UPPER = LSAME( UPLO, 'U' )
- IF( .NOT.UPPER .AND. .NOT.LSAME( UPLO, 'L' ) ) THEN
- INFO = -1
- ELSE IF( N.LT.0 ) THEN
- INFO = -2
- ELSE IF( LDA.LT.MAX( 1, N ) ) THEN
- INFO = -4
- ELSE IF( ANORM.LT.ZERO ) THEN
- INFO = -6
- END IF
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'DSYCON', -INFO )
- RETURN
- END IF
-*
-* Quick return if possible
-*
- RCOND = ZERO
- IF( N.EQ.0 ) THEN
- RCOND = ONE
- RETURN
- ELSE IF( ANORM.LE.ZERO ) THEN
- RETURN
- END IF
-*
-* Check that the diagonal matrix D is nonsingular.
-*
- IF( UPPER ) THEN
-*
-* Upper triangular storage: examine D from bottom to top
-*
- DO 10 I = N, 1, -1
- IF( IPIV( I ).GT.0 .AND. A( I, I ).EQ.ZERO )
- $ RETURN
- 10 CONTINUE
- ELSE
-*
-* Lower triangular storage: examine D from top to bottom.
-*
- DO 20 I = 1, N
- IF( IPIV( I ).GT.0 .AND. A( I, I ).EQ.ZERO )
- $ RETURN
- 20 CONTINUE
- END IF
-*
-* Estimate the 1-norm of the inverse.
-*
- KASE = 0
- 30 CONTINUE
- CALL DLACN2( N, WORK( N+1 ), WORK, IWORK, AINVNM, KASE, ISAVE )
- IF( KASE.NE.0 ) THEN
-*
-* Multiply by inv(L*D*L') or inv(U*D*U').
-*
- CALL DSYTRS( UPLO, N, 1, A, LDA, IPIV, WORK, N, INFO )
- GO TO 30
- END IF
-*
-* Compute the estimate of the reciprocal condition number.
-*
- IF( AINVNM.NE.ZERO )
- $ RCOND = ( ONE / AINVNM ) / ANORM
-*
- RETURN
-*
-* End of DSYCON
-*
- END
diff --git a/src/lib/lapack/dsyev.f b/src/lib/lapack/dsyev.f
deleted file mode 100644
index d73600a2..00000000
--- a/src/lib/lapack/dsyev.f
+++ /dev/null
@@ -1,211 +0,0 @@
- SUBROUTINE DSYEV( JOBZ, UPLO, N, A, LDA, W, WORK, LWORK, INFO )
-*
-* -- LAPACK driver routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- CHARACTER JOBZ, UPLO
- INTEGER INFO, LDA, LWORK, N
-* ..
-* .. Array Arguments ..
- DOUBLE PRECISION A( LDA, * ), W( * ), WORK( * )
-* ..
-*
-* Purpose
-* =======
-*
-* DSYEV computes all eigenvalues and, optionally, eigenvectors of a
-* real symmetric matrix A.
-*
-* Arguments
-* =========
-*
-* JOBZ (input) CHARACTER*1
-* = 'N': Compute eigenvalues only;
-* = 'V': Compute eigenvalues and eigenvectors.
-*
-* UPLO (input) CHARACTER*1
-* = 'U': Upper triangle of A is stored;
-* = 'L': Lower triangle of A is stored.
-*
-* N (input) INTEGER
-* The order of the matrix A. N >= 0.
-*
-* A (input/output) DOUBLE PRECISION array, dimension (LDA, N)
-* On entry, the symmetric matrix A. If UPLO = 'U', the
-* leading N-by-N upper triangular part of A contains the
-* upper triangular part of the matrix A. If UPLO = 'L',
-* the leading N-by-N lower triangular part of A contains
-* the lower triangular part of the matrix A.
-* On exit, if JOBZ = 'V', then if INFO = 0, A contains the
-* orthonormal eigenvectors of the matrix A.
-* If JOBZ = 'N', then on exit the lower triangle (if UPLO='L')
-* or the upper triangle (if UPLO='U') of A, including the
-* diagonal, is destroyed.
-*
-* LDA (input) INTEGER
-* The leading dimension of the array A. LDA >= max(1,N).
-*
-* W (output) DOUBLE PRECISION array, dimension (N)
-* If INFO = 0, the eigenvalues in ascending order.
-*
-* WORK (workspace/output) DOUBLE PRECISION array, dimension (MAX(1,LWORK))
-* On exit, if INFO = 0, WORK(1) returns the optimal LWORK.
-*
-* LWORK (input) INTEGER
-* The length of the array WORK. LWORK >= max(1,3*N-1).
-* For optimal efficiency, LWORK >= (NB+2)*N,
-* where NB is the blocksize for DSYTRD returned by ILAENV.
-*
-* If LWORK = -1, then a workspace query is assumed; the routine
-* only calculates the optimal size of the WORK array, returns
-* this value as the first entry of the WORK array, and no error
-* message related to LWORK is issued by XERBLA.
-*
-* INFO (output) INTEGER
-* = 0: successful exit
-* < 0: if INFO = -i, the i-th argument had an illegal value
-* > 0: if INFO = i, the algorithm failed to converge; i
-* off-diagonal elements of an intermediate tridiagonal
-* form did not converge to zero.
-*
-* =====================================================================
-*
-* .. Parameters ..
- DOUBLE PRECISION ZERO, ONE
- PARAMETER ( ZERO = 0.0D0, ONE = 1.0D0 )
-* ..
-* .. Local Scalars ..
- LOGICAL LOWER, LQUERY, WANTZ
- INTEGER IINFO, IMAX, INDE, INDTAU, INDWRK, ISCALE,
- $ LLWORK, LWKOPT, NB
- DOUBLE PRECISION ANRM, BIGNUM, EPS, RMAX, RMIN, SAFMIN, SIGMA,
- $ SMLNUM
-* ..
-* .. External Functions ..
- LOGICAL LSAME
- INTEGER ILAENV
- DOUBLE PRECISION DLAMCH, DLANSY
- EXTERNAL LSAME, ILAENV, DLAMCH, DLANSY
-* ..
-* .. External Subroutines ..
- EXTERNAL DLASCL, DORGTR, DSCAL, DSTEQR, DSTERF, DSYTRD,
- $ XERBLA
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC MAX, SQRT
-* ..
-* .. Executable Statements ..
-*
-* Test the input parameters.
-*
- WANTZ = LSAME( JOBZ, 'V' )
- LOWER = LSAME( UPLO, 'L' )
- LQUERY = ( LWORK.EQ.-1 )
-*
- INFO = 0
- IF( .NOT.( WANTZ .OR. LSAME( JOBZ, 'N' ) ) ) THEN
- INFO = -1
- ELSE IF( .NOT.( LOWER .OR. LSAME( UPLO, 'U' ) ) ) THEN
- INFO = -2
- ELSE IF( N.LT.0 ) THEN
- INFO = -3
- ELSE IF( LDA.LT.MAX( 1, N ) ) THEN
- INFO = -5
- END IF
-*
- IF( INFO.EQ.0 ) THEN
- NB = ILAENV( 1, 'DSYTRD', UPLO, N, -1, -1, -1 )
- LWKOPT = MAX( 1, ( NB+2 )*N )
- WORK( 1 ) = LWKOPT
-*
- IF( LWORK.LT.MAX( 1, 3*N-1 ) .AND. .NOT.LQUERY )
- $ INFO = -8
- END IF
-*
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'DSYEV ', -INFO )
- RETURN
- ELSE IF( LQUERY ) THEN
- RETURN
- END IF
-*
-* Quick return if possible
-*
- IF( N.EQ.0 ) THEN
- RETURN
- END IF
-*
- IF( N.EQ.1 ) THEN
- W( 1 ) = A( 1, 1 )
- WORK( 1 ) = 2
- IF( WANTZ )
- $ A( 1, 1 ) = ONE
- RETURN
- END IF
-*
-* Get machine constants.
-*
- SAFMIN = DLAMCH( 'Safe minimum' )
- EPS = DLAMCH( 'Precision' )
- SMLNUM = SAFMIN / EPS
- BIGNUM = ONE / SMLNUM
- RMIN = SQRT( SMLNUM )
- RMAX = SQRT( BIGNUM )
-*
-* Scale matrix to allowable range, if necessary.
-*
- ANRM = DLANSY( 'M', UPLO, N, A, LDA, WORK )
- ISCALE = 0
- IF( ANRM.GT.ZERO .AND. ANRM.LT.RMIN ) THEN
- ISCALE = 1
- SIGMA = RMIN / ANRM
- ELSE IF( ANRM.GT.RMAX ) THEN
- ISCALE = 1
- SIGMA = RMAX / ANRM
- END IF
- IF( ISCALE.EQ.1 )
- $ CALL DLASCL( UPLO, 0, 0, ONE, SIGMA, N, N, A, LDA, INFO )
-*
-* Call DSYTRD to reduce symmetric matrix to tridiagonal form.
-*
- INDE = 1
- INDTAU = INDE + N
- INDWRK = INDTAU + N
- LLWORK = LWORK - INDWRK + 1
- CALL DSYTRD( UPLO, N, A, LDA, W, WORK( INDE ), WORK( INDTAU ),
- $ WORK( INDWRK ), LLWORK, IINFO )
-*
-* For eigenvalues only, call DSTERF. For eigenvectors, first call
-* DORGTR to generate the orthogonal matrix, then call DSTEQR.
-*
- IF( .NOT.WANTZ ) THEN
- CALL DSTERF( N, W, WORK( INDE ), INFO )
- ELSE
- CALL DORGTR( UPLO, N, A, LDA, WORK( INDTAU ), WORK( INDWRK ),
- $ LLWORK, IINFO )
- CALL DSTEQR( JOBZ, N, W, WORK( INDE ), A, LDA, WORK( INDTAU ),
- $ INFO )
- END IF
-*
-* If matrix was scaled, then rescale eigenvalues appropriately.
-*
- IF( ISCALE.EQ.1 ) THEN
- IF( INFO.EQ.0 ) THEN
- IMAX = N
- ELSE
- IMAX = INFO - 1
- END IF
- CALL DSCAL( IMAX, ONE / SIGMA, W, 1 )
- END IF
-*
-* Set WORK(1) to optimal workspace size.
-*
- WORK( 1 ) = LWKOPT
-*
- RETURN
-*
-* End of DSYEV
-*
- END
diff --git a/src/lib/lapack/dsysv.f b/src/lib/lapack/dsysv.f
deleted file mode 100644
index add53850..00000000
--- a/src/lib/lapack/dsysv.f
+++ /dev/null
@@ -1,174 +0,0 @@
- SUBROUTINE DSYSV( UPLO, N, NRHS, A, LDA, IPIV, B, LDB, WORK,
- $ LWORK, INFO )
-*
-* -- LAPACK driver routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- CHARACTER UPLO
- INTEGER INFO, LDA, LDB, LWORK, N, NRHS
-* ..
-* .. Array Arguments ..
- INTEGER IPIV( * )
- DOUBLE PRECISION A( LDA, * ), B( LDB, * ), WORK( * )
-* ..
-*
-* Purpose
-* =======
-*
-* DSYSV computes the solution to a real system of linear equations
-* A * X = B,
-* where A is an N-by-N symmetric matrix and X and B are N-by-NRHS
-* matrices.
-*
-* The diagonal pivoting method is used to factor A as
-* A = U * D * U**T, if UPLO = 'U', or
-* A = L * D * L**T, if UPLO = 'L',
-* where U (or L) is a product of permutation and unit upper (lower)
-* triangular matrices, and D is symmetric and block diagonal with
-* 1-by-1 and 2-by-2 diagonal blocks. The factored form of A is then
-* used to solve the system of equations A * X = B.
-*
-* Arguments
-* =========
-*
-* UPLO (input) CHARACTER*1
-* = 'U': Upper triangle of A is stored;
-* = 'L': Lower triangle of A is stored.
-*
-* N (input) INTEGER
-* The number of linear equations, i.e., the order of the
-* matrix A. N >= 0.
-*
-* NRHS (input) INTEGER
-* The number of right hand sides, i.e., the number of columns
-* of the matrix B. NRHS >= 0.
-*
-* A (input/output) DOUBLE PRECISION array, dimension (LDA,N)
-* On entry, the symmetric matrix A. If UPLO = 'U', the leading
-* N-by-N upper triangular part of A contains the upper
-* triangular part of the matrix A, and the strictly lower
-* triangular part of A is not referenced. If UPLO = 'L', the
-* leading N-by-N lower triangular part of A contains the lower
-* triangular part of the matrix A, and the strictly upper
-* triangular part of A is not referenced.
-*
-* On exit, if INFO = 0, the block diagonal matrix D and the
-* multipliers used to obtain the factor U or L from the
-* factorization A = U*D*U**T or A = L*D*L**T as computed by
-* DSYTRF.
-*
-* LDA (input) INTEGER
-* The leading dimension of the array A. LDA >= max(1,N).
-*
-* IPIV (output) INTEGER array, dimension (N)
-* Details of the interchanges and the block structure of D, as
-* determined by DSYTRF. If IPIV(k) > 0, then rows and columns
-* k and IPIV(k) were interchanged, and D(k,k) is a 1-by-1
-* diagonal block. If UPLO = 'U' and IPIV(k) = IPIV(k-1) < 0,
-* then rows and columns k-1 and -IPIV(k) were interchanged and
-* D(k-1:k,k-1:k) is a 2-by-2 diagonal block. If UPLO = 'L' and
-* IPIV(k) = IPIV(k+1) < 0, then rows and columns k+1 and
-* -IPIV(k) were interchanged and D(k:k+1,k:k+1) is a 2-by-2
-* diagonal block.
-*
-* B (input/output) DOUBLE PRECISION array, dimension (LDB,NRHS)
-* On entry, the N-by-NRHS right hand side matrix B.
-* On exit, if INFO = 0, the N-by-NRHS solution matrix X.
-*
-* LDB (input) INTEGER
-* The leading dimension of the array B. LDB >= max(1,N).
-*
-* WORK (workspace/output) DOUBLE PRECISION array, dimension (MAX(1,LWORK))
-* On exit, if INFO = 0, WORK(1) returns the optimal LWORK.
-*
-* LWORK (input) INTEGER
-* The length of WORK. LWORK >= 1, and for best performance
-* LWORK >= max(1,N*NB), where NB is the optimal blocksize for
-* DSYTRF.
-*
-* If LWORK = -1, then a workspace query is assumed; the routine
-* only calculates the optimal size of the WORK array, returns
-* this value as the first entry of the WORK array, and no error
-* message related to LWORK is issued by XERBLA.
-*
-* INFO (output) INTEGER
-* = 0: successful exit
-* < 0: if INFO = -i, the i-th argument had an illegal value
-* > 0: if INFO = i, D(i,i) is exactly zero. The factorization
-* has been completed, but the block diagonal matrix D is
-* exactly singular, so the solution could not be computed.
-*
-* =====================================================================
-*
-* .. Local Scalars ..
- LOGICAL LQUERY
- INTEGER LWKOPT, NB
-* ..
-* .. External Functions ..
- LOGICAL LSAME
- INTEGER ILAENV
- EXTERNAL LSAME, ILAENV
-* ..
-* .. External Subroutines ..
- EXTERNAL DSYTRF, DSYTRS, XERBLA
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC MAX
-* ..
-* .. Executable Statements ..
-*
-* Test the input parameters.
-*
- INFO = 0
- LQUERY = ( LWORK.EQ.-1 )
- IF( .NOT.LSAME( UPLO, 'U' ) .AND. .NOT.LSAME( UPLO, 'L' ) ) THEN
- INFO = -1
- ELSE IF( N.LT.0 ) THEN
- INFO = -2
- ELSE IF( NRHS.LT.0 ) THEN
- INFO = -3
- ELSE IF( LDA.LT.MAX( 1, N ) ) THEN
- INFO = -5
- ELSE IF( LDB.LT.MAX( 1, N ) ) THEN
- INFO = -8
- ELSE IF( LWORK.LT.1 .AND. .NOT.LQUERY ) THEN
- INFO = -10
- END IF
-*
- IF( INFO.EQ.0 ) THEN
- IF( N.EQ.0 ) THEN
- LWKOPT = 1
- ELSE
- NB = ILAENV( 1, 'DSYTRF', UPLO, N, -1, -1, -1 )
- LWKOPT = N*NB
- END IF
- WORK( 1 ) = LWKOPT
- END IF
-*
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'DSYSV ', -INFO )
- RETURN
- ELSE IF( LQUERY ) THEN
- RETURN
- END IF
-*
-* Compute the factorization A = U*D*U' or A = L*D*L'.
-*
- CALL DSYTRF( UPLO, N, A, LDA, IPIV, WORK, LWORK, INFO )
- IF( INFO.EQ.0 ) THEN
-*
-* Solve the system A*X = B, overwriting B with X.
-*
- CALL DSYTRS( UPLO, N, NRHS, A, LDA, IPIV, B, LDB, INFO )
-*
- END IF
-*
- WORK( 1 ) = LWKOPT
-*
- RETURN
-*
-* End of DSYSV
-*
- END
diff --git a/src/lib/lapack/dsytd2.f b/src/lib/lapack/dsytd2.f
deleted file mode 100644
index c696818e..00000000
--- a/src/lib/lapack/dsytd2.f
+++ /dev/null
@@ -1,248 +0,0 @@
- SUBROUTINE DSYTD2( UPLO, N, A, LDA, D, E, TAU, INFO )
-*
-* -- LAPACK routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- CHARACTER UPLO
- INTEGER INFO, LDA, N
-* ..
-* .. Array Arguments ..
- DOUBLE PRECISION A( LDA, * ), D( * ), E( * ), TAU( * )
-* ..
-*
-* Purpose
-* =======
-*
-* DSYTD2 reduces a real symmetric matrix A to symmetric tridiagonal
-* form T by an orthogonal similarity transformation: Q' * A * Q = T.
-*
-* Arguments
-* =========
-*
-* UPLO (input) CHARACTER*1
-* Specifies whether the upper or lower triangular part of the
-* symmetric matrix A is stored:
-* = 'U': Upper triangular
-* = 'L': Lower triangular
-*
-* N (input) INTEGER
-* The order of the matrix A. N >= 0.
-*
-* A (input/output) DOUBLE PRECISION array, dimension (LDA,N)
-* On entry, the symmetric matrix A. If UPLO = 'U', the leading
-* n-by-n upper triangular part of A contains the upper
-* triangular part of the matrix A, and the strictly lower
-* triangular part of A is not referenced. If UPLO = 'L', the
-* leading n-by-n lower triangular part of A contains the lower
-* triangular part of the matrix A, and the strictly upper
-* triangular part of A is not referenced.
-* On exit, if UPLO = 'U', the diagonal and first superdiagonal
-* of A are overwritten by the corresponding elements of the
-* tridiagonal matrix T, and the elements above the first
-* superdiagonal, with the array TAU, represent the orthogonal
-* matrix Q as a product of elementary reflectors; if UPLO
-* = 'L', the diagonal and first subdiagonal of A are over-
-* written by the corresponding elements of the tridiagonal
-* matrix T, and the elements below the first subdiagonal, with
-* the array TAU, represent the orthogonal matrix Q as a product
-* of elementary reflectors. See Further Details.
-*
-* LDA (input) INTEGER
-* The leading dimension of the array A. LDA >= max(1,N).
-*
-* D (output) DOUBLE PRECISION array, dimension (N)
-* The diagonal elements of the tridiagonal matrix T:
-* D(i) = A(i,i).
-*
-* E (output) DOUBLE PRECISION array, dimension (N-1)
-* The off-diagonal elements of the tridiagonal matrix T:
-* E(i) = A(i,i+1) if UPLO = 'U', E(i) = A(i+1,i) if UPLO = 'L'.
-*
-* TAU (output) DOUBLE PRECISION array, dimension (N-1)
-* The scalar factors of the elementary reflectors (see Further
-* Details).
-*
-* INFO (output) INTEGER
-* = 0: successful exit
-* < 0: if INFO = -i, the i-th argument had an illegal value.
-*
-* Further Details
-* ===============
-*
-* If UPLO = 'U', the matrix Q is represented as a product of elementary
-* reflectors
-*
-* Q = H(n-1) . . . H(2) H(1).
-*
-* Each H(i) has the form
-*
-* H(i) = I - tau * v * v'
-*
-* where tau is a real scalar, and v is a real vector with
-* v(i+1:n) = 0 and v(i) = 1; v(1:i-1) is stored on exit in
-* A(1:i-1,i+1), and tau in TAU(i).
-*
-* If UPLO = 'L', the matrix Q is represented as a product of elementary
-* reflectors
-*
-* Q = H(1) H(2) . . . H(n-1).
-*
-* Each H(i) has the form
-*
-* H(i) = I - tau * v * v'
-*
-* where tau is a real scalar, and v is a real vector with
-* v(1:i) = 0 and v(i+1) = 1; v(i+2:n) is stored on exit in A(i+2:n,i),
-* and tau in TAU(i).
-*
-* The contents of A on exit are illustrated by the following examples
-* with n = 5:
-*
-* if UPLO = 'U': if UPLO = 'L':
-*
-* ( d e v2 v3 v4 ) ( d )
-* ( d e v3 v4 ) ( e d )
-* ( d e v4 ) ( v1 e d )
-* ( d e ) ( v1 v2 e d )
-* ( d ) ( v1 v2 v3 e d )
-*
-* where d and e denote diagonal and off-diagonal elements of T, and vi
-* denotes an element of the vector defining H(i).
-*
-* =====================================================================
-*
-* .. Parameters ..
- DOUBLE PRECISION ONE, ZERO, HALF
- PARAMETER ( ONE = 1.0D0, ZERO = 0.0D0,
- $ HALF = 1.0D0 / 2.0D0 )
-* ..
-* .. Local Scalars ..
- LOGICAL UPPER
- INTEGER I
- DOUBLE PRECISION ALPHA, TAUI
-* ..
-* .. External Subroutines ..
- EXTERNAL DAXPY, DLARFG, DSYMV, DSYR2, XERBLA
-* ..
-* .. External Functions ..
- LOGICAL LSAME
- DOUBLE PRECISION DDOT
- EXTERNAL LSAME, DDOT
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC MAX, MIN
-* ..
-* .. Executable Statements ..
-*
-* Test the input parameters
-*
- INFO = 0
- UPPER = LSAME( UPLO, 'U' )
- IF( .NOT.UPPER .AND. .NOT.LSAME( UPLO, 'L' ) ) THEN
- INFO = -1
- ELSE IF( N.LT.0 ) THEN
- INFO = -2
- ELSE IF( LDA.LT.MAX( 1, N ) ) THEN
- INFO = -4
- END IF
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'DSYTD2', -INFO )
- RETURN
- END IF
-*
-* Quick return if possible
-*
- IF( N.LE.0 )
- $ RETURN
-*
- IF( UPPER ) THEN
-*
-* Reduce the upper triangle of A
-*
- DO 10 I = N - 1, 1, -1
-*
-* Generate elementary reflector H(i) = I - tau * v * v'
-* to annihilate A(1:i-1,i+1)
-*
- CALL DLARFG( I, A( I, I+1 ), A( 1, I+1 ), 1, TAUI )
- E( I ) = A( I, I+1 )
-*
- IF( TAUI.NE.ZERO ) THEN
-*
-* Apply H(i) from both sides to A(1:i,1:i)
-*
- A( I, I+1 ) = ONE
-*
-* Compute x := tau * A * v storing x in TAU(1:i)
-*
- CALL DSYMV( UPLO, I, TAUI, A, LDA, A( 1, I+1 ), 1, ZERO,
- $ TAU, 1 )
-*
-* Compute w := x - 1/2 * tau * (x'*v) * v
-*
- ALPHA = -HALF*TAUI*DDOT( I, TAU, 1, A( 1, I+1 ), 1 )
- CALL DAXPY( I, ALPHA, A( 1, I+1 ), 1, TAU, 1 )
-*
-* Apply the transformation as a rank-2 update:
-* A := A - v * w' - w * v'
-*
- CALL DSYR2( UPLO, I, -ONE, A( 1, I+1 ), 1, TAU, 1, A,
- $ LDA )
-*
- A( I, I+1 ) = E( I )
- END IF
- D( I+1 ) = A( I+1, I+1 )
- TAU( I ) = TAUI
- 10 CONTINUE
- D( 1 ) = A( 1, 1 )
- ELSE
-*
-* Reduce the lower triangle of A
-*
- DO 20 I = 1, N - 1
-*
-* Generate elementary reflector H(i) = I - tau * v * v'
-* to annihilate A(i+2:n,i)
-*
- CALL DLARFG( N-I, A( I+1, I ), A( MIN( I+2, N ), I ), 1,
- $ TAUI )
- E( I ) = A( I+1, I )
-*
- IF( TAUI.NE.ZERO ) THEN
-*
-* Apply H(i) from both sides to A(i+1:n,i+1:n)
-*
- A( I+1, I ) = ONE
-*
-* Compute x := tau * A * v storing y in TAU(i:n-1)
-*
- CALL DSYMV( UPLO, N-I, TAUI, A( I+1, I+1 ), LDA,
- $ A( I+1, I ), 1, ZERO, TAU( I ), 1 )
-*
-* Compute w := x - 1/2 * tau * (x'*v) * v
-*
- ALPHA = -HALF*TAUI*DDOT( N-I, TAU( I ), 1, A( I+1, I ),
- $ 1 )
- CALL DAXPY( N-I, ALPHA, A( I+1, I ), 1, TAU( I ), 1 )
-*
-* Apply the transformation as a rank-2 update:
-* A := A - v * w' - w * v'
-*
- CALL DSYR2( UPLO, N-I, -ONE, A( I+1, I ), 1, TAU( I ), 1,
- $ A( I+1, I+1 ), LDA )
-*
- A( I+1, I ) = E( I )
- END IF
- D( I ) = A( I, I )
- TAU( I ) = TAUI
- 20 CONTINUE
- D( N ) = A( N, N )
- END IF
-*
- RETURN
-*
-* End of DSYTD2
-*
- END
diff --git a/src/lib/lapack/dsytf2.f b/src/lib/lapack/dsytf2.f
deleted file mode 100644
index d5234625..00000000
--- a/src/lib/lapack/dsytf2.f
+++ /dev/null
@@ -1,521 +0,0 @@
- SUBROUTINE DSYTF2( UPLO, N, A, LDA, IPIV, INFO )
-*
-* -- LAPACK routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- CHARACTER UPLO
- INTEGER INFO, LDA, N
-* ..
-* .. Array Arguments ..
- INTEGER IPIV( * )
- DOUBLE PRECISION A( LDA, * )
-* ..
-*
-* Purpose
-* =======
-*
-* DSYTF2 computes the factorization of a real symmetric matrix A using
-* the Bunch-Kaufman diagonal pivoting method:
-*
-* A = U*D*U' or A = L*D*L'
-*
-* where U (or L) is a product of permutation and unit upper (lower)
-* triangular matrices, U' is the transpose of U, and D is symmetric and
-* block diagonal with 1-by-1 and 2-by-2 diagonal blocks.
-*
-* This is the unblocked version of the algorithm, calling Level 2 BLAS.
-*
-* Arguments
-* =========
-*
-* UPLO (input) CHARACTER*1
-* Specifies whether the upper or lower triangular part of the
-* symmetric matrix A is stored:
-* = 'U': Upper triangular
-* = 'L': Lower triangular
-*
-* N (input) INTEGER
-* The order of the matrix A. N >= 0.
-*
-* A (input/output) DOUBLE PRECISION array, dimension (LDA,N)
-* On entry, the symmetric matrix A. If UPLO = 'U', the leading
-* n-by-n upper triangular part of A contains the upper
-* triangular part of the matrix A, and the strictly lower
-* triangular part of A is not referenced. If UPLO = 'L', the
-* leading n-by-n lower triangular part of A contains the lower
-* triangular part of the matrix A, and the strictly upper
-* triangular part of A is not referenced.
-*
-* On exit, the block diagonal matrix D and the multipliers used
-* to obtain the factor U or L (see below for further details).
-*
-* LDA (input) INTEGER
-* The leading dimension of the array A. LDA >= max(1,N).
-*
-* IPIV (output) INTEGER array, dimension (N)
-* Details of the interchanges and the block structure of D.
-* If IPIV(k) > 0, then rows and columns k and IPIV(k) were
-* interchanged and D(k,k) is a 1-by-1 diagonal block.
-* If UPLO = 'U' and IPIV(k) = IPIV(k-1) < 0, then rows and
-* columns k-1 and -IPIV(k) were interchanged and D(k-1:k,k-1:k)
-* is a 2-by-2 diagonal block. If UPLO = 'L' and IPIV(k) =
-* IPIV(k+1) < 0, then rows and columns k+1 and -IPIV(k) were
-* interchanged and D(k:k+1,k:k+1) is a 2-by-2 diagonal block.
-*
-* INFO (output) INTEGER
-* = 0: successful exit
-* < 0: if INFO = -k, the k-th argument had an illegal value
-* > 0: if INFO = k, D(k,k) is exactly zero. The factorization
-* has been completed, but the block diagonal matrix D is
-* exactly singular, and division by zero will occur if it
-* is used to solve a system of equations.
-*
-* Further Details
-* ===============
-*
-* 09-29-06 - patch from
-* Bobby Cheng, MathWorks
-*
-* Replace l.204 and l.372
-* IF( MAX( ABSAKK, COLMAX ).EQ.ZERO ) THEN
-* by
-* IF( (MAX( ABSAKK, COLMAX ).EQ.ZERO) .OR. DISNAN(ABSAKK) ) THEN
-*
-* 01-01-96 - Based on modifications by
-* J. Lewis, Boeing Computer Services Company
-* A. Petitet, Computer Science Dept., Univ. of Tenn., Knoxville, USA
-* 1-96 - Based on modifications by J. Lewis, Boeing Computer Services
-* Company
-*
-* If UPLO = 'U', then A = U*D*U', where
-* U = P(n)*U(n)* ... *P(k)U(k)* ...,
-* i.e., U is a product of terms P(k)*U(k), where k decreases from n to
-* 1 in steps of 1 or 2, and D is a block diagonal matrix with 1-by-1
-* and 2-by-2 diagonal blocks D(k). P(k) is a permutation matrix as
-* defined by IPIV(k), and U(k) is a unit upper triangular matrix, such
-* that if the diagonal block D(k) is of order s (s = 1 or 2), then
-*
-* ( I v 0 ) k-s
-* U(k) = ( 0 I 0 ) s
-* ( 0 0 I ) n-k
-* k-s s n-k
-*
-* If s = 1, D(k) overwrites A(k,k), and v overwrites A(1:k-1,k).
-* If s = 2, the upper triangle of D(k) overwrites A(k-1,k-1), A(k-1,k),
-* and A(k,k), and v overwrites A(1:k-2,k-1:k).
-*
-* If UPLO = 'L', then A = L*D*L', where
-* L = P(1)*L(1)* ... *P(k)*L(k)* ...,
-* i.e., L is a product of terms P(k)*L(k), where k increases from 1 to
-* n in steps of 1 or 2, and D is a block diagonal matrix with 1-by-1
-* and 2-by-2 diagonal blocks D(k). P(k) is a permutation matrix as
-* defined by IPIV(k), and L(k) is a unit lower triangular matrix, such
-* that if the diagonal block D(k) is of order s (s = 1 or 2), then
-*
-* ( I 0 0 ) k-1
-* L(k) = ( 0 I 0 ) s
-* ( 0 v I ) n-k-s+1
-* k-1 s n-k-s+1
-*
-* If s = 1, D(k) overwrites A(k,k), and v overwrites A(k+1:n,k).
-* If s = 2, the lower triangle of D(k) overwrites A(k,k), A(k+1,k),
-* and A(k+1,k+1), and v overwrites A(k+2:n,k:k+1).
-*
-* =====================================================================
-*
-* .. Parameters ..
- DOUBLE PRECISION ZERO, ONE
- PARAMETER ( ZERO = 0.0D+0, ONE = 1.0D+0 )
- DOUBLE PRECISION EIGHT, SEVTEN
- PARAMETER ( EIGHT = 8.0D+0, SEVTEN = 17.0D+0 )
-* ..
-* .. Local Scalars ..
- LOGICAL UPPER
- INTEGER I, IMAX, J, JMAX, K, KK, KP, KSTEP
- DOUBLE PRECISION ABSAKK, ALPHA, COLMAX, D11, D12, D21, D22, R1,
- $ ROWMAX, T, WK, WKM1, WKP1
-* ..
-* .. External Functions ..
- LOGICAL LSAME, DISNAN
- INTEGER IDAMAX
- EXTERNAL LSAME, IDAMAX, DISNAN
-* ..
-* .. External Subroutines ..
- EXTERNAL DSCAL, DSWAP, DSYR, XERBLA
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC ABS, MAX, SQRT
-* ..
-* .. Executable Statements ..
-*
-* Test the input parameters.
-*
- INFO = 0
- UPPER = LSAME( UPLO, 'U' )
- IF( .NOT.UPPER .AND. .NOT.LSAME( UPLO, 'L' ) ) THEN
- INFO = -1
- ELSE IF( N.LT.0 ) THEN
- INFO = -2
- ELSE IF( LDA.LT.MAX( 1, N ) ) THEN
- INFO = -4
- END IF
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'DSYTF2', -INFO )
- RETURN
- END IF
-*
-* Initialize ALPHA for use in choosing pivot block size.
-*
- ALPHA = ( ONE+SQRT( SEVTEN ) ) / EIGHT
-*
- IF( UPPER ) THEN
-*
-* Factorize A as U*D*U' using the upper triangle of A
-*
-* K is the main loop index, decreasing from N to 1 in steps of
-* 1 or 2
-*
- K = N
- 10 CONTINUE
-*
-* If K < 1, exit from loop
-*
- IF( K.LT.1 )
- $ GO TO 70
- KSTEP = 1
-*
-* Determine rows and columns to be interchanged and whether
-* a 1-by-1 or 2-by-2 pivot block will be used
-*
- ABSAKK = ABS( A( K, K ) )
-*
-* IMAX is the row-index of the largest off-diagonal element in
-* column K, and COLMAX is its absolute value
-*
- IF( K.GT.1 ) THEN
- IMAX = IDAMAX( K-1, A( 1, K ), 1 )
- COLMAX = ABS( A( IMAX, K ) )
- ELSE
- COLMAX = ZERO
- END IF
-*
- IF( (MAX( ABSAKK, COLMAX ).EQ.ZERO) .OR. DISNAN(ABSAKK) ) THEN
-*
-* Column K is zero or contains a NaN: set INFO and continue
-*
- IF( INFO.EQ.0 )
- $ INFO = K
- KP = K
- ELSE
- IF( ABSAKK.GE.ALPHA*COLMAX ) THEN
-*
-* no interchange, use 1-by-1 pivot block
-*
- KP = K
- ELSE
-*
-* JMAX is the column-index of the largest off-diagonal
-* element in row IMAX, and ROWMAX is its absolute value
-*
- JMAX = IMAX + IDAMAX( K-IMAX, A( IMAX, IMAX+1 ), LDA )
- ROWMAX = ABS( A( IMAX, JMAX ) )
- IF( IMAX.GT.1 ) THEN
- JMAX = IDAMAX( IMAX-1, A( 1, IMAX ), 1 )
- ROWMAX = MAX( ROWMAX, ABS( A( JMAX, IMAX ) ) )
- END IF
-*
- IF( ABSAKK.GE.ALPHA*COLMAX*( COLMAX / ROWMAX ) ) THEN
-*
-* no interchange, use 1-by-1 pivot block
-*
- KP = K
- ELSE IF( ABS( A( IMAX, IMAX ) ).GE.ALPHA*ROWMAX ) THEN
-*
-* interchange rows and columns K and IMAX, use 1-by-1
-* pivot block
-*
- KP = IMAX
- ELSE
-*
-* interchange rows and columns K-1 and IMAX, use 2-by-2
-* pivot block
-*
- KP = IMAX
- KSTEP = 2
- END IF
- END IF
-*
- KK = K - KSTEP + 1
- IF( KP.NE.KK ) THEN
-*
-* Interchange rows and columns KK and KP in the leading
-* submatrix A(1:k,1:k)
-*
- CALL DSWAP( KP-1, A( 1, KK ), 1, A( 1, KP ), 1 )
- CALL DSWAP( KK-KP-1, A( KP+1, KK ), 1, A( KP, KP+1 ),
- $ LDA )
- T = A( KK, KK )
- A( KK, KK ) = A( KP, KP )
- A( KP, KP ) = T
- IF( KSTEP.EQ.2 ) THEN
- T = A( K-1, K )
- A( K-1, K ) = A( KP, K )
- A( KP, K ) = T
- END IF
- END IF
-*
-* Update the leading submatrix
-*
- IF( KSTEP.EQ.1 ) THEN
-*
-* 1-by-1 pivot block D(k): column k now holds
-*
-* W(k) = U(k)*D(k)
-*
-* where U(k) is the k-th column of U
-*
-* Perform a rank-1 update of A(1:k-1,1:k-1) as
-*
-* A := A - U(k)*D(k)*U(k)' = A - W(k)*1/D(k)*W(k)'
-*
- R1 = ONE / A( K, K )
- CALL DSYR( UPLO, K-1, -R1, A( 1, K ), 1, A, LDA )
-*
-* Store U(k) in column k
-*
- CALL DSCAL( K-1, R1, A( 1, K ), 1 )
- ELSE
-*
-* 2-by-2 pivot block D(k): columns k and k-1 now hold
-*
-* ( W(k-1) W(k) ) = ( U(k-1) U(k) )*D(k)
-*
-* where U(k) and U(k-1) are the k-th and (k-1)-th columns
-* of U
-*
-* Perform a rank-2 update of A(1:k-2,1:k-2) as
-*
-* A := A - ( U(k-1) U(k) )*D(k)*( U(k-1) U(k) )'
-* = A - ( W(k-1) W(k) )*inv(D(k))*( W(k-1) W(k) )'
-*
- IF( K.GT.2 ) THEN
-*
- D12 = A( K-1, K )
- D22 = A( K-1, K-1 ) / D12
- D11 = A( K, K ) / D12
- T = ONE / ( D11*D22-ONE )
- D12 = T / D12
-*
- DO 30 J = K - 2, 1, -1
- WKM1 = D12*( D11*A( J, K-1 )-A( J, K ) )
- WK = D12*( D22*A( J, K )-A( J, K-1 ) )
- DO 20 I = J, 1, -1
- A( I, J ) = A( I, J ) - A( I, K )*WK -
- $ A( I, K-1 )*WKM1
- 20 CONTINUE
- A( J, K ) = WK
- A( J, K-1 ) = WKM1
- 30 CONTINUE
-*
- END IF
-*
- END IF
- END IF
-*
-* Store details of the interchanges in IPIV
-*
- IF( KSTEP.EQ.1 ) THEN
- IPIV( K ) = KP
- ELSE
- IPIV( K ) = -KP
- IPIV( K-1 ) = -KP
- END IF
-*
-* Decrease K and return to the start of the main loop
-*
- K = K - KSTEP
- GO TO 10
-*
- ELSE
-*
-* Factorize A as L*D*L' using the lower triangle of A
-*
-* K is the main loop index, increasing from 1 to N in steps of
-* 1 or 2
-*
- K = 1
- 40 CONTINUE
-*
-* If K > N, exit from loop
-*
- IF( K.GT.N )
- $ GO TO 70
- KSTEP = 1
-*
-* Determine rows and columns to be interchanged and whether
-* a 1-by-1 or 2-by-2 pivot block will be used
-*
- ABSAKK = ABS( A( K, K ) )
-*
-* IMAX is the row-index of the largest off-diagonal element in
-* column K, and COLMAX is its absolute value
-*
- IF( K.LT.N ) THEN
- IMAX = K + IDAMAX( N-K, A( K+1, K ), 1 )
- COLMAX = ABS( A( IMAX, K ) )
- ELSE
- COLMAX = ZERO
- END IF
-*
- IF( (MAX( ABSAKK, COLMAX ).EQ.ZERO) .OR. DISNAN(ABSAKK) ) THEN
-*
-* Column K is zero or contains a NaN: set INFO and continue
-*
- IF( INFO.EQ.0 )
- $ INFO = K
- KP = K
- ELSE
- IF( ABSAKK.GE.ALPHA*COLMAX ) THEN
-*
-* no interchange, use 1-by-1 pivot block
-*
- KP = K
- ELSE
-*
-* JMAX is the column-index of the largest off-diagonal
-* element in row IMAX, and ROWMAX is its absolute value
-*
- JMAX = K - 1 + IDAMAX( IMAX-K, A( IMAX, K ), LDA )
- ROWMAX = ABS( A( IMAX, JMAX ) )
- IF( IMAX.LT.N ) THEN
- JMAX = IMAX + IDAMAX( N-IMAX, A( IMAX+1, IMAX ), 1 )
- ROWMAX = MAX( ROWMAX, ABS( A( JMAX, IMAX ) ) )
- END IF
-*
- IF( ABSAKK.GE.ALPHA*COLMAX*( COLMAX / ROWMAX ) ) THEN
-*
-* no interchange, use 1-by-1 pivot block
-*
- KP = K
- ELSE IF( ABS( A( IMAX, IMAX ) ).GE.ALPHA*ROWMAX ) THEN
-*
-* interchange rows and columns K and IMAX, use 1-by-1
-* pivot block
-*
- KP = IMAX
- ELSE
-*
-* interchange rows and columns K+1 and IMAX, use 2-by-2
-* pivot block
-*
- KP = IMAX
- KSTEP = 2
- END IF
- END IF
-*
- KK = K + KSTEP - 1
- IF( KP.NE.KK ) THEN
-*
-* Interchange rows and columns KK and KP in the trailing
-* submatrix A(k:n,k:n)
-*
- IF( KP.LT.N )
- $ CALL DSWAP( N-KP, A( KP+1, KK ), 1, A( KP+1, KP ), 1 )
- CALL DSWAP( KP-KK-1, A( KK+1, KK ), 1, A( KP, KK+1 ),
- $ LDA )
- T = A( KK, KK )
- A( KK, KK ) = A( KP, KP )
- A( KP, KP ) = T
- IF( KSTEP.EQ.2 ) THEN
- T = A( K+1, K )
- A( K+1, K ) = A( KP, K )
- A( KP, K ) = T
- END IF
- END IF
-*
-* Update the trailing submatrix
-*
- IF( KSTEP.EQ.1 ) THEN
-*
-* 1-by-1 pivot block D(k): column k now holds
-*
-* W(k) = L(k)*D(k)
-*
-* where L(k) is the k-th column of L
-*
- IF( K.LT.N ) THEN
-*
-* Perform a rank-1 update of A(k+1:n,k+1:n) as
-*
-* A := A - L(k)*D(k)*L(k)' = A - W(k)*(1/D(k))*W(k)'
-*
- D11 = ONE / A( K, K )
- CALL DSYR( UPLO, N-K, -D11, A( K+1, K ), 1,
- $ A( K+1, K+1 ), LDA )
-*
-* Store L(k) in column K
-*
- CALL DSCAL( N-K, D11, A( K+1, K ), 1 )
- END IF
- ELSE
-*
-* 2-by-2 pivot block D(k)
-*
- IF( K.LT.N-1 ) THEN
-*
-* Perform a rank-2 update of A(k+2:n,k+2:n) as
-*
-* A := A - ( (A(k) A(k+1))*D(k)**(-1) ) * (A(k) A(k+1))'
-*
-* where L(k) and L(k+1) are the k-th and (k+1)-th
-* columns of L
-*
- D21 = A( K+1, K )
- D11 = A( K+1, K+1 ) / D21
- D22 = A( K, K ) / D21
- T = ONE / ( D11*D22-ONE )
- D21 = T / D21
-*
- DO 60 J = K + 2, N
-*
- WK = D21*( D11*A( J, K )-A( J, K+1 ) )
- WKP1 = D21*( D22*A( J, K+1 )-A( J, K ) )
-*
- DO 50 I = J, N
- A( I, J ) = A( I, J ) - A( I, K )*WK -
- $ A( I, K+1 )*WKP1
- 50 CONTINUE
-*
- A( J, K ) = WK
- A( J, K+1 ) = WKP1
-*
- 60 CONTINUE
- END IF
- END IF
- END IF
-*
-* Store details of the interchanges in IPIV
-*
- IF( KSTEP.EQ.1 ) THEN
- IPIV( K ) = KP
- ELSE
- IPIV( K ) = -KP
- IPIV( K+1 ) = -KP
- END IF
-*
-* Increase K and return to the start of the main loop
-*
- K = K + KSTEP
- GO TO 40
-*
- END IF
-*
- 70 CONTINUE
-*
- RETURN
-*
-* End of DSYTF2
-*
- END
diff --git a/src/lib/lapack/dsytrd.f b/src/lib/lapack/dsytrd.f
deleted file mode 100644
index 569ee35b..00000000
--- a/src/lib/lapack/dsytrd.f
+++ /dev/null
@@ -1,294 +0,0 @@
- SUBROUTINE DSYTRD( UPLO, N, A, LDA, D, E, TAU, WORK, LWORK, INFO )
-*
-* -- LAPACK routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- CHARACTER UPLO
- INTEGER INFO, LDA, LWORK, N
-* ..
-* .. Array Arguments ..
- DOUBLE PRECISION A( LDA, * ), D( * ), E( * ), TAU( * ),
- $ WORK( * )
-* ..
-*
-* Purpose
-* =======
-*
-* DSYTRD reduces a real symmetric matrix A to real symmetric
-* tridiagonal form T by an orthogonal similarity transformation:
-* Q**T * A * Q = T.
-*
-* Arguments
-* =========
-*
-* UPLO (input) CHARACTER*1
-* = 'U': Upper triangle of A is stored;
-* = 'L': Lower triangle of A is stored.
-*
-* N (input) INTEGER
-* The order of the matrix A. N >= 0.
-*
-* A (input/output) DOUBLE PRECISION array, dimension (LDA,N)
-* On entry, the symmetric matrix A. If UPLO = 'U', the leading
-* N-by-N upper triangular part of A contains the upper
-* triangular part of the matrix A, and the strictly lower
-* triangular part of A is not referenced. If UPLO = 'L', the
-* leading N-by-N lower triangular part of A contains the lower
-* triangular part of the matrix A, and the strictly upper
-* triangular part of A is not referenced.
-* On exit, if UPLO = 'U', the diagonal and first superdiagonal
-* of A are overwritten by the corresponding elements of the
-* tridiagonal matrix T, and the elements above the first
-* superdiagonal, with the array TAU, represent the orthogonal
-* matrix Q as a product of elementary reflectors; if UPLO
-* = 'L', the diagonal and first subdiagonal of A are over-
-* written by the corresponding elements of the tridiagonal
-* matrix T, and the elements below the first subdiagonal, with
-* the array TAU, represent the orthogonal matrix Q as a product
-* of elementary reflectors. See Further Details.
-*
-* LDA (input) INTEGER
-* The leading dimension of the array A. LDA >= max(1,N).
-*
-* D (output) DOUBLE PRECISION array, dimension (N)
-* The diagonal elements of the tridiagonal matrix T:
-* D(i) = A(i,i).
-*
-* E (output) DOUBLE PRECISION array, dimension (N-1)
-* The off-diagonal elements of the tridiagonal matrix T:
-* E(i) = A(i,i+1) if UPLO = 'U', E(i) = A(i+1,i) if UPLO = 'L'.
-*
-* TAU (output) DOUBLE PRECISION array, dimension (N-1)
-* The scalar factors of the elementary reflectors (see Further
-* Details).
-*
-* WORK (workspace/output) DOUBLE PRECISION array, dimension (MAX(1,LWORK))
-* On exit, if INFO = 0, WORK(1) returns the optimal LWORK.
-*
-* LWORK (input) INTEGER
-* The dimension of the array WORK. LWORK >= 1.
-* For optimum performance LWORK >= N*NB, where NB is the
-* optimal blocksize.
-*
-* If LWORK = -1, then a workspace query is assumed; the routine
-* only calculates the optimal size of the WORK array, returns
-* this value as the first entry of the WORK array, and no error
-* message related to LWORK is issued by XERBLA.
-*
-* INFO (output) INTEGER
-* = 0: successful exit
-* < 0: if INFO = -i, the i-th argument had an illegal value
-*
-* Further Details
-* ===============
-*
-* If UPLO = 'U', the matrix Q is represented as a product of elementary
-* reflectors
-*
-* Q = H(n-1) . . . H(2) H(1).
-*
-* Each H(i) has the form
-*
-* H(i) = I - tau * v * v'
-*
-* where tau is a real scalar, and v is a real vector with
-* v(i+1:n) = 0 and v(i) = 1; v(1:i-1) is stored on exit in
-* A(1:i-1,i+1), and tau in TAU(i).
-*
-* If UPLO = 'L', the matrix Q is represented as a product of elementary
-* reflectors
-*
-* Q = H(1) H(2) . . . H(n-1).
-*
-* Each H(i) has the form
-*
-* H(i) = I - tau * v * v'
-*
-* where tau is a real scalar, and v is a real vector with
-* v(1:i) = 0 and v(i+1) = 1; v(i+2:n) is stored on exit in A(i+2:n,i),
-* and tau in TAU(i).
-*
-* The contents of A on exit are illustrated by the following examples
-* with n = 5:
-*
-* if UPLO = 'U': if UPLO = 'L':
-*
-* ( d e v2 v3 v4 ) ( d )
-* ( d e v3 v4 ) ( e d )
-* ( d e v4 ) ( v1 e d )
-* ( d e ) ( v1 v2 e d )
-* ( d ) ( v1 v2 v3 e d )
-*
-* where d and e denote diagonal and off-diagonal elements of T, and vi
-* denotes an element of the vector defining H(i).
-*
-* =====================================================================
-*
-* .. Parameters ..
- DOUBLE PRECISION ONE
- PARAMETER ( ONE = 1.0D+0 )
-* ..
-* .. Local Scalars ..
- LOGICAL LQUERY, UPPER
- INTEGER I, IINFO, IWS, J, KK, LDWORK, LWKOPT, NB,
- $ NBMIN, NX
-* ..
-* .. External Subroutines ..
- EXTERNAL DLATRD, DSYR2K, DSYTD2, XERBLA
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC MAX
-* ..
-* .. External Functions ..
- LOGICAL LSAME
- INTEGER ILAENV
- EXTERNAL LSAME, ILAENV
-* ..
-* .. Executable Statements ..
-*
-* Test the input parameters
-*
- INFO = 0
- UPPER = LSAME( UPLO, 'U' )
- LQUERY = ( LWORK.EQ.-1 )
- IF( .NOT.UPPER .AND. .NOT.LSAME( UPLO, 'L' ) ) THEN
- INFO = -1
- ELSE IF( N.LT.0 ) THEN
- INFO = -2
- ELSE IF( LDA.LT.MAX( 1, N ) ) THEN
- INFO = -4
- ELSE IF( LWORK.LT.1 .AND. .NOT.LQUERY ) THEN
- INFO = -9
- END IF
-*
- IF( INFO.EQ.0 ) THEN
-*
-* Determine the block size.
-*
- NB = ILAENV( 1, 'DSYTRD', UPLO, N, -1, -1, -1 )
- LWKOPT = N*NB
- WORK( 1 ) = LWKOPT
- END IF
-*
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'DSYTRD', -INFO )
- RETURN
- ELSE IF( LQUERY ) THEN
- RETURN
- END IF
-*
-* Quick return if possible
-*
- IF( N.EQ.0 ) THEN
- WORK( 1 ) = 1
- RETURN
- END IF
-*
- NX = N
- IWS = 1
- IF( NB.GT.1 .AND. NB.LT.N ) THEN
-*
-* Determine when to cross over from blocked to unblocked code
-* (last block is always handled by unblocked code).
-*
- NX = MAX( NB, ILAENV( 3, 'DSYTRD', UPLO, N, -1, -1, -1 ) )
- IF( NX.LT.N ) THEN
-*
-* Determine if workspace is large enough for blocked code.
-*
- LDWORK = N
- IWS = LDWORK*NB
- IF( LWORK.LT.IWS ) THEN
-*
-* Not enough workspace to use optimal NB: determine the
-* minimum value of NB, and reduce NB or force use of
-* unblocked code by setting NX = N.
-*
- NB = MAX( LWORK / LDWORK, 1 )
- NBMIN = ILAENV( 2, 'DSYTRD', UPLO, N, -1, -1, -1 )
- IF( NB.LT.NBMIN )
- $ NX = N
- END IF
- ELSE
- NX = N
- END IF
- ELSE
- NB = 1
- END IF
-*
- IF( UPPER ) THEN
-*
-* Reduce the upper triangle of A.
-* Columns 1:kk are handled by the unblocked method.
-*
- KK = N - ( ( N-NX+NB-1 ) / NB )*NB
- DO 20 I = N - NB + 1, KK + 1, -NB
-*
-* Reduce columns i:i+nb-1 to tridiagonal form and form the
-* matrix W which is needed to update the unreduced part of
-* the matrix
-*
- CALL DLATRD( UPLO, I+NB-1, NB, A, LDA, E, TAU, WORK,
- $ LDWORK )
-*
-* Update the unreduced submatrix A(1:i-1,1:i-1), using an
-* update of the form: A := A - V*W' - W*V'
-*
- CALL DSYR2K( UPLO, 'No transpose', I-1, NB, -ONE, A( 1, I ),
- $ LDA, WORK, LDWORK, ONE, A, LDA )
-*
-* Copy superdiagonal elements back into A, and diagonal
-* elements into D
-*
- DO 10 J = I, I + NB - 1
- A( J-1, J ) = E( J-1 )
- D( J ) = A( J, J )
- 10 CONTINUE
- 20 CONTINUE
-*
-* Use unblocked code to reduce the last or only block
-*
- CALL DSYTD2( UPLO, KK, A, LDA, D, E, TAU, IINFO )
- ELSE
-*
-* Reduce the lower triangle of A
-*
- DO 40 I = 1, N - NX, NB
-*
-* Reduce columns i:i+nb-1 to tridiagonal form and form the
-* matrix W which is needed to update the unreduced part of
-* the matrix
-*
- CALL DLATRD( UPLO, N-I+1, NB, A( I, I ), LDA, E( I ),
- $ TAU( I ), WORK, LDWORK )
-*
-* Update the unreduced submatrix A(i+ib:n,i+ib:n), using
-* an update of the form: A := A - V*W' - W*V'
-*
- CALL DSYR2K( UPLO, 'No transpose', N-I-NB+1, NB, -ONE,
- $ A( I+NB, I ), LDA, WORK( NB+1 ), LDWORK, ONE,
- $ A( I+NB, I+NB ), LDA )
-*
-* Copy subdiagonal elements back into A, and diagonal
-* elements into D
-*
- DO 30 J = I, I + NB - 1
- A( J+1, J ) = E( J )
- D( J ) = A( J, J )
- 30 CONTINUE
- 40 CONTINUE
-*
-* Use unblocked code to reduce the last or only block
-*
- CALL DSYTD2( UPLO, N-I+1, A( I, I ), LDA, D( I ), E( I ),
- $ TAU( I ), IINFO )
- END IF
-*
- WORK( 1 ) = LWKOPT
- RETURN
-*
-* End of DSYTRD
-*
- END
diff --git a/src/lib/lapack/dsytrf.f b/src/lib/lapack/dsytrf.f
deleted file mode 100644
index 43a31248..00000000
--- a/src/lib/lapack/dsytrf.f
+++ /dev/null
@@ -1,287 +0,0 @@
- SUBROUTINE DSYTRF( UPLO, N, A, LDA, IPIV, WORK, LWORK, INFO )
-*
-* -- LAPACK routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- CHARACTER UPLO
- INTEGER INFO, LDA, LWORK, N
-* ..
-* .. Array Arguments ..
- INTEGER IPIV( * )
- DOUBLE PRECISION A( LDA, * ), WORK( * )
-* ..
-*
-* Purpose
-* =======
-*
-* DSYTRF computes the factorization of a real symmetric matrix A using
-* the Bunch-Kaufman diagonal pivoting method. The form of the
-* factorization is
-*
-* A = U*D*U**T or A = L*D*L**T
-*
-* where U (or L) is a product of permutation and unit upper (lower)
-* triangular matrices, and D is symmetric and block diagonal with
-* 1-by-1 and 2-by-2 diagonal blocks.
-*
-* This is the blocked version of the algorithm, calling Level 3 BLAS.
-*
-* Arguments
-* =========
-*
-* UPLO (input) CHARACTER*1
-* = 'U': Upper triangle of A is stored;
-* = 'L': Lower triangle of A is stored.
-*
-* N (input) INTEGER
-* The order of the matrix A. N >= 0.
-*
-* A (input/output) DOUBLE PRECISION array, dimension (LDA,N)
-* On entry, the symmetric matrix A. If UPLO = 'U', the leading
-* N-by-N upper triangular part of A contains the upper
-* triangular part of the matrix A, and the strictly lower
-* triangular part of A is not referenced. If UPLO = 'L', the
-* leading N-by-N lower triangular part of A contains the lower
-* triangular part of the matrix A, and the strictly upper
-* triangular part of A is not referenced.
-*
-* On exit, the block diagonal matrix D and the multipliers used
-* to obtain the factor U or L (see below for further details).
-*
-* LDA (input) INTEGER
-* The leading dimension of the array A. LDA >= max(1,N).
-*
-* IPIV (output) INTEGER array, dimension (N)
-* Details of the interchanges and the block structure of D.
-* If IPIV(k) > 0, then rows and columns k and IPIV(k) were
-* interchanged and D(k,k) is a 1-by-1 diagonal block.
-* If UPLO = 'U' and IPIV(k) = IPIV(k-1) < 0, then rows and
-* columns k-1 and -IPIV(k) were interchanged and D(k-1:k,k-1:k)
-* is a 2-by-2 diagonal block. If UPLO = 'L' and IPIV(k) =
-* IPIV(k+1) < 0, then rows and columns k+1 and -IPIV(k) were
-* interchanged and D(k:k+1,k:k+1) is a 2-by-2 diagonal block.
-*
-* WORK (workspace/output) DOUBLE PRECISION array, dimension (MAX(1,LWORK))
-* On exit, if INFO = 0, WORK(1) returns the optimal LWORK.
-*
-* LWORK (input) INTEGER
-* The length of WORK. LWORK >=1. For best performance
-* LWORK >= N*NB, where NB is the block size returned by ILAENV.
-*
-* If LWORK = -1, then a workspace query is assumed; the routine
-* only calculates the optimal size of the WORK array, returns
-* this value as the first entry of the WORK array, and no error
-* message related to LWORK is issued by XERBLA.
-*
-* INFO (output) INTEGER
-* = 0: successful exit
-* < 0: if INFO = -i, the i-th argument had an illegal value
-* > 0: if INFO = i, D(i,i) is exactly zero. The factorization
-* has been completed, but the block diagonal matrix D is
-* exactly singular, and division by zero will occur if it
-* is used to solve a system of equations.
-*
-* Further Details
-* ===============
-*
-* If UPLO = 'U', then A = U*D*U', where
-* U = P(n)*U(n)* ... *P(k)U(k)* ...,
-* i.e., U is a product of terms P(k)*U(k), where k decreases from n to
-* 1 in steps of 1 or 2, and D is a block diagonal matrix with 1-by-1
-* and 2-by-2 diagonal blocks D(k). P(k) is a permutation matrix as
-* defined by IPIV(k), and U(k) is a unit upper triangular matrix, such
-* that if the diagonal block D(k) is of order s (s = 1 or 2), then
-*
-* ( I v 0 ) k-s
-* U(k) = ( 0 I 0 ) s
-* ( 0 0 I ) n-k
-* k-s s n-k
-*
-* If s = 1, D(k) overwrites A(k,k), and v overwrites A(1:k-1,k).
-* If s = 2, the upper triangle of D(k) overwrites A(k-1,k-1), A(k-1,k),
-* and A(k,k), and v overwrites A(1:k-2,k-1:k).
-*
-* If UPLO = 'L', then A = L*D*L', where
-* L = P(1)*L(1)* ... *P(k)*L(k)* ...,
-* i.e., L is a product of terms P(k)*L(k), where k increases from 1 to
-* n in steps of 1 or 2, and D is a block diagonal matrix with 1-by-1
-* and 2-by-2 diagonal blocks D(k). P(k) is a permutation matrix as
-* defined by IPIV(k), and L(k) is a unit lower triangular matrix, such
-* that if the diagonal block D(k) is of order s (s = 1 or 2), then
-*
-* ( I 0 0 ) k-1
-* L(k) = ( 0 I 0 ) s
-* ( 0 v I ) n-k-s+1
-* k-1 s n-k-s+1
-*
-* If s = 1, D(k) overwrites A(k,k), and v overwrites A(k+1:n,k).
-* If s = 2, the lower triangle of D(k) overwrites A(k,k), A(k+1,k),
-* and A(k+1,k+1), and v overwrites A(k+2:n,k:k+1).
-*
-* =====================================================================
-*
-* .. Local Scalars ..
- LOGICAL LQUERY, UPPER
- INTEGER IINFO, IWS, J, K, KB, LDWORK, LWKOPT, NB, NBMIN
-* ..
-* .. External Functions ..
- LOGICAL LSAME
- INTEGER ILAENV
- EXTERNAL LSAME, ILAENV
-* ..
-* .. External Subroutines ..
- EXTERNAL DLASYF, DSYTF2, XERBLA
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC MAX
-* ..
-* .. Executable Statements ..
-*
-* Test the input parameters.
-*
- INFO = 0
- UPPER = LSAME( UPLO, 'U' )
- LQUERY = ( LWORK.EQ.-1 )
- IF( .NOT.UPPER .AND. .NOT.LSAME( UPLO, 'L' ) ) THEN
- INFO = -1
- ELSE IF( N.LT.0 ) THEN
- INFO = -2
- ELSE IF( LDA.LT.MAX( 1, N ) ) THEN
- INFO = -4
- ELSE IF( LWORK.LT.1 .AND. .NOT.LQUERY ) THEN
- INFO = -7
- END IF
-*
- IF( INFO.EQ.0 ) THEN
-*
-* Determine the block size
-*
- NB = ILAENV( 1, 'DSYTRF', UPLO, N, -1, -1, -1 )
- LWKOPT = N*NB
- WORK( 1 ) = LWKOPT
- END IF
-*
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'DSYTRF', -INFO )
- RETURN
- ELSE IF( LQUERY ) THEN
- RETURN
- END IF
-*
- NBMIN = 2
- LDWORK = N
- IF( NB.GT.1 .AND. NB.LT.N ) THEN
- IWS = LDWORK*NB
- IF( LWORK.LT.IWS ) THEN
- NB = MAX( LWORK / LDWORK, 1 )
- NBMIN = MAX( 2, ILAENV( 2, 'DSYTRF', UPLO, N, -1, -1, -1 ) )
- END IF
- ELSE
- IWS = 1
- END IF
- IF( NB.LT.NBMIN )
- $ NB = N
-*
- IF( UPPER ) THEN
-*
-* Factorize A as U*D*U' using the upper triangle of A
-*
-* K is the main loop index, decreasing from N to 1 in steps of
-* KB, where KB is the number of columns factorized by DLASYF;
-* KB is either NB or NB-1, or K for the last block
-*
- K = N
- 10 CONTINUE
-*
-* If K < 1, exit from loop
-*
- IF( K.LT.1 )
- $ GO TO 40
-*
- IF( K.GT.NB ) THEN
-*
-* Factorize columns k-kb+1:k of A and use blocked code to
-* update columns 1:k-kb
-*
- CALL DLASYF( UPLO, K, NB, KB, A, LDA, IPIV, WORK, LDWORK,
- $ IINFO )
- ELSE
-*
-* Use unblocked code to factorize columns 1:k of A
-*
- CALL DSYTF2( UPLO, K, A, LDA, IPIV, IINFO )
- KB = K
- END IF
-*
-* Set INFO on the first occurrence of a zero pivot
-*
- IF( INFO.EQ.0 .AND. IINFO.GT.0 )
- $ INFO = IINFO
-*
-* Decrease K and return to the start of the main loop
-*
- K = K - KB
- GO TO 10
-*
- ELSE
-*
-* Factorize A as L*D*L' using the lower triangle of A
-*
-* K is the main loop index, increasing from 1 to N in steps of
-* KB, where KB is the number of columns factorized by DLASYF;
-* KB is either NB or NB-1, or N-K+1 for the last block
-*
- K = 1
- 20 CONTINUE
-*
-* If K > N, exit from loop
-*
- IF( K.GT.N )
- $ GO TO 40
-*
- IF( K.LE.N-NB ) THEN
-*
-* Factorize columns k:k+kb-1 of A and use blocked code to
-* update columns k+kb:n
-*
- CALL DLASYF( UPLO, N-K+1, NB, KB, A( K, K ), LDA, IPIV( K ),
- $ WORK, LDWORK, IINFO )
- ELSE
-*
-* Use unblocked code to factorize columns k:n of A
-*
- CALL DSYTF2( UPLO, N-K+1, A( K, K ), LDA, IPIV( K ), IINFO )
- KB = N - K + 1
- END IF
-*
-* Set INFO on the first occurrence of a zero pivot
-*
- IF( INFO.EQ.0 .AND. IINFO.GT.0 )
- $ INFO = IINFO + K - 1
-*
-* Adjust IPIV
-*
- DO 30 J = K, K + KB - 1
- IF( IPIV( J ).GT.0 ) THEN
- IPIV( J ) = IPIV( J ) + K - 1
- ELSE
- IPIV( J ) = IPIV( J ) - K + 1
- END IF
- 30 CONTINUE
-*
-* Increase K and return to the start of the main loop
-*
- K = K + KB
- GO TO 20
-*
- END IF
-*
- 40 CONTINUE
- WORK( 1 ) = LWKOPT
- RETURN
-*
-* End of DSYTRF
-*
- END
diff --git a/src/lib/lapack/dsytri.f b/src/lib/lapack/dsytri.f
deleted file mode 100644
index 361de9a3..00000000
--- a/src/lib/lapack/dsytri.f
+++ /dev/null
@@ -1,312 +0,0 @@
- SUBROUTINE DSYTRI( UPLO, N, A, LDA, IPIV, WORK, INFO )
-*
-* -- LAPACK routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- CHARACTER UPLO
- INTEGER INFO, LDA, N
-* ..
-* .. Array Arguments ..
- INTEGER IPIV( * )
- DOUBLE PRECISION A( LDA, * ), WORK( * )
-* ..
-*
-* Purpose
-* =======
-*
-* DSYTRI computes the inverse of a real symmetric indefinite matrix
-* A using the factorization A = U*D*U**T or A = L*D*L**T computed by
-* DSYTRF.
-*
-* Arguments
-* =========
-*
-* UPLO (input) CHARACTER*1
-* Specifies whether the details of the factorization are stored
-* as an upper or lower triangular matrix.
-* = 'U': Upper triangular, form is A = U*D*U**T;
-* = 'L': Lower triangular, form is A = L*D*L**T.
-*
-* N (input) INTEGER
-* The order of the matrix A. N >= 0.
-*
-* A (input/output) DOUBLE PRECISION array, dimension (LDA,N)
-* On entry, the block diagonal matrix D and the multipliers
-* used to obtain the factor U or L as computed by DSYTRF.
-*
-* On exit, if INFO = 0, the (symmetric) inverse of the original
-* matrix. If UPLO = 'U', the upper triangular part of the
-* inverse is formed and the part of A below the diagonal is not
-* referenced; if UPLO = 'L' the lower triangular part of the
-* inverse is formed and the part of A above the diagonal is
-* not referenced.
-*
-* LDA (input) INTEGER
-* The leading dimension of the array A. LDA >= max(1,N).
-*
-* IPIV (input) INTEGER array, dimension (N)
-* Details of the interchanges and the block structure of D
-* as determined by DSYTRF.
-*
-* WORK (workspace) DOUBLE PRECISION array, dimension (N)
-*
-* INFO (output) INTEGER
-* = 0: successful exit
-* < 0: if INFO = -i, the i-th argument had an illegal value
-* > 0: if INFO = i, D(i,i) = 0; the matrix is singular and its
-* inverse could not be computed.
-*
-* =====================================================================
-*
-* .. Parameters ..
- DOUBLE PRECISION ONE, ZERO
- PARAMETER ( ONE = 1.0D+0, ZERO = 0.0D+0 )
-* ..
-* .. Local Scalars ..
- LOGICAL UPPER
- INTEGER K, KP, KSTEP
- DOUBLE PRECISION AK, AKKP1, AKP1, D, T, TEMP
-* ..
-* .. External Functions ..
- LOGICAL LSAME
- DOUBLE PRECISION DDOT
- EXTERNAL LSAME, DDOT
-* ..
-* .. External Subroutines ..
- EXTERNAL DCOPY, DSWAP, DSYMV, XERBLA
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC ABS, MAX
-* ..
-* .. Executable Statements ..
-*
-* Test the input parameters.
-*
- INFO = 0
- UPPER = LSAME( UPLO, 'U' )
- IF( .NOT.UPPER .AND. .NOT.LSAME( UPLO, 'L' ) ) THEN
- INFO = -1
- ELSE IF( N.LT.0 ) THEN
- INFO = -2
- ELSE IF( LDA.LT.MAX( 1, N ) ) THEN
- INFO = -4
- END IF
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'DSYTRI', -INFO )
- RETURN
- END IF
-*
-* Quick return if possible
-*
- IF( N.EQ.0 )
- $ RETURN
-*
-* Check that the diagonal matrix D is nonsingular.
-*
- IF( UPPER ) THEN
-*
-* Upper triangular storage: examine D from bottom to top
-*
- DO 10 INFO = N, 1, -1
- IF( IPIV( INFO ).GT.0 .AND. A( INFO, INFO ).EQ.ZERO )
- $ RETURN
- 10 CONTINUE
- ELSE
-*
-* Lower triangular storage: examine D from top to bottom.
-*
- DO 20 INFO = 1, N
- IF( IPIV( INFO ).GT.0 .AND. A( INFO, INFO ).EQ.ZERO )
- $ RETURN
- 20 CONTINUE
- END IF
- INFO = 0
-*
- IF( UPPER ) THEN
-*
-* Compute inv(A) from the factorization A = U*D*U'.
-*
-* K is the main loop index, increasing from 1 to N in steps of
-* 1 or 2, depending on the size of the diagonal blocks.
-*
- K = 1
- 30 CONTINUE
-*
-* If K > N, exit from loop.
-*
- IF( K.GT.N )
- $ GO TO 40
-*
- IF( IPIV( K ).GT.0 ) THEN
-*
-* 1 x 1 diagonal block
-*
-* Invert the diagonal block.
-*
- A( K, K ) = ONE / A( K, K )
-*
-* Compute column K of the inverse.
-*
- IF( K.GT.1 ) THEN
- CALL DCOPY( K-1, A( 1, K ), 1, WORK, 1 )
- CALL DSYMV( UPLO, K-1, -ONE, A, LDA, WORK, 1, ZERO,
- $ A( 1, K ), 1 )
- A( K, K ) = A( K, K ) - DDOT( K-1, WORK, 1, A( 1, K ),
- $ 1 )
- END IF
- KSTEP = 1
- ELSE
-*
-* 2 x 2 diagonal block
-*
-* Invert the diagonal block.
-*
- T = ABS( A( K, K+1 ) )
- AK = A( K, K ) / T
- AKP1 = A( K+1, K+1 ) / T
- AKKP1 = A( K, K+1 ) / T
- D = T*( AK*AKP1-ONE )
- A( K, K ) = AKP1 / D
- A( K+1, K+1 ) = AK / D
- A( K, K+1 ) = -AKKP1 / D
-*
-* Compute columns K and K+1 of the inverse.
-*
- IF( K.GT.1 ) THEN
- CALL DCOPY( K-1, A( 1, K ), 1, WORK, 1 )
- CALL DSYMV( UPLO, K-1, -ONE, A, LDA, WORK, 1, ZERO,
- $ A( 1, K ), 1 )
- A( K, K ) = A( K, K ) - DDOT( K-1, WORK, 1, A( 1, K ),
- $ 1 )
- A( K, K+1 ) = A( K, K+1 ) -
- $ DDOT( K-1, A( 1, K ), 1, A( 1, K+1 ), 1 )
- CALL DCOPY( K-1, A( 1, K+1 ), 1, WORK, 1 )
- CALL DSYMV( UPLO, K-1, -ONE, A, LDA, WORK, 1, ZERO,
- $ A( 1, K+1 ), 1 )
- A( K+1, K+1 ) = A( K+1, K+1 ) -
- $ DDOT( K-1, WORK, 1, A( 1, K+1 ), 1 )
- END IF
- KSTEP = 2
- END IF
-*
- KP = ABS( IPIV( K ) )
- IF( KP.NE.K ) THEN
-*
-* Interchange rows and columns K and KP in the leading
-* submatrix A(1:k+1,1:k+1)
-*
- CALL DSWAP( KP-1, A( 1, K ), 1, A( 1, KP ), 1 )
- CALL DSWAP( K-KP-1, A( KP+1, K ), 1, A( KP, KP+1 ), LDA )
- TEMP = A( K, K )
- A( K, K ) = A( KP, KP )
- A( KP, KP ) = TEMP
- IF( KSTEP.EQ.2 ) THEN
- TEMP = A( K, K+1 )
- A( K, K+1 ) = A( KP, K+1 )
- A( KP, K+1 ) = TEMP
- END IF
- END IF
-*
- K = K + KSTEP
- GO TO 30
- 40 CONTINUE
-*
- ELSE
-*
-* Compute inv(A) from the factorization A = L*D*L'.
-*
-* K is the main loop index, increasing from 1 to N in steps of
-* 1 or 2, depending on the size of the diagonal blocks.
-*
- K = N
- 50 CONTINUE
-*
-* If K < 1, exit from loop.
-*
- IF( K.LT.1 )
- $ GO TO 60
-*
- IF( IPIV( K ).GT.0 ) THEN
-*
-* 1 x 1 diagonal block
-*
-* Invert the diagonal block.
-*
- A( K, K ) = ONE / A( K, K )
-*
-* Compute column K of the inverse.
-*
- IF( K.LT.N ) THEN
- CALL DCOPY( N-K, A( K+1, K ), 1, WORK, 1 )
- CALL DSYMV( UPLO, N-K, -ONE, A( K+1, K+1 ), LDA, WORK, 1,
- $ ZERO, A( K+1, K ), 1 )
- A( K, K ) = A( K, K ) - DDOT( N-K, WORK, 1, A( K+1, K ),
- $ 1 )
- END IF
- KSTEP = 1
- ELSE
-*
-* 2 x 2 diagonal block
-*
-* Invert the diagonal block.
-*
- T = ABS( A( K, K-1 ) )
- AK = A( K-1, K-1 ) / T
- AKP1 = A( K, K ) / T
- AKKP1 = A( K, K-1 ) / T
- D = T*( AK*AKP1-ONE )
- A( K-1, K-1 ) = AKP1 / D
- A( K, K ) = AK / D
- A( K, K-1 ) = -AKKP1 / D
-*
-* Compute columns K-1 and K of the inverse.
-*
- IF( K.LT.N ) THEN
- CALL DCOPY( N-K, A( K+1, K ), 1, WORK, 1 )
- CALL DSYMV( UPLO, N-K, -ONE, A( K+1, K+1 ), LDA, WORK, 1,
- $ ZERO, A( K+1, K ), 1 )
- A( K, K ) = A( K, K ) - DDOT( N-K, WORK, 1, A( K+1, K ),
- $ 1 )
- A( K, K-1 ) = A( K, K-1 ) -
- $ DDOT( N-K, A( K+1, K ), 1, A( K+1, K-1 ),
- $ 1 )
- CALL DCOPY( N-K, A( K+1, K-1 ), 1, WORK, 1 )
- CALL DSYMV( UPLO, N-K, -ONE, A( K+1, K+1 ), LDA, WORK, 1,
- $ ZERO, A( K+1, K-1 ), 1 )
- A( K-1, K-1 ) = A( K-1, K-1 ) -
- $ DDOT( N-K, WORK, 1, A( K+1, K-1 ), 1 )
- END IF
- KSTEP = 2
- END IF
-*
- KP = ABS( IPIV( K ) )
- IF( KP.NE.K ) THEN
-*
-* Interchange rows and columns K and KP in the trailing
-* submatrix A(k-1:n,k-1:n)
-*
- IF( KP.LT.N )
- $ CALL DSWAP( N-KP, A( KP+1, K ), 1, A( KP+1, KP ), 1 )
- CALL DSWAP( KP-K-1, A( K+1, K ), 1, A( KP, K+1 ), LDA )
- TEMP = A( K, K )
- A( K, K ) = A( KP, KP )
- A( KP, KP ) = TEMP
- IF( KSTEP.EQ.2 ) THEN
- TEMP = A( K, K-1 )
- A( K, K-1 ) = A( KP, K-1 )
- A( KP, K-1 ) = TEMP
- END IF
- END IF
-*
- K = K - KSTEP
- GO TO 50
- 60 CONTINUE
- END IF
-*
- RETURN
-*
-* End of DSYTRI
-*
- END
diff --git a/src/lib/lapack/dsytrs.f b/src/lib/lapack/dsytrs.f
deleted file mode 100644
index 163ed5b9..00000000
--- a/src/lib/lapack/dsytrs.f
+++ /dev/null
@@ -1,369 +0,0 @@
- SUBROUTINE DSYTRS( UPLO, N, NRHS, A, LDA, IPIV, B, LDB, INFO )
-*
-* -- LAPACK routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- CHARACTER UPLO
- INTEGER INFO, LDA, LDB, N, NRHS
-* ..
-* .. Array Arguments ..
- INTEGER IPIV( * )
- DOUBLE PRECISION A( LDA, * ), B( LDB, * )
-* ..
-*
-* Purpose
-* =======
-*
-* DSYTRS solves a system of linear equations A*X = B with a real
-* symmetric matrix A using the factorization A = U*D*U**T or
-* A = L*D*L**T computed by DSYTRF.
-*
-* Arguments
-* =========
-*
-* UPLO (input) CHARACTER*1
-* Specifies whether the details of the factorization are stored
-* as an upper or lower triangular matrix.
-* = 'U': Upper triangular, form is A = U*D*U**T;
-* = 'L': Lower triangular, form is A = L*D*L**T.
-*
-* N (input) INTEGER
-* The order of the matrix A. N >= 0.
-*
-* NRHS (input) INTEGER
-* The number of right hand sides, i.e., the number of columns
-* of the matrix B. NRHS >= 0.
-*
-* A (input) DOUBLE PRECISION array, dimension (LDA,N)
-* The block diagonal matrix D and the multipliers used to
-* obtain the factor U or L as computed by DSYTRF.
-*
-* LDA (input) INTEGER
-* The leading dimension of the array A. LDA >= max(1,N).
-*
-* IPIV (input) INTEGER array, dimension (N)
-* Details of the interchanges and the block structure of D
-* as determined by DSYTRF.
-*
-* B (input/output) DOUBLE PRECISION array, dimension (LDB,NRHS)
-* On entry, the right hand side matrix B.
-* On exit, the solution matrix X.
-*
-* LDB (input) INTEGER
-* The leading dimension of the array B. LDB >= max(1,N).
-*
-* INFO (output) INTEGER
-* = 0: successful exit
-* < 0: if INFO = -i, the i-th argument had an illegal value
-*
-* =====================================================================
-*
-* .. Parameters ..
- DOUBLE PRECISION ONE
- PARAMETER ( ONE = 1.0D+0 )
-* ..
-* .. Local Scalars ..
- LOGICAL UPPER
- INTEGER J, K, KP
- DOUBLE PRECISION AK, AKM1, AKM1K, BK, BKM1, DENOM
-* ..
-* .. External Functions ..
- LOGICAL LSAME
- EXTERNAL LSAME
-* ..
-* .. External Subroutines ..
- EXTERNAL DGEMV, DGER, DSCAL, DSWAP, XERBLA
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC MAX
-* ..
-* .. Executable Statements ..
-*
- INFO = 0
- UPPER = LSAME( UPLO, 'U' )
- IF( .NOT.UPPER .AND. .NOT.LSAME( UPLO, 'L' ) ) THEN
- INFO = -1
- ELSE IF( N.LT.0 ) THEN
- INFO = -2
- ELSE IF( NRHS.LT.0 ) THEN
- INFO = -3
- ELSE IF( LDA.LT.MAX( 1, N ) ) THEN
- INFO = -5
- ELSE IF( LDB.LT.MAX( 1, N ) ) THEN
- INFO = -8
- END IF
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'DSYTRS', -INFO )
- RETURN
- END IF
-*
-* Quick return if possible
-*
- IF( N.EQ.0 .OR. NRHS.EQ.0 )
- $ RETURN
-*
- IF( UPPER ) THEN
-*
-* Solve A*X = B, where A = U*D*U'.
-*
-* First solve U*D*X = B, overwriting B with X.
-*
-* K is the main loop index, decreasing from N to 1 in steps of
-* 1 or 2, depending on the size of the diagonal blocks.
-*
- K = N
- 10 CONTINUE
-*
-* If K < 1, exit from loop.
-*
- IF( K.LT.1 )
- $ GO TO 30
-*
- IF( IPIV( K ).GT.0 ) THEN
-*
-* 1 x 1 diagonal block
-*
-* Interchange rows K and IPIV(K).
-*
- KP = IPIV( K )
- IF( KP.NE.K )
- $ CALL DSWAP( NRHS, B( K, 1 ), LDB, B( KP, 1 ), LDB )
-*
-* Multiply by inv(U(K)), where U(K) is the transformation
-* stored in column K of A.
-*
- CALL DGER( K-1, NRHS, -ONE, A( 1, K ), 1, B( K, 1 ), LDB,
- $ B( 1, 1 ), LDB )
-*
-* Multiply by the inverse of the diagonal block.
-*
- CALL DSCAL( NRHS, ONE / A( K, K ), B( K, 1 ), LDB )
- K = K - 1
- ELSE
-*
-* 2 x 2 diagonal block
-*
-* Interchange rows K-1 and -IPIV(K).
-*
- KP = -IPIV( K )
- IF( KP.NE.K-1 )
- $ CALL DSWAP( NRHS, B( K-1, 1 ), LDB, B( KP, 1 ), LDB )
-*
-* Multiply by inv(U(K)), where U(K) is the transformation
-* stored in columns K-1 and K of A.
-*
- CALL DGER( K-2, NRHS, -ONE, A( 1, K ), 1, B( K, 1 ), LDB,
- $ B( 1, 1 ), LDB )
- CALL DGER( K-2, NRHS, -ONE, A( 1, K-1 ), 1, B( K-1, 1 ),
- $ LDB, B( 1, 1 ), LDB )
-*
-* Multiply by the inverse of the diagonal block.
-*
- AKM1K = A( K-1, K )
- AKM1 = A( K-1, K-1 ) / AKM1K
- AK = A( K, K ) / AKM1K
- DENOM = AKM1*AK - ONE
- DO 20 J = 1, NRHS
- BKM1 = B( K-1, J ) / AKM1K
- BK = B( K, J ) / AKM1K
- B( K-1, J ) = ( AK*BKM1-BK ) / DENOM
- B( K, J ) = ( AKM1*BK-BKM1 ) / DENOM
- 20 CONTINUE
- K = K - 2
- END IF
-*
- GO TO 10
- 30 CONTINUE
-*
-* Next solve U'*X = B, overwriting B with X.
-*
-* K is the main loop index, increasing from 1 to N in steps of
-* 1 or 2, depending on the size of the diagonal blocks.
-*
- K = 1
- 40 CONTINUE
-*
-* If K > N, exit from loop.
-*
- IF( K.GT.N )
- $ GO TO 50
-*
- IF( IPIV( K ).GT.0 ) THEN
-*
-* 1 x 1 diagonal block
-*
-* Multiply by inv(U'(K)), where U(K) is the transformation
-* stored in column K of A.
-*
- CALL DGEMV( 'Transpose', K-1, NRHS, -ONE, B, LDB, A( 1, K ),
- $ 1, ONE, B( K, 1 ), LDB )
-*
-* Interchange rows K and IPIV(K).
-*
- KP = IPIV( K )
- IF( KP.NE.K )
- $ CALL DSWAP( NRHS, B( K, 1 ), LDB, B( KP, 1 ), LDB )
- K = K + 1
- ELSE
-*
-* 2 x 2 diagonal block
-*
-* Multiply by inv(U'(K+1)), where U(K+1) is the transformation
-* stored in columns K and K+1 of A.
-*
- CALL DGEMV( 'Transpose', K-1, NRHS, -ONE, B, LDB, A( 1, K ),
- $ 1, ONE, B( K, 1 ), LDB )
- CALL DGEMV( 'Transpose', K-1, NRHS, -ONE, B, LDB,
- $ A( 1, K+1 ), 1, ONE, B( K+1, 1 ), LDB )
-*
-* Interchange rows K and -IPIV(K).
-*
- KP = -IPIV( K )
- IF( KP.NE.K )
- $ CALL DSWAP( NRHS, B( K, 1 ), LDB, B( KP, 1 ), LDB )
- K = K + 2
- END IF
-*
- GO TO 40
- 50 CONTINUE
-*
- ELSE
-*
-* Solve A*X = B, where A = L*D*L'.
-*
-* First solve L*D*X = B, overwriting B with X.
-*
-* K is the main loop index, increasing from 1 to N in steps of
-* 1 or 2, depending on the size of the diagonal blocks.
-*
- K = 1
- 60 CONTINUE
-*
-* If K > N, exit from loop.
-*
- IF( K.GT.N )
- $ GO TO 80
-*
- IF( IPIV( K ).GT.0 ) THEN
-*
-* 1 x 1 diagonal block
-*
-* Interchange rows K and IPIV(K).
-*
- KP = IPIV( K )
- IF( KP.NE.K )
- $ CALL DSWAP( NRHS, B( K, 1 ), LDB, B( KP, 1 ), LDB )
-*
-* Multiply by inv(L(K)), where L(K) is the transformation
-* stored in column K of A.
-*
- IF( K.LT.N )
- $ CALL DGER( N-K, NRHS, -ONE, A( K+1, K ), 1, B( K, 1 ),
- $ LDB, B( K+1, 1 ), LDB )
-*
-* Multiply by the inverse of the diagonal block.
-*
- CALL DSCAL( NRHS, ONE / A( K, K ), B( K, 1 ), LDB )
- K = K + 1
- ELSE
-*
-* 2 x 2 diagonal block
-*
-* Interchange rows K+1 and -IPIV(K).
-*
- KP = -IPIV( K )
- IF( KP.NE.K+1 )
- $ CALL DSWAP( NRHS, B( K+1, 1 ), LDB, B( KP, 1 ), LDB )
-*
-* Multiply by inv(L(K)), where L(K) is the transformation
-* stored in columns K and K+1 of A.
-*
- IF( K.LT.N-1 ) THEN
- CALL DGER( N-K-1, NRHS, -ONE, A( K+2, K ), 1, B( K, 1 ),
- $ LDB, B( K+2, 1 ), LDB )
- CALL DGER( N-K-1, NRHS, -ONE, A( K+2, K+1 ), 1,
- $ B( K+1, 1 ), LDB, B( K+2, 1 ), LDB )
- END IF
-*
-* Multiply by the inverse of the diagonal block.
-*
- AKM1K = A( K+1, K )
- AKM1 = A( K, K ) / AKM1K
- AK = A( K+1, K+1 ) / AKM1K
- DENOM = AKM1*AK - ONE
- DO 70 J = 1, NRHS
- BKM1 = B( K, J ) / AKM1K
- BK = B( K+1, J ) / AKM1K
- B( K, J ) = ( AK*BKM1-BK ) / DENOM
- B( K+1, J ) = ( AKM1*BK-BKM1 ) / DENOM
- 70 CONTINUE
- K = K + 2
- END IF
-*
- GO TO 60
- 80 CONTINUE
-*
-* Next solve L'*X = B, overwriting B with X.
-*
-* K is the main loop index, decreasing from N to 1 in steps of
-* 1 or 2, depending on the size of the diagonal blocks.
-*
- K = N
- 90 CONTINUE
-*
-* If K < 1, exit from loop.
-*
- IF( K.LT.1 )
- $ GO TO 100
-*
- IF( IPIV( K ).GT.0 ) THEN
-*
-* 1 x 1 diagonal block
-*
-* Multiply by inv(L'(K)), where L(K) is the transformation
-* stored in column K of A.
-*
- IF( K.LT.N )
- $ CALL DGEMV( 'Transpose', N-K, NRHS, -ONE, B( K+1, 1 ),
- $ LDB, A( K+1, K ), 1, ONE, B( K, 1 ), LDB )
-*
-* Interchange rows K and IPIV(K).
-*
- KP = IPIV( K )
- IF( KP.NE.K )
- $ CALL DSWAP( NRHS, B( K, 1 ), LDB, B( KP, 1 ), LDB )
- K = K - 1
- ELSE
-*
-* 2 x 2 diagonal block
-*
-* Multiply by inv(L'(K-1)), where L(K-1) is the transformation
-* stored in columns K-1 and K of A.
-*
- IF( K.LT.N ) THEN
- CALL DGEMV( 'Transpose', N-K, NRHS, -ONE, B( K+1, 1 ),
- $ LDB, A( K+1, K ), 1, ONE, B( K, 1 ), LDB )
- CALL DGEMV( 'Transpose', N-K, NRHS, -ONE, B( K+1, 1 ),
- $ LDB, A( K+1, K-1 ), 1, ONE, B( K-1, 1 ),
- $ LDB )
- END IF
-*
-* Interchange rows K and -IPIV(K).
-*
- KP = -IPIV( K )
- IF( KP.NE.K )
- $ CALL DSWAP( NRHS, B( K, 1 ), LDB, B( KP, 1 ), LDB )
- K = K - 2
- END IF
-*
- GO TO 90
- 100 CONTINUE
- END IF
-*
- RETURN
-*
-* End of DSYTRS
-*
- END
diff --git a/src/lib/lapack/dtgevc.f b/src/lib/lapack/dtgevc.f
deleted file mode 100644
index 091c3f65..00000000
--- a/src/lib/lapack/dtgevc.f
+++ /dev/null
@@ -1,1147 +0,0 @@
- SUBROUTINE DTGEVC( SIDE, HOWMNY, SELECT, N, S, LDS, P, LDP, VL,
- $ LDVL, VR, LDVR, MM, M, WORK, INFO )
-*
-* -- LAPACK routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- CHARACTER HOWMNY, SIDE
- INTEGER INFO, LDP, LDS, LDVL, LDVR, M, MM, N
-* ..
-* .. Array Arguments ..
- LOGICAL SELECT( * )
- DOUBLE PRECISION P( LDP, * ), S( LDS, * ), VL( LDVL, * ),
- $ VR( LDVR, * ), WORK( * )
-* ..
-*
-*
-* Purpose
-* =======
-*
-* DTGEVC computes some or all of the right and/or left eigenvectors of
-* a pair of real matrices (S,P), where S is a quasi-triangular matrix
-* and P is upper triangular. Matrix pairs of this type are produced by
-* the generalized Schur factorization of a matrix pair (A,B):
-*
-* A = Q*S*Z**T, B = Q*P*Z**T
-*
-* as computed by DGGHRD + DHGEQZ.
-*
-* The right eigenvector x and the left eigenvector y of (S,P)
-* corresponding to an eigenvalue w are defined by:
-*
-* S*x = w*P*x, (y**H)*S = w*(y**H)*P,
-*
-* where y**H denotes the conjugate tranpose of y.
-* The eigenvalues are not input to this routine, but are computed
-* directly from the diagonal blocks of S and P.
-*
-* This routine returns the matrices X and/or Y of right and left
-* eigenvectors of (S,P), or the products Z*X and/or Q*Y,
-* where Z and Q are input matrices.
-* If Q and Z are the orthogonal factors from the generalized Schur
-* factorization of a matrix pair (A,B), then Z*X and Q*Y
-* are the matrices of right and left eigenvectors of (A,B).
-*
-* Arguments
-* =========
-*
-* SIDE (input) CHARACTER*1
-* = 'R': compute right eigenvectors only;
-* = 'L': compute left eigenvectors only;
-* = 'B': compute both right and left eigenvectors.
-*
-* HOWMNY (input) CHARACTER*1
-* = 'A': compute all right and/or left eigenvectors;
-* = 'B': compute all right and/or left eigenvectors,
-* backtransformed by the matrices in VR and/or VL;
-* = 'S': compute selected right and/or left eigenvectors,
-* specified by the logical array SELECT.
-*
-* SELECT (input) LOGICAL array, dimension (N)
-* If HOWMNY='S', SELECT specifies the eigenvectors to be
-* computed. If w(j) is a real eigenvalue, the corresponding
-* real eigenvector is computed if SELECT(j) is .TRUE..
-* If w(j) and w(j+1) are the real and imaginary parts of a
-* complex eigenvalue, the corresponding complex eigenvector
-* is computed if either SELECT(j) or SELECT(j+1) is .TRUE.,
-* and on exit SELECT(j) is set to .TRUE. and SELECT(j+1) is
-* set to .FALSE..
-* Not referenced if HOWMNY = 'A' or 'B'.
-*
-* N (input) INTEGER
-* The order of the matrices S and P. N >= 0.
-*
-* S (input) DOUBLE PRECISION array, dimension (LDS,N)
-* The upper quasi-triangular matrix S from a generalized Schur
-* factorization, as computed by DHGEQZ.
-*
-* LDS (input) INTEGER
-* The leading dimension of array S. LDS >= max(1,N).
-*
-* P (input) DOUBLE PRECISION array, dimension (LDP,N)
-* The upper triangular matrix P from a generalized Schur
-* factorization, as computed by DHGEQZ.
-* 2-by-2 diagonal blocks of P corresponding to 2-by-2 blocks
-* of S must be in positive diagonal form.
-*
-* LDP (input) INTEGER
-* The leading dimension of array P. LDP >= max(1,N).
-*
-* VL (input/output) DOUBLE PRECISION array, dimension (LDVL,MM)
-* On entry, if SIDE = 'L' or 'B' and HOWMNY = 'B', VL must
-* contain an N-by-N matrix Q (usually the orthogonal matrix Q
-* of left Schur vectors returned by DHGEQZ).
-* On exit, if SIDE = 'L' or 'B', VL contains:
-* if HOWMNY = 'A', the matrix Y of left eigenvectors of (S,P);
-* if HOWMNY = 'B', the matrix Q*Y;
-* if HOWMNY = 'S', the left eigenvectors of (S,P) specified by
-* SELECT, stored consecutively in the columns of
-* VL, in the same order as their eigenvalues.
-*
-* A complex eigenvector corresponding to a complex eigenvalue
-* is stored in two consecutive columns, the first holding the
-* real part, and the second the imaginary part.
-*
-* Not referenced if SIDE = 'R'.
-*
-* LDVL (input) INTEGER
-* The leading dimension of array VL. LDVL >= 1, and if
-* SIDE = 'L' or 'B', LDVL >= N.
-*
-* VR (input/output) DOUBLE PRECISION array, dimension (LDVR,MM)
-* On entry, if SIDE = 'R' or 'B' and HOWMNY = 'B', VR must
-* contain an N-by-N matrix Z (usually the orthogonal matrix Z
-* of right Schur vectors returned by DHGEQZ).
-*
-* On exit, if SIDE = 'R' or 'B', VR contains:
-* if HOWMNY = 'A', the matrix X of right eigenvectors of (S,P);
-* if HOWMNY = 'B' or 'b', the matrix Z*X;
-* if HOWMNY = 'S' or 's', the right eigenvectors of (S,P)
-* specified by SELECT, stored consecutively in the
-* columns of VR, in the same order as their
-* eigenvalues.
-*
-* A complex eigenvector corresponding to a complex eigenvalue
-* is stored in two consecutive columns, the first holding the
-* real part and the second the imaginary part.
-*
-* Not referenced if SIDE = 'L'.
-*
-* LDVR (input) INTEGER
-* The leading dimension of the array VR. LDVR >= 1, and if
-* SIDE = 'R' or 'B', LDVR >= N.
-*
-* MM (input) INTEGER
-* The number of columns in the arrays VL and/or VR. MM >= M.
-*
-* M (output) INTEGER
-* The number of columns in the arrays VL and/or VR actually
-* used to store the eigenvectors. If HOWMNY = 'A' or 'B', M
-* is set to N. Each selected real eigenvector occupies one
-* column and each selected complex eigenvector occupies two
-* columns.
-*
-* WORK (workspace) DOUBLE PRECISION array, dimension (6*N)
-*
-* INFO (output) INTEGER
-* = 0: successful exit.
-* < 0: if INFO = -i, the i-th argument had an illegal value.
-* > 0: the 2-by-2 block (INFO:INFO+1) does not have a complex
-* eigenvalue.
-*
-* Further Details
-* ===============
-*
-* Allocation of workspace:
-* ---------- -- ---------
-*
-* WORK( j ) = 1-norm of j-th column of A, above the diagonal
-* WORK( N+j ) = 1-norm of j-th column of B, above the diagonal
-* WORK( 2*N+1:3*N ) = real part of eigenvector
-* WORK( 3*N+1:4*N ) = imaginary part of eigenvector
-* WORK( 4*N+1:5*N ) = real part of back-transformed eigenvector
-* WORK( 5*N+1:6*N ) = imaginary part of back-transformed eigenvector
-*
-* Rowwise vs. columnwise solution methods:
-* ------- -- ---------- -------- -------
-*
-* Finding a generalized eigenvector consists basically of solving the
-* singular triangular system
-*
-* (A - w B) x = 0 (for right) or: (A - w B)**H y = 0 (for left)
-*
-* Consider finding the i-th right eigenvector (assume all eigenvalues
-* are real). The equation to be solved is:
-* n i
-* 0 = sum C(j,k) v(k) = sum C(j,k) v(k) for j = i,. . .,1
-* k=j k=j
-*
-* where C = (A - w B) (The components v(i+1:n) are 0.)
-*
-* The "rowwise" method is:
-*
-* (1) v(i) := 1
-* for j = i-1,. . .,1:
-* i
-* (2) compute s = - sum C(j,k) v(k) and
-* k=j+1
-*
-* (3) v(j) := s / C(j,j)
-*
-* Step 2 is sometimes called the "dot product" step, since it is an
-* inner product between the j-th row and the portion of the eigenvector
-* that has been computed so far.
-*
-* The "columnwise" method consists basically in doing the sums
-* for all the rows in parallel. As each v(j) is computed, the
-* contribution of v(j) times the j-th column of C is added to the
-* partial sums. Since FORTRAN arrays are stored columnwise, this has
-* the advantage that at each step, the elements of C that are accessed
-* are adjacent to one another, whereas with the rowwise method, the
-* elements accessed at a step are spaced LDS (and LDP) words apart.
-*
-* When finding left eigenvectors, the matrix in question is the
-* transpose of the one in storage, so the rowwise method then
-* actually accesses columns of A and B at each step, and so is the
-* preferred method.
-*
-* =====================================================================
-*
-* .. Parameters ..
- DOUBLE PRECISION ZERO, ONE, SAFETY
- PARAMETER ( ZERO = 0.0D+0, ONE = 1.0D+0,
- $ SAFETY = 1.0D+2 )
-* ..
-* .. Local Scalars ..
- LOGICAL COMPL, COMPR, IL2BY2, ILABAD, ILALL, ILBACK,
- $ ILBBAD, ILCOMP, ILCPLX, LSA, LSB
- INTEGER I, IBEG, IEIG, IEND, IHWMNY, IINFO, IM, ISIDE,
- $ J, JA, JC, JE, JR, JW, NA, NW
- DOUBLE PRECISION ACOEF, ACOEFA, ANORM, ASCALE, BCOEFA, BCOEFI,
- $ BCOEFR, BIG, BIGNUM, BNORM, BSCALE, CIM2A,
- $ CIM2B, CIMAGA, CIMAGB, CRE2A, CRE2B, CREALA,
- $ CREALB, DMIN, SAFMIN, SALFAR, SBETA, SCALE,
- $ SMALL, TEMP, TEMP2, TEMP2I, TEMP2R, ULP, XMAX,
- $ XSCALE
-* ..
-* .. Local Arrays ..
- DOUBLE PRECISION BDIAG( 2 ), SUM( 2, 2 ), SUMS( 2, 2 ),
- $ SUMP( 2, 2 )
-* ..
-* .. External Functions ..
- LOGICAL LSAME
- DOUBLE PRECISION DLAMCH
- EXTERNAL LSAME, DLAMCH
-* ..
-* .. External Subroutines ..
- EXTERNAL DGEMV, DLABAD, DLACPY, DLAG2, DLALN2, XERBLA
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC ABS, MAX, MIN
-* ..
-* .. Executable Statements ..
-*
-* Decode and Test the input parameters
-*
- IF( LSAME( HOWMNY, 'A' ) ) THEN
- IHWMNY = 1
- ILALL = .TRUE.
- ILBACK = .FALSE.
- ELSE IF( LSAME( HOWMNY, 'S' ) ) THEN
- IHWMNY = 2
- ILALL = .FALSE.
- ILBACK = .FALSE.
- ELSE IF( LSAME( HOWMNY, 'B' ) ) THEN
- IHWMNY = 3
- ILALL = .TRUE.
- ILBACK = .TRUE.
- ELSE
- IHWMNY = -1
- ILALL = .TRUE.
- END IF
-*
- IF( LSAME( SIDE, 'R' ) ) THEN
- ISIDE = 1
- COMPL = .FALSE.
- COMPR = .TRUE.
- ELSE IF( LSAME( SIDE, 'L' ) ) THEN
- ISIDE = 2
- COMPL = .TRUE.
- COMPR = .FALSE.
- ELSE IF( LSAME( SIDE, 'B' ) ) THEN
- ISIDE = 3
- COMPL = .TRUE.
- COMPR = .TRUE.
- ELSE
- ISIDE = -1
- END IF
-*
- INFO = 0
- IF( ISIDE.LT.0 ) THEN
- INFO = -1
- ELSE IF( IHWMNY.LT.0 ) THEN
- INFO = -2
- ELSE IF( N.LT.0 ) THEN
- INFO = -4
- ELSE IF( LDS.LT.MAX( 1, N ) ) THEN
- INFO = -6
- ELSE IF( LDP.LT.MAX( 1, N ) ) THEN
- INFO = -8
- END IF
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'DTGEVC', -INFO )
- RETURN
- END IF
-*
-* Count the number of eigenvectors to be computed
-*
- IF( .NOT.ILALL ) THEN
- IM = 0
- ILCPLX = .FALSE.
- DO 10 J = 1, N
- IF( ILCPLX ) THEN
- ILCPLX = .FALSE.
- GO TO 10
- END IF
- IF( J.LT.N ) THEN
- IF( S( J+1, J ).NE.ZERO )
- $ ILCPLX = .TRUE.
- END IF
- IF( ILCPLX ) THEN
- IF( SELECT( J ) .OR. SELECT( J+1 ) )
- $ IM = IM + 2
- ELSE
- IF( SELECT( J ) )
- $ IM = IM + 1
- END IF
- 10 CONTINUE
- ELSE
- IM = N
- END IF
-*
-* Check 2-by-2 diagonal blocks of A, B
-*
- ILABAD = .FALSE.
- ILBBAD = .FALSE.
- DO 20 J = 1, N - 1
- IF( S( J+1, J ).NE.ZERO ) THEN
- IF( P( J, J ).EQ.ZERO .OR. P( J+1, J+1 ).EQ.ZERO .OR.
- $ P( J, J+1 ).NE.ZERO )ILBBAD = .TRUE.
- IF( J.LT.N-1 ) THEN
- IF( S( J+2, J+1 ).NE.ZERO )
- $ ILABAD = .TRUE.
- END IF
- END IF
- 20 CONTINUE
-*
- IF( ILABAD ) THEN
- INFO = -5
- ELSE IF( ILBBAD ) THEN
- INFO = -7
- ELSE IF( COMPL .AND. LDVL.LT.N .OR. LDVL.LT.1 ) THEN
- INFO = -10
- ELSE IF( COMPR .AND. LDVR.LT.N .OR. LDVR.LT.1 ) THEN
- INFO = -12
- ELSE IF( MM.LT.IM ) THEN
- INFO = -13
- END IF
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'DTGEVC', -INFO )
- RETURN
- END IF
-*
-* Quick return if possible
-*
- M = IM
- IF( N.EQ.0 )
- $ RETURN
-*
-* Machine Constants
-*
- SAFMIN = DLAMCH( 'Safe minimum' )
- BIG = ONE / SAFMIN
- CALL DLABAD( SAFMIN, BIG )
- ULP = DLAMCH( 'Epsilon' )*DLAMCH( 'Base' )
- SMALL = SAFMIN*N / ULP
- BIG = ONE / SMALL
- BIGNUM = ONE / ( SAFMIN*N )
-*
-* Compute the 1-norm of each column of the strictly upper triangular
-* part (i.e., excluding all elements belonging to the diagonal
-* blocks) of A and B to check for possible overflow in the
-* triangular solver.
-*
- ANORM = ABS( S( 1, 1 ) )
- IF( N.GT.1 )
- $ ANORM = ANORM + ABS( S( 2, 1 ) )
- BNORM = ABS( P( 1, 1 ) )
- WORK( 1 ) = ZERO
- WORK( N+1 ) = ZERO
-*
- DO 50 J = 2, N
- TEMP = ZERO
- TEMP2 = ZERO
- IF( S( J, J-1 ).EQ.ZERO ) THEN
- IEND = J - 1
- ELSE
- IEND = J - 2
- END IF
- DO 30 I = 1, IEND
- TEMP = TEMP + ABS( S( I, J ) )
- TEMP2 = TEMP2 + ABS( P( I, J ) )
- 30 CONTINUE
- WORK( J ) = TEMP
- WORK( N+J ) = TEMP2
- DO 40 I = IEND + 1, MIN( J+1, N )
- TEMP = TEMP + ABS( S( I, J ) )
- TEMP2 = TEMP2 + ABS( P( I, J ) )
- 40 CONTINUE
- ANORM = MAX( ANORM, TEMP )
- BNORM = MAX( BNORM, TEMP2 )
- 50 CONTINUE
-*
- ASCALE = ONE / MAX( ANORM, SAFMIN )
- BSCALE = ONE / MAX( BNORM, SAFMIN )
-*
-* Left eigenvectors
-*
- IF( COMPL ) THEN
- IEIG = 0
-*
-* Main loop over eigenvalues
-*
- ILCPLX = .FALSE.
- DO 220 JE = 1, N
-*
-* Skip this iteration if (a) HOWMNY='S' and SELECT=.FALSE., or
-* (b) this would be the second of a complex pair.
-* Check for complex eigenvalue, so as to be sure of which
-* entry(-ies) of SELECT to look at.
-*
- IF( ILCPLX ) THEN
- ILCPLX = .FALSE.
- GO TO 220
- END IF
- NW = 1
- IF( JE.LT.N ) THEN
- IF( S( JE+1, JE ).NE.ZERO ) THEN
- ILCPLX = .TRUE.
- NW = 2
- END IF
- END IF
- IF( ILALL ) THEN
- ILCOMP = .TRUE.
- ELSE IF( ILCPLX ) THEN
- ILCOMP = SELECT( JE ) .OR. SELECT( JE+1 )
- ELSE
- ILCOMP = SELECT( JE )
- END IF
- IF( .NOT.ILCOMP )
- $ GO TO 220
-*
-* Decide if (a) singular pencil, (b) real eigenvalue, or
-* (c) complex eigenvalue.
-*
- IF( .NOT.ILCPLX ) THEN
- IF( ABS( S( JE, JE ) ).LE.SAFMIN .AND.
- $ ABS( P( JE, JE ) ).LE.SAFMIN ) THEN
-*
-* Singular matrix pencil -- return unit eigenvector
-*
- IEIG = IEIG + 1
- DO 60 JR = 1, N
- VL( JR, IEIG ) = ZERO
- 60 CONTINUE
- VL( IEIG, IEIG ) = ONE
- GO TO 220
- END IF
- END IF
-*
-* Clear vector
-*
- DO 70 JR = 1, NW*N
- WORK( 2*N+JR ) = ZERO
- 70 CONTINUE
-* T
-* Compute coefficients in ( a A - b B ) y = 0
-* a is ACOEF
-* b is BCOEFR + i*BCOEFI
-*
- IF( .NOT.ILCPLX ) THEN
-*
-* Real eigenvalue
-*
- TEMP = ONE / MAX( ABS( S( JE, JE ) )*ASCALE,
- $ ABS( P( JE, JE ) )*BSCALE, SAFMIN )
- SALFAR = ( TEMP*S( JE, JE ) )*ASCALE
- SBETA = ( TEMP*P( JE, JE ) )*BSCALE
- ACOEF = SBETA*ASCALE
- BCOEFR = SALFAR*BSCALE
- BCOEFI = ZERO
-*
-* Scale to avoid underflow
-*
- SCALE = ONE
- LSA = ABS( SBETA ).GE.SAFMIN .AND. ABS( ACOEF ).LT.SMALL
- LSB = ABS( SALFAR ).GE.SAFMIN .AND. ABS( BCOEFR ).LT.
- $ SMALL
- IF( LSA )
- $ SCALE = ( SMALL / ABS( SBETA ) )*MIN( ANORM, BIG )
- IF( LSB )
- $ SCALE = MAX( SCALE, ( SMALL / ABS( SALFAR ) )*
- $ MIN( BNORM, BIG ) )
- IF( LSA .OR. LSB ) THEN
- SCALE = MIN( SCALE, ONE /
- $ ( SAFMIN*MAX( ONE, ABS( ACOEF ),
- $ ABS( BCOEFR ) ) ) )
- IF( LSA ) THEN
- ACOEF = ASCALE*( SCALE*SBETA )
- ELSE
- ACOEF = SCALE*ACOEF
- END IF
- IF( LSB ) THEN
- BCOEFR = BSCALE*( SCALE*SALFAR )
- ELSE
- BCOEFR = SCALE*BCOEFR
- END IF
- END IF
- ACOEFA = ABS( ACOEF )
- BCOEFA = ABS( BCOEFR )
-*
-* First component is 1
-*
- WORK( 2*N+JE ) = ONE
- XMAX = ONE
- ELSE
-*
-* Complex eigenvalue
-*
- CALL DLAG2( S( JE, JE ), LDS, P( JE, JE ), LDP,
- $ SAFMIN*SAFETY, ACOEF, TEMP, BCOEFR, TEMP2,
- $ BCOEFI )
- BCOEFI = -BCOEFI
- IF( BCOEFI.EQ.ZERO ) THEN
- INFO = JE
- RETURN
- END IF
-*
-* Scale to avoid over/underflow
-*
- ACOEFA = ABS( ACOEF )
- BCOEFA = ABS( BCOEFR ) + ABS( BCOEFI )
- SCALE = ONE
- IF( ACOEFA*ULP.LT.SAFMIN .AND. ACOEFA.GE.SAFMIN )
- $ SCALE = ( SAFMIN / ULP ) / ACOEFA
- IF( BCOEFA*ULP.LT.SAFMIN .AND. BCOEFA.GE.SAFMIN )
- $ SCALE = MAX( SCALE, ( SAFMIN / ULP ) / BCOEFA )
- IF( SAFMIN*ACOEFA.GT.ASCALE )
- $ SCALE = ASCALE / ( SAFMIN*ACOEFA )
- IF( SAFMIN*BCOEFA.GT.BSCALE )
- $ SCALE = MIN( SCALE, BSCALE / ( SAFMIN*BCOEFA ) )
- IF( SCALE.NE.ONE ) THEN
- ACOEF = SCALE*ACOEF
- ACOEFA = ABS( ACOEF )
- BCOEFR = SCALE*BCOEFR
- BCOEFI = SCALE*BCOEFI
- BCOEFA = ABS( BCOEFR ) + ABS( BCOEFI )
- END IF
-*
-* Compute first two components of eigenvector
-*
- TEMP = ACOEF*S( JE+1, JE )
- TEMP2R = ACOEF*S( JE, JE ) - BCOEFR*P( JE, JE )
- TEMP2I = -BCOEFI*P( JE, JE )
- IF( ABS( TEMP ).GT.ABS( TEMP2R )+ABS( TEMP2I ) ) THEN
- WORK( 2*N+JE ) = ONE
- WORK( 3*N+JE ) = ZERO
- WORK( 2*N+JE+1 ) = -TEMP2R / TEMP
- WORK( 3*N+JE+1 ) = -TEMP2I / TEMP
- ELSE
- WORK( 2*N+JE+1 ) = ONE
- WORK( 3*N+JE+1 ) = ZERO
- TEMP = ACOEF*S( JE, JE+1 )
- WORK( 2*N+JE ) = ( BCOEFR*P( JE+1, JE+1 )-ACOEF*
- $ S( JE+1, JE+1 ) ) / TEMP
- WORK( 3*N+JE ) = BCOEFI*P( JE+1, JE+1 ) / TEMP
- END IF
- XMAX = MAX( ABS( WORK( 2*N+JE ) )+ABS( WORK( 3*N+JE ) ),
- $ ABS( WORK( 2*N+JE+1 ) )+ABS( WORK( 3*N+JE+1 ) ) )
- END IF
-*
- DMIN = MAX( ULP*ACOEFA*ANORM, ULP*BCOEFA*BNORM, SAFMIN )
-*
-* T
-* Triangular solve of (a A - b B) y = 0
-*
-* T
-* (rowwise in (a A - b B) , or columnwise in (a A - b B) )
-*
- IL2BY2 = .FALSE.
-*
- DO 160 J = JE + NW, N
- IF( IL2BY2 ) THEN
- IL2BY2 = .FALSE.
- GO TO 160
- END IF
-*
- NA = 1
- BDIAG( 1 ) = P( J, J )
- IF( J.LT.N ) THEN
- IF( S( J+1, J ).NE.ZERO ) THEN
- IL2BY2 = .TRUE.
- BDIAG( 2 ) = P( J+1, J+1 )
- NA = 2
- END IF
- END IF
-*
-* Check whether scaling is necessary for dot products
-*
- XSCALE = ONE / MAX( ONE, XMAX )
- TEMP = MAX( WORK( J ), WORK( N+J ),
- $ ACOEFA*WORK( J )+BCOEFA*WORK( N+J ) )
- IF( IL2BY2 )
- $ TEMP = MAX( TEMP, WORK( J+1 ), WORK( N+J+1 ),
- $ ACOEFA*WORK( J+1 )+BCOEFA*WORK( N+J+1 ) )
- IF( TEMP.GT.BIGNUM*XSCALE ) THEN
- DO 90 JW = 0, NW - 1
- DO 80 JR = JE, J - 1
- WORK( ( JW+2 )*N+JR ) = XSCALE*
- $ WORK( ( JW+2 )*N+JR )
- 80 CONTINUE
- 90 CONTINUE
- XMAX = XMAX*XSCALE
- END IF
-*
-* Compute dot products
-*
-* j-1
-* SUM = sum conjg( a*S(k,j) - b*P(k,j) )*x(k)
-* k=je
-*
-* To reduce the op count, this is done as
-*
-* _ j-1 _ j-1
-* a*conjg( sum S(k,j)*x(k) ) - b*conjg( sum P(k,j)*x(k) )
-* k=je k=je
-*
-* which may cause underflow problems if A or B are close
-* to underflow. (E.g., less than SMALL.)
-*
-*
-* A series of compiler directives to defeat vectorization
-* for the next loop
-*
-*$PL$ CMCHAR=' '
-CDIR$ NEXTSCALAR
-C$DIR SCALAR
-CDIR$ NEXT SCALAR
-CVD$L NOVECTOR
-CDEC$ NOVECTOR
-CVD$ NOVECTOR
-*VDIR NOVECTOR
-*VOCL LOOP,SCALAR
-CIBM PREFER SCALAR
-*$PL$ CMCHAR='*'
-*
- DO 120 JW = 1, NW
-*
-*$PL$ CMCHAR=' '
-CDIR$ NEXTSCALAR
-C$DIR SCALAR
-CDIR$ NEXT SCALAR
-CVD$L NOVECTOR
-CDEC$ NOVECTOR
-CVD$ NOVECTOR
-*VDIR NOVECTOR
-*VOCL LOOP,SCALAR
-CIBM PREFER SCALAR
-*$PL$ CMCHAR='*'
-*
- DO 110 JA = 1, NA
- SUMS( JA, JW ) = ZERO
- SUMP( JA, JW ) = ZERO
-*
- DO 100 JR = JE, J - 1
- SUMS( JA, JW ) = SUMS( JA, JW ) +
- $ S( JR, J+JA-1 )*
- $ WORK( ( JW+1 )*N+JR )
- SUMP( JA, JW ) = SUMP( JA, JW ) +
- $ P( JR, J+JA-1 )*
- $ WORK( ( JW+1 )*N+JR )
- 100 CONTINUE
- 110 CONTINUE
- 120 CONTINUE
-*
-*$PL$ CMCHAR=' '
-CDIR$ NEXTSCALAR
-C$DIR SCALAR
-CDIR$ NEXT SCALAR
-CVD$L NOVECTOR
-CDEC$ NOVECTOR
-CVD$ NOVECTOR
-*VDIR NOVECTOR
-*VOCL LOOP,SCALAR
-CIBM PREFER SCALAR
-*$PL$ CMCHAR='*'
-*
- DO 130 JA = 1, NA
- IF( ILCPLX ) THEN
- SUM( JA, 1 ) = -ACOEF*SUMS( JA, 1 ) +
- $ BCOEFR*SUMP( JA, 1 ) -
- $ BCOEFI*SUMP( JA, 2 )
- SUM( JA, 2 ) = -ACOEF*SUMS( JA, 2 ) +
- $ BCOEFR*SUMP( JA, 2 ) +
- $ BCOEFI*SUMP( JA, 1 )
- ELSE
- SUM( JA, 1 ) = -ACOEF*SUMS( JA, 1 ) +
- $ BCOEFR*SUMP( JA, 1 )
- END IF
- 130 CONTINUE
-*
-* T
-* Solve ( a A - b B ) y = SUM(,)
-* with scaling and perturbation of the denominator
-*
- CALL DLALN2( .TRUE., NA, NW, DMIN, ACOEF, S( J, J ), LDS,
- $ BDIAG( 1 ), BDIAG( 2 ), SUM, 2, BCOEFR,
- $ BCOEFI, WORK( 2*N+J ), N, SCALE, TEMP,
- $ IINFO )
- IF( SCALE.LT.ONE ) THEN
- DO 150 JW = 0, NW - 1
- DO 140 JR = JE, J - 1
- WORK( ( JW+2 )*N+JR ) = SCALE*
- $ WORK( ( JW+2 )*N+JR )
- 140 CONTINUE
- 150 CONTINUE
- XMAX = SCALE*XMAX
- END IF
- XMAX = MAX( XMAX, TEMP )
- 160 CONTINUE
-*
-* Copy eigenvector to VL, back transforming if
-* HOWMNY='B'.
-*
- IEIG = IEIG + 1
- IF( ILBACK ) THEN
- DO 170 JW = 0, NW - 1
- CALL DGEMV( 'N', N, N+1-JE, ONE, VL( 1, JE ), LDVL,
- $ WORK( ( JW+2 )*N+JE ), 1, ZERO,
- $ WORK( ( JW+4 )*N+1 ), 1 )
- 170 CONTINUE
- CALL DLACPY( ' ', N, NW, WORK( 4*N+1 ), N, VL( 1, JE ),
- $ LDVL )
- IBEG = 1
- ELSE
- CALL DLACPY( ' ', N, NW, WORK( 2*N+1 ), N, VL( 1, IEIG ),
- $ LDVL )
- IBEG = JE
- END IF
-*
-* Scale eigenvector
-*
- XMAX = ZERO
- IF( ILCPLX ) THEN
- DO 180 J = IBEG, N
- XMAX = MAX( XMAX, ABS( VL( J, IEIG ) )+
- $ ABS( VL( J, IEIG+1 ) ) )
- 180 CONTINUE
- ELSE
- DO 190 J = IBEG, N
- XMAX = MAX( XMAX, ABS( VL( J, IEIG ) ) )
- 190 CONTINUE
- END IF
-*
- IF( XMAX.GT.SAFMIN ) THEN
- XSCALE = ONE / XMAX
-*
- DO 210 JW = 0, NW - 1
- DO 200 JR = IBEG, N
- VL( JR, IEIG+JW ) = XSCALE*VL( JR, IEIG+JW )
- 200 CONTINUE
- 210 CONTINUE
- END IF
- IEIG = IEIG + NW - 1
-*
- 220 CONTINUE
- END IF
-*
-* Right eigenvectors
-*
- IF( COMPR ) THEN
- IEIG = IM + 1
-*
-* Main loop over eigenvalues
-*
- ILCPLX = .FALSE.
- DO 500 JE = N, 1, -1
-*
-* Skip this iteration if (a) HOWMNY='S' and SELECT=.FALSE., or
-* (b) this would be the second of a complex pair.
-* Check for complex eigenvalue, so as to be sure of which
-* entry(-ies) of SELECT to look at -- if complex, SELECT(JE)
-* or SELECT(JE-1).
-* If this is a complex pair, the 2-by-2 diagonal block
-* corresponding to the eigenvalue is in rows/columns JE-1:JE
-*
- IF( ILCPLX ) THEN
- ILCPLX = .FALSE.
- GO TO 500
- END IF
- NW = 1
- IF( JE.GT.1 ) THEN
- IF( S( JE, JE-1 ).NE.ZERO ) THEN
- ILCPLX = .TRUE.
- NW = 2
- END IF
- END IF
- IF( ILALL ) THEN
- ILCOMP = .TRUE.
- ELSE IF( ILCPLX ) THEN
- ILCOMP = SELECT( JE ) .OR. SELECT( JE-1 )
- ELSE
- ILCOMP = SELECT( JE )
- END IF
- IF( .NOT.ILCOMP )
- $ GO TO 500
-*
-* Decide if (a) singular pencil, (b) real eigenvalue, or
-* (c) complex eigenvalue.
-*
- IF( .NOT.ILCPLX ) THEN
- IF( ABS( S( JE, JE ) ).LE.SAFMIN .AND.
- $ ABS( P( JE, JE ) ).LE.SAFMIN ) THEN
-*
-* Singular matrix pencil -- unit eigenvector
-*
- IEIG = IEIG - 1
- DO 230 JR = 1, N
- VR( JR, IEIG ) = ZERO
- 230 CONTINUE
- VR( IEIG, IEIG ) = ONE
- GO TO 500
- END IF
- END IF
-*
-* Clear vector
-*
- DO 250 JW = 0, NW - 1
- DO 240 JR = 1, N
- WORK( ( JW+2 )*N+JR ) = ZERO
- 240 CONTINUE
- 250 CONTINUE
-*
-* Compute coefficients in ( a A - b B ) x = 0
-* a is ACOEF
-* b is BCOEFR + i*BCOEFI
-*
- IF( .NOT.ILCPLX ) THEN
-*
-* Real eigenvalue
-*
- TEMP = ONE / MAX( ABS( S( JE, JE ) )*ASCALE,
- $ ABS( P( JE, JE ) )*BSCALE, SAFMIN )
- SALFAR = ( TEMP*S( JE, JE ) )*ASCALE
- SBETA = ( TEMP*P( JE, JE ) )*BSCALE
- ACOEF = SBETA*ASCALE
- BCOEFR = SALFAR*BSCALE
- BCOEFI = ZERO
-*
-* Scale to avoid underflow
-*
- SCALE = ONE
- LSA = ABS( SBETA ).GE.SAFMIN .AND. ABS( ACOEF ).LT.SMALL
- LSB = ABS( SALFAR ).GE.SAFMIN .AND. ABS( BCOEFR ).LT.
- $ SMALL
- IF( LSA )
- $ SCALE = ( SMALL / ABS( SBETA ) )*MIN( ANORM, BIG )
- IF( LSB )
- $ SCALE = MAX( SCALE, ( SMALL / ABS( SALFAR ) )*
- $ MIN( BNORM, BIG ) )
- IF( LSA .OR. LSB ) THEN
- SCALE = MIN( SCALE, ONE /
- $ ( SAFMIN*MAX( ONE, ABS( ACOEF ),
- $ ABS( BCOEFR ) ) ) )
- IF( LSA ) THEN
- ACOEF = ASCALE*( SCALE*SBETA )
- ELSE
- ACOEF = SCALE*ACOEF
- END IF
- IF( LSB ) THEN
- BCOEFR = BSCALE*( SCALE*SALFAR )
- ELSE
- BCOEFR = SCALE*BCOEFR
- END IF
- END IF
- ACOEFA = ABS( ACOEF )
- BCOEFA = ABS( BCOEFR )
-*
-* First component is 1
-*
- WORK( 2*N+JE ) = ONE
- XMAX = ONE
-*
-* Compute contribution from column JE of A and B to sum
-* (See "Further Details", above.)
-*
- DO 260 JR = 1, JE - 1
- WORK( 2*N+JR ) = BCOEFR*P( JR, JE ) -
- $ ACOEF*S( JR, JE )
- 260 CONTINUE
- ELSE
-*
-* Complex eigenvalue
-*
- CALL DLAG2( S( JE-1, JE-1 ), LDS, P( JE-1, JE-1 ), LDP,
- $ SAFMIN*SAFETY, ACOEF, TEMP, BCOEFR, TEMP2,
- $ BCOEFI )
- IF( BCOEFI.EQ.ZERO ) THEN
- INFO = JE - 1
- RETURN
- END IF
-*
-* Scale to avoid over/underflow
-*
- ACOEFA = ABS( ACOEF )
- BCOEFA = ABS( BCOEFR ) + ABS( BCOEFI )
- SCALE = ONE
- IF( ACOEFA*ULP.LT.SAFMIN .AND. ACOEFA.GE.SAFMIN )
- $ SCALE = ( SAFMIN / ULP ) / ACOEFA
- IF( BCOEFA*ULP.LT.SAFMIN .AND. BCOEFA.GE.SAFMIN )
- $ SCALE = MAX( SCALE, ( SAFMIN / ULP ) / BCOEFA )
- IF( SAFMIN*ACOEFA.GT.ASCALE )
- $ SCALE = ASCALE / ( SAFMIN*ACOEFA )
- IF( SAFMIN*BCOEFA.GT.BSCALE )
- $ SCALE = MIN( SCALE, BSCALE / ( SAFMIN*BCOEFA ) )
- IF( SCALE.NE.ONE ) THEN
- ACOEF = SCALE*ACOEF
- ACOEFA = ABS( ACOEF )
- BCOEFR = SCALE*BCOEFR
- BCOEFI = SCALE*BCOEFI
- BCOEFA = ABS( BCOEFR ) + ABS( BCOEFI )
- END IF
-*
-* Compute first two components of eigenvector
-* and contribution to sums
-*
- TEMP = ACOEF*S( JE, JE-1 )
- TEMP2R = ACOEF*S( JE, JE ) - BCOEFR*P( JE, JE )
- TEMP2I = -BCOEFI*P( JE, JE )
- IF( ABS( TEMP ).GE.ABS( TEMP2R )+ABS( TEMP2I ) ) THEN
- WORK( 2*N+JE ) = ONE
- WORK( 3*N+JE ) = ZERO
- WORK( 2*N+JE-1 ) = -TEMP2R / TEMP
- WORK( 3*N+JE-1 ) = -TEMP2I / TEMP
- ELSE
- WORK( 2*N+JE-1 ) = ONE
- WORK( 3*N+JE-1 ) = ZERO
- TEMP = ACOEF*S( JE-1, JE )
- WORK( 2*N+JE ) = ( BCOEFR*P( JE-1, JE-1 )-ACOEF*
- $ S( JE-1, JE-1 ) ) / TEMP
- WORK( 3*N+JE ) = BCOEFI*P( JE-1, JE-1 ) / TEMP
- END IF
-*
- XMAX = MAX( ABS( WORK( 2*N+JE ) )+ABS( WORK( 3*N+JE ) ),
- $ ABS( WORK( 2*N+JE-1 ) )+ABS( WORK( 3*N+JE-1 ) ) )
-*
-* Compute contribution from columns JE and JE-1
-* of A and B to the sums.
-*
- CREALA = ACOEF*WORK( 2*N+JE-1 )
- CIMAGA = ACOEF*WORK( 3*N+JE-1 )
- CREALB = BCOEFR*WORK( 2*N+JE-1 ) -
- $ BCOEFI*WORK( 3*N+JE-1 )
- CIMAGB = BCOEFI*WORK( 2*N+JE-1 ) +
- $ BCOEFR*WORK( 3*N+JE-1 )
- CRE2A = ACOEF*WORK( 2*N+JE )
- CIM2A = ACOEF*WORK( 3*N+JE )
- CRE2B = BCOEFR*WORK( 2*N+JE ) - BCOEFI*WORK( 3*N+JE )
- CIM2B = BCOEFI*WORK( 2*N+JE ) + BCOEFR*WORK( 3*N+JE )
- DO 270 JR = 1, JE - 2
- WORK( 2*N+JR ) = -CREALA*S( JR, JE-1 ) +
- $ CREALB*P( JR, JE-1 ) -
- $ CRE2A*S( JR, JE ) + CRE2B*P( JR, JE )
- WORK( 3*N+JR ) = -CIMAGA*S( JR, JE-1 ) +
- $ CIMAGB*P( JR, JE-1 ) -
- $ CIM2A*S( JR, JE ) + CIM2B*P( JR, JE )
- 270 CONTINUE
- END IF
-*
- DMIN = MAX( ULP*ACOEFA*ANORM, ULP*BCOEFA*BNORM, SAFMIN )
-*
-* Columnwise triangular solve of (a A - b B) x = 0
-*
- IL2BY2 = .FALSE.
- DO 370 J = JE - NW, 1, -1
-*
-* If a 2-by-2 block, is in position j-1:j, wait until
-* next iteration to process it (when it will be j:j+1)
-*
- IF( .NOT.IL2BY2 .AND. J.GT.1 ) THEN
- IF( S( J, J-1 ).NE.ZERO ) THEN
- IL2BY2 = .TRUE.
- GO TO 370
- END IF
- END IF
- BDIAG( 1 ) = P( J, J )
- IF( IL2BY2 ) THEN
- NA = 2
- BDIAG( 2 ) = P( J+1, J+1 )
- ELSE
- NA = 1
- END IF
-*
-* Compute x(j) (and x(j+1), if 2-by-2 block)
-*
- CALL DLALN2( .FALSE., NA, NW, DMIN, ACOEF, S( J, J ),
- $ LDS, BDIAG( 1 ), BDIAG( 2 ), WORK( 2*N+J ),
- $ N, BCOEFR, BCOEFI, SUM, 2, SCALE, TEMP,
- $ IINFO )
- IF( SCALE.LT.ONE ) THEN
-*
- DO 290 JW = 0, NW - 1
- DO 280 JR = 1, JE
- WORK( ( JW+2 )*N+JR ) = SCALE*
- $ WORK( ( JW+2 )*N+JR )
- 280 CONTINUE
- 290 CONTINUE
- END IF
- XMAX = MAX( SCALE*XMAX, TEMP )
-*
- DO 310 JW = 1, NW
- DO 300 JA = 1, NA
- WORK( ( JW+1 )*N+J+JA-1 ) = SUM( JA, JW )
- 300 CONTINUE
- 310 CONTINUE
-*
-* w = w + x(j)*(a S(*,j) - b P(*,j) ) with scaling
-*
- IF( J.GT.1 ) THEN
-*
-* Check whether scaling is necessary for sum.
-*
- XSCALE = ONE / MAX( ONE, XMAX )
- TEMP = ACOEFA*WORK( J ) + BCOEFA*WORK( N+J )
- IF( IL2BY2 )
- $ TEMP = MAX( TEMP, ACOEFA*WORK( J+1 )+BCOEFA*
- $ WORK( N+J+1 ) )
- TEMP = MAX( TEMP, ACOEFA, BCOEFA )
- IF( TEMP.GT.BIGNUM*XSCALE ) THEN
-*
- DO 330 JW = 0, NW - 1
- DO 320 JR = 1, JE
- WORK( ( JW+2 )*N+JR ) = XSCALE*
- $ WORK( ( JW+2 )*N+JR )
- 320 CONTINUE
- 330 CONTINUE
- XMAX = XMAX*XSCALE
- END IF
-*
-* Compute the contributions of the off-diagonals of
-* column j (and j+1, if 2-by-2 block) of A and B to the
-* sums.
-*
-*
- DO 360 JA = 1, NA
- IF( ILCPLX ) THEN
- CREALA = ACOEF*WORK( 2*N+J+JA-1 )
- CIMAGA = ACOEF*WORK( 3*N+J+JA-1 )
- CREALB = BCOEFR*WORK( 2*N+J+JA-1 ) -
- $ BCOEFI*WORK( 3*N+J+JA-1 )
- CIMAGB = BCOEFI*WORK( 2*N+J+JA-1 ) +
- $ BCOEFR*WORK( 3*N+J+JA-1 )
- DO 340 JR = 1, J - 1
- WORK( 2*N+JR ) = WORK( 2*N+JR ) -
- $ CREALA*S( JR, J+JA-1 ) +
- $ CREALB*P( JR, J+JA-1 )
- WORK( 3*N+JR ) = WORK( 3*N+JR ) -
- $ CIMAGA*S( JR, J+JA-1 ) +
- $ CIMAGB*P( JR, J+JA-1 )
- 340 CONTINUE
- ELSE
- CREALA = ACOEF*WORK( 2*N+J+JA-1 )
- CREALB = BCOEFR*WORK( 2*N+J+JA-1 )
- DO 350 JR = 1, J - 1
- WORK( 2*N+JR ) = WORK( 2*N+JR ) -
- $ CREALA*S( JR, J+JA-1 ) +
- $ CREALB*P( JR, J+JA-1 )
- 350 CONTINUE
- END IF
- 360 CONTINUE
- END IF
-*
- IL2BY2 = .FALSE.
- 370 CONTINUE
-*
-* Copy eigenvector to VR, back transforming if
-* HOWMNY='B'.
-*
- IEIG = IEIG - NW
- IF( ILBACK ) THEN
-*
- DO 410 JW = 0, NW - 1
- DO 380 JR = 1, N
- WORK( ( JW+4 )*N+JR ) = WORK( ( JW+2 )*N+1 )*
- $ VR( JR, 1 )
- 380 CONTINUE
-*
-* A series of compiler directives to defeat
-* vectorization for the next loop
-*
-*
- DO 400 JC = 2, JE
- DO 390 JR = 1, N
- WORK( ( JW+4 )*N+JR ) = WORK( ( JW+4 )*N+JR ) +
- $ WORK( ( JW+2 )*N+JC )*VR( JR, JC )
- 390 CONTINUE
- 400 CONTINUE
- 410 CONTINUE
-*
- DO 430 JW = 0, NW - 1
- DO 420 JR = 1, N
- VR( JR, IEIG+JW ) = WORK( ( JW+4 )*N+JR )
- 420 CONTINUE
- 430 CONTINUE
-*
- IEND = N
- ELSE
- DO 450 JW = 0, NW - 1
- DO 440 JR = 1, N
- VR( JR, IEIG+JW ) = WORK( ( JW+2 )*N+JR )
- 440 CONTINUE
- 450 CONTINUE
-*
- IEND = JE
- END IF
-*
-* Scale eigenvector
-*
- XMAX = ZERO
- IF( ILCPLX ) THEN
- DO 460 J = 1, IEND
- XMAX = MAX( XMAX, ABS( VR( J, IEIG ) )+
- $ ABS( VR( J, IEIG+1 ) ) )
- 460 CONTINUE
- ELSE
- DO 470 J = 1, IEND
- XMAX = MAX( XMAX, ABS( VR( J, IEIG ) ) )
- 470 CONTINUE
- END IF
-*
- IF( XMAX.GT.SAFMIN ) THEN
- XSCALE = ONE / XMAX
- DO 490 JW = 0, NW - 1
- DO 480 JR = 1, IEND
- VR( JR, IEIG+JW ) = XSCALE*VR( JR, IEIG+JW )
- 480 CONTINUE
- 490 CONTINUE
- END IF
- 500 CONTINUE
- END IF
-*
- RETURN
-*
-* End of DTGEVC
-*
- END
diff --git a/src/lib/lapack/dtgex2.f b/src/lib/lapack/dtgex2.f
deleted file mode 100644
index 8351b7fd..00000000
--- a/src/lib/lapack/dtgex2.f
+++ /dev/null
@@ -1,581 +0,0 @@
- SUBROUTINE DTGEX2( WANTQ, WANTZ, N, A, LDA, B, LDB, Q, LDQ, Z,
- $ LDZ, J1, N1, N2, WORK, LWORK, INFO )
-*
-* -- LAPACK auxiliary routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- LOGICAL WANTQ, WANTZ
- INTEGER INFO, J1, LDA, LDB, LDQ, LDZ, LWORK, N, N1, N2
-* ..
-* .. Array Arguments ..
- DOUBLE PRECISION A( LDA, * ), B( LDB, * ), Q( LDQ, * ),
- $ WORK( * ), Z( LDZ, * )
-* ..
-*
-* Purpose
-* =======
-*
-* DTGEX2 swaps adjacent diagonal blocks (A11, B11) and (A22, B22)
-* of size 1-by-1 or 2-by-2 in an upper (quasi) triangular matrix pair
-* (A, B) by an orthogonal equivalence transformation.
-*
-* (A, B) must be in generalized real Schur canonical form (as returned
-* by DGGES), i.e. A is block upper triangular with 1-by-1 and 2-by-2
-* diagonal blocks. B is upper triangular.
-*
-* Optionally, the matrices Q and Z of generalized Schur vectors are
-* updated.
-*
-* Q(in) * A(in) * Z(in)' = Q(out) * A(out) * Z(out)'
-* Q(in) * B(in) * Z(in)' = Q(out) * B(out) * Z(out)'
-*
-*
-* Arguments
-* =========
-*
-* WANTQ (input) LOGICAL
-* .TRUE. : update the left transformation matrix Q;
-* .FALSE.: do not update Q.
-*
-* WANTZ (input) LOGICAL
-* .TRUE. : update the right transformation matrix Z;
-* .FALSE.: do not update Z.
-*
-* N (input) INTEGER
-* The order of the matrices A and B. N >= 0.
-*
-* A (input/output) DOUBLE PRECISION arrays, dimensions (LDA,N)
-* On entry, the matrix A in the pair (A, B).
-* On exit, the updated matrix A.
-*
-* LDA (input) INTEGER
-* The leading dimension of the array A. LDA >= max(1,N).
-*
-* B (input/output) DOUBLE PRECISION arrays, dimensions (LDB,N)
-* On entry, the matrix B in the pair (A, B).
-* On exit, the updated matrix B.
-*
-* LDB (input) INTEGER
-* The leading dimension of the array B. LDB >= max(1,N).
-*
-* Q (input/output) DOUBLE PRECISION array, dimension (LDZ,N)
-* On entry, if WANTQ = .TRUE., the orthogonal matrix Q.
-* On exit, the updated matrix Q.
-* Not referenced if WANTQ = .FALSE..
-*
-* LDQ (input) INTEGER
-* The leading dimension of the array Q. LDQ >= 1.
-* If WANTQ = .TRUE., LDQ >= N.
-*
-* Z (input/output) DOUBLE PRECISION array, dimension (LDZ,N)
-* On entry, if WANTZ =.TRUE., the orthogonal matrix Z.
-* On exit, the updated matrix Z.
-* Not referenced if WANTZ = .FALSE..
-*
-* LDZ (input) INTEGER
-* The leading dimension of the array Z. LDZ >= 1.
-* If WANTZ = .TRUE., LDZ >= N.
-*
-* J1 (input) INTEGER
-* The index to the first block (A11, B11). 1 <= J1 <= N.
-*
-* N1 (input) INTEGER
-* The order of the first block (A11, B11). N1 = 0, 1 or 2.
-*
-* N2 (input) INTEGER
-* The order of the second block (A22, B22). N2 = 0, 1 or 2.
-*
-* WORK (workspace) DOUBLE PRECISION array, dimension (MAX(1,LWORK)).
-*
-* LWORK (input) INTEGER
-* The dimension of the array WORK.
-* LWORK >= MAX( 1, N*(N2+N1), (N2+N1)*(N2+N1)*2 )
-*
-* INFO (output) INTEGER
-* =0: Successful exit
-* >0: If INFO = 1, the transformed matrix (A, B) would be
-* too far from generalized Schur form; the blocks are
-* not swapped and (A, B) and (Q, Z) are unchanged.
-* The problem of swapping is too ill-conditioned.
-* <0: If INFO = -16: LWORK is too small. Appropriate value
-* for LWORK is returned in WORK(1).
-*
-* Further Details
-* ===============
-*
-* Based on contributions by
-* Bo Kagstrom and Peter Poromaa, Department of Computing Science,
-* Umea University, S-901 87 Umea, Sweden.
-*
-* In the current code both weak and strong stability tests are
-* performed. The user can omit the strong stability test by changing
-* the internal logical parameter WANDS to .FALSE.. See ref. [2] for
-* details.
-*
-* [1] B. Kagstrom; A Direct Method for Reordering Eigenvalues in the
-* Generalized Real Schur Form of a Regular Matrix Pair (A, B), in
-* M.S. Moonen et al (eds), Linear Algebra for Large Scale and
-* Real-Time Applications, Kluwer Academic Publ. 1993, pp 195-218.
-*
-* [2] B. Kagstrom and P. Poromaa; Computing Eigenspaces with Specified
-* Eigenvalues of a Regular Matrix Pair (A, B) and Condition
-* Estimation: Theory, Algorithms and Software,
-* Report UMINF - 94.04, Department of Computing Science, Umea
-* University, S-901 87 Umea, Sweden, 1994. Also as LAPACK Working
-* Note 87. To appear in Numerical Algorithms, 1996.
-*
-* =====================================================================
-* Replaced various illegal calls to DCOPY by calls to DLASET, or by DO
-* loops. Sven Hammarling, 1/5/02.
-*
-* .. Parameters ..
- DOUBLE PRECISION ZERO, ONE
- PARAMETER ( ZERO = 0.0D+0, ONE = 1.0D+0 )
- DOUBLE PRECISION TEN
- PARAMETER ( TEN = 1.0D+01 )
- INTEGER LDST
- PARAMETER ( LDST = 4 )
- LOGICAL WANDS
- PARAMETER ( WANDS = .TRUE. )
-* ..
-* .. Local Scalars ..
- LOGICAL DTRONG, WEAK
- INTEGER I, IDUM, LINFO, M
- DOUBLE PRECISION BQRA21, BRQA21, DDUM, DNORM, DSCALE, DSUM, EPS,
- $ F, G, SA, SB, SCALE, SMLNUM, SS, THRESH, WS
-* ..
-* .. Local Arrays ..
- INTEGER IWORK( LDST )
- DOUBLE PRECISION AI( 2 ), AR( 2 ), BE( 2 ), IR( LDST, LDST ),
- $ IRCOP( LDST, LDST ), LI( LDST, LDST ),
- $ LICOP( LDST, LDST ), S( LDST, LDST ),
- $ SCPY( LDST, LDST ), T( LDST, LDST ),
- $ TAUL( LDST ), TAUR( LDST ), TCPY( LDST, LDST )
-* ..
-* .. External Functions ..
- DOUBLE PRECISION DLAMCH
- EXTERNAL DLAMCH
-* ..
-* .. External Subroutines ..
- EXTERNAL DGEMM, DGEQR2, DGERQ2, DLACPY, DLAGV2, DLARTG,
- $ DLASET, DLASSQ, DORG2R, DORGR2, DORM2R, DORMR2,
- $ DROT, DSCAL, DTGSY2
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC ABS, MAX, SQRT
-* ..
-* .. Executable Statements ..
-*
- INFO = 0
-*
-* Quick return if possible
-*
- IF( N.LE.1 .OR. N1.LE.0 .OR. N2.LE.0 )
- $ RETURN
- IF( N1.GT.N .OR. ( J1+N1 ).GT.N )
- $ RETURN
- M = N1 + N2
- IF( LWORK.LT.MAX( 1, N*M, M*M*2 ) ) THEN
- INFO = -16
- WORK( 1 ) = MAX( 1, N*M, M*M*2 )
- RETURN
- END IF
-*
- WEAK = .FALSE.
- DTRONG = .FALSE.
-*
-* Make a local copy of selected block
-*
- CALL DLASET( 'Full', LDST, LDST, ZERO, ZERO, LI, LDST )
- CALL DLASET( 'Full', LDST, LDST, ZERO, ZERO, IR, LDST )
- CALL DLACPY( 'Full', M, M, A( J1, J1 ), LDA, S, LDST )
- CALL DLACPY( 'Full', M, M, B( J1, J1 ), LDB, T, LDST )
-*
-* Compute threshold for testing acceptance of swapping.
-*
- EPS = DLAMCH( 'P' )
- SMLNUM = DLAMCH( 'S' ) / EPS
- DSCALE = ZERO
- DSUM = ONE
- CALL DLACPY( 'Full', M, M, S, LDST, WORK, M )
- CALL DLASSQ( M*M, WORK, 1, DSCALE, DSUM )
- CALL DLACPY( 'Full', M, M, T, LDST, WORK, M )
- CALL DLASSQ( M*M, WORK, 1, DSCALE, DSUM )
- DNORM = DSCALE*SQRT( DSUM )
- THRESH = MAX( TEN*EPS*DNORM, SMLNUM )
-*
- IF( M.EQ.2 ) THEN
-*
-* CASE 1: Swap 1-by-1 and 1-by-1 blocks.
-*
-* Compute orthogonal QL and RQ that swap 1-by-1 and 1-by-1 blocks
-* using Givens rotations and perform the swap tentatively.
-*
- F = S( 2, 2 )*T( 1, 1 ) - T( 2, 2 )*S( 1, 1 )
- G = S( 2, 2 )*T( 1, 2 ) - T( 2, 2 )*S( 1, 2 )
- SB = ABS( T( 2, 2 ) )
- SA = ABS( S( 2, 2 ) )
- CALL DLARTG( F, G, IR( 1, 2 ), IR( 1, 1 ), DDUM )
- IR( 2, 1 ) = -IR( 1, 2 )
- IR( 2, 2 ) = IR( 1, 1 )
- CALL DROT( 2, S( 1, 1 ), 1, S( 1, 2 ), 1, IR( 1, 1 ),
- $ IR( 2, 1 ) )
- CALL DROT( 2, T( 1, 1 ), 1, T( 1, 2 ), 1, IR( 1, 1 ),
- $ IR( 2, 1 ) )
- IF( SA.GE.SB ) THEN
- CALL DLARTG( S( 1, 1 ), S( 2, 1 ), LI( 1, 1 ), LI( 2, 1 ),
- $ DDUM )
- ELSE
- CALL DLARTG( T( 1, 1 ), T( 2, 1 ), LI( 1, 1 ), LI( 2, 1 ),
- $ DDUM )
- END IF
- CALL DROT( 2, S( 1, 1 ), LDST, S( 2, 1 ), LDST, LI( 1, 1 ),
- $ LI( 2, 1 ) )
- CALL DROT( 2, T( 1, 1 ), LDST, T( 2, 1 ), LDST, LI( 1, 1 ),
- $ LI( 2, 1 ) )
- LI( 2, 2 ) = LI( 1, 1 )
- LI( 1, 2 ) = -LI( 2, 1 )
-*
-* Weak stability test:
-* |S21| + |T21| <= O(EPS * F-norm((S, T)))
-*
- WS = ABS( S( 2, 1 ) ) + ABS( T( 2, 1 ) )
- WEAK = WS.LE.THRESH
- IF( .NOT.WEAK )
- $ GO TO 70
-*
- IF( WANDS ) THEN
-*
-* Strong stability test:
-* F-norm((A-QL'*S*QR, B-QL'*T*QR)) <= O(EPS*F-norm((A,B)))
-*
- CALL DLACPY( 'Full', M, M, A( J1, J1 ), LDA, WORK( M*M+1 ),
- $ M )
- CALL DGEMM( 'N', 'N', M, M, M, ONE, LI, LDST, S, LDST, ZERO,
- $ WORK, M )
- CALL DGEMM( 'N', 'T', M, M, M, -ONE, WORK, M, IR, LDST, ONE,
- $ WORK( M*M+1 ), M )
- DSCALE = ZERO
- DSUM = ONE
- CALL DLASSQ( M*M, WORK( M*M+1 ), 1, DSCALE, DSUM )
-*
- CALL DLACPY( 'Full', M, M, B( J1, J1 ), LDB, WORK( M*M+1 ),
- $ M )
- CALL DGEMM( 'N', 'N', M, M, M, ONE, LI, LDST, T, LDST, ZERO,
- $ WORK, M )
- CALL DGEMM( 'N', 'T', M, M, M, -ONE, WORK, M, IR, LDST, ONE,
- $ WORK( M*M+1 ), M )
- CALL DLASSQ( M*M, WORK( M*M+1 ), 1, DSCALE, DSUM )
- SS = DSCALE*SQRT( DSUM )
- DTRONG = SS.LE.THRESH
- IF( .NOT.DTRONG )
- $ GO TO 70
- END IF
-*
-* Update (A(J1:J1+M-1, M+J1:N), B(J1:J1+M-1, M+J1:N)) and
-* (A(1:J1-1, J1:J1+M), B(1:J1-1, J1:J1+M)).
-*
- CALL DROT( J1+1, A( 1, J1 ), 1, A( 1, J1+1 ), 1, IR( 1, 1 ),
- $ IR( 2, 1 ) )
- CALL DROT( J1+1, B( 1, J1 ), 1, B( 1, J1+1 ), 1, IR( 1, 1 ),
- $ IR( 2, 1 ) )
- CALL DROT( N-J1+1, A( J1, J1 ), LDA, A( J1+1, J1 ), LDA,
- $ LI( 1, 1 ), LI( 2, 1 ) )
- CALL DROT( N-J1+1, B( J1, J1 ), LDB, B( J1+1, J1 ), LDB,
- $ LI( 1, 1 ), LI( 2, 1 ) )
-*
-* Set N1-by-N2 (2,1) - blocks to ZERO.
-*
- A( J1+1, J1 ) = ZERO
- B( J1+1, J1 ) = ZERO
-*
-* Accumulate transformations into Q and Z if requested.
-*
- IF( WANTZ )
- $ CALL DROT( N, Z( 1, J1 ), 1, Z( 1, J1+1 ), 1, IR( 1, 1 ),
- $ IR( 2, 1 ) )
- IF( WANTQ )
- $ CALL DROT( N, Q( 1, J1 ), 1, Q( 1, J1+1 ), 1, LI( 1, 1 ),
- $ LI( 2, 1 ) )
-*
-* Exit with INFO = 0 if swap was successfully performed.
-*
- RETURN
-*
- ELSE
-*
-* CASE 2: Swap 1-by-1 and 2-by-2 blocks, or 2-by-2
-* and 2-by-2 blocks.
-*
-* Solve the generalized Sylvester equation
-* S11 * R - L * S22 = SCALE * S12
-* T11 * R - L * T22 = SCALE * T12
-* for R and L. Solutions in LI and IR.
-*
- CALL DLACPY( 'Full', N1, N2, T( 1, N1+1 ), LDST, LI, LDST )
- CALL DLACPY( 'Full', N1, N2, S( 1, N1+1 ), LDST,
- $ IR( N2+1, N1+1 ), LDST )
- CALL DTGSY2( 'N', 0, N1, N2, S, LDST, S( N1+1, N1+1 ), LDST,
- $ IR( N2+1, N1+1 ), LDST, T, LDST, T( N1+1, N1+1 ),
- $ LDST, LI, LDST, SCALE, DSUM, DSCALE, IWORK, IDUM,
- $ LINFO )
-*
-* Compute orthogonal matrix QL:
-*
-* QL' * LI = [ TL ]
-* [ 0 ]
-* where
-* LI = [ -L ]
-* [ SCALE * identity(N2) ]
-*
- DO 10 I = 1, N2
- CALL DSCAL( N1, -ONE, LI( 1, I ), 1 )
- LI( N1+I, I ) = SCALE
- 10 CONTINUE
- CALL DGEQR2( M, N2, LI, LDST, TAUL, WORK, LINFO )
- IF( LINFO.NE.0 )
- $ GO TO 70
- CALL DORG2R( M, M, N2, LI, LDST, TAUL, WORK, LINFO )
- IF( LINFO.NE.0 )
- $ GO TO 70
-*
-* Compute orthogonal matrix RQ:
-*
-* IR * RQ' = [ 0 TR],
-*
-* where IR = [ SCALE * identity(N1), R ]
-*
- DO 20 I = 1, N1
- IR( N2+I, I ) = SCALE
- 20 CONTINUE
- CALL DGERQ2( N1, M, IR( N2+1, 1 ), LDST, TAUR, WORK, LINFO )
- IF( LINFO.NE.0 )
- $ GO TO 70
- CALL DORGR2( M, M, N1, IR, LDST, TAUR, WORK, LINFO )
- IF( LINFO.NE.0 )
- $ GO TO 70
-*
-* Perform the swapping tentatively:
-*
- CALL DGEMM( 'T', 'N', M, M, M, ONE, LI, LDST, S, LDST, ZERO,
- $ WORK, M )
- CALL DGEMM( 'N', 'T', M, M, M, ONE, WORK, M, IR, LDST, ZERO, S,
- $ LDST )
- CALL DGEMM( 'T', 'N', M, M, M, ONE, LI, LDST, T, LDST, ZERO,
- $ WORK, M )
- CALL DGEMM( 'N', 'T', M, M, M, ONE, WORK, M, IR, LDST, ZERO, T,
- $ LDST )
- CALL DLACPY( 'F', M, M, S, LDST, SCPY, LDST )
- CALL DLACPY( 'F', M, M, T, LDST, TCPY, LDST )
- CALL DLACPY( 'F', M, M, IR, LDST, IRCOP, LDST )
- CALL DLACPY( 'F', M, M, LI, LDST, LICOP, LDST )
-*
-* Triangularize the B-part by an RQ factorization.
-* Apply transformation (from left) to A-part, giving S.
-*
- CALL DGERQ2( M, M, T, LDST, TAUR, WORK, LINFO )
- IF( LINFO.NE.0 )
- $ GO TO 70
- CALL DORMR2( 'R', 'T', M, M, M, T, LDST, TAUR, S, LDST, WORK,
- $ LINFO )
- IF( LINFO.NE.0 )
- $ GO TO 70
- CALL DORMR2( 'L', 'N', M, M, M, T, LDST, TAUR, IR, LDST, WORK,
- $ LINFO )
- IF( LINFO.NE.0 )
- $ GO TO 70
-*
-* Compute F-norm(S21) in BRQA21. (T21 is 0.)
-*
- DSCALE = ZERO
- DSUM = ONE
- DO 30 I = 1, N2
- CALL DLASSQ( N1, S( N2+1, I ), 1, DSCALE, DSUM )
- 30 CONTINUE
- BRQA21 = DSCALE*SQRT( DSUM )
-*
-* Triangularize the B-part by a QR factorization.
-* Apply transformation (from right) to A-part, giving S.
-*
- CALL DGEQR2( M, M, TCPY, LDST, TAUL, WORK, LINFO )
- IF( LINFO.NE.0 )
- $ GO TO 70
- CALL DORM2R( 'L', 'T', M, M, M, TCPY, LDST, TAUL, SCPY, LDST,
- $ WORK, INFO )
- CALL DORM2R( 'R', 'N', M, M, M, TCPY, LDST, TAUL, LICOP, LDST,
- $ WORK, INFO )
- IF( LINFO.NE.0 )
- $ GO TO 70
-*
-* Compute F-norm(S21) in BQRA21. (T21 is 0.)
-*
- DSCALE = ZERO
- DSUM = ONE
- DO 40 I = 1, N2
- CALL DLASSQ( N1, SCPY( N2+1, I ), 1, DSCALE, DSUM )
- 40 CONTINUE
- BQRA21 = DSCALE*SQRT( DSUM )
-*
-* Decide which method to use.
-* Weak stability test:
-* F-norm(S21) <= O(EPS * F-norm((S, T)))
-*
- IF( BQRA21.LE.BRQA21 .AND. BQRA21.LE.THRESH ) THEN
- CALL DLACPY( 'F', M, M, SCPY, LDST, S, LDST )
- CALL DLACPY( 'F', M, M, TCPY, LDST, T, LDST )
- CALL DLACPY( 'F', M, M, IRCOP, LDST, IR, LDST )
- CALL DLACPY( 'F', M, M, LICOP, LDST, LI, LDST )
- ELSE IF( BRQA21.GE.THRESH ) THEN
- GO TO 70
- END IF
-*
-* Set lower triangle of B-part to zero
-*
- CALL DLASET( 'Lower', M-1, M-1, ZERO, ZERO, T(2,1), LDST )
-*
- IF( WANDS ) THEN
-*
-* Strong stability test:
-* F-norm((A-QL*S*QR', B-QL*T*QR')) <= O(EPS*F-norm((A,B)))
-*
- CALL DLACPY( 'Full', M, M, A( J1, J1 ), LDA, WORK( M*M+1 ),
- $ M )
- CALL DGEMM( 'N', 'N', M, M, M, ONE, LI, LDST, S, LDST, ZERO,
- $ WORK, M )
- CALL DGEMM( 'N', 'N', M, M, M, -ONE, WORK, M, IR, LDST, ONE,
- $ WORK( M*M+1 ), M )
- DSCALE = ZERO
- DSUM = ONE
- CALL DLASSQ( M*M, WORK( M*M+1 ), 1, DSCALE, DSUM )
-*
- CALL DLACPY( 'Full', M, M, B( J1, J1 ), LDB, WORK( M*M+1 ),
- $ M )
- CALL DGEMM( 'N', 'N', M, M, M, ONE, LI, LDST, T, LDST, ZERO,
- $ WORK, M )
- CALL DGEMM( 'N', 'N', M, M, M, -ONE, WORK, M, IR, LDST, ONE,
- $ WORK( M*M+1 ), M )
- CALL DLASSQ( M*M, WORK( M*M+1 ), 1, DSCALE, DSUM )
- SS = DSCALE*SQRT( DSUM )
- DTRONG = ( SS.LE.THRESH )
- IF( .NOT.DTRONG )
- $ GO TO 70
-*
- END IF
-*
-* If the swap is accepted ("weakly" and "strongly"), apply the
-* transformations and set N1-by-N2 (2,1)-block to zero.
-*
- CALL DLASET( 'Full', N1, N2, ZERO, ZERO, S(N2+1,1), LDST )
-*
-* copy back M-by-M diagonal block starting at index J1 of (A, B)
-*
- CALL DLACPY( 'F', M, M, S, LDST, A( J1, J1 ), LDA )
- CALL DLACPY( 'F', M, M, T, LDST, B( J1, J1 ), LDB )
- CALL DLASET( 'Full', LDST, LDST, ZERO, ZERO, T, LDST )
-*
-* Standardize existing 2-by-2 blocks.
-*
- DO 50 I = 1, M*M
- WORK(I) = ZERO
- 50 CONTINUE
- WORK( 1 ) = ONE
- T( 1, 1 ) = ONE
- IDUM = LWORK - M*M - 2
- IF( N2.GT.1 ) THEN
- CALL DLAGV2( A( J1, J1 ), LDA, B( J1, J1 ), LDB, AR, AI, BE,
- $ WORK( 1 ), WORK( 2 ), T( 1, 1 ), T( 2, 1 ) )
- WORK( M+1 ) = -WORK( 2 )
- WORK( M+2 ) = WORK( 1 )
- T( N2, N2 ) = T( 1, 1 )
- T( 1, 2 ) = -T( 2, 1 )
- END IF
- WORK( M*M ) = ONE
- T( M, M ) = ONE
-*
- IF( N1.GT.1 ) THEN
- CALL DLAGV2( A( J1+N2, J1+N2 ), LDA, B( J1+N2, J1+N2 ), LDB,
- $ TAUR, TAUL, WORK( M*M+1 ), WORK( N2*M+N2+1 ),
- $ WORK( N2*M+N2+2 ), T( N2+1, N2+1 ),
- $ T( M, M-1 ) )
- WORK( M*M ) = WORK( N2*M+N2+1 )
- WORK( M*M-1 ) = -WORK( N2*M+N2+2 )
- T( M, M ) = T( N2+1, N2+1 )
- T( M-1, M ) = -T( M, M-1 )
- END IF
- CALL DGEMM( 'T', 'N', N2, N1, N2, ONE, WORK, M, A( J1, J1+N2 ),
- $ LDA, ZERO, WORK( M*M+1 ), N2 )
- CALL DLACPY( 'Full', N2, N1, WORK( M*M+1 ), N2, A( J1, J1+N2 ),
- $ LDA )
- CALL DGEMM( 'T', 'N', N2, N1, N2, ONE, WORK, M, B( J1, J1+N2 ),
- $ LDB, ZERO, WORK( M*M+1 ), N2 )
- CALL DLACPY( 'Full', N2, N1, WORK( M*M+1 ), N2, B( J1, J1+N2 ),
- $ LDB )
- CALL DGEMM( 'N', 'N', M, M, M, ONE, LI, LDST, WORK, M, ZERO,
- $ WORK( M*M+1 ), M )
- CALL DLACPY( 'Full', M, M, WORK( M*M+1 ), M, LI, LDST )
- CALL DGEMM( 'N', 'N', N2, N1, N1, ONE, A( J1, J1+N2 ), LDA,
- $ T( N2+1, N2+1 ), LDST, ZERO, WORK, N2 )
- CALL DLACPY( 'Full', N2, N1, WORK, N2, A( J1, J1+N2 ), LDA )
- CALL DGEMM( 'N', 'N', N2, N1, N1, ONE, B( J1, J1+N2 ), LDB,
- $ T( N2+1, N2+1 ), LDST, ZERO, WORK, N2 )
- CALL DLACPY( 'Full', N2, N1, WORK, N2, B( J1, J1+N2 ), LDB )
- CALL DGEMM( 'T', 'N', M, M, M, ONE, IR, LDST, T, LDST, ZERO,
- $ WORK, M )
- CALL DLACPY( 'Full', M, M, WORK, M, IR, LDST )
-*
-* Accumulate transformations into Q and Z if requested.
-*
- IF( WANTQ ) THEN
- CALL DGEMM( 'N', 'N', N, M, M, ONE, Q( 1, J1 ), LDQ, LI,
- $ LDST, ZERO, WORK, N )
- CALL DLACPY( 'Full', N, M, WORK, N, Q( 1, J1 ), LDQ )
-*
- END IF
-*
- IF( WANTZ ) THEN
- CALL DGEMM( 'N', 'N', N, M, M, ONE, Z( 1, J1 ), LDZ, IR,
- $ LDST, ZERO, WORK, N )
- CALL DLACPY( 'Full', N, M, WORK, N, Z( 1, J1 ), LDZ )
-*
- END IF
-*
-* Update (A(J1:J1+M-1, M+J1:N), B(J1:J1+M-1, M+J1:N)) and
-* (A(1:J1-1, J1:J1+M), B(1:J1-1, J1:J1+M)).
-*
- I = J1 + M
- IF( I.LE.N ) THEN
- CALL DGEMM( 'T', 'N', M, N-I+1, M, ONE, LI, LDST,
- $ A( J1, I ), LDA, ZERO, WORK, M )
- CALL DLACPY( 'Full', M, N-I+1, WORK, M, A( J1, I ), LDA )
- CALL DGEMM( 'T', 'N', M, N-I+1, M, ONE, LI, LDST,
- $ B( J1, I ), LDA, ZERO, WORK, M )
- CALL DLACPY( 'Full', M, N-I+1, WORK, M, B( J1, I ), LDB )
- END IF
- I = J1 - 1
- IF( I.GT.0 ) THEN
- CALL DGEMM( 'N', 'N', I, M, M, ONE, A( 1, J1 ), LDA, IR,
- $ LDST, ZERO, WORK, I )
- CALL DLACPY( 'Full', I, M, WORK, I, A( 1, J1 ), LDA )
- CALL DGEMM( 'N', 'N', I, M, M, ONE, B( 1, J1 ), LDB, IR,
- $ LDST, ZERO, WORK, I )
- CALL DLACPY( 'Full', I, M, WORK, I, B( 1, J1 ), LDB )
- END IF
-*
-* Exit with INFO = 0 if swap was successfully performed.
-*
- RETURN
-*
- END IF
-*
-* Exit with INFO = 1 if swap was rejected.
-*
- 70 CONTINUE
-*
- INFO = 1
- RETURN
-*
-* End of DTGEX2
-*
- END
diff --git a/src/lib/lapack/dtgexc.f b/src/lib/lapack/dtgexc.f
deleted file mode 100644
index bafefea2..00000000
--- a/src/lib/lapack/dtgexc.f
+++ /dev/null
@@ -1,440 +0,0 @@
- SUBROUTINE DTGEXC( WANTQ, WANTZ, N, A, LDA, B, LDB, Q, LDQ, Z,
- $ LDZ, IFST, ILST, WORK, LWORK, INFO )
-*
-* -- LAPACK routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- LOGICAL WANTQ, WANTZ
- INTEGER IFST, ILST, INFO, LDA, LDB, LDQ, LDZ, LWORK, N
-* ..
-* .. Array Arguments ..
- DOUBLE PRECISION A( LDA, * ), B( LDB, * ), Q( LDQ, * ),
- $ WORK( * ), Z( LDZ, * )
-* ..
-*
-* Purpose
-* =======
-*
-* DTGEXC reorders the generalized real Schur decomposition of a real
-* matrix pair (A,B) using an orthogonal equivalence transformation
-*
-* (A, B) = Q * (A, B) * Z',
-*
-* so that the diagonal block of (A, B) with row index IFST is moved
-* to row ILST.
-*
-* (A, B) must be in generalized real Schur canonical form (as returned
-* by DGGES), i.e. A is block upper triangular with 1-by-1 and 2-by-2
-* diagonal blocks. B is upper triangular.
-*
-* Optionally, the matrices Q and Z of generalized Schur vectors are
-* updated.
-*
-* Q(in) * A(in) * Z(in)' = Q(out) * A(out) * Z(out)'
-* Q(in) * B(in) * Z(in)' = Q(out) * B(out) * Z(out)'
-*
-*
-* Arguments
-* =========
-*
-* WANTQ (input) LOGICAL
-* .TRUE. : update the left transformation matrix Q;
-* .FALSE.: do not update Q.
-*
-* WANTZ (input) LOGICAL
-* .TRUE. : update the right transformation matrix Z;
-* .FALSE.: do not update Z.
-*
-* N (input) INTEGER
-* The order of the matrices A and B. N >= 0.
-*
-* A (input/output) DOUBLE PRECISION array, dimension (LDA,N)
-* On entry, the matrix A in generalized real Schur canonical
-* form.
-* On exit, the updated matrix A, again in generalized
-* real Schur canonical form.
-*
-* LDA (input) INTEGER
-* The leading dimension of the array A. LDA >= max(1,N).
-*
-* B (input/output) DOUBLE PRECISION array, dimension (LDB,N)
-* On entry, the matrix B in generalized real Schur canonical
-* form (A,B).
-* On exit, the updated matrix B, again in generalized
-* real Schur canonical form (A,B).
-*
-* LDB (input) INTEGER
-* The leading dimension of the array B. LDB >= max(1,N).
-*
-* Q (input/output) DOUBLE PRECISION array, dimension (LDZ,N)
-* On entry, if WANTQ = .TRUE., the orthogonal matrix Q.
-* On exit, the updated matrix Q.
-* If WANTQ = .FALSE., Q is not referenced.
-*
-* LDQ (input) INTEGER
-* The leading dimension of the array Q. LDQ >= 1.
-* If WANTQ = .TRUE., LDQ >= N.
-*
-* Z (input/output) DOUBLE PRECISION array, dimension (LDZ,N)
-* On entry, if WANTZ = .TRUE., the orthogonal matrix Z.
-* On exit, the updated matrix Z.
-* If WANTZ = .FALSE., Z is not referenced.
-*
-* LDZ (input) INTEGER
-* The leading dimension of the array Z. LDZ >= 1.
-* If WANTZ = .TRUE., LDZ >= N.
-*
-* IFST (input/output) INTEGER
-* ILST (input/output) INTEGER
-* Specify the reordering of the diagonal blocks of (A, B).
-* The block with row index IFST is moved to row ILST, by a
-* sequence of swapping between adjacent blocks.
-* On exit, if IFST pointed on entry to the second row of
-* a 2-by-2 block, it is changed to point to the first row;
-* ILST always points to the first row of the block in its
-* final position (which may differ from its input value by
-* +1 or -1). 1 <= IFST, ILST <= N.
-*
-* WORK (workspace/output) DOUBLE PRECISION array, dimension (MAX(1,LWORK))
-* On exit, if INFO = 0, WORK(1) returns the optimal LWORK.
-*
-* LWORK (input) INTEGER
-* The dimension of the array WORK.
-* LWORK >= 1 when N <= 1, otherwise LWORK >= 4*N + 16.
-*
-* If LWORK = -1, then a workspace query is assumed; the routine
-* only calculates the optimal size of the WORK array, returns
-* this value as the first entry of the WORK array, and no error
-* message related to LWORK is issued by XERBLA.
-*
-* INFO (output) INTEGER
-* =0: successful exit.
-* <0: if INFO = -i, the i-th argument had an illegal value.
-* =1: The transformed matrix pair (A, B) would be too far
-* from generalized Schur form; the problem is ill-
-* conditioned. (A, B) may have been partially reordered,
-* and ILST points to the first row of the current
-* position of the block being moved.
-*
-* Further Details
-* ===============
-*
-* Based on contributions by
-* Bo Kagstrom and Peter Poromaa, Department of Computing Science,
-* Umea University, S-901 87 Umea, Sweden.
-*
-* [1] B. Kagstrom; A Direct Method for Reordering Eigenvalues in the
-* Generalized Real Schur Form of a Regular Matrix Pair (A, B), in
-* M.S. Moonen et al (eds), Linear Algebra for Large Scale and
-* Real-Time Applications, Kluwer Academic Publ. 1993, pp 195-218.
-*
-* =====================================================================
-*
-* .. Parameters ..
- DOUBLE PRECISION ZERO
- PARAMETER ( ZERO = 0.0D+0 )
-* ..
-* .. Local Scalars ..
- LOGICAL LQUERY
- INTEGER HERE, LWMIN, NBF, NBL, NBNEXT
-* ..
-* .. External Subroutines ..
- EXTERNAL DTGEX2, XERBLA
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC MAX
-* ..
-* .. Executable Statements ..
-*
-* Decode and test input arguments.
-*
- INFO = 0
- LQUERY = ( LWORK.EQ.-1 )
- IF( N.LT.0 ) THEN
- INFO = -3
- ELSE IF( LDA.LT.MAX( 1, N ) ) THEN
- INFO = -5
- ELSE IF( LDB.LT.MAX( 1, N ) ) THEN
- INFO = -7
- ELSE IF( LDQ.LT.1 .OR. WANTQ .AND. ( LDQ.LT.MAX( 1, N ) ) ) THEN
- INFO = -9
- ELSE IF( LDZ.LT.1 .OR. WANTZ .AND. ( LDZ.LT.MAX( 1, N ) ) ) THEN
- INFO = -11
- ELSE IF( IFST.LT.1 .OR. IFST.GT.N ) THEN
- INFO = -12
- ELSE IF( ILST.LT.1 .OR. ILST.GT.N ) THEN
- INFO = -13
- END IF
-*
- IF( INFO.EQ.0 ) THEN
- IF( N.LE.1 ) THEN
- LWMIN = 1
- ELSE
- LWMIN = 4*N + 16
- END IF
- WORK(1) = LWMIN
-*
- IF (LWORK.LT.LWMIN .AND. .NOT.LQUERY) THEN
- INFO = -15
- END IF
- END IF
-*
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'DTGEXC', -INFO )
- RETURN
- ELSE IF( LQUERY ) THEN
- RETURN
- END IF
-*
-* Quick return if possible
-*
- IF( N.LE.1 )
- $ RETURN
-*
-* Determine the first row of the specified block and find out
-* if it is 1-by-1 or 2-by-2.
-*
- IF( IFST.GT.1 ) THEN
- IF( A( IFST, IFST-1 ).NE.ZERO )
- $ IFST = IFST - 1
- END IF
- NBF = 1
- IF( IFST.LT.N ) THEN
- IF( A( IFST+1, IFST ).NE.ZERO )
- $ NBF = 2
- END IF
-*
-* Determine the first row of the final block
-* and find out if it is 1-by-1 or 2-by-2.
-*
- IF( ILST.GT.1 ) THEN
- IF( A( ILST, ILST-1 ).NE.ZERO )
- $ ILST = ILST - 1
- END IF
- NBL = 1
- IF( ILST.LT.N ) THEN
- IF( A( ILST+1, ILST ).NE.ZERO )
- $ NBL = 2
- END IF
- IF( IFST.EQ.ILST )
- $ RETURN
-*
- IF( IFST.LT.ILST ) THEN
-*
-* Update ILST.
-*
- IF( NBF.EQ.2 .AND. NBL.EQ.1 )
- $ ILST = ILST - 1
- IF( NBF.EQ.1 .AND. NBL.EQ.2 )
- $ ILST = ILST + 1
-*
- HERE = IFST
-*
- 10 CONTINUE
-*
-* Swap with next one below.
-*
- IF( NBF.EQ.1 .OR. NBF.EQ.2 ) THEN
-*
-* Current block either 1-by-1 or 2-by-2.
-*
- NBNEXT = 1
- IF( HERE+NBF+1.LE.N ) THEN
- IF( A( HERE+NBF+1, HERE+NBF ).NE.ZERO )
- $ NBNEXT = 2
- END IF
- CALL DTGEX2( WANTQ, WANTZ, N, A, LDA, B, LDB, Q, LDQ, Z,
- $ LDZ, HERE, NBF, NBNEXT, WORK, LWORK, INFO )
- IF( INFO.NE.0 ) THEN
- ILST = HERE
- RETURN
- END IF
- HERE = HERE + NBNEXT
-*
-* Test if 2-by-2 block breaks into two 1-by-1 blocks.
-*
- IF( NBF.EQ.2 ) THEN
- IF( A( HERE+1, HERE ).EQ.ZERO )
- $ NBF = 3
- END IF
-*
- ELSE
-*
-* Current block consists of two 1-by-1 blocks, each of which
-* must be swapped individually.
-*
- NBNEXT = 1
- IF( HERE+3.LE.N ) THEN
- IF( A( HERE+3, HERE+2 ).NE.ZERO )
- $ NBNEXT = 2
- END IF
- CALL DTGEX2( WANTQ, WANTZ, N, A, LDA, B, LDB, Q, LDQ, Z,
- $ LDZ, HERE+1, 1, NBNEXT, WORK, LWORK, INFO )
- IF( INFO.NE.0 ) THEN
- ILST = HERE
- RETURN
- END IF
- IF( NBNEXT.EQ.1 ) THEN
-*
-* Swap two 1-by-1 blocks.
-*
- CALL DTGEX2( WANTQ, WANTZ, N, A, LDA, B, LDB, Q, LDQ, Z,
- $ LDZ, HERE, 1, 1, WORK, LWORK, INFO )
- IF( INFO.NE.0 ) THEN
- ILST = HERE
- RETURN
- END IF
- HERE = HERE + 1
-*
- ELSE
-*
-* Recompute NBNEXT in case of 2-by-2 split.
-*
- IF( A( HERE+2, HERE+1 ).EQ.ZERO )
- $ NBNEXT = 1
- IF( NBNEXT.EQ.2 ) THEN
-*
-* 2-by-2 block did not split.
-*
- CALL DTGEX2( WANTQ, WANTZ, N, A, LDA, B, LDB, Q, LDQ,
- $ Z, LDZ, HERE, 1, NBNEXT, WORK, LWORK,
- $ INFO )
- IF( INFO.NE.0 ) THEN
- ILST = HERE
- RETURN
- END IF
- HERE = HERE + 2
- ELSE
-*
-* 2-by-2 block did split.
-*
- CALL DTGEX2( WANTQ, WANTZ, N, A, LDA, B, LDB, Q, LDQ,
- $ Z, LDZ, HERE, 1, 1, WORK, LWORK, INFO )
- IF( INFO.NE.0 ) THEN
- ILST = HERE
- RETURN
- END IF
- HERE = HERE + 1
- CALL DTGEX2( WANTQ, WANTZ, N, A, LDA, B, LDB, Q, LDQ,
- $ Z, LDZ, HERE, 1, 1, WORK, LWORK, INFO )
- IF( INFO.NE.0 ) THEN
- ILST = HERE
- RETURN
- END IF
- HERE = HERE + 1
- END IF
-*
- END IF
- END IF
- IF( HERE.LT.ILST )
- $ GO TO 10
- ELSE
- HERE = IFST
-*
- 20 CONTINUE
-*
-* Swap with next one below.
-*
- IF( NBF.EQ.1 .OR. NBF.EQ.2 ) THEN
-*
-* Current block either 1-by-1 or 2-by-2.
-*
- NBNEXT = 1
- IF( HERE.GE.3 ) THEN
- IF( A( HERE-1, HERE-2 ).NE.ZERO )
- $ NBNEXT = 2
- END IF
- CALL DTGEX2( WANTQ, WANTZ, N, A, LDA, B, LDB, Q, LDQ, Z,
- $ LDZ, HERE-NBNEXT, NBNEXT, NBF, WORK, LWORK,
- $ INFO )
- IF( INFO.NE.0 ) THEN
- ILST = HERE
- RETURN
- END IF
- HERE = HERE - NBNEXT
-*
-* Test if 2-by-2 block breaks into two 1-by-1 blocks.
-*
- IF( NBF.EQ.2 ) THEN
- IF( A( HERE+1, HERE ).EQ.ZERO )
- $ NBF = 3
- END IF
-*
- ELSE
-*
-* Current block consists of two 1-by-1 blocks, each of which
-* must be swapped individually.
-*
- NBNEXT = 1
- IF( HERE.GE.3 ) THEN
- IF( A( HERE-1, HERE-2 ).NE.ZERO )
- $ NBNEXT = 2
- END IF
- CALL DTGEX2( WANTQ, WANTZ, N, A, LDA, B, LDB, Q, LDQ, Z,
- $ LDZ, HERE-NBNEXT, NBNEXT, 1, WORK, LWORK,
- $ INFO )
- IF( INFO.NE.0 ) THEN
- ILST = HERE
- RETURN
- END IF
- IF( NBNEXT.EQ.1 ) THEN
-*
-* Swap two 1-by-1 blocks.
-*
- CALL DTGEX2( WANTQ, WANTZ, N, A, LDA, B, LDB, Q, LDQ, Z,
- $ LDZ, HERE, NBNEXT, 1, WORK, LWORK, INFO )
- IF( INFO.NE.0 ) THEN
- ILST = HERE
- RETURN
- END IF
- HERE = HERE - 1
- ELSE
-*
-* Recompute NBNEXT in case of 2-by-2 split.
-*
- IF( A( HERE, HERE-1 ).EQ.ZERO )
- $ NBNEXT = 1
- IF( NBNEXT.EQ.2 ) THEN
-*
-* 2-by-2 block did not split.
-*
- CALL DTGEX2( WANTQ, WANTZ, N, A, LDA, B, LDB, Q, LDQ,
- $ Z, LDZ, HERE-1, 2, 1, WORK, LWORK, INFO )
- IF( INFO.NE.0 ) THEN
- ILST = HERE
- RETURN
- END IF
- HERE = HERE - 2
- ELSE
-*
-* 2-by-2 block did split.
-*
- CALL DTGEX2( WANTQ, WANTZ, N, A, LDA, B, LDB, Q, LDQ,
- $ Z, LDZ, HERE, 1, 1, WORK, LWORK, INFO )
- IF( INFO.NE.0 ) THEN
- ILST = HERE
- RETURN
- END IF
- HERE = HERE - 1
- CALL DTGEX2( WANTQ, WANTZ, N, A, LDA, B, LDB, Q, LDQ,
- $ Z, LDZ, HERE, 1, 1, WORK, LWORK, INFO )
- IF( INFO.NE.0 ) THEN
- ILST = HERE
- RETURN
- END IF
- HERE = HERE - 1
- END IF
- END IF
- END IF
- IF( HERE.GT.ILST )
- $ GO TO 20
- END IF
- ILST = HERE
- WORK( 1 ) = LWMIN
- RETURN
-*
-* End of DTGEXC
-*
- END
diff --git a/src/lib/lapack/dtgsen.f b/src/lib/lapack/dtgsen.f
deleted file mode 100644
index 917a7b0f..00000000
--- a/src/lib/lapack/dtgsen.f
+++ /dev/null
@@ -1,723 +0,0 @@
- SUBROUTINE DTGSEN( IJOB, WANTQ, WANTZ, SELECT, N, A, LDA, B, LDB,
- $ ALPHAR, ALPHAI, BETA, Q, LDQ, Z, LDZ, M, PL,
- $ PR, DIF, WORK, LWORK, IWORK, LIWORK, INFO )
-*
-* -- LAPACK routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* Modified to call DLACN2 in place of DLACON, 5 Feb 03, SJH.
-*
-* .. Scalar Arguments ..
- LOGICAL WANTQ, WANTZ
- INTEGER IJOB, INFO, LDA, LDB, LDQ, LDZ, LIWORK, LWORK,
- $ M, N
- DOUBLE PRECISION PL, PR
-* ..
-* .. Array Arguments ..
- LOGICAL SELECT( * )
- INTEGER IWORK( * )
- DOUBLE PRECISION A( LDA, * ), ALPHAI( * ), ALPHAR( * ),
- $ B( LDB, * ), BETA( * ), DIF( * ), Q( LDQ, * ),
- $ WORK( * ), Z( LDZ, * )
-* ..
-*
-* Purpose
-* =======
-*
-* DTGSEN reorders the generalized real Schur decomposition of a real
-* matrix pair (A, B) (in terms of an orthonormal equivalence trans-
-* formation Q' * (A, B) * Z), so that a selected cluster of eigenvalues
-* appears in the leading diagonal blocks of the upper quasi-triangular
-* matrix A and the upper triangular B. The leading columns of Q and
-* Z form orthonormal bases of the corresponding left and right eigen-
-* spaces (deflating subspaces). (A, B) must be in generalized real
-* Schur canonical form (as returned by DGGES), i.e. A is block upper
-* triangular with 1-by-1 and 2-by-2 diagonal blocks. B is upper
-* triangular.
-*
-* DTGSEN also computes the generalized eigenvalues
-*
-* w(j) = (ALPHAR(j) + i*ALPHAI(j))/BETA(j)
-*
-* of the reordered matrix pair (A, B).
-*
-* Optionally, DTGSEN computes the estimates of reciprocal condition
-* numbers for eigenvalues and eigenspaces. These are Difu[(A11,B11),
-* (A22,B22)] and Difl[(A11,B11), (A22,B22)], i.e. the separation(s)
-* between the matrix pairs (A11, B11) and (A22,B22) that correspond to
-* the selected cluster and the eigenvalues outside the cluster, resp.,
-* and norms of "projections" onto left and right eigenspaces w.r.t.
-* the selected cluster in the (1,1)-block.
-*
-* Arguments
-* =========
-*
-* IJOB (input) INTEGER
-* Specifies whether condition numbers are required for the
-* cluster of eigenvalues (PL and PR) or the deflating subspaces
-* (Difu and Difl):
-* =0: Only reorder w.r.t. SELECT. No extras.
-* =1: Reciprocal of norms of "projections" onto left and right
-* eigenspaces w.r.t. the selected cluster (PL and PR).
-* =2: Upper bounds on Difu and Difl. F-norm-based estimate
-* (DIF(1:2)).
-* =3: Estimate of Difu and Difl. 1-norm-based estimate
-* (DIF(1:2)).
-* About 5 times as expensive as IJOB = 2.
-* =4: Compute PL, PR and DIF (i.e. 0, 1 and 2 above): Economic
-* version to get it all.
-* =5: Compute PL, PR and DIF (i.e. 0, 1 and 3 above)
-*
-* WANTQ (input) LOGICAL
-* .TRUE. : update the left transformation matrix Q;
-* .FALSE.: do not update Q.
-*
-* WANTZ (input) LOGICAL
-* .TRUE. : update the right transformation matrix Z;
-* .FALSE.: do not update Z.
-*
-* SELECT (input) LOGICAL array, dimension (N)
-* SELECT specifies the eigenvalues in the selected cluster.
-* To select a real eigenvalue w(j), SELECT(j) must be set to
-* .TRUE.. To select a complex conjugate pair of eigenvalues
-* w(j) and w(j+1), corresponding to a 2-by-2 diagonal block,
-* either SELECT(j) or SELECT(j+1) or both must be set to
-* .TRUE.; a complex conjugate pair of eigenvalues must be
-* either both included in the cluster or both excluded.
-*
-* N (input) INTEGER
-* The order of the matrices A and B. N >= 0.
-*
-* A (input/output) DOUBLE PRECISION array, dimension(LDA,N)
-* On entry, the upper quasi-triangular matrix A, with (A, B) in
-* generalized real Schur canonical form.
-* On exit, A is overwritten by the reordered matrix A.
-*
-* LDA (input) INTEGER
-* The leading dimension of the array A. LDA >= max(1,N).
-*
-* B (input/output) DOUBLE PRECISION array, dimension(LDB,N)
-* On entry, the upper triangular matrix B, with (A, B) in
-* generalized real Schur canonical form.
-* On exit, B is overwritten by the reordered matrix B.
-*
-* LDB (input) INTEGER
-* The leading dimension of the array B. LDB >= max(1,N).
-*
-* ALPHAR (output) DOUBLE PRECISION array, dimension (N)
-* ALPHAI (output) DOUBLE PRECISION array, dimension (N)
-* BETA (output) DOUBLE PRECISION array, dimension (N)
-* On exit, (ALPHAR(j) + ALPHAI(j)*i)/BETA(j), j=1,...,N, will
-* be the generalized eigenvalues. ALPHAR(j) + ALPHAI(j)*i
-* and BETA(j),j=1,...,N are the diagonals of the complex Schur
-* form (S,T) that would result if the 2-by-2 diagonal blocks of
-* the real generalized Schur form of (A,B) were further reduced
-* to triangular form using complex unitary transformations.
-* If ALPHAI(j) is zero, then the j-th eigenvalue is real; if
-* positive, then the j-th and (j+1)-st eigenvalues are a
-* complex conjugate pair, with ALPHAI(j+1) negative.
-*
-* Q (input/output) DOUBLE PRECISION array, dimension (LDQ,N)
-* On entry, if WANTQ = .TRUE., Q is an N-by-N matrix.
-* On exit, Q has been postmultiplied by the left orthogonal
-* transformation matrix which reorder (A, B); The leading M
-* columns of Q form orthonormal bases for the specified pair of
-* left eigenspaces (deflating subspaces).
-* If WANTQ = .FALSE., Q is not referenced.
-*
-* LDQ (input) INTEGER
-* The leading dimension of the array Q. LDQ >= 1;
-* and if WANTQ = .TRUE., LDQ >= N.
-*
-* Z (input/output) DOUBLE PRECISION array, dimension (LDZ,N)
-* On entry, if WANTZ = .TRUE., Z is an N-by-N matrix.
-* On exit, Z has been postmultiplied by the left orthogonal
-* transformation matrix which reorder (A, B); The leading M
-* columns of Z form orthonormal bases for the specified pair of
-* left eigenspaces (deflating subspaces).
-* If WANTZ = .FALSE., Z is not referenced.
-*
-* LDZ (input) INTEGER
-* The leading dimension of the array Z. LDZ >= 1;
-* If WANTZ = .TRUE., LDZ >= N.
-*
-* M (output) INTEGER
-* The dimension of the specified pair of left and right eigen-
-* spaces (deflating subspaces). 0 <= M <= N.
-*
-* PL (output) DOUBLE PRECISION
-* PR (output) DOUBLE PRECISION
-* If IJOB = 1, 4 or 5, PL, PR are lower bounds on the
-* reciprocal of the norm of "projections" onto left and right
-* eigenspaces with respect to the selected cluster.
-* 0 < PL, PR <= 1.
-* If M = 0 or M = N, PL = PR = 1.
-* If IJOB = 0, 2 or 3, PL and PR are not referenced.
-*
-* DIF (output) DOUBLE PRECISION array, dimension (2).
-* If IJOB >= 2, DIF(1:2) store the estimates of Difu and Difl.
-* If IJOB = 2 or 4, DIF(1:2) are F-norm-based upper bounds on
-* Difu and Difl. If IJOB = 3 or 5, DIF(1:2) are 1-norm-based
-* estimates of Difu and Difl.
-* If M = 0 or N, DIF(1:2) = F-norm([A, B]).
-* If IJOB = 0 or 1, DIF is not referenced.
-*
-* WORK (workspace/output) DOUBLE PRECISION array, dimension (MAX(1,LWORK))
-* IF IJOB = 0, WORK is not referenced. Otherwise,
-* on exit, if INFO = 0, WORK(1) returns the optimal LWORK.
-*
-* LWORK (input) INTEGER
-* The dimension of the array WORK. LWORK >= 4*N+16.
-* If IJOB = 1, 2 or 4, LWORK >= MAX(4*N+16, 2*M*(N-M)).
-* If IJOB = 3 or 5, LWORK >= MAX(4*N+16, 4*M*(N-M)).
-*
-* If LWORK = -1, then a workspace query is assumed; the routine
-* only calculates the optimal size of the WORK array, returns
-* this value as the first entry of the WORK array, and no error
-* message related to LWORK is issued by XERBLA.
-*
-* IWORK (workspace/output) INTEGER array, dimension (MAX(1,LIWORK))
-* IF IJOB = 0, IWORK is not referenced. Otherwise,
-* on exit, if INFO = 0, IWORK(1) returns the optimal LIWORK.
-*
-* LIWORK (input) INTEGER
-* The dimension of the array IWORK. LIWORK >= 1.
-* If IJOB = 1, 2 or 4, LIWORK >= N+6.
-* If IJOB = 3 or 5, LIWORK >= MAX(2*M*(N-M), N+6).
-*
-* If LIWORK = -1, then a workspace query is assumed; the
-* routine only calculates the optimal size of the IWORK array,
-* returns this value as the first entry of the IWORK array, and
-* no error message related to LIWORK is issued by XERBLA.
-*
-* INFO (output) INTEGER
-* =0: Successful exit.
-* <0: If INFO = -i, the i-th argument had an illegal value.
-* =1: Reordering of (A, B) failed because the transformed
-* matrix pair (A, B) would be too far from generalized
-* Schur form; the problem is very ill-conditioned.
-* (A, B) may have been partially reordered.
-* If requested, 0 is returned in DIF(*), PL and PR.
-*
-* Further Details
-* ===============
-*
-* DTGSEN first collects the selected eigenvalues by computing
-* orthogonal U and W that move them to the top left corner of (A, B).
-* In other words, the selected eigenvalues are the eigenvalues of
-* (A11, B11) in:
-*
-* U'*(A, B)*W = (A11 A12) (B11 B12) n1
-* ( 0 A22),( 0 B22) n2
-* n1 n2 n1 n2
-*
-* where N = n1+n2 and U' means the transpose of U. The first n1 columns
-* of U and W span the specified pair of left and right eigenspaces
-* (deflating subspaces) of (A, B).
-*
-* If (A, B) has been obtained from the generalized real Schur
-* decomposition of a matrix pair (C, D) = Q*(A, B)*Z', then the
-* reordered generalized real Schur form of (C, D) is given by
-*
-* (C, D) = (Q*U)*(U'*(A, B)*W)*(Z*W)',
-*
-* and the first n1 columns of Q*U and Z*W span the corresponding
-* deflating subspaces of (C, D) (Q and Z store Q*U and Z*W, resp.).
-*
-* Note that if the selected eigenvalue is sufficiently ill-conditioned,
-* then its value may differ significantly from its value before
-* reordering.
-*
-* The reciprocal condition numbers of the left and right eigenspaces
-* spanned by the first n1 columns of U and W (or Q*U and Z*W) may
-* be returned in DIF(1:2), corresponding to Difu and Difl, resp.
-*
-* The Difu and Difl are defined as:
-*
-* Difu[(A11, B11), (A22, B22)] = sigma-min( Zu )
-* and
-* Difl[(A11, B11), (A22, B22)] = Difu[(A22, B22), (A11, B11)],
-*
-* where sigma-min(Zu) is the smallest singular value of the
-* (2*n1*n2)-by-(2*n1*n2) matrix
-*
-* Zu = [ kron(In2, A11) -kron(A22', In1) ]
-* [ kron(In2, B11) -kron(B22', In1) ].
-*
-* Here, Inx is the identity matrix of size nx and A22' is the
-* transpose of A22. kron(X, Y) is the Kronecker product between
-* the matrices X and Y.
-*
-* When DIF(2) is small, small changes in (A, B) can cause large changes
-* in the deflating subspace. An approximate (asymptotic) bound on the
-* maximum angular error in the computed deflating subspaces is
-*
-* EPS * norm((A, B)) / DIF(2),
-*
-* where EPS is the machine precision.
-*
-* The reciprocal norm of the projectors on the left and right
-* eigenspaces associated with (A11, B11) may be returned in PL and PR.
-* They are computed as follows. First we compute L and R so that
-* P*(A, B)*Q is block diagonal, where
-*
-* P = ( I -L ) n1 Q = ( I R ) n1
-* ( 0 I ) n2 and ( 0 I ) n2
-* n1 n2 n1 n2
-*
-* and (L, R) is the solution to the generalized Sylvester equation
-*
-* A11*R - L*A22 = -A12
-* B11*R - L*B22 = -B12
-*
-* Then PL = (F-norm(L)**2+1)**(-1/2) and PR = (F-norm(R)**2+1)**(-1/2).
-* An approximate (asymptotic) bound on the average absolute error of
-* the selected eigenvalues is
-*
-* EPS * norm((A, B)) / PL.
-*
-* There are also global error bounds which valid for perturbations up
-* to a certain restriction: A lower bound (x) on the smallest
-* F-norm(E,F) for which an eigenvalue of (A11, B11) may move and
-* coalesce with an eigenvalue of (A22, B22) under perturbation (E,F),
-* (i.e. (A + E, B + F), is
-*
-* x = min(Difu,Difl)/((1/(PL*PL)+1/(PR*PR))**(1/2)+2*max(1/PL,1/PR)).
-*
-* An approximate bound on x can be computed from DIF(1:2), PL and PR.
-*
-* If y = ( F-norm(E,F) / x) <= 1, the angles between the perturbed
-* (L', R') and unperturbed (L, R) left and right deflating subspaces
-* associated with the selected cluster in the (1,1)-blocks can be
-* bounded as
-*
-* max-angle(L, L') <= arctan( y * PL / (1 - y * (1 - PL * PL)**(1/2))
-* max-angle(R, R') <= arctan( y * PR / (1 - y * (1 - PR * PR)**(1/2))
-*
-* See LAPACK User's Guide section 4.11 or the following references
-* for more information.
-*
-* Note that if the default method for computing the Frobenius-norm-
-* based estimate DIF is not wanted (see DLATDF), then the parameter
-* IDIFJB (see below) should be changed from 3 to 4 (routine DLATDF
-* (IJOB = 2 will be used)). See DTGSYL for more details.
-*
-* Based on contributions by
-* Bo Kagstrom and Peter Poromaa, Department of Computing Science,
-* Umea University, S-901 87 Umea, Sweden.
-*
-* References
-* ==========
-*
-* [1] B. Kagstrom; A Direct Method for Reordering Eigenvalues in the
-* Generalized Real Schur Form of a Regular Matrix Pair (A, B), in
-* M.S. Moonen et al (eds), Linear Algebra for Large Scale and
-* Real-Time Applications, Kluwer Academic Publ. 1993, pp 195-218.
-*
-* [2] B. Kagstrom and P. Poromaa; Computing Eigenspaces with Specified
-* Eigenvalues of a Regular Matrix Pair (A, B) and Condition
-* Estimation: Theory, Algorithms and Software,
-* Report UMINF - 94.04, Department of Computing Science, Umea
-* University, S-901 87 Umea, Sweden, 1994. Also as LAPACK Working
-* Note 87. To appear in Numerical Algorithms, 1996.
-*
-* [3] B. Kagstrom and P. Poromaa, LAPACK-Style Algorithms and Software
-* for Solving the Generalized Sylvester Equation and Estimating the
-* Separation between Regular Matrix Pairs, Report UMINF - 93.23,
-* Department of Computing Science, Umea University, S-901 87 Umea,
-* Sweden, December 1993, Revised April 1994, Also as LAPACK Working
-* Note 75. To appear in ACM Trans. on Math. Software, Vol 22, No 1,
-* 1996.
-*
-* =====================================================================
-*
-* .. Parameters ..
- INTEGER IDIFJB
- PARAMETER ( IDIFJB = 3 )
- DOUBLE PRECISION ZERO, ONE
- PARAMETER ( ZERO = 0.0D+0, ONE = 1.0D+0 )
-* ..
-* .. Local Scalars ..
- LOGICAL LQUERY, PAIR, SWAP, WANTD, WANTD1, WANTD2,
- $ WANTP
- INTEGER I, IERR, IJB, K, KASE, KK, KS, LIWMIN, LWMIN,
- $ MN2, N1, N2
- DOUBLE PRECISION DSCALE, DSUM, EPS, RDSCAL, SMLNUM
-* ..
-* .. Local Arrays ..
- INTEGER ISAVE( 3 )
-* ..
-* .. External Subroutines ..
- EXTERNAL DLACN2, DLACPY, DLAG2, DLASSQ, DTGEXC, DTGSYL,
- $ XERBLA
-* ..
-* .. External Functions ..
- DOUBLE PRECISION DLAMCH
- EXTERNAL DLAMCH
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC MAX, SIGN, SQRT
-* ..
-* .. Executable Statements ..
-*
-* Decode and test the input parameters
-*
- INFO = 0
- LQUERY = ( LWORK.EQ.-1 .OR. LIWORK.EQ.-1 )
-*
- IF( IJOB.LT.0 .OR. IJOB.GT.5 ) THEN
- INFO = -1
- ELSE IF( N.LT.0 ) THEN
- INFO = -5
- ELSE IF( LDA.LT.MAX( 1, N ) ) THEN
- INFO = -7
- ELSE IF( LDB.LT.MAX( 1, N ) ) THEN
- INFO = -9
- ELSE IF( LDQ.LT.1 .OR. ( WANTQ .AND. LDQ.LT.N ) ) THEN
- INFO = -14
- ELSE IF( LDZ.LT.1 .OR. ( WANTZ .AND. LDZ.LT.N ) ) THEN
- INFO = -16
- END IF
-*
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'DTGSEN', -INFO )
- RETURN
- END IF
-*
-* Get machine constants
-*
- EPS = DLAMCH( 'P' )
- SMLNUM = DLAMCH( 'S' ) / EPS
- IERR = 0
-*
- WANTP = IJOB.EQ.1 .OR. IJOB.GE.4
- WANTD1 = IJOB.EQ.2 .OR. IJOB.EQ.4
- WANTD2 = IJOB.EQ.3 .OR. IJOB.EQ.5
- WANTD = WANTD1 .OR. WANTD2
-*
-* Set M to the dimension of the specified pair of deflating
-* subspaces.
-*
- M = 0
- PAIR = .FALSE.
- DO 10 K = 1, N
- IF( PAIR ) THEN
- PAIR = .FALSE.
- ELSE
- IF( K.LT.N ) THEN
- IF( A( K+1, K ).EQ.ZERO ) THEN
- IF( SELECT( K ) )
- $ M = M + 1
- ELSE
- PAIR = .TRUE.
- IF( SELECT( K ) .OR. SELECT( K+1 ) )
- $ M = M + 2
- END IF
- ELSE
- IF( SELECT( N ) )
- $ M = M + 1
- END IF
- END IF
- 10 CONTINUE
-*
- IF( IJOB.EQ.1 .OR. IJOB.EQ.2 .OR. IJOB.EQ.4 ) THEN
- LWMIN = MAX( 1, 4*N+16, 2*M*( N-M ) )
- LIWMIN = MAX( 1, N+6 )
- ELSE IF( IJOB.EQ.3 .OR. IJOB.EQ.5 ) THEN
- LWMIN = MAX( 1, 4*N+16, 4*M*( N-M ) )
- LIWMIN = MAX( 1, 2*M*( N-M ), N+6 )
- ELSE
- LWMIN = MAX( 1, 4*N+16 )
- LIWMIN = 1
- END IF
-*
- WORK( 1 ) = LWMIN
- IWORK( 1 ) = LIWMIN
-*
- IF( LWORK.LT.LWMIN .AND. .NOT.LQUERY ) THEN
- INFO = -22
- ELSE IF( LIWORK.LT.LIWMIN .AND. .NOT.LQUERY ) THEN
- INFO = -24
- END IF
-*
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'DTGSEN', -INFO )
- RETURN
- ELSE IF( LQUERY ) THEN
- RETURN
- END IF
-*
-* Quick return if possible.
-*
- IF( M.EQ.N .OR. M.EQ.0 ) THEN
- IF( WANTP ) THEN
- PL = ONE
- PR = ONE
- END IF
- IF( WANTD ) THEN
- DSCALE = ZERO
- DSUM = ONE
- DO 20 I = 1, N
- CALL DLASSQ( N, A( 1, I ), 1, DSCALE, DSUM )
- CALL DLASSQ( N, B( 1, I ), 1, DSCALE, DSUM )
- 20 CONTINUE
- DIF( 1 ) = DSCALE*SQRT( DSUM )
- DIF( 2 ) = DIF( 1 )
- END IF
- GO TO 60
- END IF
-*
-* Collect the selected blocks at the top-left corner of (A, B).
-*
- KS = 0
- PAIR = .FALSE.
- DO 30 K = 1, N
- IF( PAIR ) THEN
- PAIR = .FALSE.
- ELSE
-*
- SWAP = SELECT( K )
- IF( K.LT.N ) THEN
- IF( A( K+1, K ).NE.ZERO ) THEN
- PAIR = .TRUE.
- SWAP = SWAP .OR. SELECT( K+1 )
- END IF
- END IF
-*
- IF( SWAP ) THEN
- KS = KS + 1
-*
-* Swap the K-th block to position KS.
-* Perform the reordering of diagonal blocks in (A, B)
-* by orthogonal transformation matrices and update
-* Q and Z accordingly (if requested):
-*
- KK = K
- IF( K.NE.KS )
- $ CALL DTGEXC( WANTQ, WANTZ, N, A, LDA, B, LDB, Q, LDQ,
- $ Z, LDZ, KK, KS, WORK, LWORK, IERR )
-*
- IF( IERR.GT.0 ) THEN
-*
-* Swap is rejected: exit.
-*
- INFO = 1
- IF( WANTP ) THEN
- PL = ZERO
- PR = ZERO
- END IF
- IF( WANTD ) THEN
- DIF( 1 ) = ZERO
- DIF( 2 ) = ZERO
- END IF
- GO TO 60
- END IF
-*
- IF( PAIR )
- $ KS = KS + 1
- END IF
- END IF
- 30 CONTINUE
- IF( WANTP ) THEN
-*
-* Solve generalized Sylvester equation for R and L
-* and compute PL and PR.
-*
- N1 = M
- N2 = N - M
- I = N1 + 1
- IJB = 0
- CALL DLACPY( 'Full', N1, N2, A( 1, I ), LDA, WORK, N1 )
- CALL DLACPY( 'Full', N1, N2, B( 1, I ), LDB, WORK( N1*N2+1 ),
- $ N1 )
- CALL DTGSYL( 'N', IJB, N1, N2, A, LDA, A( I, I ), LDA, WORK,
- $ N1, B, LDB, B( I, I ), LDB, WORK( N1*N2+1 ), N1,
- $ DSCALE, DIF( 1 ), WORK( N1*N2*2+1 ),
- $ LWORK-2*N1*N2, IWORK, IERR )
-*
-* Estimate the reciprocal of norms of "projections" onto left
-* and right eigenspaces.
-*
- RDSCAL = ZERO
- DSUM = ONE
- CALL DLASSQ( N1*N2, WORK, 1, RDSCAL, DSUM )
- PL = RDSCAL*SQRT( DSUM )
- IF( PL.EQ.ZERO ) THEN
- PL = ONE
- ELSE
- PL = DSCALE / ( SQRT( DSCALE*DSCALE / PL+PL )*SQRT( PL ) )
- END IF
- RDSCAL = ZERO
- DSUM = ONE
- CALL DLASSQ( N1*N2, WORK( N1*N2+1 ), 1, RDSCAL, DSUM )
- PR = RDSCAL*SQRT( DSUM )
- IF( PR.EQ.ZERO ) THEN
- PR = ONE
- ELSE
- PR = DSCALE / ( SQRT( DSCALE*DSCALE / PR+PR )*SQRT( PR ) )
- END IF
- END IF
-*
- IF( WANTD ) THEN
-*
-* Compute estimates of Difu and Difl.
-*
- IF( WANTD1 ) THEN
- N1 = M
- N2 = N - M
- I = N1 + 1
- IJB = IDIFJB
-*
-* Frobenius norm-based Difu-estimate.
-*
- CALL DTGSYL( 'N', IJB, N1, N2, A, LDA, A( I, I ), LDA, WORK,
- $ N1, B, LDB, B( I, I ), LDB, WORK( N1*N2+1 ),
- $ N1, DSCALE, DIF( 1 ), WORK( 2*N1*N2+1 ),
- $ LWORK-2*N1*N2, IWORK, IERR )
-*
-* Frobenius norm-based Difl-estimate.
-*
- CALL DTGSYL( 'N', IJB, N2, N1, A( I, I ), LDA, A, LDA, WORK,
- $ N2, B( I, I ), LDB, B, LDB, WORK( N1*N2+1 ),
- $ N2, DSCALE, DIF( 2 ), WORK( 2*N1*N2+1 ),
- $ LWORK-2*N1*N2, IWORK, IERR )
- ELSE
-*
-*
-* Compute 1-norm-based estimates of Difu and Difl using
-* reversed communication with DLACN2. In each step a
-* generalized Sylvester equation or a transposed variant
-* is solved.
-*
- KASE = 0
- N1 = M
- N2 = N - M
- I = N1 + 1
- IJB = 0
- MN2 = 2*N1*N2
-*
-* 1-norm-based estimate of Difu.
-*
- 40 CONTINUE
- CALL DLACN2( MN2, WORK( MN2+1 ), WORK, IWORK, DIF( 1 ),
- $ KASE, ISAVE )
- IF( KASE.NE.0 ) THEN
- IF( KASE.EQ.1 ) THEN
-*
-* Solve generalized Sylvester equation.
-*
- CALL DTGSYL( 'N', IJB, N1, N2, A, LDA, A( I, I ), LDA,
- $ WORK, N1, B, LDB, B( I, I ), LDB,
- $ WORK( N1*N2+1 ), N1, DSCALE, DIF( 1 ),
- $ WORK( 2*N1*N2+1 ), LWORK-2*N1*N2, IWORK,
- $ IERR )
- ELSE
-*
-* Solve the transposed variant.
-*
- CALL DTGSYL( 'T', IJB, N1, N2, A, LDA, A( I, I ), LDA,
- $ WORK, N1, B, LDB, B( I, I ), LDB,
- $ WORK( N1*N2+1 ), N1, DSCALE, DIF( 1 ),
- $ WORK( 2*N1*N2+1 ), LWORK-2*N1*N2, IWORK,
- $ IERR )
- END IF
- GO TO 40
- END IF
- DIF( 1 ) = DSCALE / DIF( 1 )
-*
-* 1-norm-based estimate of Difl.
-*
- 50 CONTINUE
- CALL DLACN2( MN2, WORK( MN2+1 ), WORK, IWORK, DIF( 2 ),
- $ KASE, ISAVE )
- IF( KASE.NE.0 ) THEN
- IF( KASE.EQ.1 ) THEN
-*
-* Solve generalized Sylvester equation.
-*
- CALL DTGSYL( 'N', IJB, N2, N1, A( I, I ), LDA, A, LDA,
- $ WORK, N2, B( I, I ), LDB, B, LDB,
- $ WORK( N1*N2+1 ), N2, DSCALE, DIF( 2 ),
- $ WORK( 2*N1*N2+1 ), LWORK-2*N1*N2, IWORK,
- $ IERR )
- ELSE
-*
-* Solve the transposed variant.
-*
- CALL DTGSYL( 'T', IJB, N2, N1, A( I, I ), LDA, A, LDA,
- $ WORK, N2, B( I, I ), LDB, B, LDB,
- $ WORK( N1*N2+1 ), N2, DSCALE, DIF( 2 ),
- $ WORK( 2*N1*N2+1 ), LWORK-2*N1*N2, IWORK,
- $ IERR )
- END IF
- GO TO 50
- END IF
- DIF( 2 ) = DSCALE / DIF( 2 )
-*
- END IF
- END IF
-*
- 60 CONTINUE
-*
-* Compute generalized eigenvalues of reordered pair (A, B) and
-* normalize the generalized Schur form.
-*
- PAIR = .FALSE.
- DO 80 K = 1, N
- IF( PAIR ) THEN
- PAIR = .FALSE.
- ELSE
-*
- IF( K.LT.N ) THEN
- IF( A( K+1, K ).NE.ZERO ) THEN
- PAIR = .TRUE.
- END IF
- END IF
-*
- IF( PAIR ) THEN
-*
-* Compute the eigenvalue(s) at position K.
-*
- WORK( 1 ) = A( K, K )
- WORK( 2 ) = A( K+1, K )
- WORK( 3 ) = A( K, K+1 )
- WORK( 4 ) = A( K+1, K+1 )
- WORK( 5 ) = B( K, K )
- WORK( 6 ) = B( K+1, K )
- WORK( 7 ) = B( K, K+1 )
- WORK( 8 ) = B( K+1, K+1 )
- CALL DLAG2( WORK, 2, WORK( 5 ), 2, SMLNUM*EPS, BETA( K ),
- $ BETA( K+1 ), ALPHAR( K ), ALPHAR( K+1 ),
- $ ALPHAI( K ) )
- ALPHAI( K+1 ) = -ALPHAI( K )
-*
- ELSE
-*
- IF( SIGN( ONE, B( K, K ) ).LT.ZERO ) THEN
-*
-* If B(K,K) is negative, make it positive
-*
- DO 70 I = 1, N
- A( K, I ) = -A( K, I )
- B( K, I ) = -B( K, I )
- Q( I, K ) = -Q( I, K )
- 70 CONTINUE
- END IF
-*
- ALPHAR( K ) = A( K, K )
- ALPHAI( K ) = ZERO
- BETA( K ) = B( K, K )
-*
- END IF
- END IF
- 80 CONTINUE
-*
- WORK( 1 ) = LWMIN
- IWORK( 1 ) = LIWMIN
-*
- RETURN
-*
-* End of DTGSEN
-*
- END
diff --git a/src/lib/lapack/dtgsy2.f b/src/lib/lapack/dtgsy2.f
deleted file mode 100644
index 3ebc912f..00000000
--- a/src/lib/lapack/dtgsy2.f
+++ /dev/null
@@ -1,956 +0,0 @@
- SUBROUTINE DTGSY2( TRANS, IJOB, M, N, A, LDA, B, LDB, C, LDC, D,
- $ LDD, E, LDE, F, LDF, SCALE, RDSUM, RDSCAL,
- $ IWORK, PQ, INFO )
-*
-* -- LAPACK auxiliary routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- CHARACTER TRANS
- INTEGER IJOB, INFO, LDA, LDB, LDC, LDD, LDE, LDF, M, N,
- $ PQ
- DOUBLE PRECISION RDSCAL, RDSUM, SCALE
-* ..
-* .. Array Arguments ..
- INTEGER IWORK( * )
- DOUBLE PRECISION A( LDA, * ), B( LDB, * ), C( LDC, * ),
- $ D( LDD, * ), E( LDE, * ), F( LDF, * )
-* ..
-*
-* Purpose
-* =======
-*
-* DTGSY2 solves the generalized Sylvester equation:
-*
-* A * R - L * B = scale * C (1)
-* D * R - L * E = scale * F,
-*
-* using Level 1 and 2 BLAS. where R and L are unknown M-by-N matrices,
-* (A, D), (B, E) and (C, F) are given matrix pairs of size M-by-M,
-* N-by-N and M-by-N, respectively, with real entries. (A, D) and (B, E)
-* must be in generalized Schur canonical form, i.e. A, B are upper
-* quasi triangular and D, E are upper triangular. The solution (R, L)
-* overwrites (C, F). 0 <= SCALE <= 1 is an output scaling factor
-* chosen to avoid overflow.
-*
-* In matrix notation solving equation (1) corresponds to solve
-* Z*x = scale*b, where Z is defined as
-*
-* Z = [ kron(In, A) -kron(B', Im) ] (2)
-* [ kron(In, D) -kron(E', Im) ],
-*
-* Ik is the identity matrix of size k and X' is the transpose of X.
-* kron(X, Y) is the Kronecker product between the matrices X and Y.
-* In the process of solving (1), we solve a number of such systems
-* where Dim(In), Dim(In) = 1 or 2.
-*
-* If TRANS = 'T', solve the transposed system Z'*y = scale*b for y,
-* which is equivalent to solve for R and L in
-*
-* A' * R + D' * L = scale * C (3)
-* R * B' + L * E' = scale * -F
-*
-* This case is used to compute an estimate of Dif[(A, D), (B, E)] =
-* sigma_min(Z) using reverse communicaton with DLACON.
-*
-* DTGSY2 also (IJOB >= 1) contributes to the computation in STGSYL
-* of an upper bound on the separation between to matrix pairs. Then
-* the input (A, D), (B, E) are sub-pencils of the matrix pair in
-* DTGSYL. See STGSYL for details.
-*
-* Arguments
-* =========
-*
-* TRANS (input) CHARACTER*1
-* = 'N', solve the generalized Sylvester equation (1).
-* = 'T': solve the 'transposed' system (3).
-*
-* IJOB (input) INTEGER
-* Specifies what kind of functionality to be performed.
-* = 0: solve (1) only.
-* = 1: A contribution from this subsystem to a Frobenius
-* norm-based estimate of the separation between two matrix
-* pairs is computed. (look ahead strategy is used).
-* = 2: A contribution from this subsystem to a Frobenius
-* norm-based estimate of the separation between two matrix
-* pairs is computed. (DGECON on sub-systems is used.)
-* Not referenced if TRANS = 'T'.
-*
-* M (input) INTEGER
-* On entry, M specifies the order of A and D, and the row
-* dimension of C, F, R and L.
-*
-* N (input) INTEGER
-* On entry, N specifies the order of B and E, and the column
-* dimension of C, F, R and L.
-*
-* A (input) DOUBLE PRECISION array, dimension (LDA, M)
-* On entry, A contains an upper quasi triangular matrix.
-*
-* LDA (input) INTEGER
-* The leading dimension of the matrix A. LDA >= max(1, M).
-*
-* B (input) DOUBLE PRECISION array, dimension (LDB, N)
-* On entry, B contains an upper quasi triangular matrix.
-*
-* LDB (input) INTEGER
-* The leading dimension of the matrix B. LDB >= max(1, N).
-*
-* C (input/output) DOUBLE PRECISION array, dimension (LDC, N)
-* On entry, C contains the right-hand-side of the first matrix
-* equation in (1).
-* On exit, if IJOB = 0, C has been overwritten by the
-* solution R.
-*
-* LDC (input) INTEGER
-* The leading dimension of the matrix C. LDC >= max(1, M).
-*
-* D (input) DOUBLE PRECISION array, dimension (LDD, M)
-* On entry, D contains an upper triangular matrix.
-*
-* LDD (input) INTEGER
-* The leading dimension of the matrix D. LDD >= max(1, M).
-*
-* E (input) DOUBLE PRECISION array, dimension (LDE, N)
-* On entry, E contains an upper triangular matrix.
-*
-* LDE (input) INTEGER
-* The leading dimension of the matrix E. LDE >= max(1, N).
-*
-* F (input/output) DOUBLE PRECISION array, dimension (LDF, N)
-* On entry, F contains the right-hand-side of the second matrix
-* equation in (1).
-* On exit, if IJOB = 0, F has been overwritten by the
-* solution L.
-*
-* LDF (input) INTEGER
-* The leading dimension of the matrix F. LDF >= max(1, M).
-*
-* SCALE (output) DOUBLE PRECISION
-* On exit, 0 <= SCALE <= 1. If 0 < SCALE < 1, the solutions
-* R and L (C and F on entry) will hold the solutions to a
-* slightly perturbed system but the input matrices A, B, D and
-* E have not been changed. If SCALE = 0, R and L will hold the
-* solutions to the homogeneous system with C = F = 0. Normally,
-* SCALE = 1.
-*
-* RDSUM (input/output) DOUBLE PRECISION
-* On entry, the sum of squares of computed contributions to
-* the Dif-estimate under computation by DTGSYL, where the
-* scaling factor RDSCAL (see below) has been factored out.
-* On exit, the corresponding sum of squares updated with the
-* contributions from the current sub-system.
-* If TRANS = 'T' RDSUM is not touched.
-* NOTE: RDSUM only makes sense when DTGSY2 is called by STGSYL.
-*
-* RDSCAL (input/output) DOUBLE PRECISION
-* On entry, scaling factor used to prevent overflow in RDSUM.
-* On exit, RDSCAL is updated w.r.t. the current contributions
-* in RDSUM.
-* If TRANS = 'T', RDSCAL is not touched.
-* NOTE: RDSCAL only makes sense when DTGSY2 is called by
-* DTGSYL.
-*
-* IWORK (workspace) INTEGER array, dimension (M+N+2)
-*
-* PQ (output) INTEGER
-* On exit, the number of subsystems (of size 2-by-2, 4-by-4 and
-* 8-by-8) solved by this routine.
-*
-* INFO (output) INTEGER
-* On exit, if INFO is set to
-* =0: Successful exit
-* <0: If INFO = -i, the i-th argument had an illegal value.
-* >0: The matrix pairs (A, D) and (B, E) have common or very
-* close eigenvalues.
-*
-* Further Details
-* ===============
-*
-* Based on contributions by
-* Bo Kagstrom and Peter Poromaa, Department of Computing Science,
-* Umea University, S-901 87 Umea, Sweden.
-*
-* =====================================================================
-* Replaced various illegal calls to DCOPY by calls to DLASET.
-* Sven Hammarling, 27/5/02.
-*
-* .. Parameters ..
- INTEGER LDZ
- PARAMETER ( LDZ = 8 )
- DOUBLE PRECISION ZERO, ONE
- PARAMETER ( ZERO = 0.0D+0, ONE = 1.0D+0 )
-* ..
-* .. Local Scalars ..
- LOGICAL NOTRAN
- INTEGER I, IE, IERR, II, IS, ISP1, J, JE, JJ, JS, JSP1,
- $ K, MB, NB, P, Q, ZDIM
- DOUBLE PRECISION ALPHA, SCALOC
-* ..
-* .. Local Arrays ..
- INTEGER IPIV( LDZ ), JPIV( LDZ )
- DOUBLE PRECISION RHS( LDZ ), Z( LDZ, LDZ )
-* ..
-* .. External Functions ..
- LOGICAL LSAME
- EXTERNAL LSAME
-* ..
-* .. External Subroutines ..
- EXTERNAL DAXPY, DCOPY, DGEMM, DGEMV, DGER, DGESC2,
- $ DGETC2, DLASET, DLATDF, DSCAL, XERBLA
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC MAX
-* ..
-* .. Executable Statements ..
-*
-* Decode and test input parameters
-*
- INFO = 0
- IERR = 0
- NOTRAN = LSAME( TRANS, 'N' )
- IF( .NOT.NOTRAN .AND. .NOT.LSAME( TRANS, 'T' ) ) THEN
- INFO = -1
- ELSE IF( NOTRAN ) THEN
- IF( ( IJOB.LT.0 ) .OR. ( IJOB.GT.2 ) ) THEN
- INFO = -2
- END IF
- END IF
- IF( INFO.EQ.0 ) THEN
- IF( M.LE.0 ) THEN
- INFO = -3
- ELSE IF( N.LE.0 ) THEN
- INFO = -4
- ELSE IF( LDA.LT.MAX( 1, M ) ) THEN
- INFO = -5
- ELSE IF( LDB.LT.MAX( 1, N ) ) THEN
- INFO = -8
- ELSE IF( LDC.LT.MAX( 1, M ) ) THEN
- INFO = -10
- ELSE IF( LDD.LT.MAX( 1, M ) ) THEN
- INFO = -12
- ELSE IF( LDE.LT.MAX( 1, N ) ) THEN
- INFO = -14
- ELSE IF( LDF.LT.MAX( 1, M ) ) THEN
- INFO = -16
- END IF
- END IF
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'DTGSY2', -INFO )
- RETURN
- END IF
-*
-* Determine block structure of A
-*
- PQ = 0
- P = 0
- I = 1
- 10 CONTINUE
- IF( I.GT.M )
- $ GO TO 20
- P = P + 1
- IWORK( P ) = I
- IF( I.EQ.M )
- $ GO TO 20
- IF( A( I+1, I ).NE.ZERO ) THEN
- I = I + 2
- ELSE
- I = I + 1
- END IF
- GO TO 10
- 20 CONTINUE
- IWORK( P+1 ) = M + 1
-*
-* Determine block structure of B
-*
- Q = P + 1
- J = 1
- 30 CONTINUE
- IF( J.GT.N )
- $ GO TO 40
- Q = Q + 1
- IWORK( Q ) = J
- IF( J.EQ.N )
- $ GO TO 40
- IF( B( J+1, J ).NE.ZERO ) THEN
- J = J + 2
- ELSE
- J = J + 1
- END IF
- GO TO 30
- 40 CONTINUE
- IWORK( Q+1 ) = N + 1
- PQ = P*( Q-P-1 )
-*
- IF( NOTRAN ) THEN
-*
-* Solve (I, J) - subsystem
-* A(I, I) * R(I, J) - L(I, J) * B(J, J) = C(I, J)
-* D(I, I) * R(I, J) - L(I, J) * E(J, J) = F(I, J)
-* for I = P, P - 1, ..., 1; J = 1, 2, ..., Q
-*
- SCALE = ONE
- SCALOC = ONE
- DO 120 J = P + 2, Q
- JS = IWORK( J )
- JSP1 = JS + 1
- JE = IWORK( J+1 ) - 1
- NB = JE - JS + 1
- DO 110 I = P, 1, -1
-*
- IS = IWORK( I )
- ISP1 = IS + 1
- IE = IWORK( I+1 ) - 1
- MB = IE - IS + 1
- ZDIM = MB*NB*2
-*
- IF( ( MB.EQ.1 ) .AND. ( NB.EQ.1 ) ) THEN
-*
-* Build a 2-by-2 system Z * x = RHS
-*
- Z( 1, 1 ) = A( IS, IS )
- Z( 2, 1 ) = D( IS, IS )
- Z( 1, 2 ) = -B( JS, JS )
- Z( 2, 2 ) = -E( JS, JS )
-*
-* Set up right hand side(s)
-*
- RHS( 1 ) = C( IS, JS )
- RHS( 2 ) = F( IS, JS )
-*
-* Solve Z * x = RHS
-*
- CALL DGETC2( ZDIM, Z, LDZ, IPIV, JPIV, IERR )
- IF( IERR.GT.0 )
- $ INFO = IERR
-*
- IF( IJOB.EQ.0 ) THEN
- CALL DGESC2( ZDIM, Z, LDZ, RHS, IPIV, JPIV,
- $ SCALOC )
- IF( SCALOC.NE.ONE ) THEN
- DO 50 K = 1, N
- CALL DSCAL( M, SCALOC, C( 1, K ), 1 )
- CALL DSCAL( M, SCALOC, F( 1, K ), 1 )
- 50 CONTINUE
- SCALE = SCALE*SCALOC
- END IF
- ELSE
- CALL DLATDF( IJOB, ZDIM, Z, LDZ, RHS, RDSUM,
- $ RDSCAL, IPIV, JPIV )
- END IF
-*
-* Unpack solution vector(s)
-*
- C( IS, JS ) = RHS( 1 )
- F( IS, JS ) = RHS( 2 )
-*
-* Substitute R(I, J) and L(I, J) into remaining
-* equation.
-*
- IF( I.GT.1 ) THEN
- ALPHA = -RHS( 1 )
- CALL DAXPY( IS-1, ALPHA, A( 1, IS ), 1, C( 1, JS ),
- $ 1 )
- CALL DAXPY( IS-1, ALPHA, D( 1, IS ), 1, F( 1, JS ),
- $ 1 )
- END IF
- IF( J.LT.Q ) THEN
- CALL DAXPY( N-JE, RHS( 2 ), B( JS, JE+1 ), LDB,
- $ C( IS, JE+1 ), LDC )
- CALL DAXPY( N-JE, RHS( 2 ), E( JS, JE+1 ), LDE,
- $ F( IS, JE+1 ), LDF )
- END IF
-*
- ELSE IF( ( MB.EQ.1 ) .AND. ( NB.EQ.2 ) ) THEN
-*
-* Build a 4-by-4 system Z * x = RHS
-*
- Z( 1, 1 ) = A( IS, IS )
- Z( 2, 1 ) = ZERO
- Z( 3, 1 ) = D( IS, IS )
- Z( 4, 1 ) = ZERO
-*
- Z( 1, 2 ) = ZERO
- Z( 2, 2 ) = A( IS, IS )
- Z( 3, 2 ) = ZERO
- Z( 4, 2 ) = D( IS, IS )
-*
- Z( 1, 3 ) = -B( JS, JS )
- Z( 2, 3 ) = -B( JS, JSP1 )
- Z( 3, 3 ) = -E( JS, JS )
- Z( 4, 3 ) = -E( JS, JSP1 )
-*
- Z( 1, 4 ) = -B( JSP1, JS )
- Z( 2, 4 ) = -B( JSP1, JSP1 )
- Z( 3, 4 ) = ZERO
- Z( 4, 4 ) = -E( JSP1, JSP1 )
-*
-* Set up right hand side(s)
-*
- RHS( 1 ) = C( IS, JS )
- RHS( 2 ) = C( IS, JSP1 )
- RHS( 3 ) = F( IS, JS )
- RHS( 4 ) = F( IS, JSP1 )
-*
-* Solve Z * x = RHS
-*
- CALL DGETC2( ZDIM, Z, LDZ, IPIV, JPIV, IERR )
- IF( IERR.GT.0 )
- $ INFO = IERR
-*
- IF( IJOB.EQ.0 ) THEN
- CALL DGESC2( ZDIM, Z, LDZ, RHS, IPIV, JPIV,
- $ SCALOC )
- IF( SCALOC.NE.ONE ) THEN
- DO 60 K = 1, N
- CALL DSCAL( M, SCALOC, C( 1, K ), 1 )
- CALL DSCAL( M, SCALOC, F( 1, K ), 1 )
- 60 CONTINUE
- SCALE = SCALE*SCALOC
- END IF
- ELSE
- CALL DLATDF( IJOB, ZDIM, Z, LDZ, RHS, RDSUM,
- $ RDSCAL, IPIV, JPIV )
- END IF
-*
-* Unpack solution vector(s)
-*
- C( IS, JS ) = RHS( 1 )
- C( IS, JSP1 ) = RHS( 2 )
- F( IS, JS ) = RHS( 3 )
- F( IS, JSP1 ) = RHS( 4 )
-*
-* Substitute R(I, J) and L(I, J) into remaining
-* equation.
-*
- IF( I.GT.1 ) THEN
- CALL DGER( IS-1, NB, -ONE, A( 1, IS ), 1, RHS( 1 ),
- $ 1, C( 1, JS ), LDC )
- CALL DGER( IS-1, NB, -ONE, D( 1, IS ), 1, RHS( 1 ),
- $ 1, F( 1, JS ), LDF )
- END IF
- IF( J.LT.Q ) THEN
- CALL DAXPY( N-JE, RHS( 3 ), B( JS, JE+1 ), LDB,
- $ C( IS, JE+1 ), LDC )
- CALL DAXPY( N-JE, RHS( 3 ), E( JS, JE+1 ), LDE,
- $ F( IS, JE+1 ), LDF )
- CALL DAXPY( N-JE, RHS( 4 ), B( JSP1, JE+1 ), LDB,
- $ C( IS, JE+1 ), LDC )
- CALL DAXPY( N-JE, RHS( 4 ), E( JSP1, JE+1 ), LDE,
- $ F( IS, JE+1 ), LDF )
- END IF
-*
- ELSE IF( ( MB.EQ.2 ) .AND. ( NB.EQ.1 ) ) THEN
-*
-* Build a 4-by-4 system Z * x = RHS
-*
- Z( 1, 1 ) = A( IS, IS )
- Z( 2, 1 ) = A( ISP1, IS )
- Z( 3, 1 ) = D( IS, IS )
- Z( 4, 1 ) = ZERO
-*
- Z( 1, 2 ) = A( IS, ISP1 )
- Z( 2, 2 ) = A( ISP1, ISP1 )
- Z( 3, 2 ) = D( IS, ISP1 )
- Z( 4, 2 ) = D( ISP1, ISP1 )
-*
- Z( 1, 3 ) = -B( JS, JS )
- Z( 2, 3 ) = ZERO
- Z( 3, 3 ) = -E( JS, JS )
- Z( 4, 3 ) = ZERO
-*
- Z( 1, 4 ) = ZERO
- Z( 2, 4 ) = -B( JS, JS )
- Z( 3, 4 ) = ZERO
- Z( 4, 4 ) = -E( JS, JS )
-*
-* Set up right hand side(s)
-*
- RHS( 1 ) = C( IS, JS )
- RHS( 2 ) = C( ISP1, JS )
- RHS( 3 ) = F( IS, JS )
- RHS( 4 ) = F( ISP1, JS )
-*
-* Solve Z * x = RHS
-*
- CALL DGETC2( ZDIM, Z, LDZ, IPIV, JPIV, IERR )
- IF( IERR.GT.0 )
- $ INFO = IERR
- IF( IJOB.EQ.0 ) THEN
- CALL DGESC2( ZDIM, Z, LDZ, RHS, IPIV, JPIV,
- $ SCALOC )
- IF( SCALOC.NE.ONE ) THEN
- DO 70 K = 1, N
- CALL DSCAL( M, SCALOC, C( 1, K ), 1 )
- CALL DSCAL( M, SCALOC, F( 1, K ), 1 )
- 70 CONTINUE
- SCALE = SCALE*SCALOC
- END IF
- ELSE
- CALL DLATDF( IJOB, ZDIM, Z, LDZ, RHS, RDSUM,
- $ RDSCAL, IPIV, JPIV )
- END IF
-*
-* Unpack solution vector(s)
-*
- C( IS, JS ) = RHS( 1 )
- C( ISP1, JS ) = RHS( 2 )
- F( IS, JS ) = RHS( 3 )
- F( ISP1, JS ) = RHS( 4 )
-*
-* Substitute R(I, J) and L(I, J) into remaining
-* equation.
-*
- IF( I.GT.1 ) THEN
- CALL DGEMV( 'N', IS-1, MB, -ONE, A( 1, IS ), LDA,
- $ RHS( 1 ), 1, ONE, C( 1, JS ), 1 )
- CALL DGEMV( 'N', IS-1, MB, -ONE, D( 1, IS ), LDD,
- $ RHS( 1 ), 1, ONE, F( 1, JS ), 1 )
- END IF
- IF( J.LT.Q ) THEN
- CALL DGER( MB, N-JE, ONE, RHS( 3 ), 1,
- $ B( JS, JE+1 ), LDB, C( IS, JE+1 ), LDC )
- CALL DGER( MB, N-JE, ONE, RHS( 3 ), 1,
- $ E( JS, JE+1 ), LDB, F( IS, JE+1 ), LDC )
- END IF
-*
- ELSE IF( ( MB.EQ.2 ) .AND. ( NB.EQ.2 ) ) THEN
-*
-* Build an 8-by-8 system Z * x = RHS
-*
- CALL DLASET( 'F', LDZ, LDZ, ZERO, ZERO, Z, LDZ )
-*
- Z( 1, 1 ) = A( IS, IS )
- Z( 2, 1 ) = A( ISP1, IS )
- Z( 5, 1 ) = D( IS, IS )
-*
- Z( 1, 2 ) = A( IS, ISP1 )
- Z( 2, 2 ) = A( ISP1, ISP1 )
- Z( 5, 2 ) = D( IS, ISP1 )
- Z( 6, 2 ) = D( ISP1, ISP1 )
-*
- Z( 3, 3 ) = A( IS, IS )
- Z( 4, 3 ) = A( ISP1, IS )
- Z( 7, 3 ) = D( IS, IS )
-*
- Z( 3, 4 ) = A( IS, ISP1 )
- Z( 4, 4 ) = A( ISP1, ISP1 )
- Z( 7, 4 ) = D( IS, ISP1 )
- Z( 8, 4 ) = D( ISP1, ISP1 )
-*
- Z( 1, 5 ) = -B( JS, JS )
- Z( 3, 5 ) = -B( JS, JSP1 )
- Z( 5, 5 ) = -E( JS, JS )
- Z( 7, 5 ) = -E( JS, JSP1 )
-*
- Z( 2, 6 ) = -B( JS, JS )
- Z( 4, 6 ) = -B( JS, JSP1 )
- Z( 6, 6 ) = -E( JS, JS )
- Z( 8, 6 ) = -E( JS, JSP1 )
-*
- Z( 1, 7 ) = -B( JSP1, JS )
- Z( 3, 7 ) = -B( JSP1, JSP1 )
- Z( 7, 7 ) = -E( JSP1, JSP1 )
-*
- Z( 2, 8 ) = -B( JSP1, JS )
- Z( 4, 8 ) = -B( JSP1, JSP1 )
- Z( 8, 8 ) = -E( JSP1, JSP1 )
-*
-* Set up right hand side(s)
-*
- K = 1
- II = MB*NB + 1
- DO 80 JJ = 0, NB - 1
- CALL DCOPY( MB, C( IS, JS+JJ ), 1, RHS( K ), 1 )
- CALL DCOPY( MB, F( IS, JS+JJ ), 1, RHS( II ), 1 )
- K = K + MB
- II = II + MB
- 80 CONTINUE
-*
-* Solve Z * x = RHS
-*
- CALL DGETC2( ZDIM, Z, LDZ, IPIV, JPIV, IERR )
- IF( IERR.GT.0 )
- $ INFO = IERR
- IF( IJOB.EQ.0 ) THEN
- CALL DGESC2( ZDIM, Z, LDZ, RHS, IPIV, JPIV,
- $ SCALOC )
- IF( SCALOC.NE.ONE ) THEN
- DO 90 K = 1, N
- CALL DSCAL( M, SCALOC, C( 1, K ), 1 )
- CALL DSCAL( M, SCALOC, F( 1, K ), 1 )
- 90 CONTINUE
- SCALE = SCALE*SCALOC
- END IF
- ELSE
- CALL DLATDF( IJOB, ZDIM, Z, LDZ, RHS, RDSUM,
- $ RDSCAL, IPIV, JPIV )
- END IF
-*
-* Unpack solution vector(s)
-*
- K = 1
- II = MB*NB + 1
- DO 100 JJ = 0, NB - 1
- CALL DCOPY( MB, RHS( K ), 1, C( IS, JS+JJ ), 1 )
- CALL DCOPY( MB, RHS( II ), 1, F( IS, JS+JJ ), 1 )
- K = K + MB
- II = II + MB
- 100 CONTINUE
-*
-* Substitute R(I, J) and L(I, J) into remaining
-* equation.
-*
- IF( I.GT.1 ) THEN
- CALL DGEMM( 'N', 'N', IS-1, NB, MB, -ONE,
- $ A( 1, IS ), LDA, RHS( 1 ), MB, ONE,
- $ C( 1, JS ), LDC )
- CALL DGEMM( 'N', 'N', IS-1, NB, MB, -ONE,
- $ D( 1, IS ), LDD, RHS( 1 ), MB, ONE,
- $ F( 1, JS ), LDF )
- END IF
- IF( J.LT.Q ) THEN
- K = MB*NB + 1
- CALL DGEMM( 'N', 'N', MB, N-JE, NB, ONE, RHS( K ),
- $ MB, B( JS, JE+1 ), LDB, ONE,
- $ C( IS, JE+1 ), LDC )
- CALL DGEMM( 'N', 'N', MB, N-JE, NB, ONE, RHS( K ),
- $ MB, E( JS, JE+1 ), LDE, ONE,
- $ F( IS, JE+1 ), LDF )
- END IF
-*
- END IF
-*
- 110 CONTINUE
- 120 CONTINUE
- ELSE
-*
-* Solve (I, J) - subsystem
-* A(I, I)' * R(I, J) + D(I, I)' * L(J, J) = C(I, J)
-* R(I, I) * B(J, J) + L(I, J) * E(J, J) = -F(I, J)
-* for I = 1, 2, ..., P, J = Q, Q - 1, ..., 1
-*
- SCALE = ONE
- SCALOC = ONE
- DO 200 I = 1, P
-*
- IS = IWORK( I )
- ISP1 = IS + 1
- IE = ( I+1 ) - 1
- MB = IE - IS + 1
- DO 190 J = Q, P + 2, -1
-*
- JS = IWORK( J )
- JSP1 = JS + 1
- JE = IWORK( J+1 ) - 1
- NB = JE - JS + 1
- ZDIM = MB*NB*2
- IF( ( MB.EQ.1 ) .AND. ( NB.EQ.1 ) ) THEN
-*
-* Build a 2-by-2 system Z' * x = RHS
-*
- Z( 1, 1 ) = A( IS, IS )
- Z( 2, 1 ) = -B( JS, JS )
- Z( 1, 2 ) = D( IS, IS )
- Z( 2, 2 ) = -E( JS, JS )
-*
-* Set up right hand side(s)
-*
- RHS( 1 ) = C( IS, JS )
- RHS( 2 ) = F( IS, JS )
-*
-* Solve Z' * x = RHS
-*
- CALL DGETC2( ZDIM, Z, LDZ, IPIV, JPIV, IERR )
- IF( IERR.GT.0 )
- $ INFO = IERR
-*
- CALL DGESC2( ZDIM, Z, LDZ, RHS, IPIV, JPIV, SCALOC )
- IF( SCALOC.NE.ONE ) THEN
- DO 130 K = 1, N
- CALL DSCAL( M, SCALOC, C( 1, K ), 1 )
- CALL DSCAL( M, SCALOC, F( 1, K ), 1 )
- 130 CONTINUE
- SCALE = SCALE*SCALOC
- END IF
-*
-* Unpack solution vector(s)
-*
- C( IS, JS ) = RHS( 1 )
- F( IS, JS ) = RHS( 2 )
-*
-* Substitute R(I, J) and L(I, J) into remaining
-* equation.
-*
- IF( J.GT.P+2 ) THEN
- ALPHA = RHS( 1 )
- CALL DAXPY( JS-1, ALPHA, B( 1, JS ), 1, F( IS, 1 ),
- $ LDF )
- ALPHA = RHS( 2 )
- CALL DAXPY( JS-1, ALPHA, E( 1, JS ), 1, F( IS, 1 ),
- $ LDF )
- END IF
- IF( I.LT.P ) THEN
- ALPHA = -RHS( 1 )
- CALL DAXPY( M-IE, ALPHA, A( IS, IE+1 ), LDA,
- $ C( IE+1, JS ), 1 )
- ALPHA = -RHS( 2 )
- CALL DAXPY( M-IE, ALPHA, D( IS, IE+1 ), LDD,
- $ C( IE+1, JS ), 1 )
- END IF
-*
- ELSE IF( ( MB.EQ.1 ) .AND. ( NB.EQ.2 ) ) THEN
-*
-* Build a 4-by-4 system Z' * x = RHS
-*
- Z( 1, 1 ) = A( IS, IS )
- Z( 2, 1 ) = ZERO
- Z( 3, 1 ) = -B( JS, JS )
- Z( 4, 1 ) = -B( JSP1, JS )
-*
- Z( 1, 2 ) = ZERO
- Z( 2, 2 ) = A( IS, IS )
- Z( 3, 2 ) = -B( JS, JSP1 )
- Z( 4, 2 ) = -B( JSP1, JSP1 )
-*
- Z( 1, 3 ) = D( IS, IS )
- Z( 2, 3 ) = ZERO
- Z( 3, 3 ) = -E( JS, JS )
- Z( 4, 3 ) = ZERO
-*
- Z( 1, 4 ) = ZERO
- Z( 2, 4 ) = D( IS, IS )
- Z( 3, 4 ) = -E( JS, JSP1 )
- Z( 4, 4 ) = -E( JSP1, JSP1 )
-*
-* Set up right hand side(s)
-*
- RHS( 1 ) = C( IS, JS )
- RHS( 2 ) = C( IS, JSP1 )
- RHS( 3 ) = F( IS, JS )
- RHS( 4 ) = F( IS, JSP1 )
-*
-* Solve Z' * x = RHS
-*
- CALL DGETC2( ZDIM, Z, LDZ, IPIV, JPIV, IERR )
- IF( IERR.GT.0 )
- $ INFO = IERR
- CALL DGESC2( ZDIM, Z, LDZ, RHS, IPIV, JPIV, SCALOC )
- IF( SCALOC.NE.ONE ) THEN
- DO 140 K = 1, N
- CALL DSCAL( M, SCALOC, C( 1, K ), 1 )
- CALL DSCAL( M, SCALOC, F( 1, K ), 1 )
- 140 CONTINUE
- SCALE = SCALE*SCALOC
- END IF
-*
-* Unpack solution vector(s)
-*
- C( IS, JS ) = RHS( 1 )
- C( IS, JSP1 ) = RHS( 2 )
- F( IS, JS ) = RHS( 3 )
- F( IS, JSP1 ) = RHS( 4 )
-*
-* Substitute R(I, J) and L(I, J) into remaining
-* equation.
-*
- IF( J.GT.P+2 ) THEN
- CALL DAXPY( JS-1, RHS( 1 ), B( 1, JS ), 1,
- $ F( IS, 1 ), LDF )
- CALL DAXPY( JS-1, RHS( 2 ), B( 1, JSP1 ), 1,
- $ F( IS, 1 ), LDF )
- CALL DAXPY( JS-1, RHS( 3 ), E( 1, JS ), 1,
- $ F( IS, 1 ), LDF )
- CALL DAXPY( JS-1, RHS( 4 ), E( 1, JSP1 ), 1,
- $ F( IS, 1 ), LDF )
- END IF
- IF( I.LT.P ) THEN
- CALL DGER( M-IE, NB, -ONE, A( IS, IE+1 ), LDA,
- $ RHS( 1 ), 1, C( IE+1, JS ), LDC )
- CALL DGER( M-IE, NB, -ONE, D( IS, IE+1 ), LDD,
- $ RHS( 3 ), 1, C( IE+1, JS ), LDC )
- END IF
-*
- ELSE IF( ( MB.EQ.2 ) .AND. ( NB.EQ.1 ) ) THEN
-*
-* Build a 4-by-4 system Z' * x = RHS
-*
- Z( 1, 1 ) = A( IS, IS )
- Z( 2, 1 ) = A( IS, ISP1 )
- Z( 3, 1 ) = -B( JS, JS )
- Z( 4, 1 ) = ZERO
-*
- Z( 1, 2 ) = A( ISP1, IS )
- Z( 2, 2 ) = A( ISP1, ISP1 )
- Z( 3, 2 ) = ZERO
- Z( 4, 2 ) = -B( JS, JS )
-*
- Z( 1, 3 ) = D( IS, IS )
- Z( 2, 3 ) = D( IS, ISP1 )
- Z( 3, 3 ) = -E( JS, JS )
- Z( 4, 3 ) = ZERO
-*
- Z( 1, 4 ) = ZERO
- Z( 2, 4 ) = D( ISP1, ISP1 )
- Z( 3, 4 ) = ZERO
- Z( 4, 4 ) = -E( JS, JS )
-*
-* Set up right hand side(s)
-*
- RHS( 1 ) = C( IS, JS )
- RHS( 2 ) = C( ISP1, JS )
- RHS( 3 ) = F( IS, JS )
- RHS( 4 ) = F( ISP1, JS )
-*
-* Solve Z' * x = RHS
-*
- CALL DGETC2( ZDIM, Z, LDZ, IPIV, JPIV, IERR )
- IF( IERR.GT.0 )
- $ INFO = IERR
-*
- CALL DGESC2( ZDIM, Z, LDZ, RHS, IPIV, JPIV, SCALOC )
- IF( SCALOC.NE.ONE ) THEN
- DO 150 K = 1, N
- CALL DSCAL( M, SCALOC, C( 1, K ), 1 )
- CALL DSCAL( M, SCALOC, F( 1, K ), 1 )
- 150 CONTINUE
- SCALE = SCALE*SCALOC
- END IF
-*
-* Unpack solution vector(s)
-*
- C( IS, JS ) = RHS( 1 )
- C( ISP1, JS ) = RHS( 2 )
- F( IS, JS ) = RHS( 3 )
- F( ISP1, JS ) = RHS( 4 )
-*
-* Substitute R(I, J) and L(I, J) into remaining
-* equation.
-*
- IF( J.GT.P+2 ) THEN
- CALL DGER( MB, JS-1, ONE, RHS( 1 ), 1, B( 1, JS ),
- $ 1, F( IS, 1 ), LDF )
- CALL DGER( MB, JS-1, ONE, RHS( 3 ), 1, E( 1, JS ),
- $ 1, F( IS, 1 ), LDF )
- END IF
- IF( I.LT.P ) THEN
- CALL DGEMV( 'T', MB, M-IE, -ONE, A( IS, IE+1 ),
- $ LDA, RHS( 1 ), 1, ONE, C( IE+1, JS ),
- $ 1 )
- CALL DGEMV( 'T', MB, M-IE, -ONE, D( IS, IE+1 ),
- $ LDD, RHS( 3 ), 1, ONE, C( IE+1, JS ),
- $ 1 )
- END IF
-*
- ELSE IF( ( MB.EQ.2 ) .AND. ( NB.EQ.2 ) ) THEN
-*
-* Build an 8-by-8 system Z' * x = RHS
-*
- CALL DLASET( 'F', LDZ, LDZ, ZERO, ZERO, Z, LDZ )
-*
- Z( 1, 1 ) = A( IS, IS )
- Z( 2, 1 ) = A( IS, ISP1 )
- Z( 5, 1 ) = -B( JS, JS )
- Z( 7, 1 ) = -B( JSP1, JS )
-*
- Z( 1, 2 ) = A( ISP1, IS )
- Z( 2, 2 ) = A( ISP1, ISP1 )
- Z( 6, 2 ) = -B( JS, JS )
- Z( 8, 2 ) = -B( JSP1, JS )
-*
- Z( 3, 3 ) = A( IS, IS )
- Z( 4, 3 ) = A( IS, ISP1 )
- Z( 5, 3 ) = -B( JS, JSP1 )
- Z( 7, 3 ) = -B( JSP1, JSP1 )
-*
- Z( 3, 4 ) = A( ISP1, IS )
- Z( 4, 4 ) = A( ISP1, ISP1 )
- Z( 6, 4 ) = -B( JS, JSP1 )
- Z( 8, 4 ) = -B( JSP1, JSP1 )
-*
- Z( 1, 5 ) = D( IS, IS )
- Z( 2, 5 ) = D( IS, ISP1 )
- Z( 5, 5 ) = -E( JS, JS )
-*
- Z( 2, 6 ) = D( ISP1, ISP1 )
- Z( 6, 6 ) = -E( JS, JS )
-*
- Z( 3, 7 ) = D( IS, IS )
- Z( 4, 7 ) = D( IS, ISP1 )
- Z( 5, 7 ) = -E( JS, JSP1 )
- Z( 7, 7 ) = -E( JSP1, JSP1 )
-*
- Z( 4, 8 ) = D( ISP1, ISP1 )
- Z( 6, 8 ) = -E( JS, JSP1 )
- Z( 8, 8 ) = -E( JSP1, JSP1 )
-*
-* Set up right hand side(s)
-*
- K = 1
- II = MB*NB + 1
- DO 160 JJ = 0, NB - 1
- CALL DCOPY( MB, C( IS, JS+JJ ), 1, RHS( K ), 1 )
- CALL DCOPY( MB, F( IS, JS+JJ ), 1, RHS( II ), 1 )
- K = K + MB
- II = II + MB
- 160 CONTINUE
-*
-*
-* Solve Z' * x = RHS
-*
- CALL DGETC2( ZDIM, Z, LDZ, IPIV, JPIV, IERR )
- IF( IERR.GT.0 )
- $ INFO = IERR
-*
- CALL DGESC2( ZDIM, Z, LDZ, RHS, IPIV, JPIV, SCALOC )
- IF( SCALOC.NE.ONE ) THEN
- DO 170 K = 1, N
- CALL DSCAL( M, SCALOC, C( 1, K ), 1 )
- CALL DSCAL( M, SCALOC, F( 1, K ), 1 )
- 170 CONTINUE
- SCALE = SCALE*SCALOC
- END IF
-*
-* Unpack solution vector(s)
-*
- K = 1
- II = MB*NB + 1
- DO 180 JJ = 0, NB - 1
- CALL DCOPY( MB, RHS( K ), 1, C( IS, JS+JJ ), 1 )
- CALL DCOPY( MB, RHS( II ), 1, F( IS, JS+JJ ), 1 )
- K = K + MB
- II = II + MB
- 180 CONTINUE
-*
-* Substitute R(I, J) and L(I, J) into remaining
-* equation.
-*
- IF( J.GT.P+2 ) THEN
- CALL DGEMM( 'N', 'T', MB, JS-1, NB, ONE,
- $ C( IS, JS ), LDC, B( 1, JS ), LDB, ONE,
- $ F( IS, 1 ), LDF )
- CALL DGEMM( 'N', 'T', MB, JS-1, NB, ONE,
- $ F( IS, JS ), LDF, E( 1, JS ), LDE, ONE,
- $ F( IS, 1 ), LDF )
- END IF
- IF( I.LT.P ) THEN
- CALL DGEMM( 'T', 'N', M-IE, NB, MB, -ONE,
- $ A( IS, IE+1 ), LDA, C( IS, JS ), LDC,
- $ ONE, C( IE+1, JS ), LDC )
- CALL DGEMM( 'T', 'N', M-IE, NB, MB, -ONE,
- $ D( IS, IE+1 ), LDD, F( IS, JS ), LDF,
- $ ONE, C( IE+1, JS ), LDC )
- END IF
-*
- END IF
-*
- 190 CONTINUE
- 200 CONTINUE
-*
- END IF
- RETURN
-*
-* End of DTGSY2
-*
- END
diff --git a/src/lib/lapack/dtgsyl.f b/src/lib/lapack/dtgsyl.f
deleted file mode 100644
index 01866717..00000000
--- a/src/lib/lapack/dtgsyl.f
+++ /dev/null
@@ -1,556 +0,0 @@
- SUBROUTINE DTGSYL( TRANS, IJOB, M, N, A, LDA, B, LDB, C, LDC, D,
- $ LDD, E, LDE, F, LDF, SCALE, DIF, WORK, LWORK,
- $ IWORK, INFO )
-*
-* -- LAPACK routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- CHARACTER TRANS
- INTEGER IJOB, INFO, LDA, LDB, LDC, LDD, LDE, LDF,
- $ LWORK, M, N
- DOUBLE PRECISION DIF, SCALE
-* ..
-* .. Array Arguments ..
- INTEGER IWORK( * )
- DOUBLE PRECISION A( LDA, * ), B( LDB, * ), C( LDC, * ),
- $ D( LDD, * ), E( LDE, * ), F( LDF, * ),
- $ WORK( * )
-* ..
-*
-* Purpose
-* =======
-*
-* DTGSYL solves the generalized Sylvester equation:
-*
-* A * R - L * B = scale * C (1)
-* D * R - L * E = scale * F
-*
-* where R and L are unknown m-by-n matrices, (A, D), (B, E) and
-* (C, F) are given matrix pairs of size m-by-m, n-by-n and m-by-n,
-* respectively, with real entries. (A, D) and (B, E) must be in
-* generalized (real) Schur canonical form, i.e. A, B are upper quasi
-* triangular and D, E are upper triangular.
-*
-* The solution (R, L) overwrites (C, F). 0 <= SCALE <= 1 is an output
-* scaling factor chosen to avoid overflow.
-*
-* In matrix notation (1) is equivalent to solve Zx = scale b, where
-* Z is defined as
-*
-* Z = [ kron(In, A) -kron(B', Im) ] (2)
-* [ kron(In, D) -kron(E', Im) ].
-*
-* Here Ik is the identity matrix of size k and X' is the transpose of
-* X. kron(X, Y) is the Kronecker product between the matrices X and Y.
-*
-* If TRANS = 'T', DTGSYL solves the transposed system Z'*y = scale*b,
-* which is equivalent to solve for R and L in
-*
-* A' * R + D' * L = scale * C (3)
-* R * B' + L * E' = scale * (-F)
-*
-* This case (TRANS = 'T') is used to compute an one-norm-based estimate
-* of Dif[(A,D), (B,E)], the separation between the matrix pairs (A,D)
-* and (B,E), using DLACON.
-*
-* If IJOB >= 1, DTGSYL computes a Frobenius norm-based estimate
-* of Dif[(A,D),(B,E)]. That is, the reciprocal of a lower bound on the
-* reciprocal of the smallest singular value of Z. See [1-2] for more
-* information.
-*
-* This is a level 3 BLAS algorithm.
-*
-* Arguments
-* =========
-*
-* TRANS (input) CHARACTER*1
-* = 'N', solve the generalized Sylvester equation (1).
-* = 'T', solve the 'transposed' system (3).
-*
-* IJOB (input) INTEGER
-* Specifies what kind of functionality to be performed.
-* =0: solve (1) only.
-* =1: The functionality of 0 and 3.
-* =2: The functionality of 0 and 4.
-* =3: Only an estimate of Dif[(A,D), (B,E)] is computed.
-* (look ahead strategy IJOB = 1 is used).
-* =4: Only an estimate of Dif[(A,D), (B,E)] is computed.
-* ( DGECON on sub-systems is used ).
-* Not referenced if TRANS = 'T'.
-*
-* M (input) INTEGER
-* The order of the matrices A and D, and the row dimension of
-* the matrices C, F, R and L.
-*
-* N (input) INTEGER
-* The order of the matrices B and E, and the column dimension
-* of the matrices C, F, R and L.
-*
-* A (input) DOUBLE PRECISION array, dimension (LDA, M)
-* The upper quasi triangular matrix A.
-*
-* LDA (input) INTEGER
-* The leading dimension of the array A. LDA >= max(1, M).
-*
-* B (input) DOUBLE PRECISION array, dimension (LDB, N)
-* The upper quasi triangular matrix B.
-*
-* LDB (input) INTEGER
-* The leading dimension of the array B. LDB >= max(1, N).
-*
-* C (input/output) DOUBLE PRECISION array, dimension (LDC, N)
-* On entry, C contains the right-hand-side of the first matrix
-* equation in (1) or (3).
-* On exit, if IJOB = 0, 1 or 2, C has been overwritten by
-* the solution R. If IJOB = 3 or 4 and TRANS = 'N', C holds R,
-* the solution achieved during the computation of the
-* Dif-estimate.
-*
-* LDC (input) INTEGER
-* The leading dimension of the array C. LDC >= max(1, M).
-*
-* D (input) DOUBLE PRECISION array, dimension (LDD, M)
-* The upper triangular matrix D.
-*
-* LDD (input) INTEGER
-* The leading dimension of the array D. LDD >= max(1, M).
-*
-* E (input) DOUBLE PRECISION array, dimension (LDE, N)
-* The upper triangular matrix E.
-*
-* LDE (input) INTEGER
-* The leading dimension of the array E. LDE >= max(1, N).
-*
-* F (input/output) DOUBLE PRECISION array, dimension (LDF, N)
-* On entry, F contains the right-hand-side of the second matrix
-* equation in (1) or (3).
-* On exit, if IJOB = 0, 1 or 2, F has been overwritten by
-* the solution L. If IJOB = 3 or 4 and TRANS = 'N', F holds L,
-* the solution achieved during the computation of the
-* Dif-estimate.
-*
-* LDF (input) INTEGER
-* The leading dimension of the array F. LDF >= max(1, M).
-*
-* DIF (output) DOUBLE PRECISION
-* On exit DIF is the reciprocal of a lower bound of the
-* reciprocal of the Dif-function, i.e. DIF is an upper bound of
-* Dif[(A,D), (B,E)] = sigma_min(Z), where Z as in (2).
-* IF IJOB = 0 or TRANS = 'T', DIF is not touched.
-*
-* SCALE (output) DOUBLE PRECISION
-* On exit SCALE is the scaling factor in (1) or (3).
-* If 0 < SCALE < 1, C and F hold the solutions R and L, resp.,
-* to a slightly perturbed system but the input matrices A, B, D
-* and E have not been changed. If SCALE = 0, C and F hold the
-* solutions R and L, respectively, to the homogeneous system
-* with C = F = 0. Normally, SCALE = 1.
-*
-* WORK (workspace/output) DOUBLE PRECISION array, dimension (MAX(1,LWORK))
-* On exit, if INFO = 0, WORK(1) returns the optimal LWORK.
-*
-* LWORK (input) INTEGER
-* The dimension of the array WORK. LWORK > = 1.
-* If IJOB = 1 or 2 and TRANS = 'N', LWORK >= max(1,2*M*N).
-*
-* If LWORK = -1, then a workspace query is assumed; the routine
-* only calculates the optimal size of the WORK array, returns
-* this value as the first entry of the WORK array, and no error
-* message related to LWORK is issued by XERBLA.
-*
-* IWORK (workspace) INTEGER array, dimension (M+N+6)
-*
-* INFO (output) INTEGER
-* =0: successful exit
-* <0: If INFO = -i, the i-th argument had an illegal value.
-* >0: (A, D) and (B, E) have common or close eigenvalues.
-*
-* Further Details
-* ===============
-*
-* Based on contributions by
-* Bo Kagstrom and Peter Poromaa, Department of Computing Science,
-* Umea University, S-901 87 Umea, Sweden.
-*
-* [1] B. Kagstrom and P. Poromaa, LAPACK-Style Algorithms and Software
-* for Solving the Generalized Sylvester Equation and Estimating the
-* Separation between Regular Matrix Pairs, Report UMINF - 93.23,
-* Department of Computing Science, Umea University, S-901 87 Umea,
-* Sweden, December 1993, Revised April 1994, Also as LAPACK Working
-* Note 75. To appear in ACM Trans. on Math. Software, Vol 22,
-* No 1, 1996.
-*
-* [2] B. Kagstrom, A Perturbation Analysis of the Generalized Sylvester
-* Equation (AR - LB, DR - LE ) = (C, F), SIAM J. Matrix Anal.
-* Appl., 15(4):1045-1060, 1994
-*
-* [3] B. Kagstrom and L. Westin, Generalized Schur Methods with
-* Condition Estimators for Solving the Generalized Sylvester
-* Equation, IEEE Transactions on Automatic Control, Vol. 34, No. 7,
-* July 1989, pp 745-751.
-*
-* =====================================================================
-* Replaced various illegal calls to DCOPY by calls to DLASET.
-* Sven Hammarling, 1/5/02.
-*
-* .. Parameters ..
- DOUBLE PRECISION ZERO, ONE
- PARAMETER ( ZERO = 0.0D+0, ONE = 1.0D+0 )
-* ..
-* .. Local Scalars ..
- LOGICAL LQUERY, NOTRAN
- INTEGER I, IE, IFUNC, IROUND, IS, ISOLVE, J, JE, JS, K,
- $ LINFO, LWMIN, MB, NB, P, PPQQ, PQ, Q
- DOUBLE PRECISION DSCALE, DSUM, SCALE2, SCALOC
-* ..
-* .. External Functions ..
- LOGICAL LSAME
- INTEGER ILAENV
- EXTERNAL LSAME, ILAENV
-* ..
-* .. External Subroutines ..
- EXTERNAL DGEMM, DLACPY, DLASET, DSCAL, DTGSY2, XERBLA
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC DBLE, MAX, SQRT
-* ..
-* .. Executable Statements ..
-*
-* Decode and test input parameters
-*
- INFO = 0
- NOTRAN = LSAME( TRANS, 'N' )
- LQUERY = ( LWORK.EQ.-1 )
-*
- IF( .NOT.NOTRAN .AND. .NOT.LSAME( TRANS, 'T' ) ) THEN
- INFO = -1
- ELSE IF( NOTRAN ) THEN
- IF( ( IJOB.LT.0 ) .OR. ( IJOB.GT.4 ) ) THEN
- INFO = -2
- END IF
- END IF
- IF( INFO.EQ.0 ) THEN
- IF( M.LE.0 ) THEN
- INFO = -3
- ELSE IF( N.LE.0 ) THEN
- INFO = -4
- ELSE IF( LDA.LT.MAX( 1, M ) ) THEN
- INFO = -6
- ELSE IF( LDB.LT.MAX( 1, N ) ) THEN
- INFO = -8
- ELSE IF( LDC.LT.MAX( 1, M ) ) THEN
- INFO = -10
- ELSE IF( LDD.LT.MAX( 1, M ) ) THEN
- INFO = -12
- ELSE IF( LDE.LT.MAX( 1, N ) ) THEN
- INFO = -14
- ELSE IF( LDF.LT.MAX( 1, M ) ) THEN
- INFO = -16
- END IF
- END IF
-*
- IF( INFO.EQ.0 ) THEN
- IF( NOTRAN ) THEN
- IF( IJOB.EQ.1 .OR. IJOB.EQ.2 ) THEN
- LWMIN = MAX( 1, 2*M*N )
- ELSE
- LWMIN = 1
- END IF
- ELSE
- LWMIN = 1
- END IF
- WORK( 1 ) = LWMIN
-*
- IF( LWORK.LT.LWMIN .AND. .NOT.LQUERY ) THEN
- INFO = -20
- END IF
- END IF
-*
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'DTGSYL', -INFO )
- RETURN
- ELSE IF( LQUERY ) THEN
- RETURN
- END IF
-*
-* Quick return if possible
-*
- IF( M.EQ.0 .OR. N.EQ.0 ) THEN
- SCALE = 1
- IF( NOTRAN ) THEN
- IF( IJOB.NE.0 ) THEN
- DIF = 0
- END IF
- END IF
- RETURN
- END IF
-*
-* Determine optimal block sizes MB and NB
-*
- MB = ILAENV( 2, 'DTGSYL', TRANS, M, N, -1, -1 )
- NB = ILAENV( 5, 'DTGSYL', TRANS, M, N, -1, -1 )
-*
- ISOLVE = 1
- IFUNC = 0
- IF( NOTRAN ) THEN
- IF( IJOB.GE.3 ) THEN
- IFUNC = IJOB - 2
- CALL DLASET( 'F', M, N, ZERO, ZERO, C, LDC )
- CALL DLASET( 'F', M, N, ZERO, ZERO, F, LDF )
- ELSE IF( IJOB.GE.1 ) THEN
- ISOLVE = 2
- END IF
- END IF
-*
- IF( ( MB.LE.1 .AND. NB.LE.1 ) .OR. ( MB.GE.M .AND. NB.GE.N ) )
- $ THEN
-*
- DO 30 IROUND = 1, ISOLVE
-*
-* Use unblocked Level 2 solver
-*
- DSCALE = ZERO
- DSUM = ONE
- PQ = 0
- CALL DTGSY2( TRANS, IFUNC, M, N, A, LDA, B, LDB, C, LDC, D,
- $ LDD, E, LDE, F, LDF, SCALE, DSUM, DSCALE,
- $ IWORK, PQ, INFO )
- IF( DSCALE.NE.ZERO ) THEN
- IF( IJOB.EQ.1 .OR. IJOB.EQ.3 ) THEN
- DIF = SQRT( DBLE( 2*M*N ) ) / ( DSCALE*SQRT( DSUM ) )
- ELSE
- DIF = SQRT( DBLE( PQ ) ) / ( DSCALE*SQRT( DSUM ) )
- END IF
- END IF
-*
- IF( ISOLVE.EQ.2 .AND. IROUND.EQ.1 ) THEN
- IF( NOTRAN ) THEN
- IFUNC = IJOB
- END IF
- SCALE2 = SCALE
- CALL DLACPY( 'F', M, N, C, LDC, WORK, M )
- CALL DLACPY( 'F', M, N, F, LDF, WORK( M*N+1 ), M )
- CALL DLASET( 'F', M, N, ZERO, ZERO, C, LDC )
- CALL DLASET( 'F', M, N, ZERO, ZERO, F, LDF )
- ELSE IF( ISOLVE.EQ.2 .AND. IROUND.EQ.2 ) THEN
- CALL DLACPY( 'F', M, N, WORK, M, C, LDC )
- CALL DLACPY( 'F', M, N, WORK( M*N+1 ), M, F, LDF )
- SCALE = SCALE2
- END IF
- 30 CONTINUE
-*
- RETURN
- END IF
-*
-* Determine block structure of A
-*
- P = 0
- I = 1
- 40 CONTINUE
- IF( I.GT.M )
- $ GO TO 50
- P = P + 1
- IWORK( P ) = I
- I = I + MB
- IF( I.GE.M )
- $ GO TO 50
- IF( A( I, I-1 ).NE.ZERO )
- $ I = I + 1
- GO TO 40
- 50 CONTINUE
-*
- IWORK( P+1 ) = M + 1
- IF( IWORK( P ).EQ.IWORK( P+1 ) )
- $ P = P - 1
-*
-* Determine block structure of B
-*
- Q = P + 1
- J = 1
- 60 CONTINUE
- IF( J.GT.N )
- $ GO TO 70
- Q = Q + 1
- IWORK( Q ) = J
- J = J + NB
- IF( J.GE.N )
- $ GO TO 70
- IF( B( J, J-1 ).NE.ZERO )
- $ J = J + 1
- GO TO 60
- 70 CONTINUE
-*
- IWORK( Q+1 ) = N + 1
- IF( IWORK( Q ).EQ.IWORK( Q+1 ) )
- $ Q = Q - 1
-*
- IF( NOTRAN ) THEN
-*
- DO 150 IROUND = 1, ISOLVE
-*
-* Solve (I, J)-subsystem
-* A(I, I) * R(I, J) - L(I, J) * B(J, J) = C(I, J)
-* D(I, I) * R(I, J) - L(I, J) * E(J, J) = F(I, J)
-* for I = P, P - 1,..., 1; J = 1, 2,..., Q
-*
- DSCALE = ZERO
- DSUM = ONE
- PQ = 0
- SCALE = ONE
- DO 130 J = P + 2, Q
- JS = IWORK( J )
- JE = IWORK( J+1 ) - 1
- NB = JE - JS + 1
- DO 120 I = P, 1, -1
- IS = IWORK( I )
- IE = IWORK( I+1 ) - 1
- MB = IE - IS + 1
- PPQQ = 0
- CALL DTGSY2( TRANS, IFUNC, MB, NB, A( IS, IS ), LDA,
- $ B( JS, JS ), LDB, C( IS, JS ), LDC,
- $ D( IS, IS ), LDD, E( JS, JS ), LDE,
- $ F( IS, JS ), LDF, SCALOC, DSUM, DSCALE,
- $ IWORK( Q+2 ), PPQQ, LINFO )
- IF( LINFO.GT.0 )
- $ INFO = LINFO
-*
- PQ = PQ + PPQQ
- IF( SCALOC.NE.ONE ) THEN
- DO 80 K = 1, JS - 1
- CALL DSCAL( M, SCALOC, C( 1, K ), 1 )
- CALL DSCAL( M, SCALOC, F( 1, K ), 1 )
- 80 CONTINUE
- DO 90 K = JS, JE
- CALL DSCAL( IS-1, SCALOC, C( 1, K ), 1 )
- CALL DSCAL( IS-1, SCALOC, F( 1, K ), 1 )
- 90 CONTINUE
- DO 100 K = JS, JE
- CALL DSCAL( M-IE, SCALOC, C( IE+1, K ), 1 )
- CALL DSCAL( M-IE, SCALOC, F( IE+1, K ), 1 )
- 100 CONTINUE
- DO 110 K = JE + 1, N
- CALL DSCAL( M, SCALOC, C( 1, K ), 1 )
- CALL DSCAL( M, SCALOC, F( 1, K ), 1 )
- 110 CONTINUE
- SCALE = SCALE*SCALOC
- END IF
-*
-* Substitute R(I, J) and L(I, J) into remaining
-* equation.
-*
- IF( I.GT.1 ) THEN
- CALL DGEMM( 'N', 'N', IS-1, NB, MB, -ONE,
- $ A( 1, IS ), LDA, C( IS, JS ), LDC, ONE,
- $ C( 1, JS ), LDC )
- CALL DGEMM( 'N', 'N', IS-1, NB, MB, -ONE,
- $ D( 1, IS ), LDD, C( IS, JS ), LDC, ONE,
- $ F( 1, JS ), LDF )
- END IF
- IF( J.LT.Q ) THEN
- CALL DGEMM( 'N', 'N', MB, N-JE, NB, ONE,
- $ F( IS, JS ), LDF, B( JS, JE+1 ), LDB,
- $ ONE, C( IS, JE+1 ), LDC )
- CALL DGEMM( 'N', 'N', MB, N-JE, NB, ONE,
- $ F( IS, JS ), LDF, E( JS, JE+1 ), LDE,
- $ ONE, F( IS, JE+1 ), LDF )
- END IF
- 120 CONTINUE
- 130 CONTINUE
- IF( DSCALE.NE.ZERO ) THEN
- IF( IJOB.EQ.1 .OR. IJOB.EQ.3 ) THEN
- DIF = SQRT( DBLE( 2*M*N ) ) / ( DSCALE*SQRT( DSUM ) )
- ELSE
- DIF = SQRT( DBLE( PQ ) ) / ( DSCALE*SQRT( DSUM ) )
- END IF
- END IF
- IF( ISOLVE.EQ.2 .AND. IROUND.EQ.1 ) THEN
- IF( NOTRAN ) THEN
- IFUNC = IJOB
- END IF
- SCALE2 = SCALE
- CALL DLACPY( 'F', M, N, C, LDC, WORK, M )
- CALL DLACPY( 'F', M, N, F, LDF, WORK( M*N+1 ), M )
- CALL DLASET( 'F', M, N, ZERO, ZERO, C, LDC )
- CALL DLASET( 'F', M, N, ZERO, ZERO, F, LDF )
- ELSE IF( ISOLVE.EQ.2 .AND. IROUND.EQ.2 ) THEN
- CALL DLACPY( 'F', M, N, WORK, M, C, LDC )
- CALL DLACPY( 'F', M, N, WORK( M*N+1 ), M, F, LDF )
- SCALE = SCALE2
- END IF
- 150 CONTINUE
-*
- ELSE
-*
-* Solve transposed (I, J)-subsystem
-* A(I, I)' * R(I, J) + D(I, I)' * L(I, J) = C(I, J)
-* R(I, J) * B(J, J)' + L(I, J) * E(J, J)' = -F(I, J)
-* for I = 1,2,..., P; J = Q, Q-1,..., 1
-*
- SCALE = ONE
- DO 210 I = 1, P
- IS = IWORK( I )
- IE = IWORK( I+1 ) - 1
- MB = IE - IS + 1
- DO 200 J = Q, P + 2, -1
- JS = IWORK( J )
- JE = IWORK( J+1 ) - 1
- NB = JE - JS + 1
- CALL DTGSY2( TRANS, IFUNC, MB, NB, A( IS, IS ), LDA,
- $ B( JS, JS ), LDB, C( IS, JS ), LDC,
- $ D( IS, IS ), LDD, E( JS, JS ), LDE,
- $ F( IS, JS ), LDF, SCALOC, DSUM, DSCALE,
- $ IWORK( Q+2 ), PPQQ, LINFO )
- IF( LINFO.GT.0 )
- $ INFO = LINFO
- IF( SCALOC.NE.ONE ) THEN
- DO 160 K = 1, JS - 1
- CALL DSCAL( M, SCALOC, C( 1, K ), 1 )
- CALL DSCAL( M, SCALOC, F( 1, K ), 1 )
- 160 CONTINUE
- DO 170 K = JS, JE
- CALL DSCAL( IS-1, SCALOC, C( 1, K ), 1 )
- CALL DSCAL( IS-1, SCALOC, F( 1, K ), 1 )
- 170 CONTINUE
- DO 180 K = JS, JE
- CALL DSCAL( M-IE, SCALOC, C( IE+1, K ), 1 )
- CALL DSCAL( M-IE, SCALOC, F( IE+1, K ), 1 )
- 180 CONTINUE
- DO 190 K = JE + 1, N
- CALL DSCAL( M, SCALOC, C( 1, K ), 1 )
- CALL DSCAL( M, SCALOC, F( 1, K ), 1 )
- 190 CONTINUE
- SCALE = SCALE*SCALOC
- END IF
-*
-* Substitute R(I, J) and L(I, J) into remaining equation.
-*
- IF( J.GT.P+2 ) THEN
- CALL DGEMM( 'N', 'T', MB, JS-1, NB, ONE, C( IS, JS ),
- $ LDC, B( 1, JS ), LDB, ONE, F( IS, 1 ),
- $ LDF )
- CALL DGEMM( 'N', 'T', MB, JS-1, NB, ONE, F( IS, JS ),
- $ LDF, E( 1, JS ), LDE, ONE, F( IS, 1 ),
- $ LDF )
- END IF
- IF( I.LT.P ) THEN
- CALL DGEMM( 'T', 'N', M-IE, NB, MB, -ONE,
- $ A( IS, IE+1 ), LDA, C( IS, JS ), LDC, ONE,
- $ C( IE+1, JS ), LDC )
- CALL DGEMM( 'T', 'N', M-IE, NB, MB, -ONE,
- $ D( IS, IE+1 ), LDD, F( IS, JS ), LDF, ONE,
- $ C( IE+1, JS ), LDC )
- END IF
- 200 CONTINUE
- 210 CONTINUE
-*
- END IF
-*
- WORK( 1 ) = LWMIN
-*
- RETURN
-*
-* End of DTGSYL
-*
- END
diff --git a/src/lib/lapack/dtrcon.f b/src/lib/lapack/dtrcon.f
deleted file mode 100644
index 23da5927..00000000
--- a/src/lib/lapack/dtrcon.f
+++ /dev/null
@@ -1,197 +0,0 @@
- SUBROUTINE DTRCON( NORM, UPLO, DIAG, N, A, LDA, RCOND, WORK,
- $ IWORK, INFO )
-*
-* -- LAPACK routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* Modified to call DLACN2 in place of DLACON, 5 Feb 03, SJH.
-*
-* .. Scalar Arguments ..
- CHARACTER DIAG, NORM, UPLO
- INTEGER INFO, LDA, N
- DOUBLE PRECISION RCOND
-* ..
-* .. Array Arguments ..
- INTEGER IWORK( * )
- DOUBLE PRECISION A( LDA, * ), WORK( * )
-* ..
-*
-* Purpose
-* =======
-*
-* DTRCON estimates the reciprocal of the condition number of a
-* triangular matrix A, in either the 1-norm or the infinity-norm.
-*
-* The norm of A is computed and an estimate is obtained for
-* norm(inv(A)), then the reciprocal of the condition number is
-* computed as
-* RCOND = 1 / ( norm(A) * norm(inv(A)) ).
-*
-* Arguments
-* =========
-*
-* NORM (input) CHARACTER*1
-* Specifies whether the 1-norm condition number or the
-* infinity-norm condition number is required:
-* = '1' or 'O': 1-norm;
-* = 'I': Infinity-norm.
-*
-* UPLO (input) CHARACTER*1
-* = 'U': A is upper triangular;
-* = 'L': A is lower triangular.
-*
-* DIAG (input) CHARACTER*1
-* = 'N': A is non-unit triangular;
-* = 'U': A is unit triangular.
-*
-* N (input) INTEGER
-* The order of the matrix A. N >= 0.
-*
-* A (input) DOUBLE PRECISION array, dimension (LDA,N)
-* The triangular matrix A. If UPLO = 'U', the leading N-by-N
-* upper triangular part of the array A contains the upper
-* triangular matrix, and the strictly lower triangular part of
-* A is not referenced. If UPLO = 'L', the leading N-by-N lower
-* triangular part of the array A contains the lower triangular
-* matrix, and the strictly upper triangular part of A is not
-* referenced. If DIAG = 'U', the diagonal elements of A are
-* also not referenced and are assumed to be 1.
-*
-* LDA (input) INTEGER
-* The leading dimension of the array A. LDA >= max(1,N).
-*
-* RCOND (output) DOUBLE PRECISION
-* The reciprocal of the condition number of the matrix A,
-* computed as RCOND = 1/(norm(A) * norm(inv(A))).
-*
-* WORK (workspace) DOUBLE PRECISION array, dimension (3*N)
-*
-* IWORK (workspace) INTEGER array, dimension (N)
-*
-* INFO (output) INTEGER
-* = 0: successful exit
-* < 0: if INFO = -i, the i-th argument had an illegal value
-*
-* =====================================================================
-*
-* .. Parameters ..
- DOUBLE PRECISION ONE, ZERO
- PARAMETER ( ONE = 1.0D+0, ZERO = 0.0D+0 )
-* ..
-* .. Local Scalars ..
- LOGICAL NOUNIT, ONENRM, UPPER
- CHARACTER NORMIN
- INTEGER IX, KASE, KASE1
- DOUBLE PRECISION AINVNM, ANORM, SCALE, SMLNUM, XNORM
-* ..
-* .. Local Arrays ..
- INTEGER ISAVE( 3 )
-* ..
-* .. External Functions ..
- LOGICAL LSAME
- INTEGER IDAMAX
- DOUBLE PRECISION DLAMCH, DLANTR
- EXTERNAL LSAME, IDAMAX, DLAMCH, DLANTR
-* ..
-* .. External Subroutines ..
- EXTERNAL DLACN2, DLATRS, DRSCL, XERBLA
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC ABS, DBLE, MAX
-* ..
-* .. Executable Statements ..
-*
-* Test the input parameters.
-*
- INFO = 0
- UPPER = LSAME( UPLO, 'U' )
- ONENRM = NORM.EQ.'1' .OR. LSAME( NORM, 'O' )
- NOUNIT = LSAME( DIAG, 'N' )
-*
- IF( .NOT.ONENRM .AND. .NOT.LSAME( NORM, 'I' ) ) THEN
- INFO = -1
- ELSE IF( .NOT.UPPER .AND. .NOT.LSAME( UPLO, 'L' ) ) THEN
- INFO = -2
- ELSE IF( .NOT.NOUNIT .AND. .NOT.LSAME( DIAG, 'U' ) ) THEN
- INFO = -3
- ELSE IF( N.LT.0 ) THEN
- INFO = -4
- ELSE IF( LDA.LT.MAX( 1, N ) ) THEN
- INFO = -6
- END IF
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'DTRCON', -INFO )
- RETURN
- END IF
-*
-* Quick return if possible
-*
- IF( N.EQ.0 ) THEN
- RCOND = ONE
- RETURN
- END IF
-*
- RCOND = ZERO
- SMLNUM = DLAMCH( 'Safe minimum' )*DBLE( MAX( 1, N ) )
-*
-* Compute the norm of the triangular matrix A.
-*
- ANORM = DLANTR( NORM, UPLO, DIAG, N, N, A, LDA, WORK )
-*
-* Continue only if ANORM > 0.
-*
- IF( ANORM.GT.ZERO ) THEN
-*
-* Estimate the norm of the inverse of A.
-*
- AINVNM = ZERO
- NORMIN = 'N'
- IF( ONENRM ) THEN
- KASE1 = 1
- ELSE
- KASE1 = 2
- END IF
- KASE = 0
- 10 CONTINUE
- CALL DLACN2( N, WORK( N+1 ), WORK, IWORK, AINVNM, KASE, ISAVE )
- IF( KASE.NE.0 ) THEN
- IF( KASE.EQ.KASE1 ) THEN
-*
-* Multiply by inv(A).
-*
- CALL DLATRS( UPLO, 'No transpose', DIAG, NORMIN, N, A,
- $ LDA, WORK, SCALE, WORK( 2*N+1 ), INFO )
- ELSE
-*
-* Multiply by inv(A').
-*
- CALL DLATRS( UPLO, 'Transpose', DIAG, NORMIN, N, A, LDA,
- $ WORK, SCALE, WORK( 2*N+1 ), INFO )
- END IF
- NORMIN = 'Y'
-*
-* Multiply by 1/SCALE if doing so will not cause overflow.
-*
- IF( SCALE.NE.ONE ) THEN
- IX = IDAMAX( N, WORK, 1 )
- XNORM = ABS( WORK( IX ) )
- IF( SCALE.LT.XNORM*SMLNUM .OR. SCALE.EQ.ZERO )
- $ GO TO 20
- CALL DRSCL( N, SCALE, WORK, 1 )
- END IF
- GO TO 10
- END IF
-*
-* Compute the estimate of the reciprocal condition number.
-*
- IF( AINVNM.NE.ZERO )
- $ RCOND = ( ONE / ANORM ) / AINVNM
- END IF
-*
- 20 CONTINUE
- RETURN
-*
-* End of DTRCON
-*
- END
diff --git a/src/lib/lapack/dtrevc.f b/src/lib/lapack/dtrevc.f
deleted file mode 100644
index a0215f02..00000000
--- a/src/lib/lapack/dtrevc.f
+++ /dev/null
@@ -1,980 +0,0 @@
- SUBROUTINE DTREVC( SIDE, HOWMNY, SELECT, N, T, LDT, VL, LDVL, VR,
- $ LDVR, MM, M, WORK, INFO )
-*
-* -- LAPACK routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- CHARACTER HOWMNY, SIDE
- INTEGER INFO, LDT, LDVL, LDVR, M, MM, N
-* ..
-* .. Array Arguments ..
- LOGICAL SELECT( * )
- DOUBLE PRECISION T( LDT, * ), VL( LDVL, * ), VR( LDVR, * ),
- $ WORK( * )
-* ..
-*
-* Purpose
-* =======
-*
-* DTREVC computes some or all of the right and/or left eigenvectors of
-* a real upper quasi-triangular matrix T.
-* Matrices of this type are produced by the Schur factorization of
-* a real general matrix: A = Q*T*Q**T, as computed by DHSEQR.
-*
-* The right eigenvector x and the left eigenvector y of T corresponding
-* to an eigenvalue w are defined by:
-*
-* T*x = w*x, (y**H)*T = w*(y**H)
-*
-* where y**H denotes the conjugate transpose of y.
-* The eigenvalues are not input to this routine, but are read directly
-* from the diagonal blocks of T.
-*
-* This routine returns the matrices X and/or Y of right and left
-* eigenvectors of T, or the products Q*X and/or Q*Y, where Q is an
-* input matrix. If Q is the orthogonal factor that reduces a matrix
-* A to Schur form T, then Q*X and Q*Y are the matrices of right and
-* left eigenvectors of A.
-*
-* Arguments
-* =========
-*
-* SIDE (input) CHARACTER*1
-* = 'R': compute right eigenvectors only;
-* = 'L': compute left eigenvectors only;
-* = 'B': compute both right and left eigenvectors.
-*
-* HOWMNY (input) CHARACTER*1
-* = 'A': compute all right and/or left eigenvectors;
-* = 'B': compute all right and/or left eigenvectors,
-* backtransformed by the matrices in VR and/or VL;
-* = 'S': compute selected right and/or left eigenvectors,
-* as indicated by the logical array SELECT.
-*
-* SELECT (input/output) LOGICAL array, dimension (N)
-* If HOWMNY = 'S', SELECT specifies the eigenvectors to be
-* computed.
-* If w(j) is a real eigenvalue, the corresponding real
-* eigenvector is computed if SELECT(j) is .TRUE..
-* If w(j) and w(j+1) are the real and imaginary parts of a
-* complex eigenvalue, the corresponding complex eigenvector is
-* computed if either SELECT(j) or SELECT(j+1) is .TRUE., and
-* on exit SELECT(j) is set to .TRUE. and SELECT(j+1) is set to
-* .FALSE..
-* Not referenced if HOWMNY = 'A' or 'B'.
-*
-* N (input) INTEGER
-* The order of the matrix T. N >= 0.
-*
-* T (input) DOUBLE PRECISION array, dimension (LDT,N)
-* The upper quasi-triangular matrix T in Schur canonical form.
-*
-* LDT (input) INTEGER
-* The leading dimension of the array T. LDT >= max(1,N).
-*
-* VL (input/output) DOUBLE PRECISION array, dimension (LDVL,MM)
-* On entry, if SIDE = 'L' or 'B' and HOWMNY = 'B', VL must
-* contain an N-by-N matrix Q (usually the orthogonal matrix Q
-* of Schur vectors returned by DHSEQR).
-* On exit, if SIDE = 'L' or 'B', VL contains:
-* if HOWMNY = 'A', the matrix Y of left eigenvectors of T;
-* if HOWMNY = 'B', the matrix Q*Y;
-* if HOWMNY = 'S', the left eigenvectors of T specified by
-* SELECT, stored consecutively in the columns
-* of VL, in the same order as their
-* eigenvalues.
-* A complex eigenvector corresponding to a complex eigenvalue
-* is stored in two consecutive columns, the first holding the
-* real part, and the second the imaginary part.
-* Not referenced if SIDE = 'R'.
-*
-* LDVL (input) INTEGER
-* The leading dimension of the array VL. LDVL >= 1, and if
-* SIDE = 'L' or 'B', LDVL >= N.
-*
-* VR (input/output) DOUBLE PRECISION array, dimension (LDVR,MM)
-* On entry, if SIDE = 'R' or 'B' and HOWMNY = 'B', VR must
-* contain an N-by-N matrix Q (usually the orthogonal matrix Q
-* of Schur vectors returned by DHSEQR).
-* On exit, if SIDE = 'R' or 'B', VR contains:
-* if HOWMNY = 'A', the matrix X of right eigenvectors of T;
-* if HOWMNY = 'B', the matrix Q*X;
-* if HOWMNY = 'S', the right eigenvectors of T specified by
-* SELECT, stored consecutively in the columns
-* of VR, in the same order as their
-* eigenvalues.
-* A complex eigenvector corresponding to a complex eigenvalue
-* is stored in two consecutive columns, the first holding the
-* real part and the second the imaginary part.
-* Not referenced if SIDE = 'L'.
-*
-* LDVR (input) INTEGER
-* The leading dimension of the array VR. LDVR >= 1, and if
-* SIDE = 'R' or 'B', LDVR >= N.
-*
-* MM (input) INTEGER
-* The number of columns in the arrays VL and/or VR. MM >= M.
-*
-* M (output) INTEGER
-* The number of columns in the arrays VL and/or VR actually
-* used to store the eigenvectors.
-* If HOWMNY = 'A' or 'B', M is set to N.
-* Each selected real eigenvector occupies one column and each
-* selected complex eigenvector occupies two columns.
-*
-* WORK (workspace) DOUBLE PRECISION array, dimension (3*N)
-*
-* INFO (output) INTEGER
-* = 0: successful exit
-* < 0: if INFO = -i, the i-th argument had an illegal value
-*
-* Further Details
-* ===============
-*
-* The algorithm used in this program is basically backward (forward)
-* substitution, with scaling to make the the code robust against
-* possible overflow.
-*
-* Each eigenvector is normalized so that the element of largest
-* magnitude has magnitude 1; here the magnitude of a complex number
-* (x,y) is taken to be |x| + |y|.
-*
-* =====================================================================
-*
-* .. Parameters ..
- DOUBLE PRECISION ZERO, ONE
- PARAMETER ( ZERO = 0.0D+0, ONE = 1.0D+0 )
-* ..
-* .. Local Scalars ..
- LOGICAL ALLV, BOTHV, LEFTV, OVER, PAIR, RIGHTV, SOMEV
- INTEGER I, IERR, II, IP, IS, J, J1, J2, JNXT, K, KI, N2
- DOUBLE PRECISION BETA, BIGNUM, EMAX, OVFL, REC, REMAX, SCALE,
- $ SMIN, SMLNUM, ULP, UNFL, VCRIT, VMAX, WI, WR,
- $ XNORM
-* ..
-* .. External Functions ..
- LOGICAL LSAME
- INTEGER IDAMAX
- DOUBLE PRECISION DDOT, DLAMCH
- EXTERNAL LSAME, IDAMAX, DDOT, DLAMCH
-* ..
-* .. External Subroutines ..
- EXTERNAL DAXPY, DCOPY, DGEMV, DLALN2, DSCAL, XERBLA
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC ABS, MAX, SQRT
-* ..
-* .. Local Arrays ..
- DOUBLE PRECISION X( 2, 2 )
-* ..
-* .. Executable Statements ..
-*
-* Decode and test the input parameters
-*
- BOTHV = LSAME( SIDE, 'B' )
- RIGHTV = LSAME( SIDE, 'R' ) .OR. BOTHV
- LEFTV = LSAME( SIDE, 'L' ) .OR. BOTHV
-*
- ALLV = LSAME( HOWMNY, 'A' )
- OVER = LSAME( HOWMNY, 'B' )
- SOMEV = LSAME( HOWMNY, 'S' )
-*
- INFO = 0
- IF( .NOT.RIGHTV .AND. .NOT.LEFTV ) THEN
- INFO = -1
- ELSE IF( .NOT.ALLV .AND. .NOT.OVER .AND. .NOT.SOMEV ) THEN
- INFO = -2
- ELSE IF( N.LT.0 ) THEN
- INFO = -4
- ELSE IF( LDT.LT.MAX( 1, N ) ) THEN
- INFO = -6
- ELSE IF( LDVL.LT.1 .OR. ( LEFTV .AND. LDVL.LT.N ) ) THEN
- INFO = -8
- ELSE IF( LDVR.LT.1 .OR. ( RIGHTV .AND. LDVR.LT.N ) ) THEN
- INFO = -10
- ELSE
-*
-* Set M to the number of columns required to store the selected
-* eigenvectors, standardize the array SELECT if necessary, and
-* test MM.
-*
- IF( SOMEV ) THEN
- M = 0
- PAIR = .FALSE.
- DO 10 J = 1, N
- IF( PAIR ) THEN
- PAIR = .FALSE.
- SELECT( J ) = .FALSE.
- ELSE
- IF( J.LT.N ) THEN
- IF( T( J+1, J ).EQ.ZERO ) THEN
- IF( SELECT( J ) )
- $ M = M + 1
- ELSE
- PAIR = .TRUE.
- IF( SELECT( J ) .OR. SELECT( J+1 ) ) THEN
- SELECT( J ) = .TRUE.
- M = M + 2
- END IF
- END IF
- ELSE
- IF( SELECT( N ) )
- $ M = M + 1
- END IF
- END IF
- 10 CONTINUE
- ELSE
- M = N
- END IF
-*
- IF( MM.LT.M ) THEN
- INFO = -11
- END IF
- END IF
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'DTREVC', -INFO )
- RETURN
- END IF
-*
-* Quick return if possible.
-*
- IF( N.EQ.0 )
- $ RETURN
-*
-* Set the constants to control overflow.
-*
- UNFL = DLAMCH( 'Safe minimum' )
- OVFL = ONE / UNFL
- CALL DLABAD( UNFL, OVFL )
- ULP = DLAMCH( 'Precision' )
- SMLNUM = UNFL*( N / ULP )
- BIGNUM = ( ONE-ULP ) / SMLNUM
-*
-* Compute 1-norm of each column of strictly upper triangular
-* part of T to control overflow in triangular solver.
-*
- WORK( 1 ) = ZERO
- DO 30 J = 2, N
- WORK( J ) = ZERO
- DO 20 I = 1, J - 1
- WORK( J ) = WORK( J ) + ABS( T( I, J ) )
- 20 CONTINUE
- 30 CONTINUE
-*
-* Index IP is used to specify the real or complex eigenvalue:
-* IP = 0, real eigenvalue,
-* 1, first of conjugate complex pair: (wr,wi)
-* -1, second of conjugate complex pair: (wr,wi)
-*
- N2 = 2*N
-*
- IF( RIGHTV ) THEN
-*
-* Compute right eigenvectors.
-*
- IP = 0
- IS = M
- DO 140 KI = N, 1, -1
-*
- IF( IP.EQ.1 )
- $ GO TO 130
- IF( KI.EQ.1 )
- $ GO TO 40
- IF( T( KI, KI-1 ).EQ.ZERO )
- $ GO TO 40
- IP = -1
-*
- 40 CONTINUE
- IF( SOMEV ) THEN
- IF( IP.EQ.0 ) THEN
- IF( .NOT.SELECT( KI ) )
- $ GO TO 130
- ELSE
- IF( .NOT.SELECT( KI-1 ) )
- $ GO TO 130
- END IF
- END IF
-*
-* Compute the KI-th eigenvalue (WR,WI).
-*
- WR = T( KI, KI )
- WI = ZERO
- IF( IP.NE.0 )
- $ WI = SQRT( ABS( T( KI, KI-1 ) ) )*
- $ SQRT( ABS( T( KI-1, KI ) ) )
- SMIN = MAX( ULP*( ABS( WR )+ABS( WI ) ), SMLNUM )
-*
- IF( IP.EQ.0 ) THEN
-*
-* Real right eigenvector
-*
- WORK( KI+N ) = ONE
-*
-* Form right-hand side
-*
- DO 50 K = 1, KI - 1
- WORK( K+N ) = -T( K, KI )
- 50 CONTINUE
-*
-* Solve the upper quasi-triangular system:
-* (T(1:KI-1,1:KI-1) - WR)*X = SCALE*WORK.
-*
- JNXT = KI - 1
- DO 60 J = KI - 1, 1, -1
- IF( J.GT.JNXT )
- $ GO TO 60
- J1 = J
- J2 = J
- JNXT = J - 1
- IF( J.GT.1 ) THEN
- IF( T( J, J-1 ).NE.ZERO ) THEN
- J1 = J - 1
- JNXT = J - 2
- END IF
- END IF
-*
- IF( J1.EQ.J2 ) THEN
-*
-* 1-by-1 diagonal block
-*
- CALL DLALN2( .FALSE., 1, 1, SMIN, ONE, T( J, J ),
- $ LDT, ONE, ONE, WORK( J+N ), N, WR,
- $ ZERO, X, 2, SCALE, XNORM, IERR )
-*
-* Scale X(1,1) to avoid overflow when updating
-* the right-hand side.
-*
- IF( XNORM.GT.ONE ) THEN
- IF( WORK( J ).GT.BIGNUM / XNORM ) THEN
- X( 1, 1 ) = X( 1, 1 ) / XNORM
- SCALE = SCALE / XNORM
- END IF
- END IF
-*
-* Scale if necessary
-*
- IF( SCALE.NE.ONE )
- $ CALL DSCAL( KI, SCALE, WORK( 1+N ), 1 )
- WORK( J+N ) = X( 1, 1 )
-*
-* Update right-hand side
-*
- CALL DAXPY( J-1, -X( 1, 1 ), T( 1, J ), 1,
- $ WORK( 1+N ), 1 )
-*
- ELSE
-*
-* 2-by-2 diagonal block
-*
- CALL DLALN2( .FALSE., 2, 1, SMIN, ONE,
- $ T( J-1, J-1 ), LDT, ONE, ONE,
- $ WORK( J-1+N ), N, WR, ZERO, X, 2,
- $ SCALE, XNORM, IERR )
-*
-* Scale X(1,1) and X(2,1) to avoid overflow when
-* updating the right-hand side.
-*
- IF( XNORM.GT.ONE ) THEN
- BETA = MAX( WORK( J-1 ), WORK( J ) )
- IF( BETA.GT.BIGNUM / XNORM ) THEN
- X( 1, 1 ) = X( 1, 1 ) / XNORM
- X( 2, 1 ) = X( 2, 1 ) / XNORM
- SCALE = SCALE / XNORM
- END IF
- END IF
-*
-* Scale if necessary
-*
- IF( SCALE.NE.ONE )
- $ CALL DSCAL( KI, SCALE, WORK( 1+N ), 1 )
- WORK( J-1+N ) = X( 1, 1 )
- WORK( J+N ) = X( 2, 1 )
-*
-* Update right-hand side
-*
- CALL DAXPY( J-2, -X( 1, 1 ), T( 1, J-1 ), 1,
- $ WORK( 1+N ), 1 )
- CALL DAXPY( J-2, -X( 2, 1 ), T( 1, J ), 1,
- $ WORK( 1+N ), 1 )
- END IF
- 60 CONTINUE
-*
-* Copy the vector x or Q*x to VR and normalize.
-*
- IF( .NOT.OVER ) THEN
- CALL DCOPY( KI, WORK( 1+N ), 1, VR( 1, IS ), 1 )
-*
- II = IDAMAX( KI, VR( 1, IS ), 1 )
- REMAX = ONE / ABS( VR( II, IS ) )
- CALL DSCAL( KI, REMAX, VR( 1, IS ), 1 )
-*
- DO 70 K = KI + 1, N
- VR( K, IS ) = ZERO
- 70 CONTINUE
- ELSE
- IF( KI.GT.1 )
- $ CALL DGEMV( 'N', N, KI-1, ONE, VR, LDVR,
- $ WORK( 1+N ), 1, WORK( KI+N ),
- $ VR( 1, KI ), 1 )
-*
- II = IDAMAX( N, VR( 1, KI ), 1 )
- REMAX = ONE / ABS( VR( II, KI ) )
- CALL DSCAL( N, REMAX, VR( 1, KI ), 1 )
- END IF
-*
- ELSE
-*
-* Complex right eigenvector.
-*
-* Initial solve
-* [ (T(KI-1,KI-1) T(KI-1,KI) ) - (WR + I* WI)]*X = 0.
-* [ (T(KI,KI-1) T(KI,KI) ) ]
-*
- IF( ABS( T( KI-1, KI ) ).GE.ABS( T( KI, KI-1 ) ) ) THEN
- WORK( KI-1+N ) = ONE
- WORK( KI+N2 ) = WI / T( KI-1, KI )
- ELSE
- WORK( KI-1+N ) = -WI / T( KI, KI-1 )
- WORK( KI+N2 ) = ONE
- END IF
- WORK( KI+N ) = ZERO
- WORK( KI-1+N2 ) = ZERO
-*
-* Form right-hand side
-*
- DO 80 K = 1, KI - 2
- WORK( K+N ) = -WORK( KI-1+N )*T( K, KI-1 )
- WORK( K+N2 ) = -WORK( KI+N2 )*T( K, KI )
- 80 CONTINUE
-*
-* Solve upper quasi-triangular system:
-* (T(1:KI-2,1:KI-2) - (WR+i*WI))*X = SCALE*(WORK+i*WORK2)
-*
- JNXT = KI - 2
- DO 90 J = KI - 2, 1, -1
- IF( J.GT.JNXT )
- $ GO TO 90
- J1 = J
- J2 = J
- JNXT = J - 1
- IF( J.GT.1 ) THEN
- IF( T( J, J-1 ).NE.ZERO ) THEN
- J1 = J - 1
- JNXT = J - 2
- END IF
- END IF
-*
- IF( J1.EQ.J2 ) THEN
-*
-* 1-by-1 diagonal block
-*
- CALL DLALN2( .FALSE., 1, 2, SMIN, ONE, T( J, J ),
- $ LDT, ONE, ONE, WORK( J+N ), N, WR, WI,
- $ X, 2, SCALE, XNORM, IERR )
-*
-* Scale X(1,1) and X(1,2) to avoid overflow when
-* updating the right-hand side.
-*
- IF( XNORM.GT.ONE ) THEN
- IF( WORK( J ).GT.BIGNUM / XNORM ) THEN
- X( 1, 1 ) = X( 1, 1 ) / XNORM
- X( 1, 2 ) = X( 1, 2 ) / XNORM
- SCALE = SCALE / XNORM
- END IF
- END IF
-*
-* Scale if necessary
-*
- IF( SCALE.NE.ONE ) THEN
- CALL DSCAL( KI, SCALE, WORK( 1+N ), 1 )
- CALL DSCAL( KI, SCALE, WORK( 1+N2 ), 1 )
- END IF
- WORK( J+N ) = X( 1, 1 )
- WORK( J+N2 ) = X( 1, 2 )
-*
-* Update the right-hand side
-*
- CALL DAXPY( J-1, -X( 1, 1 ), T( 1, J ), 1,
- $ WORK( 1+N ), 1 )
- CALL DAXPY( J-1, -X( 1, 2 ), T( 1, J ), 1,
- $ WORK( 1+N2 ), 1 )
-*
- ELSE
-*
-* 2-by-2 diagonal block
-*
- CALL DLALN2( .FALSE., 2, 2, SMIN, ONE,
- $ T( J-1, J-1 ), LDT, ONE, ONE,
- $ WORK( J-1+N ), N, WR, WI, X, 2, SCALE,
- $ XNORM, IERR )
-*
-* Scale X to avoid overflow when updating
-* the right-hand side.
-*
- IF( XNORM.GT.ONE ) THEN
- BETA = MAX( WORK( J-1 ), WORK( J ) )
- IF( BETA.GT.BIGNUM / XNORM ) THEN
- REC = ONE / XNORM
- X( 1, 1 ) = X( 1, 1 )*REC
- X( 1, 2 ) = X( 1, 2 )*REC
- X( 2, 1 ) = X( 2, 1 )*REC
- X( 2, 2 ) = X( 2, 2 )*REC
- SCALE = SCALE*REC
- END IF
- END IF
-*
-* Scale if necessary
-*
- IF( SCALE.NE.ONE ) THEN
- CALL DSCAL( KI, SCALE, WORK( 1+N ), 1 )
- CALL DSCAL( KI, SCALE, WORK( 1+N2 ), 1 )
- END IF
- WORK( J-1+N ) = X( 1, 1 )
- WORK( J+N ) = X( 2, 1 )
- WORK( J-1+N2 ) = X( 1, 2 )
- WORK( J+N2 ) = X( 2, 2 )
-*
-* Update the right-hand side
-*
- CALL DAXPY( J-2, -X( 1, 1 ), T( 1, J-1 ), 1,
- $ WORK( 1+N ), 1 )
- CALL DAXPY( J-2, -X( 2, 1 ), T( 1, J ), 1,
- $ WORK( 1+N ), 1 )
- CALL DAXPY( J-2, -X( 1, 2 ), T( 1, J-1 ), 1,
- $ WORK( 1+N2 ), 1 )
- CALL DAXPY( J-2, -X( 2, 2 ), T( 1, J ), 1,
- $ WORK( 1+N2 ), 1 )
- END IF
- 90 CONTINUE
-*
-* Copy the vector x or Q*x to VR and normalize.
-*
- IF( .NOT.OVER ) THEN
- CALL DCOPY( KI, WORK( 1+N ), 1, VR( 1, IS-1 ), 1 )
- CALL DCOPY( KI, WORK( 1+N2 ), 1, VR( 1, IS ), 1 )
-*
- EMAX = ZERO
- DO 100 K = 1, KI
- EMAX = MAX( EMAX, ABS( VR( K, IS-1 ) )+
- $ ABS( VR( K, IS ) ) )
- 100 CONTINUE
-*
- REMAX = ONE / EMAX
- CALL DSCAL( KI, REMAX, VR( 1, IS-1 ), 1 )
- CALL DSCAL( KI, REMAX, VR( 1, IS ), 1 )
-*
- DO 110 K = KI + 1, N
- VR( K, IS-1 ) = ZERO
- VR( K, IS ) = ZERO
- 110 CONTINUE
-*
- ELSE
-*
- IF( KI.GT.2 ) THEN
- CALL DGEMV( 'N', N, KI-2, ONE, VR, LDVR,
- $ WORK( 1+N ), 1, WORK( KI-1+N ),
- $ VR( 1, KI-1 ), 1 )
- CALL DGEMV( 'N', N, KI-2, ONE, VR, LDVR,
- $ WORK( 1+N2 ), 1, WORK( KI+N2 ),
- $ VR( 1, KI ), 1 )
- ELSE
- CALL DSCAL( N, WORK( KI-1+N ), VR( 1, KI-1 ), 1 )
- CALL DSCAL( N, WORK( KI+N2 ), VR( 1, KI ), 1 )
- END IF
-*
- EMAX = ZERO
- DO 120 K = 1, N
- EMAX = MAX( EMAX, ABS( VR( K, KI-1 ) )+
- $ ABS( VR( K, KI ) ) )
- 120 CONTINUE
- REMAX = ONE / EMAX
- CALL DSCAL( N, REMAX, VR( 1, KI-1 ), 1 )
- CALL DSCAL( N, REMAX, VR( 1, KI ), 1 )
- END IF
- END IF
-*
- IS = IS - 1
- IF( IP.NE.0 )
- $ IS = IS - 1
- 130 CONTINUE
- IF( IP.EQ.1 )
- $ IP = 0
- IF( IP.EQ.-1 )
- $ IP = 1
- 140 CONTINUE
- END IF
-*
- IF( LEFTV ) THEN
-*
-* Compute left eigenvectors.
-*
- IP = 0
- IS = 1
- DO 260 KI = 1, N
-*
- IF( IP.EQ.-1 )
- $ GO TO 250
- IF( KI.EQ.N )
- $ GO TO 150
- IF( T( KI+1, KI ).EQ.ZERO )
- $ GO TO 150
- IP = 1
-*
- 150 CONTINUE
- IF( SOMEV ) THEN
- IF( .NOT.SELECT( KI ) )
- $ GO TO 250
- END IF
-*
-* Compute the KI-th eigenvalue (WR,WI).
-*
- WR = T( KI, KI )
- WI = ZERO
- IF( IP.NE.0 )
- $ WI = SQRT( ABS( T( KI, KI+1 ) ) )*
- $ SQRT( ABS( T( KI+1, KI ) ) )
- SMIN = MAX( ULP*( ABS( WR )+ABS( WI ) ), SMLNUM )
-*
- IF( IP.EQ.0 ) THEN
-*
-* Real left eigenvector.
-*
- WORK( KI+N ) = ONE
-*
-* Form right-hand side
-*
- DO 160 K = KI + 1, N
- WORK( K+N ) = -T( KI, K )
- 160 CONTINUE
-*
-* Solve the quasi-triangular system:
-* (T(KI+1:N,KI+1:N) - WR)'*X = SCALE*WORK
-*
- VMAX = ONE
- VCRIT = BIGNUM
-*
- JNXT = KI + 1
- DO 170 J = KI + 1, N
- IF( J.LT.JNXT )
- $ GO TO 170
- J1 = J
- J2 = J
- JNXT = J + 1
- IF( J.LT.N ) THEN
- IF( T( J+1, J ).NE.ZERO ) THEN
- J2 = J + 1
- JNXT = J + 2
- END IF
- END IF
-*
- IF( J1.EQ.J2 ) THEN
-*
-* 1-by-1 diagonal block
-*
-* Scale if necessary to avoid overflow when forming
-* the right-hand side.
-*
- IF( WORK( J ).GT.VCRIT ) THEN
- REC = ONE / VMAX
- CALL DSCAL( N-KI+1, REC, WORK( KI+N ), 1 )
- VMAX = ONE
- VCRIT = BIGNUM
- END IF
-*
- WORK( J+N ) = WORK( J+N ) -
- $ DDOT( J-KI-1, T( KI+1, J ), 1,
- $ WORK( KI+1+N ), 1 )
-*
-* Solve (T(J,J)-WR)'*X = WORK
-*
- CALL DLALN2( .FALSE., 1, 1, SMIN, ONE, T( J, J ),
- $ LDT, ONE, ONE, WORK( J+N ), N, WR,
- $ ZERO, X, 2, SCALE, XNORM, IERR )
-*
-* Scale if necessary
-*
- IF( SCALE.NE.ONE )
- $ CALL DSCAL( N-KI+1, SCALE, WORK( KI+N ), 1 )
- WORK( J+N ) = X( 1, 1 )
- VMAX = MAX( ABS( WORK( J+N ) ), VMAX )
- VCRIT = BIGNUM / VMAX
-*
- ELSE
-*
-* 2-by-2 diagonal block
-*
-* Scale if necessary to avoid overflow when forming
-* the right-hand side.
-*
- BETA = MAX( WORK( J ), WORK( J+1 ) )
- IF( BETA.GT.VCRIT ) THEN
- REC = ONE / VMAX
- CALL DSCAL( N-KI+1, REC, WORK( KI+N ), 1 )
- VMAX = ONE
- VCRIT = BIGNUM
- END IF
-*
- WORK( J+N ) = WORK( J+N ) -
- $ DDOT( J-KI-1, T( KI+1, J ), 1,
- $ WORK( KI+1+N ), 1 )
-*
- WORK( J+1+N ) = WORK( J+1+N ) -
- $ DDOT( J-KI-1, T( KI+1, J+1 ), 1,
- $ WORK( KI+1+N ), 1 )
-*
-* Solve
-* [T(J,J)-WR T(J,J+1) ]'* X = SCALE*( WORK1 )
-* [T(J+1,J) T(J+1,J+1)-WR] ( WORK2 )
-*
- CALL DLALN2( .TRUE., 2, 1, SMIN, ONE, T( J, J ),
- $ LDT, ONE, ONE, WORK( J+N ), N, WR,
- $ ZERO, X, 2, SCALE, XNORM, IERR )
-*
-* Scale if necessary
-*
- IF( SCALE.NE.ONE )
- $ CALL DSCAL( N-KI+1, SCALE, WORK( KI+N ), 1 )
- WORK( J+N ) = X( 1, 1 )
- WORK( J+1+N ) = X( 2, 1 )
-*
- VMAX = MAX( ABS( WORK( J+N ) ),
- $ ABS( WORK( J+1+N ) ), VMAX )
- VCRIT = BIGNUM / VMAX
-*
- END IF
- 170 CONTINUE
-*
-* Copy the vector x or Q*x to VL and normalize.
-*
- IF( .NOT.OVER ) THEN
- CALL DCOPY( N-KI+1, WORK( KI+N ), 1, VL( KI, IS ), 1 )
-*
- II = IDAMAX( N-KI+1, VL( KI, IS ), 1 ) + KI - 1
- REMAX = ONE / ABS( VL( II, IS ) )
- CALL DSCAL( N-KI+1, REMAX, VL( KI, IS ), 1 )
-*
- DO 180 K = 1, KI - 1
- VL( K, IS ) = ZERO
- 180 CONTINUE
-*
- ELSE
-*
- IF( KI.LT.N )
- $ CALL DGEMV( 'N', N, N-KI, ONE, VL( 1, KI+1 ), LDVL,
- $ WORK( KI+1+N ), 1, WORK( KI+N ),
- $ VL( 1, KI ), 1 )
-*
- II = IDAMAX( N, VL( 1, KI ), 1 )
- REMAX = ONE / ABS( VL( II, KI ) )
- CALL DSCAL( N, REMAX, VL( 1, KI ), 1 )
-*
- END IF
-*
- ELSE
-*
-* Complex left eigenvector.
-*
-* Initial solve:
-* ((T(KI,KI) T(KI,KI+1) )' - (WR - I* WI))*X = 0.
-* ((T(KI+1,KI) T(KI+1,KI+1)) )
-*
- IF( ABS( T( KI, KI+1 ) ).GE.ABS( T( KI+1, KI ) ) ) THEN
- WORK( KI+N ) = WI / T( KI, KI+1 )
- WORK( KI+1+N2 ) = ONE
- ELSE
- WORK( KI+N ) = ONE
- WORK( KI+1+N2 ) = -WI / T( KI+1, KI )
- END IF
- WORK( KI+1+N ) = ZERO
- WORK( KI+N2 ) = ZERO
-*
-* Form right-hand side
-*
- DO 190 K = KI + 2, N
- WORK( K+N ) = -WORK( KI+N )*T( KI, K )
- WORK( K+N2 ) = -WORK( KI+1+N2 )*T( KI+1, K )
- 190 CONTINUE
-*
-* Solve complex quasi-triangular system:
-* ( T(KI+2,N:KI+2,N) - (WR-i*WI) )*X = WORK1+i*WORK2
-*
- VMAX = ONE
- VCRIT = BIGNUM
-*
- JNXT = KI + 2
- DO 200 J = KI + 2, N
- IF( J.LT.JNXT )
- $ GO TO 200
- J1 = J
- J2 = J
- JNXT = J + 1
- IF( J.LT.N ) THEN
- IF( T( J+1, J ).NE.ZERO ) THEN
- J2 = J + 1
- JNXT = J + 2
- END IF
- END IF
-*
- IF( J1.EQ.J2 ) THEN
-*
-* 1-by-1 diagonal block
-*
-* Scale if necessary to avoid overflow when
-* forming the right-hand side elements.
-*
- IF( WORK( J ).GT.VCRIT ) THEN
- REC = ONE / VMAX
- CALL DSCAL( N-KI+1, REC, WORK( KI+N ), 1 )
- CALL DSCAL( N-KI+1, REC, WORK( KI+N2 ), 1 )
- VMAX = ONE
- VCRIT = BIGNUM
- END IF
-*
- WORK( J+N ) = WORK( J+N ) -
- $ DDOT( J-KI-2, T( KI+2, J ), 1,
- $ WORK( KI+2+N ), 1 )
- WORK( J+N2 ) = WORK( J+N2 ) -
- $ DDOT( J-KI-2, T( KI+2, J ), 1,
- $ WORK( KI+2+N2 ), 1 )
-*
-* Solve (T(J,J)-(WR-i*WI))*(X11+i*X12)= WK+I*WK2
-*
- CALL DLALN2( .FALSE., 1, 2, SMIN, ONE, T( J, J ),
- $ LDT, ONE, ONE, WORK( J+N ), N, WR,
- $ -WI, X, 2, SCALE, XNORM, IERR )
-*
-* Scale if necessary
-*
- IF( SCALE.NE.ONE ) THEN
- CALL DSCAL( N-KI+1, SCALE, WORK( KI+N ), 1 )
- CALL DSCAL( N-KI+1, SCALE, WORK( KI+N2 ), 1 )
- END IF
- WORK( J+N ) = X( 1, 1 )
- WORK( J+N2 ) = X( 1, 2 )
- VMAX = MAX( ABS( WORK( J+N ) ),
- $ ABS( WORK( J+N2 ) ), VMAX )
- VCRIT = BIGNUM / VMAX
-*
- ELSE
-*
-* 2-by-2 diagonal block
-*
-* Scale if necessary to avoid overflow when forming
-* the right-hand side elements.
-*
- BETA = MAX( WORK( J ), WORK( J+1 ) )
- IF( BETA.GT.VCRIT ) THEN
- REC = ONE / VMAX
- CALL DSCAL( N-KI+1, REC, WORK( KI+N ), 1 )
- CALL DSCAL( N-KI+1, REC, WORK( KI+N2 ), 1 )
- VMAX = ONE
- VCRIT = BIGNUM
- END IF
-*
- WORK( J+N ) = WORK( J+N ) -
- $ DDOT( J-KI-2, T( KI+2, J ), 1,
- $ WORK( KI+2+N ), 1 )
-*
- WORK( J+N2 ) = WORK( J+N2 ) -
- $ DDOT( J-KI-2, T( KI+2, J ), 1,
- $ WORK( KI+2+N2 ), 1 )
-*
- WORK( J+1+N ) = WORK( J+1+N ) -
- $ DDOT( J-KI-2, T( KI+2, J+1 ), 1,
- $ WORK( KI+2+N ), 1 )
-*
- WORK( J+1+N2 ) = WORK( J+1+N2 ) -
- $ DDOT( J-KI-2, T( KI+2, J+1 ), 1,
- $ WORK( KI+2+N2 ), 1 )
-*
-* Solve 2-by-2 complex linear equation
-* ([T(j,j) T(j,j+1) ]'-(wr-i*wi)*I)*X = SCALE*B
-* ([T(j+1,j) T(j+1,j+1)] )
-*
- CALL DLALN2( .TRUE., 2, 2, SMIN, ONE, T( J, J ),
- $ LDT, ONE, ONE, WORK( J+N ), N, WR,
- $ -WI, X, 2, SCALE, XNORM, IERR )
-*
-* Scale if necessary
-*
- IF( SCALE.NE.ONE ) THEN
- CALL DSCAL( N-KI+1, SCALE, WORK( KI+N ), 1 )
- CALL DSCAL( N-KI+1, SCALE, WORK( KI+N2 ), 1 )
- END IF
- WORK( J+N ) = X( 1, 1 )
- WORK( J+N2 ) = X( 1, 2 )
- WORK( J+1+N ) = X( 2, 1 )
- WORK( J+1+N2 ) = X( 2, 2 )
- VMAX = MAX( ABS( X( 1, 1 ) ), ABS( X( 1, 2 ) ),
- $ ABS( X( 2, 1 ) ), ABS( X( 2, 2 ) ), VMAX )
- VCRIT = BIGNUM / VMAX
-*
- END IF
- 200 CONTINUE
-*
-* Copy the vector x or Q*x to VL and normalize.
-*
- IF( .NOT.OVER ) THEN
- CALL DCOPY( N-KI+1, WORK( KI+N ), 1, VL( KI, IS ), 1 )
- CALL DCOPY( N-KI+1, WORK( KI+N2 ), 1, VL( KI, IS+1 ),
- $ 1 )
-*
- EMAX = ZERO
- DO 220 K = KI, N
- EMAX = MAX( EMAX, ABS( VL( K, IS ) )+
- $ ABS( VL( K, IS+1 ) ) )
- 220 CONTINUE
- REMAX = ONE / EMAX
- CALL DSCAL( N-KI+1, REMAX, VL( KI, IS ), 1 )
- CALL DSCAL( N-KI+1, REMAX, VL( KI, IS+1 ), 1 )
-*
- DO 230 K = 1, KI - 1
- VL( K, IS ) = ZERO
- VL( K, IS+1 ) = ZERO
- 230 CONTINUE
- ELSE
- IF( KI.LT.N-1 ) THEN
- CALL DGEMV( 'N', N, N-KI-1, ONE, VL( 1, KI+2 ),
- $ LDVL, WORK( KI+2+N ), 1, WORK( KI+N ),
- $ VL( 1, KI ), 1 )
- CALL DGEMV( 'N', N, N-KI-1, ONE, VL( 1, KI+2 ),
- $ LDVL, WORK( KI+2+N2 ), 1,
- $ WORK( KI+1+N2 ), VL( 1, KI+1 ), 1 )
- ELSE
- CALL DSCAL( N, WORK( KI+N ), VL( 1, KI ), 1 )
- CALL DSCAL( N, WORK( KI+1+N2 ), VL( 1, KI+1 ), 1 )
- END IF
-*
- EMAX = ZERO
- DO 240 K = 1, N
- EMAX = MAX( EMAX, ABS( VL( K, KI ) )+
- $ ABS( VL( K, KI+1 ) ) )
- 240 CONTINUE
- REMAX = ONE / EMAX
- CALL DSCAL( N, REMAX, VL( 1, KI ), 1 )
- CALL DSCAL( N, REMAX, VL( 1, KI+1 ), 1 )
-*
- END IF
-*
- END IF
-*
- IS = IS + 1
- IF( IP.NE.0 )
- $ IS = IS + 1
- 250 CONTINUE
- IF( IP.EQ.-1 )
- $ IP = 0
- IF( IP.EQ.1 )
- $ IP = -1
-*
- 260 CONTINUE
-*
- END IF
-*
- RETURN
-*
-* End of DTREVC
-*
- END
diff --git a/src/lib/lapack/dtrexc.f b/src/lib/lapack/dtrexc.f
deleted file mode 100644
index db9be753..00000000
--- a/src/lib/lapack/dtrexc.f
+++ /dev/null
@@ -1,345 +0,0 @@
- SUBROUTINE DTREXC( COMPQ, N, T, LDT, Q, LDQ, IFST, ILST, WORK,
- $ INFO )
-*
-* -- LAPACK routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- CHARACTER COMPQ
- INTEGER IFST, ILST, INFO, LDQ, LDT, N
-* ..
-* .. Array Arguments ..
- DOUBLE PRECISION Q( LDQ, * ), T( LDT, * ), WORK( * )
-* ..
-*
-* Purpose
-* =======
-*
-* DTREXC reorders the real Schur factorization of a real matrix
-* A = Q*T*Q**T, so that the diagonal block of T with row index IFST is
-* moved to row ILST.
-*
-* The real Schur form T is reordered by an orthogonal similarity
-* transformation Z**T*T*Z, and optionally the matrix Q of Schur vectors
-* is updated by postmultiplying it with Z.
-*
-* T must be in Schur canonical form (as returned by DHSEQR), that is,
-* block upper triangular with 1-by-1 and 2-by-2 diagonal blocks; each
-* 2-by-2 diagonal block has its diagonal elements equal and its
-* off-diagonal elements of opposite sign.
-*
-* Arguments
-* =========
-*
-* COMPQ (input) CHARACTER*1
-* = 'V': update the matrix Q of Schur vectors;
-* = 'N': do not update Q.
-*
-* N (input) INTEGER
-* The order of the matrix T. N >= 0.
-*
-* T (input/output) DOUBLE PRECISION array, dimension (LDT,N)
-* On entry, the upper quasi-triangular matrix T, in Schur
-* Schur canonical form.
-* On exit, the reordered upper quasi-triangular matrix, again
-* in Schur canonical form.
-*
-* LDT (input) INTEGER
-* The leading dimension of the array T. LDT >= max(1,N).
-*
-* Q (input/output) DOUBLE PRECISION array, dimension (LDQ,N)
-* On entry, if COMPQ = 'V', the matrix Q of Schur vectors.
-* On exit, if COMPQ = 'V', Q has been postmultiplied by the
-* orthogonal transformation matrix Z which reorders T.
-* If COMPQ = 'N', Q is not referenced.
-*
-* LDQ (input) INTEGER
-* The leading dimension of the array Q. LDQ >= max(1,N).
-*
-* IFST (input/output) INTEGER
-* ILST (input/output) INTEGER
-* Specify the reordering of the diagonal blocks of T.
-* The block with row index IFST is moved to row ILST, by a
-* sequence of transpositions between adjacent blocks.
-* On exit, if IFST pointed on entry to the second row of a
-* 2-by-2 block, it is changed to point to the first row; ILST
-* always points to the first row of the block in its final
-* position (which may differ from its input value by +1 or -1).
-* 1 <= IFST <= N; 1 <= ILST <= N.
-*
-* WORK (workspace) DOUBLE PRECISION array, dimension (N)
-*
-* INFO (output) INTEGER
-* = 0: successful exit
-* < 0: if INFO = -i, the i-th argument had an illegal value
-* = 1: two adjacent blocks were too close to swap (the problem
-* is very ill-conditioned); T may have been partially
-* reordered, and ILST points to the first row of the
-* current position of the block being moved.
-*
-* =====================================================================
-*
-* .. Parameters ..
- DOUBLE PRECISION ZERO
- PARAMETER ( ZERO = 0.0D+0 )
-* ..
-* .. Local Scalars ..
- LOGICAL WANTQ
- INTEGER HERE, NBF, NBL, NBNEXT
-* ..
-* .. External Functions ..
- LOGICAL LSAME
- EXTERNAL LSAME
-* ..
-* .. External Subroutines ..
- EXTERNAL DLAEXC, XERBLA
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC MAX
-* ..
-* .. Executable Statements ..
-*
-* Decode and test the input arguments.
-*
- INFO = 0
- WANTQ = LSAME( COMPQ, 'V' )
- IF( .NOT.WANTQ .AND. .NOT.LSAME( COMPQ, 'N' ) ) THEN
- INFO = -1
- ELSE IF( N.LT.0 ) THEN
- INFO = -2
- ELSE IF( LDT.LT.MAX( 1, N ) ) THEN
- INFO = -4
- ELSE IF( LDQ.LT.1 .OR. ( WANTQ .AND. LDQ.LT.MAX( 1, N ) ) ) THEN
- INFO = -6
- ELSE IF( IFST.LT.1 .OR. IFST.GT.N ) THEN
- INFO = -7
- ELSE IF( ILST.LT.1 .OR. ILST.GT.N ) THEN
- INFO = -8
- END IF
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'DTREXC', -INFO )
- RETURN
- END IF
-*
-* Quick return if possible
-*
- IF( N.LE.1 )
- $ RETURN
-*
-* Determine the first row of specified block
-* and find out it is 1 by 1 or 2 by 2.
-*
- IF( IFST.GT.1 ) THEN
- IF( T( IFST, IFST-1 ).NE.ZERO )
- $ IFST = IFST - 1
- END IF
- NBF = 1
- IF( IFST.LT.N ) THEN
- IF( T( IFST+1, IFST ).NE.ZERO )
- $ NBF = 2
- END IF
-*
-* Determine the first row of the final block
-* and find out it is 1 by 1 or 2 by 2.
-*
- IF( ILST.GT.1 ) THEN
- IF( T( ILST, ILST-1 ).NE.ZERO )
- $ ILST = ILST - 1
- END IF
- NBL = 1
- IF( ILST.LT.N ) THEN
- IF( T( ILST+1, ILST ).NE.ZERO )
- $ NBL = 2
- END IF
-*
- IF( IFST.EQ.ILST )
- $ RETURN
-*
- IF( IFST.LT.ILST ) THEN
-*
-* Update ILST
-*
- IF( NBF.EQ.2 .AND. NBL.EQ.1 )
- $ ILST = ILST - 1
- IF( NBF.EQ.1 .AND. NBL.EQ.2 )
- $ ILST = ILST + 1
-*
- HERE = IFST
-*
- 10 CONTINUE
-*
-* Swap block with next one below
-*
- IF( NBF.EQ.1 .OR. NBF.EQ.2 ) THEN
-*
-* Current block either 1 by 1 or 2 by 2
-*
- NBNEXT = 1
- IF( HERE+NBF+1.LE.N ) THEN
- IF( T( HERE+NBF+1, HERE+NBF ).NE.ZERO )
- $ NBNEXT = 2
- END IF
- CALL DLAEXC( WANTQ, N, T, LDT, Q, LDQ, HERE, NBF, NBNEXT,
- $ WORK, INFO )
- IF( INFO.NE.0 ) THEN
- ILST = HERE
- RETURN
- END IF
- HERE = HERE + NBNEXT
-*
-* Test if 2 by 2 block breaks into two 1 by 1 blocks
-*
- IF( NBF.EQ.2 ) THEN
- IF( T( HERE+1, HERE ).EQ.ZERO )
- $ NBF = 3
- END IF
-*
- ELSE
-*
-* Current block consists of two 1 by 1 blocks each of which
-* must be swapped individually
-*
- NBNEXT = 1
- IF( HERE+3.LE.N ) THEN
- IF( T( HERE+3, HERE+2 ).NE.ZERO )
- $ NBNEXT = 2
- END IF
- CALL DLAEXC( WANTQ, N, T, LDT, Q, LDQ, HERE+1, 1, NBNEXT,
- $ WORK, INFO )
- IF( INFO.NE.0 ) THEN
- ILST = HERE
- RETURN
- END IF
- IF( NBNEXT.EQ.1 ) THEN
-*
-* Swap two 1 by 1 blocks, no problems possible
-*
- CALL DLAEXC( WANTQ, N, T, LDT, Q, LDQ, HERE, 1, NBNEXT,
- $ WORK, INFO )
- HERE = HERE + 1
- ELSE
-*
-* Recompute NBNEXT in case 2 by 2 split
-*
- IF( T( HERE+2, HERE+1 ).EQ.ZERO )
- $ NBNEXT = 1
- IF( NBNEXT.EQ.2 ) THEN
-*
-* 2 by 2 Block did not split
-*
- CALL DLAEXC( WANTQ, N, T, LDT, Q, LDQ, HERE, 1,
- $ NBNEXT, WORK, INFO )
- IF( INFO.NE.0 ) THEN
- ILST = HERE
- RETURN
- END IF
- HERE = HERE + 2
- ELSE
-*
-* 2 by 2 Block did split
-*
- CALL DLAEXC( WANTQ, N, T, LDT, Q, LDQ, HERE, 1, 1,
- $ WORK, INFO )
- CALL DLAEXC( WANTQ, N, T, LDT, Q, LDQ, HERE+1, 1, 1,
- $ WORK, INFO )
- HERE = HERE + 2
- END IF
- END IF
- END IF
- IF( HERE.LT.ILST )
- $ GO TO 10
-*
- ELSE
-*
- HERE = IFST
- 20 CONTINUE
-*
-* Swap block with next one above
-*
- IF( NBF.EQ.1 .OR. NBF.EQ.2 ) THEN
-*
-* Current block either 1 by 1 or 2 by 2
-*
- NBNEXT = 1
- IF( HERE.GE.3 ) THEN
- IF( T( HERE-1, HERE-2 ).NE.ZERO )
- $ NBNEXT = 2
- END IF
- CALL DLAEXC( WANTQ, N, T, LDT, Q, LDQ, HERE-NBNEXT, NBNEXT,
- $ NBF, WORK, INFO )
- IF( INFO.NE.0 ) THEN
- ILST = HERE
- RETURN
- END IF
- HERE = HERE - NBNEXT
-*
-* Test if 2 by 2 block breaks into two 1 by 1 blocks
-*
- IF( NBF.EQ.2 ) THEN
- IF( T( HERE+1, HERE ).EQ.ZERO )
- $ NBF = 3
- END IF
-*
- ELSE
-*
-* Current block consists of two 1 by 1 blocks each of which
-* must be swapped individually
-*
- NBNEXT = 1
- IF( HERE.GE.3 ) THEN
- IF( T( HERE-1, HERE-2 ).NE.ZERO )
- $ NBNEXT = 2
- END IF
- CALL DLAEXC( WANTQ, N, T, LDT, Q, LDQ, HERE-NBNEXT, NBNEXT,
- $ 1, WORK, INFO )
- IF( INFO.NE.0 ) THEN
- ILST = HERE
- RETURN
- END IF
- IF( NBNEXT.EQ.1 ) THEN
-*
-* Swap two 1 by 1 blocks, no problems possible
-*
- CALL DLAEXC( WANTQ, N, T, LDT, Q, LDQ, HERE, NBNEXT, 1,
- $ WORK, INFO )
- HERE = HERE - 1
- ELSE
-*
-* Recompute NBNEXT in case 2 by 2 split
-*
- IF( T( HERE, HERE-1 ).EQ.ZERO )
- $ NBNEXT = 1
- IF( NBNEXT.EQ.2 ) THEN
-*
-* 2 by 2 Block did not split
-*
- CALL DLAEXC( WANTQ, N, T, LDT, Q, LDQ, HERE-1, 2, 1,
- $ WORK, INFO )
- IF( INFO.NE.0 ) THEN
- ILST = HERE
- RETURN
- END IF
- HERE = HERE - 2
- ELSE
-*
-* 2 by 2 Block did split
-*
- CALL DLAEXC( WANTQ, N, T, LDT, Q, LDQ, HERE, 1, 1,
- $ WORK, INFO )
- CALL DLAEXC( WANTQ, N, T, LDT, Q, LDQ, HERE-1, 1, 1,
- $ WORK, INFO )
- HERE = HERE - 2
- END IF
- END IF
- END IF
- IF( HERE.GT.ILST )
- $ GO TO 20
- END IF
- ILST = HERE
-*
- RETURN
-*
-* End of DTREXC
-*
- END
diff --git a/src/lib/lapack/dtrsen.f b/src/lib/lapack/dtrsen.f
deleted file mode 100644
index 1d3ab03a..00000000
--- a/src/lib/lapack/dtrsen.f
+++ /dev/null
@@ -1,459 +0,0 @@
- SUBROUTINE DTRSEN( JOB, COMPQ, SELECT, N, T, LDT, Q, LDQ, WR, WI,
- $ M, S, SEP, WORK, LWORK, IWORK, LIWORK, INFO )
-*
-* -- LAPACK routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- CHARACTER COMPQ, JOB
- INTEGER INFO, LDQ, LDT, LIWORK, LWORK, M, N
- DOUBLE PRECISION S, SEP
-* ..
-* .. Array Arguments ..
- LOGICAL SELECT( * )
- INTEGER IWORK( * )
- DOUBLE PRECISION Q( LDQ, * ), T( LDT, * ), WI( * ), WORK( * ),
- $ WR( * )
-* ..
-*
-* Purpose
-* =======
-*
-* DTRSEN reorders the real Schur factorization of a real matrix
-* A = Q*T*Q**T, so that a selected cluster of eigenvalues appears in
-* the leading diagonal blocks of the upper quasi-triangular matrix T,
-* and the leading columns of Q form an orthonormal basis of the
-* corresponding right invariant subspace.
-*
-* Optionally the routine computes the reciprocal condition numbers of
-* the cluster of eigenvalues and/or the invariant subspace.
-*
-* T must be in Schur canonical form (as returned by DHSEQR), that is,
-* block upper triangular with 1-by-1 and 2-by-2 diagonal blocks; each
-* 2-by-2 diagonal block has its diagonal elemnts equal and its
-* off-diagonal elements of opposite sign.
-*
-* Arguments
-* =========
-*
-* JOB (input) CHARACTER*1
-* Specifies whether condition numbers are required for the
-* cluster of eigenvalues (S) or the invariant subspace (SEP):
-* = 'N': none;
-* = 'E': for eigenvalues only (S);
-* = 'V': for invariant subspace only (SEP);
-* = 'B': for both eigenvalues and invariant subspace (S and
-* SEP).
-*
-* COMPQ (input) CHARACTER*1
-* = 'V': update the matrix Q of Schur vectors;
-* = 'N': do not update Q.
-*
-* SELECT (input) LOGICAL array, dimension (N)
-* SELECT specifies the eigenvalues in the selected cluster. To
-* select a real eigenvalue w(j), SELECT(j) must be set to
-* .TRUE.. To select a complex conjugate pair of eigenvalues
-* w(j) and w(j+1), corresponding to a 2-by-2 diagonal block,
-* either SELECT(j) or SELECT(j+1) or both must be set to
-* .TRUE.; a complex conjugate pair of eigenvalues must be
-* either both included in the cluster or both excluded.
-*
-* N (input) INTEGER
-* The order of the matrix T. N >= 0.
-*
-* T (input/output) DOUBLE PRECISION array, dimension (LDT,N)
-* On entry, the upper quasi-triangular matrix T, in Schur
-* canonical form.
-* On exit, T is overwritten by the reordered matrix T, again in
-* Schur canonical form, with the selected eigenvalues in the
-* leading diagonal blocks.
-*
-* LDT (input) INTEGER
-* The leading dimension of the array T. LDT >= max(1,N).
-*
-* Q (input/output) DOUBLE PRECISION array, dimension (LDQ,N)
-* On entry, if COMPQ = 'V', the matrix Q of Schur vectors.
-* On exit, if COMPQ = 'V', Q has been postmultiplied by the
-* orthogonal transformation matrix which reorders T; the
-* leading M columns of Q form an orthonormal basis for the
-* specified invariant subspace.
-* If COMPQ = 'N', Q is not referenced.
-*
-* LDQ (input) INTEGER
-* The leading dimension of the array Q.
-* LDQ >= 1; and if COMPQ = 'V', LDQ >= N.
-*
-* WR (output) DOUBLE PRECISION array, dimension (N)
-* WI (output) DOUBLE PRECISION array, dimension (N)
-* The real and imaginary parts, respectively, of the reordered
-* eigenvalues of T. The eigenvalues are stored in the same
-* order as on the diagonal of T, with WR(i) = T(i,i) and, if
-* T(i:i+1,i:i+1) is a 2-by-2 diagonal block, WI(i) > 0 and
-* WI(i+1) = -WI(i). Note that if a complex eigenvalue is
-* sufficiently ill-conditioned, then its value may differ
-* significantly from its value before reordering.
-*
-* M (output) INTEGER
-* The dimension of the specified invariant subspace.
-* 0 < = M <= N.
-*
-* S (output) DOUBLE PRECISION
-* If JOB = 'E' or 'B', S is a lower bound on the reciprocal
-* condition number for the selected cluster of eigenvalues.
-* S cannot underestimate the true reciprocal condition number
-* by more than a factor of sqrt(N). If M = 0 or N, S = 1.
-* If JOB = 'N' or 'V', S is not referenced.
-*
-* SEP (output) DOUBLE PRECISION
-* If JOB = 'V' or 'B', SEP is the estimated reciprocal
-* condition number of the specified invariant subspace. If
-* M = 0 or N, SEP = norm(T).
-* If JOB = 'N' or 'E', SEP is not referenced.
-*
-* WORK (workspace/output) DOUBLE PRECISION array, dimension (MAX(1,LWORK))
-* On exit, if INFO = 0, WORK(1) returns the optimal LWORK.
-*
-* LWORK (input) INTEGER
-* The dimension of the array WORK.
-* If JOB = 'N', LWORK >= max(1,N);
-* if JOB = 'E', LWORK >= max(1,M*(N-M));
-* if JOB = 'V' or 'B', LWORK >= max(1,2*M*(N-M)).
-*
-* If LWORK = -1, then a workspace query is assumed; the routine
-* only calculates the optimal size of the WORK array, returns
-* this value as the first entry of the WORK array, and no error
-* message related to LWORK is issued by XERBLA.
-*
-* IWORK (workspace) INTEGER array, dimension (MAX(1,LIWORK))
-* On exit, if INFO = 0, IWORK(1) returns the optimal LIWORK.
-*
-* LIWORK (input) INTEGER
-* The dimension of the array IWORK.
-* If JOB = 'N' or 'E', LIWORK >= 1;
-* if JOB = 'V' or 'B', LIWORK >= max(1,M*(N-M)).
-*
-* If LIWORK = -1, then a workspace query is assumed; the
-* routine only calculates the optimal size of the IWORK array,
-* returns this value as the first entry of the IWORK array, and
-* no error message related to LIWORK is issued by XERBLA.
-*
-* INFO (output) INTEGER
-* = 0: successful exit
-* < 0: if INFO = -i, the i-th argument had an illegal value
-* = 1: reordering of T failed because some eigenvalues are too
-* close to separate (the problem is very ill-conditioned);
-* T may have been partially reordered, and WR and WI
-* contain the eigenvalues in the same order as in T; S and
-* SEP (if requested) are set to zero.
-*
-* Further Details
-* ===============
-*
-* DTRSEN first collects the selected eigenvalues by computing an
-* orthogonal transformation Z to move them to the top left corner of T.
-* In other words, the selected eigenvalues are the eigenvalues of T11
-* in:
-*
-* Z'*T*Z = ( T11 T12 ) n1
-* ( 0 T22 ) n2
-* n1 n2
-*
-* where N = n1+n2 and Z' means the transpose of Z. The first n1 columns
-* of Z span the specified invariant subspace of T.
-*
-* If T has been obtained from the real Schur factorization of a matrix
-* A = Q*T*Q', then the reordered real Schur factorization of A is given
-* by A = (Q*Z)*(Z'*T*Z)*(Q*Z)', and the first n1 columns of Q*Z span
-* the corresponding invariant subspace of A.
-*
-* The reciprocal condition number of the average of the eigenvalues of
-* T11 may be returned in S. S lies between 0 (very badly conditioned)
-* and 1 (very well conditioned). It is computed as follows. First we
-* compute R so that
-*
-* P = ( I R ) n1
-* ( 0 0 ) n2
-* n1 n2
-*
-* is the projector on the invariant subspace associated with T11.
-* R is the solution of the Sylvester equation:
-*
-* T11*R - R*T22 = T12.
-*
-* Let F-norm(M) denote the Frobenius-norm of M and 2-norm(M) denote
-* the two-norm of M. Then S is computed as the lower bound
-*
-* (1 + F-norm(R)**2)**(-1/2)
-*
-* on the reciprocal of 2-norm(P), the true reciprocal condition number.
-* S cannot underestimate 1 / 2-norm(P) by more than a factor of
-* sqrt(N).
-*
-* An approximate error bound for the computed average of the
-* eigenvalues of T11 is
-*
-* EPS * norm(T) / S
-*
-* where EPS is the machine precision.
-*
-* The reciprocal condition number of the right invariant subspace
-* spanned by the first n1 columns of Z (or of Q*Z) is returned in SEP.
-* SEP is defined as the separation of T11 and T22:
-*
-* sep( T11, T22 ) = sigma-min( C )
-*
-* where sigma-min(C) is the smallest singular value of the
-* n1*n2-by-n1*n2 matrix
-*
-* C = kprod( I(n2), T11 ) - kprod( transpose(T22), I(n1) )
-*
-* I(m) is an m by m identity matrix, and kprod denotes the Kronecker
-* product. We estimate sigma-min(C) by the reciprocal of an estimate of
-* the 1-norm of inverse(C). The true reciprocal 1-norm of inverse(C)
-* cannot differ from sigma-min(C) by more than a factor of sqrt(n1*n2).
-*
-* When SEP is small, small changes in T can cause large changes in
-* the invariant subspace. An approximate bound on the maximum angular
-* error in the computed right invariant subspace is
-*
-* EPS * norm(T) / SEP
-*
-* =====================================================================
-*
-* .. Parameters ..
- DOUBLE PRECISION ZERO, ONE
- PARAMETER ( ZERO = 0.0D+0, ONE = 1.0D+0 )
-* ..
-* .. Local Scalars ..
- LOGICAL LQUERY, PAIR, SWAP, WANTBH, WANTQ, WANTS,
- $ WANTSP
- INTEGER IERR, K, KASE, KK, KS, LIWMIN, LWMIN, N1, N2,
- $ NN
- DOUBLE PRECISION EST, RNORM, SCALE
-* ..
-* .. Local Arrays ..
- INTEGER ISAVE( 3 )
-* ..
-* .. External Functions ..
- LOGICAL LSAME
- DOUBLE PRECISION DLANGE
- EXTERNAL LSAME, DLANGE
-* ..
-* .. External Subroutines ..
- EXTERNAL DLACN2, DLACPY, DTREXC, DTRSYL, XERBLA
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC ABS, MAX, SQRT
-* ..
-* .. Executable Statements ..
-*
-* Decode and test the input parameters
-*
- WANTBH = LSAME( JOB, 'B' )
- WANTS = LSAME( JOB, 'E' ) .OR. WANTBH
- WANTSP = LSAME( JOB, 'V' ) .OR. WANTBH
- WANTQ = LSAME( COMPQ, 'V' )
-*
- INFO = 0
- LQUERY = ( LWORK.EQ.-1 )
- IF( .NOT.LSAME( JOB, 'N' ) .AND. .NOT.WANTS .AND. .NOT.WANTSP )
- $ THEN
- INFO = -1
- ELSE IF( .NOT.LSAME( COMPQ, 'N' ) .AND. .NOT.WANTQ ) THEN
- INFO = -2
- ELSE IF( N.LT.0 ) THEN
- INFO = -4
- ELSE IF( LDT.LT.MAX( 1, N ) ) THEN
- INFO = -6
- ELSE IF( LDQ.LT.1 .OR. ( WANTQ .AND. LDQ.LT.N ) ) THEN
- INFO = -8
- ELSE
-*
-* Set M to the dimension of the specified invariant subspace,
-* and test LWORK and LIWORK.
-*
- M = 0
- PAIR = .FALSE.
- DO 10 K = 1, N
- IF( PAIR ) THEN
- PAIR = .FALSE.
- ELSE
- IF( K.LT.N ) THEN
- IF( T( K+1, K ).EQ.ZERO ) THEN
- IF( SELECT( K ) )
- $ M = M + 1
- ELSE
- PAIR = .TRUE.
- IF( SELECT( K ) .OR. SELECT( K+1 ) )
- $ M = M + 2
- END IF
- ELSE
- IF( SELECT( N ) )
- $ M = M + 1
- END IF
- END IF
- 10 CONTINUE
-*
- N1 = M
- N2 = N - M
- NN = N1*N2
-*
- IF( WANTSP ) THEN
- LWMIN = MAX( 1, 2*NN )
- LIWMIN = MAX( 1, NN )
- ELSE IF( LSAME( JOB, 'N' ) ) THEN
- LWMIN = MAX( 1, N )
- LIWMIN = 1
- ELSE IF( LSAME( JOB, 'E' ) ) THEN
- LWMIN = MAX( 1, NN )
- LIWMIN = 1
- END IF
-*
- IF( LWORK.LT.LWMIN .AND. .NOT.LQUERY ) THEN
- INFO = -15
- ELSE IF( LIWORK.LT.LIWMIN .AND. .NOT.LQUERY ) THEN
- INFO = -17
- END IF
- END IF
-*
- IF( INFO.EQ.0 ) THEN
- WORK( 1 ) = LWMIN
- IWORK( 1 ) = LIWMIN
- END IF
-*
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'DTRSEN', -INFO )
- RETURN
- ELSE IF( LQUERY ) THEN
- RETURN
- END IF
-*
-* Quick return if possible.
-*
- IF( M.EQ.N .OR. M.EQ.0 ) THEN
- IF( WANTS )
- $ S = ONE
- IF( WANTSP )
- $ SEP = DLANGE( '1', N, N, T, LDT, WORK )
- GO TO 40
- END IF
-*
-* Collect the selected blocks at the top-left corner of T.
-*
- KS = 0
- PAIR = .FALSE.
- DO 20 K = 1, N
- IF( PAIR ) THEN
- PAIR = .FALSE.
- ELSE
- SWAP = SELECT( K )
- IF( K.LT.N ) THEN
- IF( T( K+1, K ).NE.ZERO ) THEN
- PAIR = .TRUE.
- SWAP = SWAP .OR. SELECT( K+1 )
- END IF
- END IF
- IF( SWAP ) THEN
- KS = KS + 1
-*
-* Swap the K-th block to position KS.
-*
- IERR = 0
- KK = K
- IF( K.NE.KS )
- $ CALL DTREXC( COMPQ, N, T, LDT, Q, LDQ, KK, KS, WORK,
- $ IERR )
- IF( IERR.EQ.1 .OR. IERR.EQ.2 ) THEN
-*
-* Blocks too close to swap: exit.
-*
- INFO = 1
- IF( WANTS )
- $ S = ZERO
- IF( WANTSP )
- $ SEP = ZERO
- GO TO 40
- END IF
- IF( PAIR )
- $ KS = KS + 1
- END IF
- END IF
- 20 CONTINUE
-*
- IF( WANTS ) THEN
-*
-* Solve Sylvester equation for R:
-*
-* T11*R - R*T22 = scale*T12
-*
- CALL DLACPY( 'F', N1, N2, T( 1, N1+1 ), LDT, WORK, N1 )
- CALL DTRSYL( 'N', 'N', -1, N1, N2, T, LDT, T( N1+1, N1+1 ),
- $ LDT, WORK, N1, SCALE, IERR )
-*
-* Estimate the reciprocal of the condition number of the cluster
-* of eigenvalues.
-*
- RNORM = DLANGE( 'F', N1, N2, WORK, N1, WORK )
- IF( RNORM.EQ.ZERO ) THEN
- S = ONE
- ELSE
- S = SCALE / ( SQRT( SCALE*SCALE / RNORM+RNORM )*
- $ SQRT( RNORM ) )
- END IF
- END IF
-*
- IF( WANTSP ) THEN
-*
-* Estimate sep(T11,T22).
-*
- EST = ZERO
- KASE = 0
- 30 CONTINUE
- CALL DLACN2( NN, WORK( NN+1 ), WORK, IWORK, EST, KASE, ISAVE )
- IF( KASE.NE.0 ) THEN
- IF( KASE.EQ.1 ) THEN
-*
-* Solve T11*R - R*T22 = scale*X.
-*
- CALL DTRSYL( 'N', 'N', -1, N1, N2, T, LDT,
- $ T( N1+1, N1+1 ), LDT, WORK, N1, SCALE,
- $ IERR )
- ELSE
-*
-* Solve T11'*R - R*T22' = scale*X.
-*
- CALL DTRSYL( 'T', 'T', -1, N1, N2, T, LDT,
- $ T( N1+1, N1+1 ), LDT, WORK, N1, SCALE,
- $ IERR )
- END IF
- GO TO 30
- END IF
-*
- SEP = SCALE / EST
- END IF
-*
- 40 CONTINUE
-*
-* Store the output eigenvalues in WR and WI.
-*
- DO 50 K = 1, N
- WR( K ) = T( K, K )
- WI( K ) = ZERO
- 50 CONTINUE
- DO 60 K = 1, N - 1
- IF( T( K+1, K ).NE.ZERO ) THEN
- WI( K ) = SQRT( ABS( T( K, K+1 ) ) )*
- $ SQRT( ABS( T( K+1, K ) ) )
- WI( K+1 ) = -WI( K )
- END IF
- 60 CONTINUE
-*
- WORK( 1 ) = LWMIN
- IWORK( 1 ) = LIWMIN
-*
- RETURN
-*
-* End of DTRSEN
-*
- END
diff --git a/src/lib/lapack/dtrsyl.f b/src/lib/lapack/dtrsyl.f
deleted file mode 100644
index 4c6c28e5..00000000
--- a/src/lib/lapack/dtrsyl.f
+++ /dev/null
@@ -1,913 +0,0 @@
- SUBROUTINE DTRSYL( TRANA, TRANB, ISGN, M, N, A, LDA, B, LDB, C,
- $ LDC, SCALE, INFO )
-*
-* -- LAPACK routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- CHARACTER TRANA, TRANB
- INTEGER INFO, ISGN, LDA, LDB, LDC, M, N
- DOUBLE PRECISION SCALE
-* ..
-* .. Array Arguments ..
- DOUBLE PRECISION A( LDA, * ), B( LDB, * ), C( LDC, * )
-* ..
-*
-* Purpose
-* =======
-*
-* DTRSYL solves the real Sylvester matrix equation:
-*
-* op(A)*X + X*op(B) = scale*C or
-* op(A)*X - X*op(B) = scale*C,
-*
-* where op(A) = A or A**T, and A and B are both upper quasi-
-* triangular. A is M-by-M and B is N-by-N; the right hand side C and
-* the solution X are M-by-N; and scale is an output scale factor, set
-* <= 1 to avoid overflow in X.
-*
-* A and B must be in Schur canonical form (as returned by DHSEQR), that
-* is, block upper triangular with 1-by-1 and 2-by-2 diagonal blocks;
-* each 2-by-2 diagonal block has its diagonal elements equal and its
-* off-diagonal elements of opposite sign.
-*
-* Arguments
-* =========
-*
-* TRANA (input) CHARACTER*1
-* Specifies the option op(A):
-* = 'N': op(A) = A (No transpose)
-* = 'T': op(A) = A**T (Transpose)
-* = 'C': op(A) = A**H (Conjugate transpose = Transpose)
-*
-* TRANB (input) CHARACTER*1
-* Specifies the option op(B):
-* = 'N': op(B) = B (No transpose)
-* = 'T': op(B) = B**T (Transpose)
-* = 'C': op(B) = B**H (Conjugate transpose = Transpose)
-*
-* ISGN (input) INTEGER
-* Specifies the sign in the equation:
-* = +1: solve op(A)*X + X*op(B) = scale*C
-* = -1: solve op(A)*X - X*op(B) = scale*C
-*
-* M (input) INTEGER
-* The order of the matrix A, and the number of rows in the
-* matrices X and C. M >= 0.
-*
-* N (input) INTEGER
-* The order of the matrix B, and the number of columns in the
-* matrices X and C. N >= 0.
-*
-* A (input) DOUBLE PRECISION array, dimension (LDA,M)
-* The upper quasi-triangular matrix A, in Schur canonical form.
-*
-* LDA (input) INTEGER
-* The leading dimension of the array A. LDA >= max(1,M).
-*
-* B (input) DOUBLE PRECISION array, dimension (LDB,N)
-* The upper quasi-triangular matrix B, in Schur canonical form.
-*
-* LDB (input) INTEGER
-* The leading dimension of the array B. LDB >= max(1,N).
-*
-* C (input/output) DOUBLE PRECISION array, dimension (LDC,N)
-* On entry, the M-by-N right hand side matrix C.
-* On exit, C is overwritten by the solution matrix X.
-*
-* LDC (input) INTEGER
-* The leading dimension of the array C. LDC >= max(1,M)
-*
-* SCALE (output) DOUBLE PRECISION
-* The scale factor, scale, set <= 1 to avoid overflow in X.
-*
-* INFO (output) INTEGER
-* = 0: successful exit
-* < 0: if INFO = -i, the i-th argument had an illegal value
-* = 1: A and B have common or very close eigenvalues; perturbed
-* values were used to solve the equation (but the matrices
-* A and B are unchanged).
-*
-* =====================================================================
-*
-* .. Parameters ..
- DOUBLE PRECISION ZERO, ONE
- PARAMETER ( ZERO = 0.0D+0, ONE = 1.0D+0 )
-* ..
-* .. Local Scalars ..
- LOGICAL NOTRNA, NOTRNB
- INTEGER IERR, J, K, K1, K2, KNEXT, L, L1, L2, LNEXT
- DOUBLE PRECISION A11, BIGNUM, DA11, DB, EPS, SCALOC, SGN, SMIN,
- $ SMLNUM, SUML, SUMR, XNORM
-* ..
-* .. Local Arrays ..
- DOUBLE PRECISION DUM( 1 ), VEC( 2, 2 ), X( 2, 2 )
-* ..
-* .. External Functions ..
- LOGICAL LSAME
- DOUBLE PRECISION DDOT, DLAMCH, DLANGE
- EXTERNAL LSAME, DDOT, DLAMCH, DLANGE
-* ..
-* .. External Subroutines ..
- EXTERNAL DLABAD, DLALN2, DLASY2, DSCAL, XERBLA
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC ABS, DBLE, MAX, MIN
-* ..
-* .. Executable Statements ..
-*
-* Decode and Test input parameters
-*
- NOTRNA = LSAME( TRANA, 'N' )
- NOTRNB = LSAME( TRANB, 'N' )
-*
- INFO = 0
- IF( .NOT.NOTRNA .AND. .NOT.LSAME( TRANA, 'T' ) .AND. .NOT.
- $ LSAME( TRANA, 'C' ) ) THEN
- INFO = -1
- ELSE IF( .NOT.NOTRNB .AND. .NOT.LSAME( TRANB, 'T' ) .AND. .NOT.
- $ LSAME( TRANB, 'C' ) ) THEN
- INFO = -2
- ELSE IF( ISGN.NE.1 .AND. ISGN.NE.-1 ) THEN
- INFO = -3
- ELSE IF( M.LT.0 ) THEN
- INFO = -4
- ELSE IF( N.LT.0 ) THEN
- INFO = -5
- ELSE IF( LDA.LT.MAX( 1, M ) ) THEN
- INFO = -7
- ELSE IF( LDB.LT.MAX( 1, N ) ) THEN
- INFO = -9
- ELSE IF( LDC.LT.MAX( 1, M ) ) THEN
- INFO = -11
- END IF
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'DTRSYL', -INFO )
- RETURN
- END IF
-*
-* Quick return if possible
-*
- IF( M.EQ.0 .OR. N.EQ.0 )
- $ RETURN
-*
-* Set constants to control overflow
-*
- EPS = DLAMCH( 'P' )
- SMLNUM = DLAMCH( 'S' )
- BIGNUM = ONE / SMLNUM
- CALL DLABAD( SMLNUM, BIGNUM )
- SMLNUM = SMLNUM*DBLE( M*N ) / EPS
- BIGNUM = ONE / SMLNUM
-*
- SMIN = MAX( SMLNUM, EPS*DLANGE( 'M', M, M, A, LDA, DUM ),
- $ EPS*DLANGE( 'M', N, N, B, LDB, DUM ) )
-*
- SCALE = ONE
- SGN = ISGN
-*
- IF( NOTRNA .AND. NOTRNB ) THEN
-*
-* Solve A*X + ISGN*X*B = scale*C.
-*
-* The (K,L)th block of X is determined starting from
-* bottom-left corner column by column by
-*
-* A(K,K)*X(K,L) + ISGN*X(K,L)*B(L,L) = C(K,L) - R(K,L)
-*
-* Where
-* M L-1
-* R(K,L) = SUM [A(K,I)*X(I,L)] + ISGN*SUM [X(K,J)*B(J,L)].
-* I=K+1 J=1
-*
-* Start column loop (index = L)
-* L1 (L2) : column index of the first (first) row of X(K,L).
-*
- LNEXT = 1
- DO 60 L = 1, N
- IF( L.LT.LNEXT )
- $ GO TO 60
- IF( L.EQ.N ) THEN
- L1 = L
- L2 = L
- ELSE
- IF( B( L+1, L ).NE.ZERO ) THEN
- L1 = L
- L2 = L + 1
- LNEXT = L + 2
- ELSE
- L1 = L
- L2 = L
- LNEXT = L + 1
- END IF
- END IF
-*
-* Start row loop (index = K)
-* K1 (K2): row index of the first (last) row of X(K,L).
-*
- KNEXT = M
- DO 50 K = M, 1, -1
- IF( K.GT.KNEXT )
- $ GO TO 50
- IF( K.EQ.1 ) THEN
- K1 = K
- K2 = K
- ELSE
- IF( A( K, K-1 ).NE.ZERO ) THEN
- K1 = K - 1
- K2 = K
- KNEXT = K - 2
- ELSE
- K1 = K
- K2 = K
- KNEXT = K - 1
- END IF
- END IF
-*
- IF( L1.EQ.L2 .AND. K1.EQ.K2 ) THEN
- SUML = DDOT( M-K1, A( K1, MIN( K1+1, M ) ), LDA,
- $ C( MIN( K1+1, M ), L1 ), 1 )
- SUMR = DDOT( L1-1, C( K1, 1 ), LDC, B( 1, L1 ), 1 )
- VEC( 1, 1 ) = C( K1, L1 ) - ( SUML+SGN*SUMR )
- SCALOC = ONE
-*
- A11 = A( K1, K1 ) + SGN*B( L1, L1 )
- DA11 = ABS( A11 )
- IF( DA11.LE.SMIN ) THEN
- A11 = SMIN
- DA11 = SMIN
- INFO = 1
- END IF
- DB = ABS( VEC( 1, 1 ) )
- IF( DA11.LT.ONE .AND. DB.GT.ONE ) THEN
- IF( DB.GT.BIGNUM*DA11 )
- $ SCALOC = ONE / DB
- END IF
- X( 1, 1 ) = ( VEC( 1, 1 )*SCALOC ) / A11
-*
- IF( SCALOC.NE.ONE ) THEN
- DO 10 J = 1, N
- CALL DSCAL( M, SCALOC, C( 1, J ), 1 )
- 10 CONTINUE
- SCALE = SCALE*SCALOC
- END IF
- C( K1, L1 ) = X( 1, 1 )
-*
- ELSE IF( L1.EQ.L2 .AND. K1.NE.K2 ) THEN
-*
- SUML = DDOT( M-K2, A( K1, MIN( K2+1, M ) ), LDA,
- $ C( MIN( K2+1, M ), L1 ), 1 )
- SUMR = DDOT( L1-1, C( K1, 1 ), LDC, B( 1, L1 ), 1 )
- VEC( 1, 1 ) = C( K1, L1 ) - ( SUML+SGN*SUMR )
-*
- SUML = DDOT( M-K2, A( K2, MIN( K2+1, M ) ), LDA,
- $ C( MIN( K2+1, M ), L1 ), 1 )
- SUMR = DDOT( L1-1, C( K2, 1 ), LDC, B( 1, L1 ), 1 )
- VEC( 2, 1 ) = C( K2, L1 ) - ( SUML+SGN*SUMR )
-*
- CALL DLALN2( .FALSE., 2, 1, SMIN, ONE, A( K1, K1 ),
- $ LDA, ONE, ONE, VEC, 2, -SGN*B( L1, L1 ),
- $ ZERO, X, 2, SCALOC, XNORM, IERR )
- IF( IERR.NE.0 )
- $ INFO = 1
-*
- IF( SCALOC.NE.ONE ) THEN
- DO 20 J = 1, N
- CALL DSCAL( M, SCALOC, C( 1, J ), 1 )
- 20 CONTINUE
- SCALE = SCALE*SCALOC
- END IF
- C( K1, L1 ) = X( 1, 1 )
- C( K2, L1 ) = X( 2, 1 )
-*
- ELSE IF( L1.NE.L2 .AND. K1.EQ.K2 ) THEN
-*
- SUML = DDOT( M-K1, A( K1, MIN( K1+1, M ) ), LDA,
- $ C( MIN( K1+1, M ), L1 ), 1 )
- SUMR = DDOT( L1-1, C( K1, 1 ), LDC, B( 1, L1 ), 1 )
- VEC( 1, 1 ) = SGN*( C( K1, L1 )-( SUML+SGN*SUMR ) )
-*
- SUML = DDOT( M-K1, A( K1, MIN( K1+1, M ) ), LDA,
- $ C( MIN( K1+1, M ), L2 ), 1 )
- SUMR = DDOT( L1-1, C( K1, 1 ), LDC, B( 1, L2 ), 1 )
- VEC( 2, 1 ) = SGN*( C( K1, L2 )-( SUML+SGN*SUMR ) )
-*
- CALL DLALN2( .TRUE., 2, 1, SMIN, ONE, B( L1, L1 ),
- $ LDB, ONE, ONE, VEC, 2, -SGN*A( K1, K1 ),
- $ ZERO, X, 2, SCALOC, XNORM, IERR )
- IF( IERR.NE.0 )
- $ INFO = 1
-*
- IF( SCALOC.NE.ONE ) THEN
- DO 30 J = 1, N
- CALL DSCAL( M, SCALOC, C( 1, J ), 1 )
- 30 CONTINUE
- SCALE = SCALE*SCALOC
- END IF
- C( K1, L1 ) = X( 1, 1 )
- C( K1, L2 ) = X( 2, 1 )
-*
- ELSE IF( L1.NE.L2 .AND. K1.NE.K2 ) THEN
-*
- SUML = DDOT( M-K2, A( K1, MIN( K2+1, M ) ), LDA,
- $ C( MIN( K2+1, M ), L1 ), 1 )
- SUMR = DDOT( L1-1, C( K1, 1 ), LDC, B( 1, L1 ), 1 )
- VEC( 1, 1 ) = C( K1, L1 ) - ( SUML+SGN*SUMR )
-*
- SUML = DDOT( M-K2, A( K1, MIN( K2+1, M ) ), LDA,
- $ C( MIN( K2+1, M ), L2 ), 1 )
- SUMR = DDOT( L1-1, C( K1, 1 ), LDC, B( 1, L2 ), 1 )
- VEC( 1, 2 ) = C( K1, L2 ) - ( SUML+SGN*SUMR )
-*
- SUML = DDOT( M-K2, A( K2, MIN( K2+1, M ) ), LDA,
- $ C( MIN( K2+1, M ), L1 ), 1 )
- SUMR = DDOT( L1-1, C( K2, 1 ), LDC, B( 1, L1 ), 1 )
- VEC( 2, 1 ) = C( K2, L1 ) - ( SUML+SGN*SUMR )
-*
- SUML = DDOT( M-K2, A( K2, MIN( K2+1, M ) ), LDA,
- $ C( MIN( K2+1, M ), L2 ), 1 )
- SUMR = DDOT( L1-1, C( K2, 1 ), LDC, B( 1, L2 ), 1 )
- VEC( 2, 2 ) = C( K2, L2 ) - ( SUML+SGN*SUMR )
-*
- CALL DLASY2( .FALSE., .FALSE., ISGN, 2, 2,
- $ A( K1, K1 ), LDA, B( L1, L1 ), LDB, VEC,
- $ 2, SCALOC, X, 2, XNORM, IERR )
- IF( IERR.NE.0 )
- $ INFO = 1
-*
- IF( SCALOC.NE.ONE ) THEN
- DO 40 J = 1, N
- CALL DSCAL( M, SCALOC, C( 1, J ), 1 )
- 40 CONTINUE
- SCALE = SCALE*SCALOC
- END IF
- C( K1, L1 ) = X( 1, 1 )
- C( K1, L2 ) = X( 1, 2 )
- C( K2, L1 ) = X( 2, 1 )
- C( K2, L2 ) = X( 2, 2 )
- END IF
-*
- 50 CONTINUE
-*
- 60 CONTINUE
-*
- ELSE IF( .NOT.NOTRNA .AND. NOTRNB ) THEN
-*
-* Solve A' *X + ISGN*X*B = scale*C.
-*
-* The (K,L)th block of X is determined starting from
-* upper-left corner column by column by
-*
-* A(K,K)'*X(K,L) + ISGN*X(K,L)*B(L,L) = C(K,L) - R(K,L)
-*
-* Where
-* K-1 L-1
-* R(K,L) = SUM [A(I,K)'*X(I,L)] +ISGN*SUM [X(K,J)*B(J,L)]
-* I=1 J=1
-*
-* Start column loop (index = L)
-* L1 (L2): column index of the first (last) row of X(K,L)
-*
- LNEXT = 1
- DO 120 L = 1, N
- IF( L.LT.LNEXT )
- $ GO TO 120
- IF( L.EQ.N ) THEN
- L1 = L
- L2 = L
- ELSE
- IF( B( L+1, L ).NE.ZERO ) THEN
- L1 = L
- L2 = L + 1
- LNEXT = L + 2
- ELSE
- L1 = L
- L2 = L
- LNEXT = L + 1
- END IF
- END IF
-*
-* Start row loop (index = K)
-* K1 (K2): row index of the first (last) row of X(K,L)
-*
- KNEXT = 1
- DO 110 K = 1, M
- IF( K.LT.KNEXT )
- $ GO TO 110
- IF( K.EQ.M ) THEN
- K1 = K
- K2 = K
- ELSE
- IF( A( K+1, K ).NE.ZERO ) THEN
- K1 = K
- K2 = K + 1
- KNEXT = K + 2
- ELSE
- K1 = K
- K2 = K
- KNEXT = K + 1
- END IF
- END IF
-*
- IF( L1.EQ.L2 .AND. K1.EQ.K2 ) THEN
- SUML = DDOT( K1-1, A( 1, K1 ), 1, C( 1, L1 ), 1 )
- SUMR = DDOT( L1-1, C( K1, 1 ), LDC, B( 1, L1 ), 1 )
- VEC( 1, 1 ) = C( K1, L1 ) - ( SUML+SGN*SUMR )
- SCALOC = ONE
-*
- A11 = A( K1, K1 ) + SGN*B( L1, L1 )
- DA11 = ABS( A11 )
- IF( DA11.LE.SMIN ) THEN
- A11 = SMIN
- DA11 = SMIN
- INFO = 1
- END IF
- DB = ABS( VEC( 1, 1 ) )
- IF( DA11.LT.ONE .AND. DB.GT.ONE ) THEN
- IF( DB.GT.BIGNUM*DA11 )
- $ SCALOC = ONE / DB
- END IF
- X( 1, 1 ) = ( VEC( 1, 1 )*SCALOC ) / A11
-*
- IF( SCALOC.NE.ONE ) THEN
- DO 70 J = 1, N
- CALL DSCAL( M, SCALOC, C( 1, J ), 1 )
- 70 CONTINUE
- SCALE = SCALE*SCALOC
- END IF
- C( K1, L1 ) = X( 1, 1 )
-*
- ELSE IF( L1.EQ.L2 .AND. K1.NE.K2 ) THEN
-*
- SUML = DDOT( K1-1, A( 1, K1 ), 1, C( 1, L1 ), 1 )
- SUMR = DDOT( L1-1, C( K1, 1 ), LDC, B( 1, L1 ), 1 )
- VEC( 1, 1 ) = C( K1, L1 ) - ( SUML+SGN*SUMR )
-*
- SUML = DDOT( K1-1, A( 1, K2 ), 1, C( 1, L1 ), 1 )
- SUMR = DDOT( L1-1, C( K2, 1 ), LDC, B( 1, L1 ), 1 )
- VEC( 2, 1 ) = C( K2, L1 ) - ( SUML+SGN*SUMR )
-*
- CALL DLALN2( .TRUE., 2, 1, SMIN, ONE, A( K1, K1 ),
- $ LDA, ONE, ONE, VEC, 2, -SGN*B( L1, L1 ),
- $ ZERO, X, 2, SCALOC, XNORM, IERR )
- IF( IERR.NE.0 )
- $ INFO = 1
-*
- IF( SCALOC.NE.ONE ) THEN
- DO 80 J = 1, N
- CALL DSCAL( M, SCALOC, C( 1, J ), 1 )
- 80 CONTINUE
- SCALE = SCALE*SCALOC
- END IF
- C( K1, L1 ) = X( 1, 1 )
- C( K2, L1 ) = X( 2, 1 )
-*
- ELSE IF( L1.NE.L2 .AND. K1.EQ.K2 ) THEN
-*
- SUML = DDOT( K1-1, A( 1, K1 ), 1, C( 1, L1 ), 1 )
- SUMR = DDOT( L1-1, C( K1, 1 ), LDC, B( 1, L1 ), 1 )
- VEC( 1, 1 ) = SGN*( C( K1, L1 )-( SUML+SGN*SUMR ) )
-*
- SUML = DDOT( K1-1, A( 1, K1 ), 1, C( 1, L2 ), 1 )
- SUMR = DDOT( L1-1, C( K1, 1 ), LDC, B( 1, L2 ), 1 )
- VEC( 2, 1 ) = SGN*( C( K1, L2 )-( SUML+SGN*SUMR ) )
-*
- CALL DLALN2( .TRUE., 2, 1, SMIN, ONE, B( L1, L1 ),
- $ LDB, ONE, ONE, VEC, 2, -SGN*A( K1, K1 ),
- $ ZERO, X, 2, SCALOC, XNORM, IERR )
- IF( IERR.NE.0 )
- $ INFO = 1
-*
- IF( SCALOC.NE.ONE ) THEN
- DO 90 J = 1, N
- CALL DSCAL( M, SCALOC, C( 1, J ), 1 )
- 90 CONTINUE
- SCALE = SCALE*SCALOC
- END IF
- C( K1, L1 ) = X( 1, 1 )
- C( K1, L2 ) = X( 2, 1 )
-*
- ELSE IF( L1.NE.L2 .AND. K1.NE.K2 ) THEN
-*
- SUML = DDOT( K1-1, A( 1, K1 ), 1, C( 1, L1 ), 1 )
- SUMR = DDOT( L1-1, C( K1, 1 ), LDC, B( 1, L1 ), 1 )
- VEC( 1, 1 ) = C( K1, L1 ) - ( SUML+SGN*SUMR )
-*
- SUML = DDOT( K1-1, A( 1, K1 ), 1, C( 1, L2 ), 1 )
- SUMR = DDOT( L1-1, C( K1, 1 ), LDC, B( 1, L2 ), 1 )
- VEC( 1, 2 ) = C( K1, L2 ) - ( SUML+SGN*SUMR )
-*
- SUML = DDOT( K1-1, A( 1, K2 ), 1, C( 1, L1 ), 1 )
- SUMR = DDOT( L1-1, C( K2, 1 ), LDC, B( 1, L1 ), 1 )
- VEC( 2, 1 ) = C( K2, L1 ) - ( SUML+SGN*SUMR )
-*
- SUML = DDOT( K1-1, A( 1, K2 ), 1, C( 1, L2 ), 1 )
- SUMR = DDOT( L1-1, C( K2, 1 ), LDC, B( 1, L2 ), 1 )
- VEC( 2, 2 ) = C( K2, L2 ) - ( SUML+SGN*SUMR )
-*
- CALL DLASY2( .TRUE., .FALSE., ISGN, 2, 2, A( K1, K1 ),
- $ LDA, B( L1, L1 ), LDB, VEC, 2, SCALOC, X,
- $ 2, XNORM, IERR )
- IF( IERR.NE.0 )
- $ INFO = 1
-*
- IF( SCALOC.NE.ONE ) THEN
- DO 100 J = 1, N
- CALL DSCAL( M, SCALOC, C( 1, J ), 1 )
- 100 CONTINUE
- SCALE = SCALE*SCALOC
- END IF
- C( K1, L1 ) = X( 1, 1 )
- C( K1, L2 ) = X( 1, 2 )
- C( K2, L1 ) = X( 2, 1 )
- C( K2, L2 ) = X( 2, 2 )
- END IF
-*
- 110 CONTINUE
- 120 CONTINUE
-*
- ELSE IF( .NOT.NOTRNA .AND. .NOT.NOTRNB ) THEN
-*
-* Solve A'*X + ISGN*X*B' = scale*C.
-*
-* The (K,L)th block of X is determined starting from
-* top-right corner column by column by
-*
-* A(K,K)'*X(K,L) + ISGN*X(K,L)*B(L,L)' = C(K,L) - R(K,L)
-*
-* Where
-* K-1 N
-* R(K,L) = SUM [A(I,K)'*X(I,L)] + ISGN*SUM [X(K,J)*B(L,J)'].
-* I=1 J=L+1
-*
-* Start column loop (index = L)
-* L1 (L2): column index of the first (last) row of X(K,L)
-*
- LNEXT = N
- DO 180 L = N, 1, -1
- IF( L.GT.LNEXT )
- $ GO TO 180
- IF( L.EQ.1 ) THEN
- L1 = L
- L2 = L
- ELSE
- IF( B( L, L-1 ).NE.ZERO ) THEN
- L1 = L - 1
- L2 = L
- LNEXT = L - 2
- ELSE
- L1 = L
- L2 = L
- LNEXT = L - 1
- END IF
- END IF
-*
-* Start row loop (index = K)
-* K1 (K2): row index of the first (last) row of X(K,L)
-*
- KNEXT = 1
- DO 170 K = 1, M
- IF( K.LT.KNEXT )
- $ GO TO 170
- IF( K.EQ.M ) THEN
- K1 = K
- K2 = K
- ELSE
- IF( A( K+1, K ).NE.ZERO ) THEN
- K1 = K
- K2 = K + 1
- KNEXT = K + 2
- ELSE
- K1 = K
- K2 = K
- KNEXT = K + 1
- END IF
- END IF
-*
- IF( L1.EQ.L2 .AND. K1.EQ.K2 ) THEN
- SUML = DDOT( K1-1, A( 1, K1 ), 1, C( 1, L1 ), 1 )
- SUMR = DDOT( N-L1, C( K1, MIN( L1+1, N ) ), LDC,
- $ B( L1, MIN( L1+1, N ) ), LDB )
- VEC( 1, 1 ) = C( K1, L1 ) - ( SUML+SGN*SUMR )
- SCALOC = ONE
-*
- A11 = A( K1, K1 ) + SGN*B( L1, L1 )
- DA11 = ABS( A11 )
- IF( DA11.LE.SMIN ) THEN
- A11 = SMIN
- DA11 = SMIN
- INFO = 1
- END IF
- DB = ABS( VEC( 1, 1 ) )
- IF( DA11.LT.ONE .AND. DB.GT.ONE ) THEN
- IF( DB.GT.BIGNUM*DA11 )
- $ SCALOC = ONE / DB
- END IF
- X( 1, 1 ) = ( VEC( 1, 1 )*SCALOC ) / A11
-*
- IF( SCALOC.NE.ONE ) THEN
- DO 130 J = 1, N
- CALL DSCAL( M, SCALOC, C( 1, J ), 1 )
- 130 CONTINUE
- SCALE = SCALE*SCALOC
- END IF
- C( K1, L1 ) = X( 1, 1 )
-*
- ELSE IF( L1.EQ.L2 .AND. K1.NE.K2 ) THEN
-*
- SUML = DDOT( K1-1, A( 1, K1 ), 1, C( 1, L1 ), 1 )
- SUMR = DDOT( N-L2, C( K1, MIN( L2+1, N ) ), LDC,
- $ B( L1, MIN( L2+1, N ) ), LDB )
- VEC( 1, 1 ) = C( K1, L1 ) - ( SUML+SGN*SUMR )
-*
- SUML = DDOT( K1-1, A( 1, K2 ), 1, C( 1, L1 ), 1 )
- SUMR = DDOT( N-L2, C( K2, MIN( L2+1, N ) ), LDC,
- $ B( L1, MIN( L2+1, N ) ), LDB )
- VEC( 2, 1 ) = C( K2, L1 ) - ( SUML+SGN*SUMR )
-*
- CALL DLALN2( .TRUE., 2, 1, SMIN, ONE, A( K1, K1 ),
- $ LDA, ONE, ONE, VEC, 2, -SGN*B( L1, L1 ),
- $ ZERO, X, 2, SCALOC, XNORM, IERR )
- IF( IERR.NE.0 )
- $ INFO = 1
-*
- IF( SCALOC.NE.ONE ) THEN
- DO 140 J = 1, N
- CALL DSCAL( M, SCALOC, C( 1, J ), 1 )
- 140 CONTINUE
- SCALE = SCALE*SCALOC
- END IF
- C( K1, L1 ) = X( 1, 1 )
- C( K2, L1 ) = X( 2, 1 )
-*
- ELSE IF( L1.NE.L2 .AND. K1.EQ.K2 ) THEN
-*
- SUML = DDOT( K1-1, A( 1, K1 ), 1, C( 1, L1 ), 1 )
- SUMR = DDOT( N-L2, C( K1, MIN( L2+1, N ) ), LDC,
- $ B( L1, MIN( L2+1, N ) ), LDB )
- VEC( 1, 1 ) = SGN*( C( K1, L1 )-( SUML+SGN*SUMR ) )
-*
- SUML = DDOT( K1-1, A( 1, K1 ), 1, C( 1, L2 ), 1 )
- SUMR = DDOT( N-L2, C( K1, MIN( L2+1, N ) ), LDC,
- $ B( L2, MIN( L2+1, N ) ), LDB )
- VEC( 2, 1 ) = SGN*( C( K1, L2 )-( SUML+SGN*SUMR ) )
-*
- CALL DLALN2( .FALSE., 2, 1, SMIN, ONE, B( L1, L1 ),
- $ LDB, ONE, ONE, VEC, 2, -SGN*A( K1, K1 ),
- $ ZERO, X, 2, SCALOC, XNORM, IERR )
- IF( IERR.NE.0 )
- $ INFO = 1
-*
- IF( SCALOC.NE.ONE ) THEN
- DO 150 J = 1, N
- CALL DSCAL( M, SCALOC, C( 1, J ), 1 )
- 150 CONTINUE
- SCALE = SCALE*SCALOC
- END IF
- C( K1, L1 ) = X( 1, 1 )
- C( K1, L2 ) = X( 2, 1 )
-*
- ELSE IF( L1.NE.L2 .AND. K1.NE.K2 ) THEN
-*
- SUML = DDOT( K1-1, A( 1, K1 ), 1, C( 1, L1 ), 1 )
- SUMR = DDOT( N-L2, C( K1, MIN( L2+1, N ) ), LDC,
- $ B( L1, MIN( L2+1, N ) ), LDB )
- VEC( 1, 1 ) = C( K1, L1 ) - ( SUML+SGN*SUMR )
-*
- SUML = DDOT( K1-1, A( 1, K1 ), 1, C( 1, L2 ), 1 )
- SUMR = DDOT( N-L2, C( K1, MIN( L2+1, N ) ), LDC,
- $ B( L2, MIN( L2+1, N ) ), LDB )
- VEC( 1, 2 ) = C( K1, L2 ) - ( SUML+SGN*SUMR )
-*
- SUML = DDOT( K1-1, A( 1, K2 ), 1, C( 1, L1 ), 1 )
- SUMR = DDOT( N-L2, C( K2, MIN( L2+1, N ) ), LDC,
- $ B( L1, MIN( L2+1, N ) ), LDB )
- VEC( 2, 1 ) = C( K2, L1 ) - ( SUML+SGN*SUMR )
-*
- SUML = DDOT( K1-1, A( 1, K2 ), 1, C( 1, L2 ), 1 )
- SUMR = DDOT( N-L2, C( K2, MIN( L2+1, N ) ), LDC,
- $ B( L2, MIN( L2+1, N ) ), LDB )
- VEC( 2, 2 ) = C( K2, L2 ) - ( SUML+SGN*SUMR )
-*
- CALL DLASY2( .TRUE., .TRUE., ISGN, 2, 2, A( K1, K1 ),
- $ LDA, B( L1, L1 ), LDB, VEC, 2, SCALOC, X,
- $ 2, XNORM, IERR )
- IF( IERR.NE.0 )
- $ INFO = 1
-*
- IF( SCALOC.NE.ONE ) THEN
- DO 160 J = 1, N
- CALL DSCAL( M, SCALOC, C( 1, J ), 1 )
- 160 CONTINUE
- SCALE = SCALE*SCALOC
- END IF
- C( K1, L1 ) = X( 1, 1 )
- C( K1, L2 ) = X( 1, 2 )
- C( K2, L1 ) = X( 2, 1 )
- C( K2, L2 ) = X( 2, 2 )
- END IF
-*
- 170 CONTINUE
- 180 CONTINUE
-*
- ELSE IF( NOTRNA .AND. .NOT.NOTRNB ) THEN
-*
-* Solve A*X + ISGN*X*B' = scale*C.
-*
-* The (K,L)th block of X is determined starting from
-* bottom-right corner column by column by
-*
-* A(K,K)*X(K,L) + ISGN*X(K,L)*B(L,L)' = C(K,L) - R(K,L)
-*
-* Where
-* M N
-* R(K,L) = SUM [A(K,I)*X(I,L)] + ISGN*SUM [X(K,J)*B(L,J)'].
-* I=K+1 J=L+1
-*
-* Start column loop (index = L)
-* L1 (L2): column index of the first (last) row of X(K,L)
-*
- LNEXT = N
- DO 240 L = N, 1, -1
- IF( L.GT.LNEXT )
- $ GO TO 240
- IF( L.EQ.1 ) THEN
- L1 = L
- L2 = L
- ELSE
- IF( B( L, L-1 ).NE.ZERO ) THEN
- L1 = L - 1
- L2 = L
- LNEXT = L - 2
- ELSE
- L1 = L
- L2 = L
- LNEXT = L - 1
- END IF
- END IF
-*
-* Start row loop (index = K)
-* K1 (K2): row index of the first (last) row of X(K,L)
-*
- KNEXT = M
- DO 230 K = M, 1, -1
- IF( K.GT.KNEXT )
- $ GO TO 230
- IF( K.EQ.1 ) THEN
- K1 = K
- K2 = K
- ELSE
- IF( A( K, K-1 ).NE.ZERO ) THEN
- K1 = K - 1
- K2 = K
- KNEXT = K - 2
- ELSE
- K1 = K
- K2 = K
- KNEXT = K - 1
- END IF
- END IF
-*
- IF( L1.EQ.L2 .AND. K1.EQ.K2 ) THEN
- SUML = DDOT( M-K1, A( K1, MIN( K1+1, M ) ), LDA,
- $ C( MIN( K1+1, M ), L1 ), 1 )
- SUMR = DDOT( N-L1, C( K1, MIN( L1+1, N ) ), LDC,
- $ B( L1, MIN( L1+1, N ) ), LDB )
- VEC( 1, 1 ) = C( K1, L1 ) - ( SUML+SGN*SUMR )
- SCALOC = ONE
-*
- A11 = A( K1, K1 ) + SGN*B( L1, L1 )
- DA11 = ABS( A11 )
- IF( DA11.LE.SMIN ) THEN
- A11 = SMIN
- DA11 = SMIN
- INFO = 1
- END IF
- DB = ABS( VEC( 1, 1 ) )
- IF( DA11.LT.ONE .AND. DB.GT.ONE ) THEN
- IF( DB.GT.BIGNUM*DA11 )
- $ SCALOC = ONE / DB
- END IF
- X( 1, 1 ) = ( VEC( 1, 1 )*SCALOC ) / A11
-*
- IF( SCALOC.NE.ONE ) THEN
- DO 190 J = 1, N
- CALL DSCAL( M, SCALOC, C( 1, J ), 1 )
- 190 CONTINUE
- SCALE = SCALE*SCALOC
- END IF
- C( K1, L1 ) = X( 1, 1 )
-*
- ELSE IF( L1.EQ.L2 .AND. K1.NE.K2 ) THEN
-*
- SUML = DDOT( M-K2, A( K1, MIN( K2+1, M ) ), LDA,
- $ C( MIN( K2+1, M ), L1 ), 1 )
- SUMR = DDOT( N-L2, C( K1, MIN( L2+1, N ) ), LDC,
- $ B( L1, MIN( L2+1, N ) ), LDB )
- VEC( 1, 1 ) = C( K1, L1 ) - ( SUML+SGN*SUMR )
-*
- SUML = DDOT( M-K2, A( K2, MIN( K2+1, M ) ), LDA,
- $ C( MIN( K2+1, M ), L1 ), 1 )
- SUMR = DDOT( N-L2, C( K2, MIN( L2+1, N ) ), LDC,
- $ B( L1, MIN( L2+1, N ) ), LDB )
- VEC( 2, 1 ) = C( K2, L1 ) - ( SUML+SGN*SUMR )
-*
- CALL DLALN2( .FALSE., 2, 1, SMIN, ONE, A( K1, K1 ),
- $ LDA, ONE, ONE, VEC, 2, -SGN*B( L1, L1 ),
- $ ZERO, X, 2, SCALOC, XNORM, IERR )
- IF( IERR.NE.0 )
- $ INFO = 1
-*
- IF( SCALOC.NE.ONE ) THEN
- DO 200 J = 1, N
- CALL DSCAL( M, SCALOC, C( 1, J ), 1 )
- 200 CONTINUE
- SCALE = SCALE*SCALOC
- END IF
- C( K1, L1 ) = X( 1, 1 )
- C( K2, L1 ) = X( 2, 1 )
-*
- ELSE IF( L1.NE.L2 .AND. K1.EQ.K2 ) THEN
-*
- SUML = DDOT( M-K1, A( K1, MIN( K1+1, M ) ), LDA,
- $ C( MIN( K1+1, M ), L1 ), 1 )
- SUMR = DDOT( N-L2, C( K1, MIN( L2+1, N ) ), LDC,
- $ B( L1, MIN( L2+1, N ) ), LDB )
- VEC( 1, 1 ) = SGN*( C( K1, L1 )-( SUML+SGN*SUMR ) )
-*
- SUML = DDOT( M-K1, A( K1, MIN( K1+1, M ) ), LDA,
- $ C( MIN( K1+1, M ), L2 ), 1 )
- SUMR = DDOT( N-L2, C( K1, MIN( L2+1, N ) ), LDC,
- $ B( L2, MIN( L2+1, N ) ), LDB )
- VEC( 2, 1 ) = SGN*( C( K1, L2 )-( SUML+SGN*SUMR ) )
-*
- CALL DLALN2( .FALSE., 2, 1, SMIN, ONE, B( L1, L1 ),
- $ LDB, ONE, ONE, VEC, 2, -SGN*A( K1, K1 ),
- $ ZERO, X, 2, SCALOC, XNORM, IERR )
- IF( IERR.NE.0 )
- $ INFO = 1
-*
- IF( SCALOC.NE.ONE ) THEN
- DO 210 J = 1, N
- CALL DSCAL( M, SCALOC, C( 1, J ), 1 )
- 210 CONTINUE
- SCALE = SCALE*SCALOC
- END IF
- C( K1, L1 ) = X( 1, 1 )
- C( K1, L2 ) = X( 2, 1 )
-*
- ELSE IF( L1.NE.L2 .AND. K1.NE.K2 ) THEN
-*
- SUML = DDOT( M-K2, A( K1, MIN( K2+1, M ) ), LDA,
- $ C( MIN( K2+1, M ), L1 ), 1 )
- SUMR = DDOT( N-L2, C( K1, MIN( L2+1, N ) ), LDC,
- $ B( L1, MIN( L2+1, N ) ), LDB )
- VEC( 1, 1 ) = C( K1, L1 ) - ( SUML+SGN*SUMR )
-*
- SUML = DDOT( M-K2, A( K1, MIN( K2+1, M ) ), LDA,
- $ C( MIN( K2+1, M ), L2 ), 1 )
- SUMR = DDOT( N-L2, C( K1, MIN( L2+1, N ) ), LDC,
- $ B( L2, MIN( L2+1, N ) ), LDB )
- VEC( 1, 2 ) = C( K1, L2 ) - ( SUML+SGN*SUMR )
-*
- SUML = DDOT( M-K2, A( K2, MIN( K2+1, M ) ), LDA,
- $ C( MIN( K2+1, M ), L1 ), 1 )
- SUMR = DDOT( N-L2, C( K2, MIN( L2+1, N ) ), LDC,
- $ B( L1, MIN( L2+1, N ) ), LDB )
- VEC( 2, 1 ) = C( K2, L1 ) - ( SUML+SGN*SUMR )
-*
- SUML = DDOT( M-K2, A( K2, MIN( K2+1, M ) ), LDA,
- $ C( MIN( K2+1, M ), L2 ), 1 )
- SUMR = DDOT( N-L2, C( K2, MIN( L2+1, N ) ), LDC,
- $ B( L2, MIN( L2+1, N ) ), LDB )
- VEC( 2, 2 ) = C( K2, L2 ) - ( SUML+SGN*SUMR )
-*
- CALL DLASY2( .FALSE., .TRUE., ISGN, 2, 2, A( K1, K1 ),
- $ LDA, B( L1, L1 ), LDB, VEC, 2, SCALOC, X,
- $ 2, XNORM, IERR )
- IF( IERR.NE.0 )
- $ INFO = 1
-*
- IF( SCALOC.NE.ONE ) THEN
- DO 220 J = 1, N
- CALL DSCAL( M, SCALOC, C( 1, J ), 1 )
- 220 CONTINUE
- SCALE = SCALE*SCALOC
- END IF
- C( K1, L1 ) = X( 1, 1 )
- C( K1, L2 ) = X( 1, 2 )
- C( K2, L1 ) = X( 2, 1 )
- C( K2, L2 ) = X( 2, 2 )
- END IF
-*
- 230 CONTINUE
- 240 CONTINUE
-*
- END IF
-*
- RETURN
-*
-* End of DTRSYL
-*
- END
diff --git a/src/lib/lapack/dtrti2.f b/src/lib/lapack/dtrti2.f
deleted file mode 100644
index e7ae764d..00000000
--- a/src/lib/lapack/dtrti2.f
+++ /dev/null
@@ -1,146 +0,0 @@
- SUBROUTINE DTRTI2( UPLO, DIAG, N, A, LDA, INFO )
-*
-* -- LAPACK routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- CHARACTER DIAG, UPLO
- INTEGER INFO, LDA, N
-* ..
-* .. Array Arguments ..
- DOUBLE PRECISION A( LDA, * )
-* ..
-*
-* Purpose
-* =======
-*
-* DTRTI2 computes the inverse of a real upper or lower triangular
-* matrix.
-*
-* This is the Level 2 BLAS version of the algorithm.
-*
-* Arguments
-* =========
-*
-* UPLO (input) CHARACTER*1
-* Specifies whether the matrix A is upper or lower triangular.
-* = 'U': Upper triangular
-* = 'L': Lower triangular
-*
-* DIAG (input) CHARACTER*1
-* Specifies whether or not the matrix A is unit triangular.
-* = 'N': Non-unit triangular
-* = 'U': Unit triangular
-*
-* N (input) INTEGER
-* The order of the matrix A. N >= 0.
-*
-* A (input/output) DOUBLE PRECISION array, dimension (LDA,N)
-* On entry, the triangular matrix A. If UPLO = 'U', the
-* leading n by n upper triangular part of the array A contains
-* the upper triangular matrix, and the strictly lower
-* triangular part of A is not referenced. If UPLO = 'L', the
-* leading n by n lower triangular part of the array A contains
-* the lower triangular matrix, and the strictly upper
-* triangular part of A is not referenced. If DIAG = 'U', the
-* diagonal elements of A are also not referenced and are
-* assumed to be 1.
-*
-* On exit, the (triangular) inverse of the original matrix, in
-* the same storage format.
-*
-* LDA (input) INTEGER
-* The leading dimension of the array A. LDA >= max(1,N).
-*
-* INFO (output) INTEGER
-* = 0: successful exit
-* < 0: if INFO = -k, the k-th argument had an illegal value
-*
-* =====================================================================
-*
-* .. Parameters ..
- DOUBLE PRECISION ONE
- PARAMETER ( ONE = 1.0D+0 )
-* ..
-* .. Local Scalars ..
- LOGICAL NOUNIT, UPPER
- INTEGER J
- DOUBLE PRECISION AJJ
-* ..
-* .. External Functions ..
- LOGICAL LSAME
- EXTERNAL LSAME
-* ..
-* .. External Subroutines ..
- EXTERNAL DSCAL, DTRMV, XERBLA
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC MAX
-* ..
-* .. Executable Statements ..
-*
-* Test the input parameters.
-*
- INFO = 0
- UPPER = LSAME( UPLO, 'U' )
- NOUNIT = LSAME( DIAG, 'N' )
- IF( .NOT.UPPER .AND. .NOT.LSAME( UPLO, 'L' ) ) THEN
- INFO = -1
- ELSE IF( .NOT.NOUNIT .AND. .NOT.LSAME( DIAG, 'U' ) ) THEN
- INFO = -2
- ELSE IF( N.LT.0 ) THEN
- INFO = -3
- ELSE IF( LDA.LT.MAX( 1, N ) ) THEN
- INFO = -5
- END IF
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'DTRTI2', -INFO )
- RETURN
- END IF
-*
- IF( UPPER ) THEN
-*
-* Compute inverse of upper triangular matrix.
-*
- DO 10 J = 1, N
- IF( NOUNIT ) THEN
- A( J, J ) = ONE / A( J, J )
- AJJ = -A( J, J )
- ELSE
- AJJ = -ONE
- END IF
-*
-* Compute elements 1:j-1 of j-th column.
-*
- CALL DTRMV( 'Upper', 'No transpose', DIAG, J-1, A, LDA,
- $ A( 1, J ), 1 )
- CALL DSCAL( J-1, AJJ, A( 1, J ), 1 )
- 10 CONTINUE
- ELSE
-*
-* Compute inverse of lower triangular matrix.
-*
- DO 20 J = N, 1, -1
- IF( NOUNIT ) THEN
- A( J, J ) = ONE / A( J, J )
- AJJ = -A( J, J )
- ELSE
- AJJ = -ONE
- END IF
- IF( J.LT.N ) THEN
-*
-* Compute elements j+1:n of j-th column.
-*
- CALL DTRMV( 'Lower', 'No transpose', DIAG, N-J,
- $ A( J+1, J+1 ), LDA, A( J+1, J ), 1 )
- CALL DSCAL( N-J, AJJ, A( J+1, J ), 1 )
- END IF
- 20 CONTINUE
- END IF
-*
- RETURN
-*
-* End of DTRTI2
-*
- END
diff --git a/src/lib/lapack/dtrtri.f b/src/lib/lapack/dtrtri.f
deleted file mode 100644
index 375813c6..00000000
--- a/src/lib/lapack/dtrtri.f
+++ /dev/null
@@ -1,176 +0,0 @@
- SUBROUTINE DTRTRI( UPLO, DIAG, N, A, LDA, INFO )
-*
-* -- LAPACK routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- CHARACTER DIAG, UPLO
- INTEGER INFO, LDA, N
-* ..
-* .. Array Arguments ..
- DOUBLE PRECISION A( LDA, * )
-* ..
-*
-* Purpose
-* =======
-*
-* DTRTRI computes the inverse of a real upper or lower triangular
-* matrix A.
-*
-* This is the Level 3 BLAS version of the algorithm.
-*
-* Arguments
-* =========
-*
-* UPLO (input) CHARACTER*1
-* = 'U': A is upper triangular;
-* = 'L': A is lower triangular.
-*
-* DIAG (input) CHARACTER*1
-* = 'N': A is non-unit triangular;
-* = 'U': A is unit triangular.
-*
-* N (input) INTEGER
-* The order of the matrix A. N >= 0.
-*
-* A (input/output) DOUBLE PRECISION array, dimension (LDA,N)
-* On entry, the triangular matrix A. If UPLO = 'U', the
-* leading N-by-N upper triangular part of the array A contains
-* the upper triangular matrix, and the strictly lower
-* triangular part of A is not referenced. If UPLO = 'L', the
-* leading N-by-N lower triangular part of the array A contains
-* the lower triangular matrix, and the strictly upper
-* triangular part of A is not referenced. If DIAG = 'U', the
-* diagonal elements of A are also not referenced and are
-* assumed to be 1.
-* On exit, the (triangular) inverse of the original matrix, in
-* the same storage format.
-*
-* LDA (input) INTEGER
-* The leading dimension of the array A. LDA >= max(1,N).
-*
-* INFO (output) INTEGER
-* = 0: successful exit
-* < 0: if INFO = -i, the i-th argument had an illegal value
-* > 0: if INFO = i, A(i,i) is exactly zero. The triangular
-* matrix is singular and its inverse can not be computed.
-*
-* =====================================================================
-*
-* .. Parameters ..
- DOUBLE PRECISION ONE, ZERO
- PARAMETER ( ONE = 1.0D+0, ZERO = 0.0D+0 )
-* ..
-* .. Local Scalars ..
- LOGICAL NOUNIT, UPPER
- INTEGER J, JB, NB, NN
-* ..
-* .. External Functions ..
- LOGICAL LSAME
- INTEGER ILAENV
- EXTERNAL LSAME, ILAENV
-* ..
-* .. External Subroutines ..
- EXTERNAL DTRMM, DTRSM, DTRTI2, XERBLA
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC MAX, MIN
-* ..
-* .. Executable Statements ..
-*
-* Test the input parameters.
-*
- INFO = 0
- UPPER = LSAME( UPLO, 'U' )
- NOUNIT = LSAME( DIAG, 'N' )
- IF( .NOT.UPPER .AND. .NOT.LSAME( UPLO, 'L' ) ) THEN
- INFO = -1
- ELSE IF( .NOT.NOUNIT .AND. .NOT.LSAME( DIAG, 'U' ) ) THEN
- INFO = -2
- ELSE IF( N.LT.0 ) THEN
- INFO = -3
- ELSE IF( LDA.LT.MAX( 1, N ) ) THEN
- INFO = -5
- END IF
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'DTRTRI', -INFO )
- RETURN
- END IF
-*
-* Quick return if possible
-*
- IF( N.EQ.0 )
- $ RETURN
-*
-* Check for singularity if non-unit.
-*
- IF( NOUNIT ) THEN
- DO 10 INFO = 1, N
- IF( A( INFO, INFO ).EQ.ZERO )
- $ RETURN
- 10 CONTINUE
- INFO = 0
- END IF
-*
-* Determine the block size for this environment.
-*
- NB = ILAENV( 1, 'DTRTRI', UPLO // DIAG, N, -1, -1, -1 )
- IF( NB.LE.1 .OR. NB.GE.N ) THEN
-*
-* Use unblocked code
-*
- CALL DTRTI2( UPLO, DIAG, N, A, LDA, INFO )
- ELSE
-*
-* Use blocked code
-*
- IF( UPPER ) THEN
-*
-* Compute inverse of upper triangular matrix
-*
- DO 20 J = 1, N, NB
- JB = MIN( NB, N-J+1 )
-*
-* Compute rows 1:j-1 of current block column
-*
- CALL DTRMM( 'Left', 'Upper', 'No transpose', DIAG, J-1,
- $ JB, ONE, A, LDA, A( 1, J ), LDA )
- CALL DTRSM( 'Right', 'Upper', 'No transpose', DIAG, J-1,
- $ JB, -ONE, A( J, J ), LDA, A( 1, J ), LDA )
-*
-* Compute inverse of current diagonal block
-*
- CALL DTRTI2( 'Upper', DIAG, JB, A( J, J ), LDA, INFO )
- 20 CONTINUE
- ELSE
-*
-* Compute inverse of lower triangular matrix
-*
- NN = ( ( N-1 ) / NB )*NB + 1
- DO 30 J = NN, 1, -NB
- JB = MIN( NB, N-J+1 )
- IF( J+JB.LE.N ) THEN
-*
-* Compute rows j+jb:n of current block column
-*
- CALL DTRMM( 'Left', 'Lower', 'No transpose', DIAG,
- $ N-J-JB+1, JB, ONE, A( J+JB, J+JB ), LDA,
- $ A( J+JB, J ), LDA )
- CALL DTRSM( 'Right', 'Lower', 'No transpose', DIAG,
- $ N-J-JB+1, JB, -ONE, A( J, J ), LDA,
- $ A( J+JB, J ), LDA )
- END IF
-*
-* Compute inverse of current diagonal block
-*
- CALL DTRTI2( 'Lower', DIAG, JB, A( J, J ), LDA, INFO )
- 30 CONTINUE
- END IF
- END IF
-*
- RETURN
-*
-* End of DTRTRI
-*
- END
diff --git a/src/lib/lapack/dtrtrs.f b/src/lib/lapack/dtrtrs.f
deleted file mode 100644
index 139ea6d4..00000000
--- a/src/lib/lapack/dtrtrs.f
+++ /dev/null
@@ -1,147 +0,0 @@
- SUBROUTINE DTRTRS( UPLO, TRANS, DIAG, N, NRHS, A, LDA, B, LDB,
- $ INFO )
-*
-* -- LAPACK routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- CHARACTER DIAG, TRANS, UPLO
- INTEGER INFO, LDA, LDB, N, NRHS
-* ..
-* .. Array Arguments ..
- DOUBLE PRECISION A( LDA, * ), B( LDB, * )
-* ..
-*
-* Purpose
-* =======
-*
-* DTRTRS solves a triangular system of the form
-*
-* A * X = B or A**T * X = B,
-*
-* where A is a triangular matrix of order N, and B is an N-by-NRHS
-* matrix. A check is made to verify that A is nonsingular.
-*
-* Arguments
-* =========
-*
-* UPLO (input) CHARACTER*1
-* = 'U': A is upper triangular;
-* = 'L': A is lower triangular.
-*
-* TRANS (input) CHARACTER*1
-* Specifies the form of the system of equations:
-* = 'N': A * X = B (No transpose)
-* = 'T': A**T * X = B (Transpose)
-* = 'C': A**H * X = B (Conjugate transpose = Transpose)
-*
-* DIAG (input) CHARACTER*1
-* = 'N': A is non-unit triangular;
-* = 'U': A is unit triangular.
-*
-* N (input) INTEGER
-* The order of the matrix A. N >= 0.
-*
-* NRHS (input) INTEGER
-* The number of right hand sides, i.e., the number of columns
-* of the matrix B. NRHS >= 0.
-*
-* A (input) DOUBLE PRECISION array, dimension (LDA,N)
-* The triangular matrix A. If UPLO = 'U', the leading N-by-N
-* upper triangular part of the array A contains the upper
-* triangular matrix, and the strictly lower triangular part of
-* A is not referenced. If UPLO = 'L', the leading N-by-N lower
-* triangular part of the array A contains the lower triangular
-* matrix, and the strictly upper triangular part of A is not
-* referenced. If DIAG = 'U', the diagonal elements of A are
-* also not referenced and are assumed to be 1.
-*
-* LDA (input) INTEGER
-* The leading dimension of the array A. LDA >= max(1,N).
-*
-* B (input/output) DOUBLE PRECISION array, dimension (LDB,NRHS)
-* On entry, the right hand side matrix B.
-* On exit, if INFO = 0, the solution matrix X.
-*
-* LDB (input) INTEGER
-* The leading dimension of the array B. LDB >= max(1,N).
-*
-* INFO (output) INTEGER
-* = 0: successful exit
-* < 0: if INFO = -i, the i-th argument had an illegal value
-* > 0: if INFO = i, the i-th diagonal element of A is zero,
-* indicating that the matrix is singular and the solutions
-* X have not been computed.
-*
-* =====================================================================
-*
-* .. Parameters ..
- DOUBLE PRECISION ZERO, ONE
- PARAMETER ( ZERO = 0.0D+0, ONE = 1.0D+0 )
-* ..
-* .. Local Scalars ..
- LOGICAL NOUNIT
-* ..
-* .. External Functions ..
- LOGICAL LSAME
- EXTERNAL LSAME
-* ..
-* .. External Subroutines ..
- EXTERNAL DTRSM, XERBLA
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC MAX
-* ..
-* .. Executable Statements ..
-*
-* Test the input parameters.
-*
- INFO = 0
- NOUNIT = LSAME( DIAG, 'N' )
- IF( .NOT.LSAME( UPLO, 'U' ) .AND. .NOT.LSAME( UPLO, 'L' ) ) THEN
- INFO = -1
- ELSE IF( .NOT.LSAME( TRANS, 'N' ) .AND. .NOT.
- $ LSAME( TRANS, 'T' ) .AND. .NOT.LSAME( TRANS, 'C' ) ) THEN
- INFO = -2
- ELSE IF( .NOT.NOUNIT .AND. .NOT.LSAME( DIAG, 'U' ) ) THEN
- INFO = -3
- ELSE IF( N.LT.0 ) THEN
- INFO = -4
- ELSE IF( NRHS.LT.0 ) THEN
- INFO = -5
- ELSE IF( LDA.LT.MAX( 1, N ) ) THEN
- INFO = -7
- ELSE IF( LDB.LT.MAX( 1, N ) ) THEN
- INFO = -9
- END IF
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'DTRTRS', -INFO )
- RETURN
- END IF
-*
-* Quick return if possible
-*
- IF( N.EQ.0 )
- $ RETURN
-*
-* Check for singularity.
-*
- IF( NOUNIT ) THEN
- DO 10 INFO = 1, N
- IF( A( INFO, INFO ).EQ.ZERO )
- $ RETURN
- 10 CONTINUE
- END IF
- INFO = 0
-*
-* Solve A * x = b or A' * x = b.
-*
- CALL DTRSM( 'Left', UPLO, TRANS, DIAG, N, NRHS, ONE, A, LDA, B,
- $ LDB )
-*
- RETURN
-*
-* End of DTRTRS
-*
- END
diff --git a/src/lib/lapack/dtzrqf.f b/src/lib/lapack/dtzrqf.f
deleted file mode 100644
index 5555df38..00000000
--- a/src/lib/lapack/dtzrqf.f
+++ /dev/null
@@ -1,164 +0,0 @@
- SUBROUTINE DTZRQF( M, N, A, LDA, TAU, INFO )
-*
-* -- LAPACK routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- INTEGER INFO, LDA, M, N
-* ..
-* .. Array Arguments ..
- DOUBLE PRECISION A( LDA, * ), TAU( * )
-* ..
-*
-* Purpose
-* =======
-*
-* This routine is deprecated and has been replaced by routine DTZRZF.
-*
-* DTZRQF reduces the M-by-N ( M<=N ) real upper trapezoidal matrix A
-* to upper triangular form by means of orthogonal transformations.
-*
-* The upper trapezoidal matrix A is factored as
-*
-* A = ( R 0 ) * Z,
-*
-* where Z is an N-by-N orthogonal matrix and R is an M-by-M upper
-* triangular matrix.
-*
-* Arguments
-* =========
-*
-* M (input) INTEGER
-* The number of rows of the matrix A. M >= 0.
-*
-* N (input) INTEGER
-* The number of columns of the matrix A. N >= M.
-*
-* A (input/output) DOUBLE PRECISION array, dimension (LDA,N)
-* On entry, the leading M-by-N upper trapezoidal part of the
-* array A must contain the matrix to be factorized.
-* On exit, the leading M-by-M upper triangular part of A
-* contains the upper triangular matrix R, and elements M+1 to
-* N of the first M rows of A, with the array TAU, represent the
-* orthogonal matrix Z as a product of M elementary reflectors.
-*
-* LDA (input) INTEGER
-* The leading dimension of the array A. LDA >= max(1,M).
-*
-* TAU (output) DOUBLE PRECISION array, dimension (M)
-* The scalar factors of the elementary reflectors.
-*
-* INFO (output) INTEGER
-* = 0: successful exit
-* < 0: if INFO = -i, the i-th argument had an illegal value
-*
-* Further Details
-* ===============
-*
-* The factorization is obtained by Householder's method. The kth
-* transformation matrix, Z( k ), which is used to introduce zeros into
-* the ( m - k + 1 )th row of A, is given in the form
-*
-* Z( k ) = ( I 0 ),
-* ( 0 T( k ) )
-*
-* where
-*
-* T( k ) = I - tau*u( k )*u( k )', u( k ) = ( 1 ),
-* ( 0 )
-* ( z( k ) )
-*
-* tau is a scalar and z( k ) is an ( n - m ) element vector.
-* tau and z( k ) are chosen to annihilate the elements of the kth row
-* of X.
-*
-* The scalar tau is returned in the kth element of TAU and the vector
-* u( k ) in the kth row of A, such that the elements of z( k ) are
-* in a( k, m + 1 ), ..., a( k, n ). The elements of R are returned in
-* the upper triangular part of A.
-*
-* Z is given by
-*
-* Z = Z( 1 ) * Z( 2 ) * ... * Z( m ).
-*
-* =====================================================================
-*
-* .. Parameters ..
- DOUBLE PRECISION ONE, ZERO
- PARAMETER ( ONE = 1.0D+0, ZERO = 0.0D+0 )
-* ..
-* .. Local Scalars ..
- INTEGER I, K, M1
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC MAX, MIN
-* ..
-* .. External Subroutines ..
- EXTERNAL DAXPY, DCOPY, DGEMV, DGER, DLARFG, XERBLA
-* ..
-* .. Executable Statements ..
-*
-* Test the input parameters.
-*
- INFO = 0
- IF( M.LT.0 ) THEN
- INFO = -1
- ELSE IF( N.LT.M ) THEN
- INFO = -2
- ELSE IF( LDA.LT.MAX( 1, M ) ) THEN
- INFO = -4
- END IF
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'DTZRQF', -INFO )
- RETURN
- END IF
-*
-* Perform the factorization.
-*
- IF( M.EQ.0 )
- $ RETURN
- IF( M.EQ.N ) THEN
- DO 10 I = 1, N
- TAU( I ) = ZERO
- 10 CONTINUE
- ELSE
- M1 = MIN( M+1, N )
- DO 20 K = M, 1, -1
-*
-* Use a Householder reflection to zero the kth row of A.
-* First set up the reflection.
-*
- CALL DLARFG( N-M+1, A( K, K ), A( K, M1 ), LDA, TAU( K ) )
-*
- IF( ( TAU( K ).NE.ZERO ) .AND. ( K.GT.1 ) ) THEN
-*
-* We now perform the operation A := A*P( k ).
-*
-* Use the first ( k - 1 ) elements of TAU to store a( k ),
-* where a( k ) consists of the first ( k - 1 ) elements of
-* the kth column of A. Also let B denote the first
-* ( k - 1 ) rows of the last ( n - m ) columns of A.
-*
- CALL DCOPY( K-1, A( 1, K ), 1, TAU, 1 )
-*
-* Form w = a( k ) + B*z( k ) in TAU.
-*
- CALL DGEMV( 'No transpose', K-1, N-M, ONE, A( 1, M1 ),
- $ LDA, A( K, M1 ), LDA, ONE, TAU, 1 )
-*
-* Now form a( k ) := a( k ) - tau*w
-* and B := B - tau*w*z( k )'.
-*
- CALL DAXPY( K-1, -TAU( K ), TAU, 1, A( 1, K ), 1 )
- CALL DGER( K-1, N-M, -TAU( K ), TAU, 1, A( K, M1 ), LDA,
- $ A( 1, M1 ), LDA )
- END IF
- 20 CONTINUE
- END IF
-*
- RETURN
-*
-* End of DTZRQF
-*
- END
diff --git a/src/lib/lapack/dtzrzf.f b/src/lib/lapack/dtzrzf.f
deleted file mode 100644
index 378eefe1..00000000
--- a/src/lib/lapack/dtzrzf.f
+++ /dev/null
@@ -1,244 +0,0 @@
- SUBROUTINE DTZRZF( M, N, A, LDA, TAU, WORK, LWORK, INFO )
-*
-* -- LAPACK routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- INTEGER INFO, LDA, LWORK, M, N
-* ..
-* .. Array Arguments ..
- DOUBLE PRECISION A( LDA, * ), TAU( * ), WORK( * )
-* ..
-*
-* Purpose
-* =======
-*
-* DTZRZF reduces the M-by-N ( M<=N ) real upper trapezoidal matrix A
-* to upper triangular form by means of orthogonal transformations.
-*
-* The upper trapezoidal matrix A is factored as
-*
-* A = ( R 0 ) * Z,
-*
-* where Z is an N-by-N orthogonal matrix and R is an M-by-M upper
-* triangular matrix.
-*
-* Arguments
-* =========
-*
-* M (input) INTEGER
-* The number of rows of the matrix A. M >= 0.
-*
-* N (input) INTEGER
-* The number of columns of the matrix A. N >= M.
-*
-* A (input/output) DOUBLE PRECISION array, dimension (LDA,N)
-* On entry, the leading M-by-N upper trapezoidal part of the
-* array A must contain the matrix to be factorized.
-* On exit, the leading M-by-M upper triangular part of A
-* contains the upper triangular matrix R, and elements M+1 to
-* N of the first M rows of A, with the array TAU, represent the
-* orthogonal matrix Z as a product of M elementary reflectors.
-*
-* LDA (input) INTEGER
-* The leading dimension of the array A. LDA >= max(1,M).
-*
-* TAU (output) DOUBLE PRECISION array, dimension (M)
-* The scalar factors of the elementary reflectors.
-*
-* WORK (workspace/output) DOUBLE PRECISION array, dimension (MAX(1,LWORK))
-* On exit, if INFO = 0, WORK(1) returns the optimal LWORK.
-*
-* LWORK (input) INTEGER
-* The dimension of the array WORK. LWORK >= max(1,M).
-* For optimum performance LWORK >= M*NB, where NB is
-* the optimal blocksize.
-*
-* If LWORK = -1, then a workspace query is assumed; the routine
-* only calculates the optimal size of the WORK array, returns
-* this value as the first entry of the WORK array, and no error
-* message related to LWORK is issued by XERBLA.
-*
-* INFO (output) INTEGER
-* = 0: successful exit
-* < 0: if INFO = -i, the i-th argument had an illegal value
-*
-* Further Details
-* ===============
-*
-* Based on contributions by
-* A. Petitet, Computer Science Dept., Univ. of Tenn., Knoxville, USA
-*
-* The factorization is obtained by Householder's method. The kth
-* transformation matrix, Z( k ), which is used to introduce zeros into
-* the ( m - k + 1 )th row of A, is given in the form
-*
-* Z( k ) = ( I 0 ),
-* ( 0 T( k ) )
-*
-* where
-*
-* T( k ) = I - tau*u( k )*u( k )', u( k ) = ( 1 ),
-* ( 0 )
-* ( z( k ) )
-*
-* tau is a scalar and z( k ) is an ( n - m ) element vector.
-* tau and z( k ) are chosen to annihilate the elements of the kth row
-* of X.
-*
-* The scalar tau is returned in the kth element of TAU and the vector
-* u( k ) in the kth row of A, such that the elements of z( k ) are
-* in a( k, m + 1 ), ..., a( k, n ). The elements of R are returned in
-* the upper triangular part of A.
-*
-* Z is given by
-*
-* Z = Z( 1 ) * Z( 2 ) * ... * Z( m ).
-*
-* =====================================================================
-*
-* .. Parameters ..
- DOUBLE PRECISION ZERO
- PARAMETER ( ZERO = 0.0D+0 )
-* ..
-* .. Local Scalars ..
- LOGICAL LQUERY
- INTEGER I, IB, IWS, KI, KK, LDWORK, LWKOPT, M1, MU, NB,
- $ NBMIN, NX
-* ..
-* .. External Subroutines ..
- EXTERNAL DLARZB, DLARZT, DLATRZ, XERBLA
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC MAX, MIN
-* ..
-* .. External Functions ..
- INTEGER ILAENV
- EXTERNAL ILAENV
-* ..
-* .. Executable Statements ..
-*
-* Test the input arguments
-*
- INFO = 0
- LQUERY = ( LWORK.EQ.-1 )
- IF( M.LT.0 ) THEN
- INFO = -1
- ELSE IF( N.LT.M ) THEN
- INFO = -2
- ELSE IF( LDA.LT.MAX( 1, M ) ) THEN
- INFO = -4
- END IF
-*
- IF( INFO.EQ.0 ) THEN
- IF( M.EQ.0 .OR. M.EQ.N ) THEN
- LWKOPT = 1
- ELSE
-*
-* Determine the block size.
-*
- NB = ILAENV( 1, 'DGERQF', ' ', M, N, -1, -1 )
- LWKOPT = M*NB
- END IF
- WORK( 1 ) = LWKOPT
-*
- IF( LWORK.LT.MAX( 1, M ) .AND. .NOT.LQUERY ) THEN
- INFO = -7
- END IF
- END IF
-*
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'DTZRZF', -INFO )
- RETURN
- ELSE IF( LQUERY ) THEN
- RETURN
- END IF
-*
-* Quick return if possible
-*
- IF( M.EQ.0 ) THEN
- RETURN
- ELSE IF( M.EQ.N ) THEN
- DO 10 I = 1, N
- TAU( I ) = ZERO
- 10 CONTINUE
- RETURN
- END IF
-*
- NBMIN = 2
- NX = 1
- IWS = M
- IF( NB.GT.1 .AND. NB.LT.M ) THEN
-*
-* Determine when to cross over from blocked to unblocked code.
-*
- NX = MAX( 0, ILAENV( 3, 'DGERQF', ' ', M, N, -1, -1 ) )
- IF( NX.LT.M ) THEN
-*
-* Determine if workspace is large enough for blocked code.
-*
- LDWORK = M
- IWS = LDWORK*NB
- IF( LWORK.LT.IWS ) THEN
-*
-* Not enough workspace to use optimal NB: reduce NB and
-* determine the minimum value of NB.
-*
- NB = LWORK / LDWORK
- NBMIN = MAX( 2, ILAENV( 2, 'DGERQF', ' ', M, N, -1,
- $ -1 ) )
- END IF
- END IF
- END IF
-*
- IF( NB.GE.NBMIN .AND. NB.LT.M .AND. NX.LT.M ) THEN
-*
-* Use blocked code initially.
-* The last kk rows are handled by the block method.
-*
- M1 = MIN( M+1, N )
- KI = ( ( M-NX-1 ) / NB )*NB
- KK = MIN( M, KI+NB )
-*
- DO 20 I = M - KK + KI + 1, M - KK + 1, -NB
- IB = MIN( M-I+1, NB )
-*
-* Compute the TZ factorization of the current block
-* A(i:i+ib-1,i:n)
-*
- CALL DLATRZ( IB, N-I+1, N-M, A( I, I ), LDA, TAU( I ),
- $ WORK )
- IF( I.GT.1 ) THEN
-*
-* Form the triangular factor of the block reflector
-* H = H(i+ib-1) . . . H(i+1) H(i)
-*
- CALL DLARZT( 'Backward', 'Rowwise', N-M, IB, A( I, M1 ),
- $ LDA, TAU( I ), WORK, LDWORK )
-*
-* Apply H to A(1:i-1,i:n) from the right
-*
- CALL DLARZB( 'Right', 'No transpose', 'Backward',
- $ 'Rowwise', I-1, N-I+1, IB, N-M, A( I, M1 ),
- $ LDA, WORK, LDWORK, A( 1, I ), LDA,
- $ WORK( IB+1 ), LDWORK )
- END IF
- 20 CONTINUE
- MU = I + NB - 1
- ELSE
- MU = M
- END IF
-*
-* Use unblocked code to factor the last or only block
-*
- IF( MU.GT.0 )
- $ CALL DLATRZ( MU, N, N-M, A, LDA, TAU, WORK )
-*
- WORK( 1 ) = LWKOPT
-*
- RETURN
-*
-* End of DTZRZF
-*
- END
diff --git a/src/lib/lapack/dzsum1.f b/src/lib/lapack/dzsum1.f
deleted file mode 100644
index 0b6c60e7..00000000
--- a/src/lib/lapack/dzsum1.f
+++ /dev/null
@@ -1,81 +0,0 @@
- DOUBLE PRECISION FUNCTION DZSUM1( N, CX, INCX )
-*
-* -- LAPACK auxiliary routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- INTEGER INCX, N
-* ..
-* .. Array Arguments ..
- COMPLEX*16 CX( * )
-* ..
-*
-* Purpose
-* =======
-*
-* DZSUM1 takes the sum of the absolute values of a complex
-* vector and returns a double precision result.
-*
-* Based on DZASUM from the Level 1 BLAS.
-* The change is to use the 'genuine' absolute value.
-*
-* Contributed by Nick Higham for use with ZLACON.
-*
-* Arguments
-* =========
-*
-* N (input) INTEGER
-* The number of elements in the vector CX.
-*
-* CX (input) COMPLEX*16 array, dimension (N)
-* The vector whose elements will be summed.
-*
-* INCX (input) INTEGER
-* The spacing between successive values of CX. INCX > 0.
-*
-* =====================================================================
-*
-* .. Local Scalars ..
- INTEGER I, NINCX
- DOUBLE PRECISION STEMP
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC ABS
-* ..
-* .. Executable Statements ..
-*
- DZSUM1 = 0.0D0
- STEMP = 0.0D0
- IF( N.LE.0 )
- $ RETURN
- IF( INCX.EQ.1 )
- $ GO TO 20
-*
-* CODE FOR INCREMENT NOT EQUAL TO 1
-*
- NINCX = N*INCX
- DO 10 I = 1, NINCX, INCX
-*
-* NEXT LINE MODIFIED.
-*
- STEMP = STEMP + ABS( CX( I ) )
- 10 CONTINUE
- DZSUM1 = STEMP
- RETURN
-*
-* CODE FOR INCREMENT EQUAL TO 1
-*
- 20 CONTINUE
- DO 30 I = 1, N
-*
-* NEXT LINE MODIFIED.
-*
- STEMP = STEMP + ABS( CX( I ) )
- 30 CONTINUE
- DZSUM1 = STEMP
- RETURN
-*
-* End of DZSUM1
-*
- END
diff --git a/src/lib/lapack/ieeeck.f b/src/lib/lapack/ieeeck.f
deleted file mode 100644
index ac4aff85..00000000
--- a/src/lib/lapack/ieeeck.f
+++ /dev/null
@@ -1,147 +0,0 @@
- INTEGER FUNCTION IEEECK( ISPEC, ZERO, ONE )
-*
-* -- LAPACK auxiliary routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- INTEGER ISPEC
- REAL ONE, ZERO
-* ..
-*
-* Purpose
-* =======
-*
-* IEEECK is called from the ILAENV to verify that Infinity and
-* possibly NaN arithmetic is safe (i.e. will not trap).
-*
-* Arguments
-* =========
-*
-* ISPEC (input) INTEGER
-* Specifies whether to test just for inifinity arithmetic
-* or whether to test for infinity and NaN arithmetic.
-* = 0: Verify infinity arithmetic only.
-* = 1: Verify infinity and NaN arithmetic.
-*
-* ZERO (input) REAL
-* Must contain the value 0.0
-* This is passed to prevent the compiler from optimizing
-* away this code.
-*
-* ONE (input) REAL
-* Must contain the value 1.0
-* This is passed to prevent the compiler from optimizing
-* away this code.
-*
-* RETURN VALUE: INTEGER
-* = 0: Arithmetic failed to produce the correct answers
-* = 1: Arithmetic produced the correct answers
-*
-* .. Local Scalars ..
- REAL NAN1, NAN2, NAN3, NAN4, NAN5, NAN6, NEGINF,
- $ NEGZRO, NEWZRO, POSINF
-* ..
-* .. Executable Statements ..
- IEEECK = 1
-*
- POSINF = ONE / ZERO
- IF( POSINF.LE.ONE ) THEN
- IEEECK = 0
- RETURN
- END IF
-*
- NEGINF = -ONE / ZERO
- IF( NEGINF.GE.ZERO ) THEN
- IEEECK = 0
- RETURN
- END IF
-*
- NEGZRO = ONE / ( NEGINF+ONE )
- IF( NEGZRO.NE.ZERO ) THEN
- IEEECK = 0
- RETURN
- END IF
-*
- NEGINF = ONE / NEGZRO
- IF( NEGINF.GE.ZERO ) THEN
- IEEECK = 0
- RETURN
- END IF
-*
- NEWZRO = NEGZRO + ZERO
- IF( NEWZRO.NE.ZERO ) THEN
- IEEECK = 0
- RETURN
- END IF
-*
- POSINF = ONE / NEWZRO
- IF( POSINF.LE.ONE ) THEN
- IEEECK = 0
- RETURN
- END IF
-*
- NEGINF = NEGINF*POSINF
- IF( NEGINF.GE.ZERO ) THEN
- IEEECK = 0
- RETURN
- END IF
-*
- POSINF = POSINF*POSINF
- IF( POSINF.LE.ONE ) THEN
- IEEECK = 0
- RETURN
- END IF
-*
-*
-*
-*
-* Return if we were only asked to check infinity arithmetic
-*
- IF( ISPEC.EQ.0 )
- $ RETURN
-*
- NAN1 = POSINF + NEGINF
-*
- NAN2 = POSINF / NEGINF
-*
- NAN3 = POSINF / POSINF
-*
- NAN4 = POSINF*ZERO
-*
- NAN5 = NEGINF*NEGZRO
-*
- NAN6 = NAN5*0.0
-*
- IF( NAN1.EQ.NAN1 ) THEN
- IEEECK = 0
- RETURN
- END IF
-*
- IF( NAN2.EQ.NAN2 ) THEN
- IEEECK = 0
- RETURN
- END IF
-*
- IF( NAN3.EQ.NAN3 ) THEN
- IEEECK = 0
- RETURN
- END IF
-*
- IF( NAN4.EQ.NAN4 ) THEN
- IEEECK = 0
- RETURN
- END IF
-*
- IF( NAN5.EQ.NAN5 ) THEN
- IEEECK = 0
- RETURN
- END IF
-*
- IF( NAN6.EQ.NAN6 ) THEN
- IEEECK = 0
- RETURN
- END IF
-*
- RETURN
- END
diff --git a/src/lib/lapack/ilaenv.f b/src/lib/lapack/ilaenv.f
deleted file mode 100644
index c375031b..00000000
--- a/src/lib/lapack/ilaenv.f
+++ /dev/null
@@ -1,552 +0,0 @@
- INTEGER FUNCTION ILAENV( ISPEC, NAME, OPTS, N1, N2, N3, N4 )
-*
-* -- LAPACK auxiliary routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- CHARACTER*( * ) NAME, OPTS
- INTEGER ISPEC, N1, N2, N3, N4
-* ..
-*
-* Purpose
-* =======
-*
-* ILAENV is called from the LAPACK routines to choose problem-dependent
-* parameters for the local environment. See ISPEC for a description of
-* the parameters.
-*
-* This version provides a set of parameters which should give good,
-* but not optimal, performance on many of the currently available
-* computers. Users are encouraged to modify this subroutine to set
-* the tuning parameters for their particular machine using the option
-* and problem size information in the arguments.
-*
-* This routine will not function correctly if it is converted to all
-* lower case. Converting it to all upper case is allowed.
-*
-* Arguments
-* =========
-*
-* ISPEC (input) INTEGER
-* Specifies the parameter to be returned as the value of
-* ILAENV.
-* = 1: the optimal blocksize; if this value is 1, an unblocked
-* algorithm will give the best performance.
-* = 2: the minimum block size for which the block routine
-* should be used; if the usable block size is less than
-* this value, an unblocked routine should be used.
-* = 3: the crossover point (in a block routine, for N less
-* than this value, an unblocked routine should be used)
-* = 4: the number of shifts, used in the nonsymmetric
-* eigenvalue routines (DEPRECATED)
-* = 5: the minimum column dimension for blocking to be used;
-* rectangular blocks must have dimension at least k by m,
-* where k is given by ILAENV(2,...) and m by ILAENV(5,...)
-* = 6: the crossover point for the SVD (when reducing an m by n
-* matrix to bidiagonal form, if max(m,n)/min(m,n) exceeds
-* this value, a QR factorization is used first to reduce
-* the matrix to a triangular form.)
-* = 7: the number of processors
-* = 8: the crossover point for the multishift QR method
-* for nonsymmetric eigenvalue problems (DEPRECATED)
-* = 9: maximum size of the subproblems at the bottom of the
-* computation tree in the divide-and-conquer algorithm
-* (used by xGELSD and xGESDD)
-* =10: ieee NaN arithmetic can be trusted not to trap
-* =11: infinity arithmetic can be trusted not to trap
-* 12 <= ISPEC <= 16:
-* xHSEQR or one of its subroutines,
-* see IPARMQ for detailed explanation
-*
-* NAME (input) CHARACTER*(*)
-* The name of the calling subroutine, in either upper case or
-* lower case.
-*
-* OPTS (input) CHARACTER*(*)
-* The character options to the subroutine NAME, concatenated
-* into a single character string. For example, UPLO = 'U',
-* TRANS = 'T', and DIAG = 'N' for a triangular routine would
-* be specified as OPTS = 'UTN'.
-*
-* N1 (input) INTEGER
-* N2 (input) INTEGER
-* N3 (input) INTEGER
-* N4 (input) INTEGER
-* Problem dimensions for the subroutine NAME; these may not all
-* be required.
-*
-* (ILAENV) (output) INTEGER
-* >= 0: the value of the parameter specified by ISPEC
-* < 0: if ILAENV = -k, the k-th argument had an illegal value.
-*
-* Further Details
-* ===============
-*
-* The following conventions have been used when calling ILAENV from the
-* LAPACK routines:
-* 1) OPTS is a concatenation of all of the character options to
-* subroutine NAME, in the same order that they appear in the
-* argument list for NAME, even if they are not used in determining
-* the value of the parameter specified by ISPEC.
-* 2) The problem dimensions N1, N2, N3, N4 are specified in the order
-* that they appear in the argument list for NAME. N1 is used
-* first, N2 second, and so on, and unused problem dimensions are
-* passed a value of -1.
-* 3) The parameter value returned by ILAENV is checked for validity in
-* the calling subroutine. For example, ILAENV is used to retrieve
-* the optimal blocksize for STRTRI as follows:
-*
-* NB = ILAENV( 1, 'STRTRI', UPLO // DIAG, N, -1, -1, -1 )
-* IF( NB.LE.1 ) NB = MAX( 1, N )
-*
-* =====================================================================
-*
-* .. Local Scalars ..
- INTEGER I, IC, IZ, NB, NBMIN, NX
- LOGICAL CNAME, SNAME
- CHARACTER C1*1, C2*2, C4*2, C3*3, SUBNAM*6
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC CHAR, ICHAR, INT, MIN, REAL
-* ..
-* .. External Functions ..
- INTEGER IEEECK, IPARMQ
- EXTERNAL IEEECK, IPARMQ
-* ..
-* .. Executable Statements ..
-*
- GO TO ( 10, 10, 10, 80, 90, 100, 110, 120,
- $ 130, 140, 150, 160, 160, 160, 160, 160 )ISPEC
-*
-* Invalid value for ISPEC
-*
- ILAENV = -1
- RETURN
-*
- 10 CONTINUE
-*
-* Convert NAME to upper case if the first character is lower case.
-*
- ILAENV = 1
- SUBNAM = NAME
- IC = ICHAR( SUBNAM( 1: 1 ) )
- IZ = ICHAR( 'Z' )
- IF( IZ.EQ.90 .OR. IZ.EQ.122 ) THEN
-*
-* ASCII character set
-*
- IF( IC.GE.97 .AND. IC.LE.122 ) THEN
- SUBNAM( 1: 1 ) = CHAR( IC-32 )
- DO 20 I = 2, 6
- IC = ICHAR( SUBNAM( I: I ) )
- IF( IC.GE.97 .AND. IC.LE.122 )
- $ SUBNAM( I: I ) = CHAR( IC-32 )
- 20 CONTINUE
- END IF
-*
- ELSE IF( IZ.EQ.233 .OR. IZ.EQ.169 ) THEN
-*
-* EBCDIC character set
-*
- IF( ( IC.GE.129 .AND. IC.LE.137 ) .OR.
- $ ( IC.GE.145 .AND. IC.LE.153 ) .OR.
- $ ( IC.GE.162 .AND. IC.LE.169 ) ) THEN
- SUBNAM( 1: 1 ) = CHAR( IC+64 )
- DO 30 I = 2, 6
- IC = ICHAR( SUBNAM( I: I ) )
- IF( ( IC.GE.129 .AND. IC.LE.137 ) .OR.
- $ ( IC.GE.145 .AND. IC.LE.153 ) .OR.
- $ ( IC.GE.162 .AND. IC.LE.169 ) )SUBNAM( I:
- $ I ) = CHAR( IC+64 )
- 30 CONTINUE
- END IF
-*
- ELSE IF( IZ.EQ.218 .OR. IZ.EQ.250 ) THEN
-*
-* Prime machines: ASCII+128
-*
- IF( IC.GE.225 .AND. IC.LE.250 ) THEN
- SUBNAM( 1: 1 ) = CHAR( IC-32 )
- DO 40 I = 2, 6
- IC = ICHAR( SUBNAM( I: I ) )
- IF( IC.GE.225 .AND. IC.LE.250 )
- $ SUBNAM( I: I ) = CHAR( IC-32 )
- 40 CONTINUE
- END IF
- END IF
-*
- C1 = SUBNAM( 1: 1 )
- SNAME = C1.EQ.'S' .OR. C1.EQ.'D'
- CNAME = C1.EQ.'C' .OR. C1.EQ.'Z'
- IF( .NOT.( CNAME .OR. SNAME ) )
- $ RETURN
- C2 = SUBNAM( 2: 3 )
- C3 = SUBNAM( 4: 6 )
- C4 = C3( 2: 3 )
-*
- GO TO ( 50, 60, 70 )ISPEC
-*
- 50 CONTINUE
-*
-* ISPEC = 1: block size
-*
-* In these examples, separate code is provided for setting NB for
-* real and complex. We assume that NB will take the same value in
-* single or double precision.
-*
- NB = 1
-*
- IF( C2.EQ.'GE' ) THEN
- IF( C3.EQ.'TRF' ) THEN
- IF( SNAME ) THEN
- NB = 64
- ELSE
- NB = 64
- END IF
- ELSE IF( C3.EQ.'QRF' .OR. C3.EQ.'RQF' .OR. C3.EQ.'LQF' .OR.
- $ C3.EQ.'QLF' ) THEN
- IF( SNAME ) THEN
- NB = 32
- ELSE
- NB = 32
- END IF
- ELSE IF( C3.EQ.'HRD' ) THEN
- IF( SNAME ) THEN
- NB = 32
- ELSE
- NB = 32
- END IF
- ELSE IF( C3.EQ.'BRD' ) THEN
- IF( SNAME ) THEN
- NB = 32
- ELSE
- NB = 32
- END IF
- ELSE IF( C3.EQ.'TRI' ) THEN
- IF( SNAME ) THEN
- NB = 64
- ELSE
- NB = 64
- END IF
- END IF
- ELSE IF( C2.EQ.'PO' ) THEN
- IF( C3.EQ.'TRF' ) THEN
- IF( SNAME ) THEN
- NB = 64
- ELSE
- NB = 64
- END IF
- END IF
- ELSE IF( C2.EQ.'SY' ) THEN
- IF( C3.EQ.'TRF' ) THEN
- IF( SNAME ) THEN
- NB = 64
- ELSE
- NB = 64
- END IF
- ELSE IF( SNAME .AND. C3.EQ.'TRD' ) THEN
- NB = 32
- ELSE IF( SNAME .AND. C3.EQ.'GST' ) THEN
- NB = 64
- END IF
- ELSE IF( CNAME .AND. C2.EQ.'HE' ) THEN
- IF( C3.EQ.'TRF' ) THEN
- NB = 64
- ELSE IF( C3.EQ.'TRD' ) THEN
- NB = 32
- ELSE IF( C3.EQ.'GST' ) THEN
- NB = 64
- END IF
- ELSE IF( SNAME .AND. C2.EQ.'OR' ) THEN
- IF( C3( 1: 1 ).EQ.'G' ) THEN
- IF( C4.EQ.'QR' .OR. C4.EQ.'RQ' .OR. C4.EQ.'LQ' .OR. C4.EQ.
- $ 'QL' .OR. C4.EQ.'HR' .OR. C4.EQ.'TR' .OR. C4.EQ.'BR' )
- $ THEN
- NB = 32
- END IF
- ELSE IF( C3( 1: 1 ).EQ.'M' ) THEN
- IF( C4.EQ.'QR' .OR. C4.EQ.'RQ' .OR. C4.EQ.'LQ' .OR. C4.EQ.
- $ 'QL' .OR. C4.EQ.'HR' .OR. C4.EQ.'TR' .OR. C4.EQ.'BR' )
- $ THEN
- NB = 32
- END IF
- END IF
- ELSE IF( CNAME .AND. C2.EQ.'UN' ) THEN
- IF( C3( 1: 1 ).EQ.'G' ) THEN
- IF( C4.EQ.'QR' .OR. C4.EQ.'RQ' .OR. C4.EQ.'LQ' .OR. C4.EQ.
- $ 'QL' .OR. C4.EQ.'HR' .OR. C4.EQ.'TR' .OR. C4.EQ.'BR' )
- $ THEN
- NB = 32
- END IF
- ELSE IF( C3( 1: 1 ).EQ.'M' ) THEN
- IF( C4.EQ.'QR' .OR. C4.EQ.'RQ' .OR. C4.EQ.'LQ' .OR. C4.EQ.
- $ 'QL' .OR. C4.EQ.'HR' .OR. C4.EQ.'TR' .OR. C4.EQ.'BR' )
- $ THEN
- NB = 32
- END IF
- END IF
- ELSE IF( C2.EQ.'GB' ) THEN
- IF( C3.EQ.'TRF' ) THEN
- IF( SNAME ) THEN
- IF( N4.LE.64 ) THEN
- NB = 1
- ELSE
- NB = 32
- END IF
- ELSE
- IF( N4.LE.64 ) THEN
- NB = 1
- ELSE
- NB = 32
- END IF
- END IF
- END IF
- ELSE IF( C2.EQ.'PB' ) THEN
- IF( C3.EQ.'TRF' ) THEN
- IF( SNAME ) THEN
- IF( N2.LE.64 ) THEN
- NB = 1
- ELSE
- NB = 32
- END IF
- ELSE
- IF( N2.LE.64 ) THEN
- NB = 1
- ELSE
- NB = 32
- END IF
- END IF
- END IF
- ELSE IF( C2.EQ.'TR' ) THEN
- IF( C3.EQ.'TRI' ) THEN
- IF( SNAME ) THEN
- NB = 64
- ELSE
- NB = 64
- END IF
- END IF
- ELSE IF( C2.EQ.'LA' ) THEN
- IF( C3.EQ.'UUM' ) THEN
- IF( SNAME ) THEN
- NB = 64
- ELSE
- NB = 64
- END IF
- END IF
- ELSE IF( SNAME .AND. C2.EQ.'ST' ) THEN
- IF( C3.EQ.'EBZ' ) THEN
- NB = 1
- END IF
- END IF
- ILAENV = NB
- RETURN
-*
- 60 CONTINUE
-*
-* ISPEC = 2: minimum block size
-*
- NBMIN = 2
- IF( C2.EQ.'GE' ) THEN
- IF( C3.EQ.'QRF' .OR. C3.EQ.'RQF' .OR. C3.EQ.'LQF' .OR. C3.EQ.
- $ 'QLF' ) THEN
- IF( SNAME ) THEN
- NBMIN = 2
- ELSE
- NBMIN = 2
- END IF
- ELSE IF( C3.EQ.'HRD' ) THEN
- IF( SNAME ) THEN
- NBMIN = 2
- ELSE
- NBMIN = 2
- END IF
- ELSE IF( C3.EQ.'BRD' ) THEN
- IF( SNAME ) THEN
- NBMIN = 2
- ELSE
- NBMIN = 2
- END IF
- ELSE IF( C3.EQ.'TRI' ) THEN
- IF( SNAME ) THEN
- NBMIN = 2
- ELSE
- NBMIN = 2
- END IF
- END IF
- ELSE IF( C2.EQ.'SY' ) THEN
- IF( C3.EQ.'TRF' ) THEN
- IF( SNAME ) THEN
- NBMIN = 8
- ELSE
- NBMIN = 8
- END IF
- ELSE IF( SNAME .AND. C3.EQ.'TRD' ) THEN
- NBMIN = 2
- END IF
- ELSE IF( CNAME .AND. C2.EQ.'HE' ) THEN
- IF( C3.EQ.'TRD' ) THEN
- NBMIN = 2
- END IF
- ELSE IF( SNAME .AND. C2.EQ.'OR' ) THEN
- IF( C3( 1: 1 ).EQ.'G' ) THEN
- IF( C4.EQ.'QR' .OR. C4.EQ.'RQ' .OR. C4.EQ.'LQ' .OR. C4.EQ.
- $ 'QL' .OR. C4.EQ.'HR' .OR. C4.EQ.'TR' .OR. C4.EQ.'BR' )
- $ THEN
- NBMIN = 2
- END IF
- ELSE IF( C3( 1: 1 ).EQ.'M' ) THEN
- IF( C4.EQ.'QR' .OR. C4.EQ.'RQ' .OR. C4.EQ.'LQ' .OR. C4.EQ.
- $ 'QL' .OR. C4.EQ.'HR' .OR. C4.EQ.'TR' .OR. C4.EQ.'BR' )
- $ THEN
- NBMIN = 2
- END IF
- END IF
- ELSE IF( CNAME .AND. C2.EQ.'UN' ) THEN
- IF( C3( 1: 1 ).EQ.'G' ) THEN
- IF( C4.EQ.'QR' .OR. C4.EQ.'RQ' .OR. C4.EQ.'LQ' .OR. C4.EQ.
- $ 'QL' .OR. C4.EQ.'HR' .OR. C4.EQ.'TR' .OR. C4.EQ.'BR' )
- $ THEN
- NBMIN = 2
- END IF
- ELSE IF( C3( 1: 1 ).EQ.'M' ) THEN
- IF( C4.EQ.'QR' .OR. C4.EQ.'RQ' .OR. C4.EQ.'LQ' .OR. C4.EQ.
- $ 'QL' .OR. C4.EQ.'HR' .OR. C4.EQ.'TR' .OR. C4.EQ.'BR' )
- $ THEN
- NBMIN = 2
- END IF
- END IF
- END IF
- ILAENV = NBMIN
- RETURN
-*
- 70 CONTINUE
-*
-* ISPEC = 3: crossover point
-*
- NX = 0
- IF( C2.EQ.'GE' ) THEN
- IF( C3.EQ.'QRF' .OR. C3.EQ.'RQF' .OR. C3.EQ.'LQF' .OR. C3.EQ.
- $ 'QLF' ) THEN
- IF( SNAME ) THEN
- NX = 128
- ELSE
- NX = 128
- END IF
- ELSE IF( C3.EQ.'HRD' ) THEN
- IF( SNAME ) THEN
- NX = 128
- ELSE
- NX = 128
- END IF
- ELSE IF( C3.EQ.'BRD' ) THEN
- IF( SNAME ) THEN
- NX = 128
- ELSE
- NX = 128
- END IF
- END IF
- ELSE IF( C2.EQ.'SY' ) THEN
- IF( SNAME .AND. C3.EQ.'TRD' ) THEN
- NX = 32
- END IF
- ELSE IF( CNAME .AND. C2.EQ.'HE' ) THEN
- IF( C3.EQ.'TRD' ) THEN
- NX = 32
- END IF
- ELSE IF( SNAME .AND. C2.EQ.'OR' ) THEN
- IF( C3( 1: 1 ).EQ.'G' ) THEN
- IF( C4.EQ.'QR' .OR. C4.EQ.'RQ' .OR. C4.EQ.'LQ' .OR. C4.EQ.
- $ 'QL' .OR. C4.EQ.'HR' .OR. C4.EQ.'TR' .OR. C4.EQ.'BR' )
- $ THEN
- NX = 128
- END IF
- END IF
- ELSE IF( CNAME .AND. C2.EQ.'UN' ) THEN
- IF( C3( 1: 1 ).EQ.'G' ) THEN
- IF( C4.EQ.'QR' .OR. C4.EQ.'RQ' .OR. C4.EQ.'LQ' .OR. C4.EQ.
- $ 'QL' .OR. C4.EQ.'HR' .OR. C4.EQ.'TR' .OR. C4.EQ.'BR' )
- $ THEN
- NX = 128
- END IF
- END IF
- END IF
- ILAENV = NX
- RETURN
-*
- 80 CONTINUE
-*
-* ISPEC = 4: number of shifts (used by xHSEQR)
-*
- ILAENV = 6
- RETURN
-*
- 90 CONTINUE
-*
-* ISPEC = 5: minimum column dimension (not used)
-*
- ILAENV = 2
- RETURN
-*
- 100 CONTINUE
-*
-* ISPEC = 6: crossover point for SVD (used by xGELSS and xGESVD)
-*
- ILAENV = INT( REAL( MIN( N1, N2 ) )*1.6E0 )
- RETURN
-*
- 110 CONTINUE
-*
-* ISPEC = 7: number of processors (not used)
-*
- ILAENV = 1
- RETURN
-*
- 120 CONTINUE
-*
-* ISPEC = 8: crossover point for multishift (used by xHSEQR)
-*
- ILAENV = 50
- RETURN
-*
- 130 CONTINUE
-*
-* ISPEC = 9: maximum size of the subproblems at the bottom of the
-* computation tree in the divide-and-conquer algorithm
-* (used by xGELSD and xGESDD)
-*
- ILAENV = 25
- RETURN
-*
- 140 CONTINUE
-*
-* ISPEC = 10: ieee NaN arithmetic can be trusted not to trap
-*
-* ILAENV = 0
- ILAENV = 1
- IF( ILAENV.EQ.1 ) THEN
- ILAENV = IEEECK( 0, 0.0, 1.0 )
- END IF
- RETURN
-*
- 150 CONTINUE
-*
-* ISPEC = 11: infinity arithmetic can be trusted not to trap
-*
-* ILAENV = 0
- ILAENV = 1
- IF( ILAENV.EQ.1 ) THEN
- ILAENV = IEEECK( 1, 0.0, 1.0 )
- END IF
- RETURN
-*
- 160 CONTINUE
-*
-* 12 <= ISPEC <= 16: xHSEQR or one of its subroutines.
-*
- ILAENV = IPARMQ( ISPEC, NAME, OPTS, N1, N2, N3, N4 )
- RETURN
-*
-* End of ILAENV
-*
- END
diff --git a/src/lib/lapack/iparmq.f b/src/lib/lapack/iparmq.f
deleted file mode 100644
index d9d0af36..00000000
--- a/src/lib/lapack/iparmq.f
+++ /dev/null
@@ -1,253 +0,0 @@
- INTEGER FUNCTION IPARMQ( ISPEC, NAME, OPTS, N, ILO, IHI, LWORK )
-*
-* -- LAPACK auxiliary routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- INTEGER IHI, ILO, ISPEC, LWORK, N
- CHARACTER NAME*( * ), OPTS*( * )
-*
-* Purpose
-* =======
-*
-* This program sets problem and machine dependent parameters
-* useful for xHSEQR and its subroutines. It is called whenever
-* ILAENV is called with 12 <= ISPEC <= 16
-*
-* Arguments
-* =========
-*
-* ISPEC (input) integer scalar
-* ISPEC specifies which tunable parameter IPARMQ should
-* return.
-*
-* ISPEC=12: (INMIN) Matrices of order nmin or less
-* are sent directly to xLAHQR, the implicit
-* double shift QR algorithm. NMIN must be
-* at least 11.
-*
-* ISPEC=13: (INWIN) Size of the deflation window.
-* This is best set greater than or equal to
-* the number of simultaneous shifts NS.
-* Larger matrices benefit from larger deflation
-* windows.
-*
-* ISPEC=14: (INIBL) Determines when to stop nibbling and
-* invest in an (expensive) multi-shift QR sweep.
-* If the aggressive early deflation subroutine
-* finds LD converged eigenvalues from an order
-* NW deflation window and LD.GT.(NW*NIBBLE)/100,
-* then the next QR sweep is skipped and early
-* deflation is applied immediately to the
-* remaining active diagonal block. Setting
-* IPARMQ(ISPEC=14) = 0 causes TTQRE to skip a
-* multi-shift QR sweep whenever early deflation
-* finds a converged eigenvalue. Setting
-* IPARMQ(ISPEC=14) greater than or equal to 100
-* prevents TTQRE from skipping a multi-shift
-* QR sweep.
-*
-* ISPEC=15: (NSHFTS) The number of simultaneous shifts in
-* a multi-shift QR iteration.
-*
-* ISPEC=16: (IACC22) IPARMQ is set to 0, 1 or 2 with the
-* following meanings.
-* 0: During the multi-shift QR sweep,
-* xLAQR5 does not accumulate reflections and
-* does not use matrix-matrix multiply to
-* update the far-from-diagonal matrix
-* entries.
-* 1: During the multi-shift QR sweep,
-* xLAQR5 and/or xLAQRaccumulates reflections and uses
-* matrix-matrix multiply to update the
-* far-from-diagonal matrix entries.
-* 2: During the multi-shift QR sweep.
-* xLAQR5 accumulates reflections and takes
-* advantage of 2-by-2 block structure during
-* matrix-matrix multiplies.
-* (If xTRMM is slower than xGEMM, then
-* IPARMQ(ISPEC=16)=1 may be more efficient than
-* IPARMQ(ISPEC=16)=2 despite the greater level of
-* arithmetic work implied by the latter choice.)
-*
-* NAME (input) character string
-* Name of the calling subroutine
-*
-* OPTS (input) character string
-* This is a concatenation of the string arguments to
-* TTQRE.
-*
-* N (input) integer scalar
-* N is the order of the Hessenberg matrix H.
-*
-* ILO (input) INTEGER
-* IHI (input) INTEGER
-* It is assumed that H is already upper triangular
-* in rows and columns 1:ILO-1 and IHI+1:N.
-*
-* LWORK (input) integer scalar
-* The amount of workspace available.
-*
-* Further Details
-* ===============
-*
-* Little is known about how best to choose these parameters.
-* It is possible to use different values of the parameters
-* for each of CHSEQR, DHSEQR, SHSEQR and ZHSEQR.
-*
-* It is probably best to choose different parameters for
-* different matrices and different parameters at different
-* times during the iteration, but this has not been
-* implemented --- yet.
-*
-*
-* The best choices of most of the parameters depend
-* in an ill-understood way on the relative execution
-* rate of xLAQR3 and xLAQR5 and on the nature of each
-* particular eigenvalue problem. Experiment may be the
-* only practical way to determine which choices are most
-* effective.
-*
-* Following is a list of default values supplied by IPARMQ.
-* These defaults may be adjusted in order to attain better
-* performance in any particular computational environment.
-*
-* IPARMQ(ISPEC=12) The xLAHQR vs xLAQR0 crossover point.
-* Default: 75. (Must be at least 11.)
-*
-* IPARMQ(ISPEC=13) Recommended deflation window size.
-* This depends on ILO, IHI and NS, the
-* number of simultaneous shifts returned
-* by IPARMQ(ISPEC=15). The default for
-* (IHI-ILO+1).LE.500 is NS. The default
-* for (IHI-ILO+1).GT.500 is 3*NS/2.
-*
-* IPARMQ(ISPEC=14) Nibble crossover point. Default: 14.
-*
-* IPARMQ(ISPEC=15) Number of simultaneous shifts, NS.
-* a multi-shift QR iteration.
-*
-* If IHI-ILO+1 is ...
-*
-* greater than ...but less ... the
-* or equal to ... than default is
-*
-* 0 30 NS = 2+
-* 30 60 NS = 4+
-* 60 150 NS = 10
-* 150 590 NS = **
-* 590 3000 NS = 64
-* 3000 6000 NS = 128
-* 6000 infinity NS = 256
-*
-* (+) By default matrices of this order are
-* passed to the implicit double shift routine
-* xLAHQR. See IPARMQ(ISPEC=12) above. These
-* values of NS are used only in case of a rare
-* xLAHQR failure.
-*
-* (**) The asterisks (**) indicate an ad-hoc
-* function increasing from 10 to 64.
-*
-* IPARMQ(ISPEC=16) Select structured matrix multiply.
-* (See ISPEC=16 above for details.)
-* Default: 3.
-*
-* ================================================================
-* .. Parameters ..
- INTEGER INMIN, INWIN, INIBL, ISHFTS, IACC22
- PARAMETER ( INMIN = 12, INWIN = 13, INIBL = 14,
- $ ISHFTS = 15, IACC22 = 16 )
- INTEGER NMIN, K22MIN, KACMIN, NIBBLE, KNWSWP
- PARAMETER ( NMIN = 75, K22MIN = 14, KACMIN = 14,
- $ NIBBLE = 14, KNWSWP = 500 )
- REAL TWO
- PARAMETER ( TWO = 2.0 )
-* ..
-* .. Local Scalars ..
- INTEGER NH, NS
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC LOG, MAX, MOD, NINT, REAL
-* ..
-* .. Executable Statements ..
- IF( ( ISPEC.EQ.ISHFTS ) .OR. ( ISPEC.EQ.INWIN ) .OR.
- $ ( ISPEC.EQ.IACC22 ) ) THEN
-*
-* ==== Set the number simultaneous shifts ====
-*
- NH = IHI - ILO + 1
- NS = 2
- IF( NH.GE.30 )
- $ NS = 4
- IF( NH.GE.60 )
- $ NS = 10
- IF( NH.GE.150 )
- $ NS = MAX( 10, NH / NINT( LOG( REAL( NH ) ) / LOG( TWO ) ) )
- IF( NH.GE.590 )
- $ NS = 64
- IF( NH.GE.3000 )
- $ NS = 128
- IF( NH.GE.6000 )
- $ NS = 256
- NS = MAX( 2, NS-MOD( NS, 2 ) )
- END IF
-*
- IF( ISPEC.EQ.INMIN ) THEN
-*
-*
-* ===== Matrices of order smaller than NMIN get sent
-* . to xLAHQR, the classic double shift algorithm.
-* . This must be at least 11. ====
-*
- IPARMQ = NMIN
-*
- ELSE IF( ISPEC.EQ.INIBL ) THEN
-*
-* ==== INIBL: skip a multi-shift qr iteration and
-* . whenever aggressive early deflation finds
-* . at least (NIBBLE*(window size)/100) deflations. ====
-*
- IPARMQ = NIBBLE
-*
- ELSE IF( ISPEC.EQ.ISHFTS ) THEN
-*
-* ==== NSHFTS: The number of simultaneous shifts =====
-*
- IPARMQ = NS
-*
- ELSE IF( ISPEC.EQ.INWIN ) THEN
-*
-* ==== NW: deflation window size. ====
-*
- IF( NH.LE.KNWSWP ) THEN
- IPARMQ = NS
- ELSE
- IPARMQ = 3*NS / 2
- END IF
-*
- ELSE IF( ISPEC.EQ.IACC22 ) THEN
-*
-* ==== IACC22: Whether to accumulate reflections
-* . before updating the far-from-diagonal elements
-* . and whether to use 2-by-2 block structure while
-* . doing it. A small amount of work could be saved
-* . by making this choice dependent also upon the
-* . NH=IHI-ILO+1.
-*
- IPARMQ = 0
- IF( NS.GE.KACMIN )
- $ IPARMQ = 1
- IF( NS.GE.K22MIN )
- $ IPARMQ = 2
-*
- ELSE
-* ===== invalid value of ispec =====
- IPARMQ = -1
-*
- END IF
-*
-* ==== End of IPARMQ ====
-*
- END
diff --git a/src/lib/lapack/izmax1.f b/src/lib/lapack/izmax1.f
deleted file mode 100644
index 7ebffee3..00000000
--- a/src/lib/lapack/izmax1.f
+++ /dev/null
@@ -1,95 +0,0 @@
- INTEGER FUNCTION IZMAX1( N, CX, INCX )
-*
-* -- LAPACK auxiliary routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- INTEGER INCX, N
-* ..
-* .. Array Arguments ..
- COMPLEX*16 CX( * )
-* ..
-*
-* Purpose
-* =======
-*
-* IZMAX1 finds the index of the element whose real part has maximum
-* absolute value.
-*
-* Based on IZAMAX from Level 1 BLAS.
-* The change is to use the 'genuine' absolute value.
-*
-* Contributed by Nick Higham for use with ZLACON.
-*
-* Arguments
-* =========
-*
-* N (input) INTEGER
-* The number of elements in the vector CX.
-*
-* CX (input) COMPLEX*16 array, dimension (N)
-* The vector whose elements will be summed.
-*
-* INCX (input) INTEGER
-* The spacing between successive values of CX. INCX >= 1.
-*
-* =====================================================================
-*
-* .. Local Scalars ..
- INTEGER I, IX
- DOUBLE PRECISION SMAX
- COMPLEX*16 ZDUM
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC ABS
-* ..
-* .. Statement Functions ..
- DOUBLE PRECISION CABS1
-* ..
-* .. Statement Function definitions ..
-*
-* NEXT LINE IS THE ONLY MODIFICATION.
- CABS1( ZDUM ) = ABS( ZDUM )
-* ..
-* .. Executable Statements ..
-*
- IZMAX1 = 0
- IF( N.LT.1 )
- $ RETURN
- IZMAX1 = 1
- IF( N.EQ.1 )
- $ RETURN
- IF( INCX.EQ.1 )
- $ GO TO 30
-*
-* CODE FOR INCREMENT NOT EQUAL TO 1
-*
- IX = 1
- SMAX = CABS1( CX( 1 ) )
- IX = IX + INCX
- DO 20 I = 2, N
- IF( CABS1( CX( IX ) ).LE.SMAX )
- $ GO TO 10
- IZMAX1 = I
- SMAX = CABS1( CX( IX ) )
- 10 CONTINUE
- IX = IX + INCX
- 20 CONTINUE
- RETURN
-*
-* CODE FOR INCREMENT EQUAL TO 1
-*
- 30 CONTINUE
- SMAX = CABS1( CX( 1 ) )
- DO 40 I = 2, N
- IF( CABS1( CX( I ) ).LE.SMAX )
- $ GO TO 40
- IZMAX1 = I
- SMAX = CABS1( CX( I ) )
- 40 CONTINUE
- RETURN
-*
-* End of IZMAX1
-*
- END
diff --git a/src/lib/lapack/lapack_f/lapack.def b/src/lib/lapack/lapack_f/lapack.def
deleted file mode 100644
index a6ce5165..00000000
--- a/src/lib/lapack/lapack_f/lapack.def
+++ /dev/null
@@ -1,306 +0,0 @@
-LIBRARY lapack.dll
-
-
-EXPORTS
- dbdsqr_
- dgebak_
- dgebal_
- dgebd2_
- dgebrd_
- dgecon_
- dgeequ_
- dgees_
- dgeesx_
- dgeev_
- dgegs_
- dgehd2_
- dgehrd_
- dgelq2_
- dgelqf_
- dgels_
- dgelss_
- dgelsx_
- dgelsy_
- dgeql2_
- dgeqlf_
- dgeqp3_
- dgeqpf_
- dgeqr2_
- dgeqrf_
- dgerfs_
- dgerq2_
- dgerqf_
- dgesc2_
- dgesv_
- dgesvd_
- dgesvx_
- dgetc2_
- dgetf2_
- dgetrf_
- dgetri_
- dgetrs_
- dggbak_
- dggbal_
- dgges_
- dggev_
- dgghrd_
- dhgeqz_
- dhseqr_
- disnan_
- dlabad_
- dlabrd_
- dlacn2_
- dlacon_
- dlacpy_
- dladiv_
- dlae2_
- dlaev2_
- dlaexc_
- dlag2_
- dlagv2_
- dlahqr_
- dlahr2_
- dlahrd_
- dlaic1_
- dlaisnan_
- dlaln2_
- dlamch_
- dlamc2_
- dlamc1_
- dlamc3_
- dlamc4_
- dlamc5_
- dlange_
- dlanhs_
- dlansp_
- dlanst_
- dlansy_
- dlantr_
- dlanv2_
- dlapmt_
- dlapy2_
- dlapy3_
- dlaqge_
- dlaqp2_
- dlaqps_
- dlaqr0_
- dlaqr1_
- dlaqr2_
- dlaqr3_
- dlaqr4_
- dlaqr5_
- dlarf_
- dlarfb_
- dlarfg_
- dlarft_
- dlarfx_
- dlartg_
- dlarz_
- dlarzb_
- dlarzt_
- dlas2_
- dlascl_
- dlaset_
- dlasq1_
- dlasq2_
- dlasq3_
- dlasq4_
- dlasq5_
- dlasq6_
- dlasr_
- dlasrt_
- dlassq_
- dlasv2_
- dlaswp_
- dlasy2_
- dlasyf_
- dlatdf_
- dlatrd_
- dlatrs_
- dlatrz_
- dlatzm_
- dlazq3_
- dlazq4_
- dopgtr_
- dorg2l_
- dorg2r_
- dorgbr_
- dorghr_
- dorgl2_
- dorglq_
- dorgql_
- dorgqr_
- dorgr2_
- dorgrq_
- dorgtr_
- dorm2l_
- dorm2r_
- dormbr_
- dormhr_
- dorml2_
- dormlq_
- dormql_
- dormqr_
- dormr2_
- dormr3_
- dormrq_
- dormrz_
- dpocon_
- dpotf2_
- dpotrf_
- dpotrs_
- dpptrf_
- drscl_
- dspev_
- dspgst_
- dspgv_
- dsptrd_
- dsptrf_
- dsteqr_
- dsterf_
- dsycon_
- dsyev_
- dsysv_
- dsytd2_
- dsytf2_
- dsytrd_
- dsytrf_
- dsytri_
- dsytrs_
- dtgevc_
- dtgex2_
- dtgexc_
- dtgsen_
- dtgsy2_
- dtgsyl_
- dtrcon_
- dtrevc_
- dtrexc_
- dtrsen_
- dtrsyl_
- dtrti2_
- dtrtri_
- dtrtrs_
- dtzrqf_
- dtzrzf_
- dzsum1_
- ieeeck_
- ilaenv_
- iparmq_
- izmax1_
- lsame_
- slamch_
- slamc2_
- slamc1_
- slamc3_
- slamc4_
- slamc5_
- zbdsqr_
- zdrot_
- zdrscl_
- zgebak_
- zgebal_
- zgebd2_
- zgebrd_
- zgecon_
- zgees_
- zgeev_
- zgehd2_
- zgehrd_
- zgelq2_
- zgelqf_
- zgelsy_
- zgeqp3_
- zgeqpf_
- zgeqr2_
- zgeqrf_
- zgesc2_
- zgesvd_
- zgetc2_
- zgetf2_
- zgetrf_
- zgetri_
- zgetrs_
- zggbak_
- zggbal_
- zgges_
- zggev_
- zgghrd_
- zheev_
- zhetd2_
- zhetrd_
- zhgeqz_
- zhseqr_
- zlabrd_
- zlacgv_
- zlacn2_
- zlacon_
- zlacpy_
- zladiv_
- zlahqr_
- zlahr2_
- zlahrd_
- zlaic1_
- zlange_
- zlanhe_
- zlanhs_
- zlaqp2_
- zlaqps_
- zlaqr0_
- zlaqr1_
- zlaqr2_
- zlaqr3_
- zlaqr4_
- zlaqr5_
- zlarf_
- zlarfb_
- zlarfg_
- zlarft_
- zlarfx_
- zlartg_
- zlarz_
- zlarzb_
- zlarzt_
- zlascl_
- zlaset_
- zlasr_
- zlassq_
- zlaswp_
- zlatdf_
- zlatrd_
- zlatrs_
- zlatrz_
- zpotf2_
- zpotrf_
- zrot_
- zsteqr_
- ztgevc_
- ztgex2_
- ztgexc_
- ztgsen_
- ztgsy2_
- ztgsyl_
- ztrevc_
- ztrexc_
- ztrsen_
- ztrsyl_
- ztrti2_
- ztrtri_
- ztzrzf_
- zung2l_
- zung2r_
- zungbr_
- zunghr_
- zungl2_
- zunglq_
- zungql_
- zungqr_
- zungtr_
- zunm2r_
- zunmbr_
- zunml2_
- zunmlq_
- zunmqr_
- zunmr3_
- zunmrz_
- \ No newline at end of file
diff --git a/src/lib/lapack/lapack_f/lapack_DLL.vfproj b/src/lib/lapack/lapack_f/lapack_DLL.vfproj
deleted file mode 100644
index 027b6234..00000000
--- a/src/lib/lapack/lapack_f/lapack_DLL.vfproj
+++ /dev/null
@@ -1,348 +0,0 @@
-<?xml version="1.0" encoding="UTF-8"?>
-<VisualStudioProject ProjectType="typeDynamicLibrary" ProjectCreator="Intel Fortran" Keyword="Dll" Version="9.10" ProjectIdGuid="{69296D00-0DE1-4F4B-B0CE-FE4F3CB43923}">
- <Platforms>
- <Platform Name="Win32"/>
- <Platform Name="x64"/></Platforms>
- <Configurations>
- <Configuration Name="Debug|Win32" OutputDirectory="$(InputDir)$(ConfigurationName)" DeleteExtensionsOnClean="*.obj;*.mod;*.pdb;*.asm;*.map;*.dyn;*.dpi;*.tmp;*.log;*.ilk;*.dll;$(TargetPath)" ConfigurationType="typeDynamicLibrary">
- <Tool Name="VFFortranCompilerTool" SuppressStartupBanner="true" DebugInformationFormat="debugEnabled" Optimization="optimizeDisabled" OptimizeForProcessor="procOptimizeBlended" F77RuntimeCompatibility="true" CallingConvention="callConventionCRef" ExternalNameUnderscore="true" ModulePath="$(INTDIR)/" ObjectFile="$(INTDIR)/" Traceback="true" RuntimeLibrary="rtMultiThreadedDebug"/>
- <Tool Name="VFLinkerTool" OutputFile="$(SolutionDir)bin/lapack.dll" LinkIncremental="linkIncrementalNo" SuppressStartupBanner="true" IgnoreDefaultLibraryNames="msvcrtd.lib" ModuleDefinitionFile="lapack.def" GenerateDebugInformation="true" SubSystem="subSystemWindows" ImportLibrary="$(SolutionDir)bin/lapack.lib" LinkDLL="true" AdditionalDependencies="libcmtd.lib "/>
- <Tool Name="VFResourceCompilerTool"/>
- <Tool Name="VFMidlTool" SuppressStartupBanner="true" HeaderFileName="$(InputName).h" TypeLibraryName="$(IntDir)/$(InputName).tlb"/>
- <Tool Name="VFCustomBuildTool"/>
- <Tool Name="VFPreLinkEventTool"/>
- <Tool Name="VFPreBuildEventTool"/>
- <Tool Name="VFPostBuildEventTool"/></Configuration>
- <Configuration Name="Release|Win32" OutputDirectory="$(InputDir)$(ConfigurationName)" DeleteExtensionsOnClean="*.obj;*.mod;*.pdb;*.asm;*.map;*.dyn;*.dpi;*.tmp;*.log;*.ilk;*.dll;$(TargetPath)" ConfigurationType="typeDynamicLibrary">
- <Tool Name="VFFortranCompilerTool" SuppressStartupBanner="true" OptimizeForProcessor="procOptimizePentiumProThruIII" UseProcessorExtensions="codeForStreamingSIMD" RequireProcessorExtensions="codeExclusivelyStreamingSIMD" F77RuntimeCompatibility="true" CallingConvention="callConventionCRef" ExternalNameUnderscore="true" ModulePath="$(INTDIR)/" ObjectFile="$(INTDIR)/"/>
- <Tool Name="VFLinkerTool" OutputFile="$(SolutionDir)bin/lapack.dll" LinkIncremental="linkIncrementalNo" SuppressStartupBanner="true" IgnoreDefaultLibraryNames="msvcrt.lib" ModuleDefinitionFile="lapack.def" SubSystem="subSystemWindows" SupportUnloadOfDelayLoadedDLL="true" ImportLibrary="$(SolutionDir)bin/lapack.lib" LinkDLL="true" AdditionalDependencies="libcmt.lib"/>
- <Tool Name="VFResourceCompilerTool"/>
- <Tool Name="VFMidlTool" SuppressStartupBanner="true" HeaderFileName="$(InputName).h" TypeLibraryName="$(IntDir)/$(InputName).tlb"/>
- <Tool Name="VFCustomBuildTool"/>
- <Tool Name="VFPreLinkEventTool"/>
- <Tool Name="VFPreBuildEventTool"/>
- <Tool Name="VFPostBuildEventTool"/></Configuration>
- <Configuration Name="Debug|x64" OutputDirectory="$(InputDir)$(ConfigurationName)" IntermediateDirectory="$(ConfigurationName)" DeleteExtensionsOnClean="*.obj;*.mod;*.pdb;*.asm;*.map;*.dyn;*.dpi;*.tmp;*.log;*.ilk;*.dll;$(TargetPath)" ConfigurationType="typeDynamicLibrary">
- <Tool Name="VFFortranCompilerTool" SuppressStartupBanner="true" DebugInformationFormat="debugEnabled" Optimization="optimizeDisabled" F77RuntimeCompatibility="true" CallingConvention="callConventionCRef" ExternalNameUnderscore="true" ModulePath="$(INTDIR)/" ObjectFile="$(INTDIR)/" Traceback="true" RuntimeLibrary="rtMultiThreadedDebugDLL"/>
- <Tool Name="VFLinkerTool" OutputFile="../../lapack.dll" LinkIncremental="linkIncrementalNo" SuppressStartupBanner="true" IgnoreDefaultLibraryNames="msvcrtd.lib" ModuleDefinitionFile="lapack.def" GenerateDebugInformation="true" SubSystem="subSystemWindows" ImportLibrary="../../lapack.lib" LinkDLL="true" AdditionalDependencies="libcmtd.lib ../../blas.lib"/>
- <Tool Name="VFResourceCompilerTool"/>
- <Tool Name="VFMidlTool" SuppressStartupBanner="true" HeaderFileName="$(InputName).h" TypeLibraryName="$(IntDir)/$(InputName).tlb"/>
- <Tool Name="VFCustomBuildTool"/>
- <Tool Name="VFPreLinkEventTool"/>
- <Tool Name="VFPreBuildEventTool"/>
- <Tool Name="VFPostBuildEventTool"/></Configuration>
- <Configuration Name="Release|x64" OutputDirectory="$(InputDir)$(ConfigurationName)" IntermediateDirectory="$(ConfigurationName)" DeleteExtensionsOnClean="*.obj;*.mod;*.pdb;*.asm;*.map;*.dyn;*.dpi;*.tmp;*.log;*.ilk;*.dll;$(TargetPath)" ConfigurationType="typeDynamicLibrary">
- <Tool Name="VFFortranCompilerTool" SuppressStartupBanner="true" F77RuntimeCompatibility="true" CallingConvention="callConventionCRef" ExternalNameUnderscore="true" ModulePath="$(INTDIR)/" ObjectFile="$(INTDIR)/"/>
- <Tool Name="VFLinkerTool" OutputFile="../../lapack.dll" LinkIncremental="linkIncrementalNo" SuppressStartupBanner="true" IgnoreDefaultLibraryNames="msvcrt.lib" ModuleDefinitionFile="lapack.def" SubSystem="subSystemWindows" SupportUnloadOfDelayLoadedDLL="true" ImportLibrary="../../lapack.lib" LinkDLL="true" AdditionalDependencies="libcmt.lib"/>
- <Tool Name="VFResourceCompilerTool"/>
- <Tool Name="VFMidlTool" SuppressStartupBanner="true" HeaderFileName="$(InputName).h" TypeLibraryName="$(IntDir)/$(InputName).tlb"/>
- <Tool Name="VFCustomBuildTool"/>
- <Tool Name="VFPreLinkEventTool"/>
- <Tool Name="VFPreBuildEventTool"/>
- <Tool Name="VFPostBuildEventTool"/></Configuration></Configurations>
- <Files>
- <Filter Name="Header Files" Filter="fi;fd"/>
- <Filter Name="Resource Files" Filter="rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe"/>
- <Filter Name="Source Files" Filter="f90;for;f;fpp;ftn;def;odl;idl">
- <File RelativePath="..\dbdsqr.f"/>
- <File RelativePath="..\dgebak.f"/>
- <File RelativePath="..\dgebal.f"/>
- <File RelativePath="..\dgebd2.f"/>
- <File RelativePath="..\dgebrd.f"/>
- <File RelativePath="..\dgecon.f"/>
- <File RelativePath="..\dgeequ.f"/>
- <File RelativePath="..\dgees.f"/>
- <File RelativePath="..\dgeesx.f"/>
- <File RelativePath="..\dgeev.f"/>
- <File RelativePath="..\dgegs.f"/>
- <File RelativePath="..\dgehd2.f"/>
- <File RelativePath="..\dgehrd.f"/>
- <File RelativePath="..\dgelq2.f"/>
- <File RelativePath="..\dgelqf.f"/>
- <File RelativePath="..\dgels.f"/>
- <File RelativePath="..\dgelss.f"/>
- <File RelativePath="..\dgelsx.f"/>
- <File RelativePath="..\dgelsy.f"/>
- <File RelativePath="..\dgeql2.f"/>
- <File RelativePath="..\dgeqlf.f"/>
- <File RelativePath="..\dgeqp3.f"/>
- <File RelativePath="..\dgeqpf.f"/>
- <File RelativePath="..\dgeqr2.f"/>
- <File RelativePath="..\dgeqrf.f"/>
- <File RelativePath="..\dgerfs.f"/>
- <File RelativePath="..\dgerq2.f"/>
- <File RelativePath="..\dgerqf.f"/>
- <File RelativePath="..\dgesc2.f"/>
- <File RelativePath="..\dgesv.f"/>
- <File RelativePath="..\dgesvd.f"/>
- <File RelativePath="..\dgesvx.f"/>
- <File RelativePath="..\dgetc2.f"/>
- <File RelativePath="..\dgetf2.f"/>
- <File RelativePath="..\dgetrf.f"/>
- <File RelativePath="..\dgetri.f"/>
- <File RelativePath="..\dgetrs.f"/>
- <File RelativePath="..\dggbak.f"/>
- <File RelativePath="..\dggbal.f"/>
- <File RelativePath="..\dgges.f"/>
- <File RelativePath="..\dggev.f"/>
- <File RelativePath="..\dgghrd.f"/>
- <File RelativePath="..\dhgeqz.f"/>
- <File RelativePath="..\dhseqr.f"/>
- <File RelativePath="..\disnan.f"/>
- <File RelativePath="..\dlabad.f"/>
- <File RelativePath="..\dlabrd.f"/>
- <File RelativePath="..\dlacn2.f"/>
- <File RelativePath="..\dlacon.f"/>
- <File RelativePath="..\dlacpy.f"/>
- <File RelativePath="..\dladiv.f"/>
- <File RelativePath="..\dlae2.f"/>
- <File RelativePath="..\dlaev2.f"/>
- <File RelativePath="..\dlaexc.f"/>
- <File RelativePath="..\dlag2.f"/>
- <File RelativePath="..\dlagv2.f"/>
- <File RelativePath="..\dlahqr.f"/>
- <File RelativePath="..\dlahr2.f"/>
- <File RelativePath="..\dlahrd.f"/>
- <File RelativePath="..\dlaic1.f"/>
- <File RelativePath="..\dlaisnan.f"/>
- <File RelativePath="..\dlaln2.f"/>
- <File RelativePath="..\dlamch.f">
- <FileConfiguration Name="Release|x64">
- <Tool Name="VFFortranCompilerTool" Optimization="optimizeDisabled"/></FileConfiguration>
- <FileConfiguration Name="Release|Win32">
- <Tool Name="VFFortranCompilerTool" Optimization="optimizeDisabled" OptimizeForProcessor="procOptimizeBlended"/></FileConfiguration></File>
- <File RelativePath="..\dlange.f"/>
- <File RelativePath="..\dlanhs.f"/>
- <File RelativePath="..\dlansp.f"/>
- <File RelativePath="..\dlanst.f"/>
- <File RelativePath="..\dlansy.f"/>
- <File RelativePath="..\dlantr.f"/>
- <File RelativePath="..\dlanv2.f"/>
- <File RelativePath="..\dlapmt.f"/>
- <File RelativePath="..\dlapy2.f"/>
- <File RelativePath="..\dlapy3.f"/>
- <File RelativePath="..\dlaqge.f"/>
- <File RelativePath="..\dlaqp2.f"/>
- <File RelativePath="..\dlaqps.f"/>
- <File RelativePath="..\dlaqr0.f"/>
- <File RelativePath="..\dlaqr1.f"/>
- <File RelativePath="..\dlaqr2.f"/>
- <File RelativePath="..\dlaqr3.f"/>
- <File RelativePath="..\dlaqr4.f"/>
- <File RelativePath="..\dlaqr5.f"/>
- <File RelativePath="..\dlarf.f"/>
- <File RelativePath="..\dlarfb.f"/>
- <File RelativePath="..\dlarfg.f"/>
- <File RelativePath="..\dlarft.f"/>
- <File RelativePath="..\dlarfx.f"/>
- <File RelativePath="..\dlartg.f"/>
- <File RelativePath="..\dlarz.f"/>
- <File RelativePath="..\dlarzb.f"/>
- <File RelativePath="..\dlarzt.f"/>
- <File RelativePath="..\dlas2.f"/>
- <File RelativePath="..\dlascl.f"/>
- <File RelativePath="..\dlaset.f"/>
- <File RelativePath="..\dlasq1.f"/>
- <File RelativePath="..\dlasq2.f"/>
- <File RelativePath="..\dlasq3.f"/>
- <File RelativePath="..\dlasq4.f"/>
- <File RelativePath="..\dlasq5.f"/>
- <File RelativePath="..\dlasq6.f"/>
- <File RelativePath="..\dlasr.f"/>
- <File RelativePath="..\dlasrt.f"/>
- <File RelativePath="..\dlassq.f"/>
- <File RelativePath="..\dlasv2.f"/>
- <File RelativePath="..\dlaswp.f"/>
- <File RelativePath="..\dlasy2.f"/>
- <File RelativePath="..\dlasyf.f"/>
- <File RelativePath="..\dlatdf.f"/>
- <File RelativePath="..\dlatrd.f"/>
- <File RelativePath="..\dlatrs.f"/>
- <File RelativePath="..\dlatrz.f"/>
- <File RelativePath="..\dlatzm.f"/>
- <File RelativePath="..\dlazq3.f"/>
- <File RelativePath="..\dlazq4.f"/>
- <File RelativePath="..\dopgtr.f"/>
- <File RelativePath="..\dorg2l.f"/>
- <File RelativePath="..\dorg2r.f"/>
- <File RelativePath="..\dorgbr.f"/>
- <File RelativePath="..\dorghr.f"/>
- <File RelativePath="..\dorgl2.f"/>
- <File RelativePath="..\dorglq.f"/>
- <File RelativePath="..\dorgql.f"/>
- <File RelativePath="..\dorgqr.f"/>
- <File RelativePath="..\dorgr2.f"/>
- <File RelativePath="..\dorgrq.f"/>
- <File RelativePath="..\dorgtr.f"/>
- <File RelativePath="..\dorm2l.f"/>
- <File RelativePath="..\dorm2r.f"/>
- <File RelativePath="..\dormbr.f"/>
- <File RelativePath="..\dormhr.f"/>
- <File RelativePath="..\dorml2.f"/>
- <File RelativePath="..\dormlq.f"/>
- <File RelativePath="..\dormql.f"/>
- <File RelativePath="..\dormqr.f"/>
- <File RelativePath="..\dormr2.f"/>
- <File RelativePath="..\dormr3.f"/>
- <File RelativePath="..\dormrq.f"/>
- <File RelativePath="..\dormrz.f"/>
- <File RelativePath="..\dpocon.f"/>
- <File RelativePath="..\dpotf2.f"/>
- <File RelativePath="..\dpotrf.f"/>
- <File RelativePath="..\dpotrs.f"/>
- <File RelativePath="..\dpptrf.f"/>
- <File RelativePath="..\drscl.f"/>
- <File RelativePath="..\dspev.f"/>
- <File RelativePath="..\dspgst.f"/>
- <File RelativePath="..\dspgv.f"/>
- <File RelativePath="..\dsptrd.f"/>
- <File RelativePath="..\dsptrf.f"/>
- <File RelativePath="..\dsteqr.f"/>
- <File RelativePath="..\dsterf.f"/>
- <File RelativePath="..\dsycon.f"/>
- <File RelativePath="..\dsyev.f"/>
- <File RelativePath="..\dsysv.f"/>
- <File RelativePath="..\dsytd2.f"/>
- <File RelativePath="..\dsytf2.f"/>
- <File RelativePath="..\dsytrd.f"/>
- <File RelativePath="..\dsytrf.f"/>
- <File RelativePath="..\dsytri.f"/>
- <File RelativePath="..\dsytrs.f"/>
- <File RelativePath="..\dtgevc.f"/>
- <File RelativePath="..\dtgex2.f"/>
- <File RelativePath="..\dtgexc.f"/>
- <File RelativePath="..\dtgsen.f"/>
- <File RelativePath="..\dtgsy2.f"/>
- <File RelativePath="..\dtgsyl.f"/>
- <File RelativePath="..\dtrcon.f"/>
- <File RelativePath="..\dtrevc.f"/>
- <File RelativePath="..\dtrexc.f"/>
- <File RelativePath="..\dtrsen.f"/>
- <File RelativePath="..\dtrsyl.f"/>
- <File RelativePath="..\dtrti2.f"/>
- <File RelativePath="..\dtrtri.f"/>
- <File RelativePath="..\dtrtrs.f"/>
- <File RelativePath="..\dtzrqf.f"/>
- <File RelativePath="..\dtzrzf.f"/>
- <File RelativePath="..\dzsum1.f"/>
- <File RelativePath="..\ieeeck.f"/>
- <File RelativePath="..\ilaenv.f"/>
- <File RelativePath="..\iparmq.f"/>
- <File RelativePath="..\izmax1.f"/>
- <File RelativePath="..\lsame.f"/>
- <File RelativePath="..\slamch.f">
- <FileConfiguration Name="Release|x64">
- <Tool Name="VFFortranCompilerTool" Optimization="optimizeDisabled"/></FileConfiguration>
- <FileConfiguration Name="Release|Win32">
- <Tool Name="VFFortranCompilerTool" Optimization="optimizeDisabled"/></FileConfiguration></File>
- <File RelativePath="..\xerbla.f"/>
- <File RelativePath="..\zbdsqr.f"/>
- <File RelativePath="..\zdrot.f"/>
- <File RelativePath="..\zdrscl.f"/>
- <File RelativePath="..\zgebak.f"/>
- <File RelativePath="..\zgebal.f"/>
- <File RelativePath="..\zgebd2.f"/>
- <File RelativePath="..\zgebrd.f"/>
- <File RelativePath="..\zgecon.f"/>
- <File RelativePath="..\zgees.f"/>
- <File RelativePath="..\zgeev.f"/>
- <File RelativePath="..\zgehd2.f"/>
- <File RelativePath="..\zgehrd.f"/>
- <File RelativePath="..\zgelq2.f"/>
- <File RelativePath="..\zgelqf.f"/>
- <File RelativePath="..\zgelsy.f"/>
- <File RelativePath="..\zgeqp3.f"/>
- <File RelativePath="..\zgeqpf.f"/>
- <File RelativePath="..\zgeqr2.f"/>
- <File RelativePath="..\zgeqrf.f"/>
- <File RelativePath="..\zgesc2.f"/>
- <File RelativePath="..\zgesvd.f"/>
- <File RelativePath="..\zgetc2.f"/>
- <File RelativePath="..\zgetf2.f"/>
- <File RelativePath="..\zgetrf.f"/>
- <File RelativePath="..\zgetri.f"/>
- <File RelativePath="..\zgetrs.f"/>
- <File RelativePath="..\zggbak.f"/>
- <File RelativePath="..\zggbal.f"/>
- <File RelativePath="..\zgges.f"/>
- <File RelativePath="..\zggev.f"/>
- <File RelativePath="..\zgghrd.f"/>
- <File RelativePath="..\zheev.f"/>
- <File RelativePath="..\zhetd2.f"/>
- <File RelativePath="..\zhetrd.f"/>
- <File RelativePath="..\zhgeqz.f"/>
- <File RelativePath="..\zhseqr.f"/>
- <File RelativePath="..\zlabrd.f"/>
- <File RelativePath="..\zlacgv.f"/>
- <File RelativePath="..\zlacn2.f"/>
- <File RelativePath="..\zlacon.f"/>
- <File RelativePath="..\zlacpy.f"/>
- <File RelativePath="..\zladiv.f"/>
- <File RelativePath="..\zlahqr.f"/>
- <File RelativePath="..\zlahr2.f"/>
- <File RelativePath="..\zlahrd.f"/>
- <File RelativePath="..\zlaic1.f"/>
- <File RelativePath="..\zlange.f"/>
- <File RelativePath="..\zlanhe.f"/>
- <File RelativePath="..\zlanhs.f"/>
- <File RelativePath="..\zlaqp2.f"/>
- <File RelativePath="..\zlaqps.f"/>
- <File RelativePath="..\zlaqr0.f"/>
- <File RelativePath="..\zlaqr1.f"/>
- <File RelativePath="..\zlaqr2.f"/>
- <File RelativePath="..\zlaqr3.f"/>
- <File RelativePath="..\zlaqr4.f"/>
- <File RelativePath="..\zlaqr5.f"/>
- <File RelativePath="..\zlarf.f"/>
- <File RelativePath="..\zlarfb.f"/>
- <File RelativePath="..\zlarfg.f"/>
- <File RelativePath="..\zlarft.f"/>
- <File RelativePath="..\zlarfx.f"/>
- <File RelativePath="..\zlartg.f"/>
- <File RelativePath="..\zlarz.f"/>
- <File RelativePath="..\zlarzb.f"/>
- <File RelativePath="..\zlarzt.f"/>
- <File RelativePath="..\zlascl.f"/>
- <File RelativePath="..\zlaset.f"/>
- <File RelativePath="..\zlasr.f"/>
- <File RelativePath="..\zlassq.f"/>
- <File RelativePath="..\zlaswp.f"/>
- <File RelativePath="..\zlatdf.f"/>
- <File RelativePath="..\zlatrd.f"/>
- <File RelativePath="..\zlatrs.f"/>
- <File RelativePath="..\zlatrz.f"/>
- <File RelativePath="..\zpotf2.f"/>
- <File RelativePath="..\zpotrf.f"/>
- <File RelativePath="..\zrot.f"/>
- <File RelativePath="..\zsteqr.f"/>
- <File RelativePath="..\ztgevc.f"/>
- <File RelativePath="..\ztgex2.f"/>
- <File RelativePath="..\ztgexc.f"/>
- <File RelativePath="..\ztgsen.f"/>
- <File RelativePath="..\ztgsy2.f"/>
- <File RelativePath="..\ztgsyl.f"/>
- <File RelativePath="..\ztrevc.f"/>
- <File RelativePath="..\ztrexc.f"/>
- <File RelativePath="..\ztrsen.f"/>
- <File RelativePath="..\ztrsyl.f"/>
- <File RelativePath="..\ztrti2.f"/>
- <File RelativePath="..\ztrtri.f"/>
- <File RelativePath="..\ztzrzf.f"/>
- <File RelativePath="..\zung2l.f"/>
- <File RelativePath="..\zung2r.f"/>
- <File RelativePath="..\zungbr.f"/>
- <File RelativePath="..\zunghr.f"/>
- <File RelativePath="..\zungl2.f"/>
- <File RelativePath="..\zunglq.f"/>
- <File RelativePath="..\zungql.f"/>
- <File RelativePath="..\zungqr.f"/>
- <File RelativePath="..\zungtr.f"/>
- <File RelativePath="..\zunm2r.f"/>
- <File RelativePath="..\zunmbr.f"/>
- <File RelativePath="..\zunml2.f"/>
- <File RelativePath="..\zunmlq.f"/>
- <File RelativePath="..\zunmqr.f"/>
- <File RelativePath="..\zunmr3.f"/>
- <File RelativePath="..\zunmrz.f"/></Filter>
- <File RelativePath=".\lapack.def"/></Files>
- <Globals/></VisualStudioProject>
diff --git a/src/lib/lapack/lapack_f/lapack_DLL_f2c.vcproj b/src/lib/lapack/lapack_f/lapack_DLL_f2c.vcproj
deleted file mode 100644
index b87e27ef..00000000
--- a/src/lib/lapack/lapack_f/lapack_DLL_f2c.vcproj
+++ /dev/null
@@ -1,2779 +0,0 @@
-<?xml version="1.0" encoding="Windows-1252"?>
-<VisualStudioProject
- ProjectType="Visual C++"
- Version="9,00"
- Name="lapack_f2c_DLL"
- ProjectGUID="{69296D00-0DE1-4F4B-B0CE-FE4F3CB43923}"
- RootNamespace="lapack_f2c_DLL"
- Keyword="Win32Proj"
- TargetFrameworkVersion="0"
- >
- <Platforms>
- <Platform
- Name="Win32"
- />
- <Platform
- Name="x64"
- />
- </Platforms>
- <ToolFiles>
- <ToolFile
- RelativePath="..\..\..\..\Visual-Studio-settings\f2c.rules"
- />
- </ToolFiles>
- <Configurations>
- <Configuration
- Name="Debug|Win32"
- OutputDirectory="$(SolutionDir)$(ConfigurationName)"
- IntermediateDirectory="$(ConfigurationName)"
- ConfigurationType="2"
- CharacterSet="2"
- >
- <Tool
- Name="f2c rule"
- ExecutionBucket="1"
- />
- <Tool
- Name="VCPreBuildEventTool"
- CommandLine=""
- ExecutionBucket="2"
- />
- <Tool
- Name="VCCustomBuildTool"
- />
- <Tool
- Name="VCWebServiceProxyGeneratorTool"
- ExecutionBucket="4"
- />
- <Tool
- Name="VCXMLDataGeneratorTool"
- />
- <Tool
- Name="VCMIDLTool"
- ExecutionBucket="5"
- />
- <Tool
- Name="VCCLCompilerTool"
- ExecutionBucket="6"
- Optimization="0"
- AdditionalIncludeDirectories="../../f2c"
- PreprocessorDefinitions="STRICT;__STDC__;_CRT_SECURE_NO_DEPRECATE"
- MinimalRebuild="true"
- BasicRuntimeChecks="0"
- RuntimeLibrary="1"
- UsePrecompiledHeader="0"
- ObjectFile="$(ConfigurationName)/"
- ProgramDataBaseFileName="$(ConfigurationName)/vc80.pdb"
- WarningLevel="3"
- Detect64BitPortabilityProblems="false"
- DebugInformationFormat="3"
- />
- <Tool
- Name="VCManagedResourceCompilerTool"
- ExecutionBucket="7"
- />
- <Tool
- Name="VCResourceCompilerTool"
- ExecutionBucket="8"
- />
- <Tool
- Name="VCPreLinkEventTool"
- Description="Build Lapack.def file"
- CommandLine=""
- ExecutionBucket="9"
- />
- <Tool
- Name="VCLinkerTool"
- ExecutionBucket="10"
- AdditionalOptions="/fixed:no"
- OutputFile="$(SolutionDir)bin\lapack.dll"
- ModuleDefinitionFile="lapack.def"
- RandomizedBaseAddress="1"
- DataExecutionPrevention="0"
- ImportLibrary="$(SolutionDir)bin\$(TargetName).lib"
- CLRUnmanagedCodeCheck="true"
- />
- <Tool
- Name="VCALinkTool"
- ExecutionBucket="11"
- />
- <Tool
- Name="VCManifestTool"
- ExecutionBucket="12"
- />
- <Tool
- Name="VCXDCMakeTool"
- ExecutionBucket="13"
- />
- <Tool
- Name="VCBscMakeTool"
- ExecutionBucket="14"
- />
- <Tool
- Name="VCFxCopTool"
- ExecutionBucket="15"
- />
- <Tool
- Name="VCPostBuildEventTool"
- CommandLine=""
- ExecutionBucket="17"
- />
- <Tool
- Name="VCAppVerifierTool"
- />
- </Configuration>
- <Configuration
- Name="Debug|x64"
- OutputDirectory="$(SolutionDir)$(ConfigurationName)"
- IntermediateDirectory="$(ConfigurationName)"
- ConfigurationType="2"
- CharacterSet="2"
- >
- <Tool
- Name="VCPreBuildEventTool"
- CommandLine=""
- />
- <Tool
- Name="VCCustomBuildTool"
- />
- <Tool
- Name="f2c rule"
- />
- <Tool
- Name="VCXMLDataGeneratorTool"
- />
- <Tool
- Name="VCWebServiceProxyGeneratorTool"
- />
- <Tool
- Name="VCMIDLTool"
- TargetEnvironment="3"
- />
- <Tool
- Name="VCCLCompilerTool"
- Optimization="0"
- AdditionalIncludeDirectories="../../f2c"
- PreprocessorDefinitions="STRICT;__STDC__;_CRT_SECURE_NO_DEPRECATE"
- MinimalRebuild="true"
- BasicRuntimeChecks="0"
- RuntimeLibrary="1"
- UsePrecompiledHeader="0"
- ObjectFile="$(ConfigurationName)/"
- ProgramDataBaseFileName="$(ConfigurationName)/vc80.pdb"
- WarningLevel="3"
- Detect64BitPortabilityProblems="false"
- DebugInformationFormat="3"
- />
- <Tool
- Name="VCManagedResourceCompilerTool"
- />
- <Tool
- Name="VCResourceCompilerTool"
- />
- <Tool
- Name="VCPreLinkEventTool"
- Description="Build Lapack.def file"
- CommandLine=""
- />
- <Tool
- Name="VCLinkerTool"
- AdditionalOptions="/fixed:no"
- OutputFile="../../../bin/lapack.dll"
- ModuleDefinitionFile="lapack.def"
- RandomizedBaseAddress="1"
- DataExecutionPrevention="0"
- TargetMachine="17"
- CLRUnmanagedCodeCheck="true"
- />
- <Tool
- Name="VCALinkTool"
- />
- <Tool
- Name="VCManifestTool"
- />
- <Tool
- Name="VCXDCMakeTool"
- />
- <Tool
- Name="VCBscMakeTool"
- />
- <Tool
- Name="VCFxCopTool"
- />
- <Tool
- Name="VCAppVerifierTool"
- />
- <Tool
- Name="VCPostBuildEventTool"
- CommandLine=""
- />
- </Configuration>
- <Configuration
- Name="Release|Win32"
- OutputDirectory="$(SolutionDir)$(ConfigurationName)"
- IntermediateDirectory="$(ConfigurationName)"
- ConfigurationType="2"
- CharacterSet="2"
- >
- <Tool
- Name="f2c rule"
- ExecutionBucket="1"
- />
- <Tool
- Name="VCPreBuildEventTool"
- CommandLine=""
- ExecutionBucket="2"
- />
- <Tool
- Name="VCCustomBuildTool"
- />
- <Tool
- Name="VCWebServiceProxyGeneratorTool"
- ExecutionBucket="4"
- />
- <Tool
- Name="VCXMLDataGeneratorTool"
- />
- <Tool
- Name="VCMIDLTool"
- ExecutionBucket="5"
- />
- <Tool
- Name="VCCLCompilerTool"
- ExecutionBucket="6"
- FavorSizeOrSpeed="1"
- AdditionalIncludeDirectories="../../f2c"
- PreprocessorDefinitions="STRICT;__STDC__;_CRT_SECURE_NO_DEPRECATE"
- RuntimeLibrary="0"
- EnableEnhancedInstructionSet="0"
- UsePrecompiledHeader="0"
- ObjectFile="$(ConfigurationName)/"
- ProgramDataBaseFileName="$(ConfigurationName)/vc80.pdb"
- WarningLevel="3"
- Detect64BitPortabilityProblems="false"
- DebugInformationFormat="3"
- />
- <Tool
- Name="VCManagedResourceCompilerTool"
- ExecutionBucket="7"
- />
- <Tool
- Name="VCResourceCompilerTool"
- ExecutionBucket="8"
- />
- <Tool
- Name="VCPreLinkEventTool"
- Description="Build Lapack.def file"
- CommandLine=""
- ExecutionBucket="9"
- />
- <Tool
- Name="VCLinkerTool"
- ExecutionBucket="10"
- OutputFile="$(SolutionDir)bin\lapack.dll"
- ModuleDefinitionFile="lapack.def"
- RandomizedBaseAddress="1"
- DataExecutionPrevention="0"
- ImportLibrary="$(SolutionDir)bin\$(TargetName).lib"
- CLRUnmanagedCodeCheck="true"
- />
- <Tool
- Name="VCALinkTool"
- ExecutionBucket="11"
- />
- <Tool
- Name="VCManifestTool"
- ExecutionBucket="12"
- />
- <Tool
- Name="VCXDCMakeTool"
- ExecutionBucket="13"
- />
- <Tool
- Name="VCBscMakeTool"
- ExecutionBucket="14"
- />
- <Tool
- Name="VCFxCopTool"
- ExecutionBucket="15"
- />
- <Tool
- Name="VCPostBuildEventTool"
- CommandLine=""
- ExecutionBucket="17"
- />
- <Tool
- Name="VCAppVerifierTool"
- />
- </Configuration>
- <Configuration
- Name="Release|x64"
- OutputDirectory="$(SolutionDir)$(ConfigurationName)"
- IntermediateDirectory="$(ConfigurationName)"
- ConfigurationType="2"
- CharacterSet="2"
- >
- <Tool
- Name="VCPreBuildEventTool"
- CommandLine=""
- />
- <Tool
- Name="VCCustomBuildTool"
- />
- <Tool
- Name="f2c rule"
- />
- <Tool
- Name="VCXMLDataGeneratorTool"
- />
- <Tool
- Name="VCWebServiceProxyGeneratorTool"
- />
- <Tool
- Name="VCMIDLTool"
- TargetEnvironment="3"
- />
- <Tool
- Name="VCCLCompilerTool"
- FavorSizeOrSpeed="1"
- AdditionalIncludeDirectories="../../f2c"
- PreprocessorDefinitions="STRICT;__STDC__;_CRT_SECURE_NO_DEPRECATE"
- RuntimeLibrary="0"
- EnableEnhancedInstructionSet="1"
- UsePrecompiledHeader="0"
- ObjectFile="$(ConfigurationName)/"
- ProgramDataBaseFileName="$(ConfigurationName)/vc80.pdb"
- WarningLevel="3"
- Detect64BitPortabilityProblems="false"
- DebugInformationFormat="3"
- />
- <Tool
- Name="VCManagedResourceCompilerTool"
- />
- <Tool
- Name="VCResourceCompilerTool"
- />
- <Tool
- Name="VCPreLinkEventTool"
- Description="Build Lapack.def file"
- CommandLine=""
- />
- <Tool
- Name="VCLinkerTool"
- OutputFile="../../../bin/lapack.dll"
- ModuleDefinitionFile="lapack.def"
- RandomizedBaseAddress="1"
- DataExecutionPrevention="0"
- TargetMachine="17"
- CLRUnmanagedCodeCheck="true"
- />
- <Tool
- Name="VCALinkTool"
- />
- <Tool
- Name="VCManifestTool"
- />
- <Tool
- Name="VCXDCMakeTool"
- />
- <Tool
- Name="VCBscMakeTool"
- />
- <Tool
- Name="VCFxCopTool"
- />
- <Tool
- Name="VCAppVerifierTool"
- />
- <Tool
- Name="VCPostBuildEventTool"
- CommandLine=""
- />
- </Configuration>
- </Configurations>
- <References>
- </References>
- <Files>
- <Filter
- Name="Source Files"
- Filter="cpp;c;cxx;def;odl;idl;hpj;bat;asm;asmx"
- >
- <File
- RelativePath="..\dbdsqr.c"
- >
- </File>
- <File
- RelativePath="..\dgebak.c"
- >
- </File>
- <File
- RelativePath="..\dgebal.c"
- >
- </File>
- <File
- RelativePath="..\dgebd2.c"
- >
- </File>
- <File
- RelativePath="..\dgebrd.c"
- >
- </File>
- <File
- RelativePath="..\dgecon.c"
- >
- </File>
- <File
- RelativePath="..\dgeequ.c"
- >
- </File>
- <File
- RelativePath="..\dgees.c"
- >
- </File>
- <File
- RelativePath="..\dgeesx.c"
- >
- </File>
- <File
- RelativePath="..\dgeev.c"
- >
- </File>
- <File
- RelativePath="..\dgegs.c"
- >
- </File>
- <File
- RelativePath="..\dgehd2.c"
- >
- </File>
- <File
- RelativePath="..\dgehrd.c"
- >
- </File>
- <File
- RelativePath="..\dgelq2.c"
- >
- </File>
- <File
- RelativePath="..\dgelqf.c"
- >
- </File>
- <File
- RelativePath="..\dgels.c"
- >
- </File>
- <File
- RelativePath="..\dgelss.c"
- >
- </File>
- <File
- RelativePath="..\dgelsx.c"
- >
- </File>
- <File
- RelativePath="..\dgelsy.c"
- >
- </File>
- <File
- RelativePath="..\dgeql2.c"
- >
- </File>
- <File
- RelativePath="..\dgeqlf.c"
- >
- </File>
- <File
- RelativePath="..\dgeqp3.c"
- >
- </File>
- <File
- RelativePath="..\dgeqpf.c"
- >
- </File>
- <File
- RelativePath="..\dgeqr2.c"
- >
- </File>
- <File
- RelativePath="..\dgeqrf.c"
- >
- </File>
- <File
- RelativePath="..\dgerfs.c"
- >
- </File>
- <File
- RelativePath="..\dgerq2.c"
- >
- </File>
- <File
- RelativePath="..\dgerqf.c"
- >
- </File>
- <File
- RelativePath="..\dgesc2.c"
- >
- </File>
- <File
- RelativePath="..\dgesv.c"
- >
- </File>
- <File
- RelativePath="..\dgesvd.c"
- >
- </File>
- <File
- RelativePath="..\dgesvx.c"
- >
- </File>
- <File
- RelativePath="..\dgetc2.c"
- >
- </File>
- <File
- RelativePath="..\dgetf2.c"
- >
- </File>
- <File
- RelativePath="..\dgetrf.c"
- >
- </File>
- <File
- RelativePath="..\dgetri.c"
- >
- </File>
- <File
- RelativePath="..\dgetrs.c"
- >
- </File>
- <File
- RelativePath="..\dggbak.c"
- >
- </File>
- <File
- RelativePath="..\dggbal.c"
- >
- </File>
- <File
- RelativePath="..\dgges.c"
- >
- </File>
- <File
- RelativePath="..\dggev.c"
- >
- </File>
- <File
- RelativePath="..\dgghrd.c"
- >
- </File>
- <File
- RelativePath="..\dhgeqz.c"
- >
- </File>
- <File
- RelativePath="..\dhseqr.c"
- >
- </File>
- <File
- RelativePath="..\disnan.c"
- >
- </File>
- <File
- RelativePath="..\dlabad.c"
- >
- </File>
- <File
- RelativePath="..\dlabrd.c"
- >
- </File>
- <File
- RelativePath="..\dlacn2.c"
- >
- </File>
- <File
- RelativePath="..\dlacon.c"
- >
- </File>
- <File
- RelativePath="..\dlacpy.c"
- >
- </File>
- <File
- RelativePath="..\dladiv.c"
- >
- </File>
- <File
- RelativePath="..\dlae2.c"
- >
- </File>
- <File
- RelativePath="..\dlaev2.c"
- >
- </File>
- <File
- RelativePath="..\dlaexc.c"
- >
- </File>
- <File
- RelativePath="..\dlag2.c"
- >
- </File>
- <File
- RelativePath="..\dlagv2.c"
- >
- </File>
- <File
- RelativePath="..\dlahqr.c"
- >
- </File>
- <File
- RelativePath="..\dlahr2.c"
- >
- </File>
- <File
- RelativePath="..\dlahrd.c"
- >
- </File>
- <File
- RelativePath="..\dlaic1.c"
- >
- </File>
- <File
- RelativePath="..\dlaisnan.c"
- >
- </File>
- <File
- RelativePath="..\dlaln2.c"
- >
- </File>
- <File
- RelativePath="..\dlamch.c"
- >
- </File>
- <File
- RelativePath="..\dlange.c"
- >
- </File>
- <File
- RelativePath="..\dlanhs.c"
- >
- </File>
- <File
- RelativePath="..\dlansp.c"
- >
- </File>
- <File
- RelativePath="..\dlanst.c"
- >
- </File>
- <File
- RelativePath="..\dlansy.c"
- >
- </File>
- <File
- RelativePath="..\dlantr.c"
- >
- </File>
- <File
- RelativePath="..\dlanv2.c"
- >
- </File>
- <File
- RelativePath="..\dlapmt.c"
- >
- </File>
- <File
- RelativePath="..\dlapy2.c"
- >
- </File>
- <File
- RelativePath="..\dlapy3.c"
- >
- </File>
- <File
- RelativePath="..\dlaqge.c"
- >
- </File>
- <File
- RelativePath="..\dlaqp2.c"
- >
- </File>
- <File
- RelativePath="..\dlaqps.c"
- >
- </File>
- <File
- RelativePath="..\dlaqr0.c"
- >
- </File>
- <File
- RelativePath="..\dlaqr1.c"
- >
- </File>
- <File
- RelativePath="..\dlaqr2.c"
- >
- </File>
- <File
- RelativePath="..\dlaqr3.c"
- >
- </File>
- <File
- RelativePath="..\dlaqr4.c"
- >
- </File>
- <File
- RelativePath="..\dlaqr5.c"
- >
- </File>
- <File
- RelativePath="..\dlarf.c"
- >
- </File>
- <File
- RelativePath="..\dlarfb.c"
- >
- </File>
- <File
- RelativePath="..\dlarfg.c"
- >
- </File>
- <File
- RelativePath="..\dlarft.c"
- >
- </File>
- <File
- RelativePath="..\dlarfx.c"
- >
- </File>
- <File
- RelativePath="..\dlartg.c"
- >
- </File>
- <File
- RelativePath="..\dlarz.c"
- >
- </File>
- <File
- RelativePath="..\dlarzb.c"
- >
- </File>
- <File
- RelativePath="..\dlarzt.c"
- >
- </File>
- <File
- RelativePath="..\dlas2.c"
- >
- </File>
- <File
- RelativePath="..\dlascl.c"
- >
- </File>
- <File
- RelativePath="..\dlaset.c"
- >
- </File>
- <File
- RelativePath="..\dlasq1.c"
- >
- </File>
- <File
- RelativePath="..\dlasq2.c"
- >
- </File>
- <File
- RelativePath="..\dlasq3.c"
- >
- </File>
- <File
- RelativePath="..\dlasq4.c"
- >
- </File>
- <File
- RelativePath="..\dlasq5.c"
- >
- </File>
- <File
- RelativePath="..\dlasq6.c"
- >
- </File>
- <File
- RelativePath="..\dlasr.c"
- >
- </File>
- <File
- RelativePath="..\dlasrt.c"
- >
- </File>
- <File
- RelativePath="..\dlassq.c"
- >
- </File>
- <File
- RelativePath="..\dlasv2.c"
- >
- </File>
- <File
- RelativePath="..\dlaswp.c"
- >
- </File>
- <File
- RelativePath="..\dlasy2.c"
- >
- </File>
- <File
- RelativePath="..\dlasyf.c"
- >
- </File>
- <File
- RelativePath="..\dlatdf.c"
- >
- </File>
- <File
- RelativePath="..\dlatrd.c"
- >
- </File>
- <File
- RelativePath="..\dlatrs.c"
- >
- </File>
- <File
- RelativePath="..\dlatrz.c"
- >
- </File>
- <File
- RelativePath="..\dlatzm.c"
- >
- </File>
- <File
- RelativePath="..\dlazq3.c"
- >
- </File>
- <File
- RelativePath="..\dlazq4.c"
- >
- </File>
- <File
- RelativePath="..\dopgtr.c"
- >
- </File>
- <File
- RelativePath="..\dorg2l.c"
- >
- </File>
- <File
- RelativePath="..\dorg2r.c"
- >
- </File>
- <File
- RelativePath="..\dorgbr.c"
- >
- </File>
- <File
- RelativePath="..\dorghr.c"
- >
- </File>
- <File
- RelativePath="..\dorgl2.c"
- >
- </File>
- <File
- RelativePath="..\dorglq.c"
- >
- </File>
- <File
- RelativePath="..\dorgql.c"
- >
- </File>
- <File
- RelativePath="..\dorgqr.c"
- >
- </File>
- <File
- RelativePath="..\dorgr2.c"
- >
- </File>
- <File
- RelativePath="..\dorgrq.c"
- >
- </File>
- <File
- RelativePath="..\dorgtr.c"
- >
- </File>
- <File
- RelativePath="..\dorm2l.c"
- >
- </File>
- <File
- RelativePath="..\dorm2r.c"
- >
- </File>
- <File
- RelativePath="..\dormbr.c"
- >
- </File>
- <File
- RelativePath="..\dormhr.c"
- >
- </File>
- <File
- RelativePath="..\dorml2.c"
- >
- </File>
- <File
- RelativePath="..\dormlq.c"
- >
- </File>
- <File
- RelativePath="..\dormql.c"
- >
- </File>
- <File
- RelativePath="..\dormqr.c"
- >
- </File>
- <File
- RelativePath="..\dormr2.c"
- >
- </File>
- <File
- RelativePath="..\dormr3.c"
- >
- </File>
- <File
- RelativePath="..\dormrq.c"
- >
- </File>
- <File
- RelativePath="..\dormrz.c"
- >
- </File>
- <File
- RelativePath="..\dpocon.c"
- >
- </File>
- <File
- RelativePath="..\dpotf2.c"
- >
- </File>
- <File
- RelativePath="..\dpotrf.c"
- >
- </File>
- <File
- RelativePath="..\dpotrs.c"
- >
- </File>
- <File
- RelativePath="..\dpptrf.c"
- >
- </File>
- <File
- RelativePath="..\drscl.c"
- >
- </File>
- <File
- RelativePath="..\dspev.c"
- >
- </File>
- <File
- RelativePath="..\dspgst.c"
- >
- </File>
- <File
- RelativePath="..\dspgv.c"
- >
- </File>
- <File
- RelativePath="..\dsptrd.c"
- >
- </File>
- <File
- RelativePath="..\dsptrf.c"
- >
- </File>
- <File
- RelativePath="..\dsteqr.c"
- >
- </File>
- <File
- RelativePath="..\dsterf.c"
- >
- </File>
- <File
- RelativePath="..\dsycon.c"
- >
- </File>
- <File
- RelativePath="..\dsyev.c"
- >
- </File>
- <File
- RelativePath="..\dsysv.c"
- >
- </File>
- <File
- RelativePath="..\dsytd2.c"
- >
- </File>
- <File
- RelativePath="..\dsytf2.c"
- >
- </File>
- <File
- RelativePath="..\dsytrd.c"
- >
- </File>
- <File
- RelativePath="..\dsytrf.c"
- >
- </File>
- <File
- RelativePath="..\dsytri.c"
- >
- </File>
- <File
- RelativePath="..\dsytrs.c"
- >
- </File>
- <File
- RelativePath="..\dtgevc.c"
- >
- </File>
- <File
- RelativePath="..\dtgex2.c"
- >
- </File>
- <File
- RelativePath="..\dtgexc.c"
- >
- </File>
- <File
- RelativePath="..\dtgsen.c"
- >
- </File>
- <File
- RelativePath="..\dtgsy2.c"
- >
- </File>
- <File
- RelativePath="..\dtgsyl.c"
- >
- </File>
- <File
- RelativePath="..\dtrcon.c"
- >
- </File>
- <File
- RelativePath="..\dtrevc.c"
- >
- </File>
- <File
- RelativePath="..\dtrexc.c"
- >
- </File>
- <File
- RelativePath="..\dtrsen.c"
- >
- </File>
- <File
- RelativePath="..\dtrsyl.c"
- >
- </File>
- <File
- RelativePath="..\dtrti2.c"
- >
- </File>
- <File
- RelativePath="..\dtrtri.c"
- >
- </File>
- <File
- RelativePath="..\dtrtrs.c"
- >
- </File>
- <File
- RelativePath="..\dtzrqf.c"
- >
- </File>
- <File
- RelativePath="..\dtzrzf.c"
- >
- </File>
- <File
- RelativePath="..\dzsum1.c"
- >
- </File>
- <File
- RelativePath="..\ieeeck.c"
- >
- </File>
- <File
- RelativePath="..\ilaenv.c"
- >
- </File>
- <File
- RelativePath="..\iparmq.c"
- >
- </File>
- <File
- RelativePath="..\izmax1.c"
- >
- </File>
- <File
- RelativePath="..\lsame.c"
- >
- </File>
- <File
- RelativePath="..\slamch.c"
- >
- </File>
- <File
- RelativePath="..\xerbla.c"
- >
- </File>
- <File
- RelativePath="..\zbdsqr.c"
- >
- </File>
- <File
- RelativePath="..\zdrot.c"
- >
- </File>
- <File
- RelativePath="..\zdrscl.c"
- >
- </File>
- <File
- RelativePath="..\zgebak.c"
- >
- </File>
- <File
- RelativePath="..\zgebal.c"
- >
- </File>
- <File
- RelativePath="..\zgebd2.c"
- >
- </File>
- <File
- RelativePath="..\zgebrd.c"
- >
- </File>
- <File
- RelativePath="..\zgecon.c"
- >
- </File>
- <File
- RelativePath="..\zgees.c"
- >
- </File>
- <File
- RelativePath="..\zgeev.c"
- >
- </File>
- <File
- RelativePath="..\zgehd2.c"
- >
- </File>
- <File
- RelativePath="..\zgehrd.c"
- >
- </File>
- <File
- RelativePath="..\zgelq2.c"
- >
- </File>
- <File
- RelativePath="..\zgelqf.c"
- >
- </File>
- <File
- RelativePath="..\zgelsy.c"
- >
- </File>
- <File
- RelativePath="..\zgeqp3.c"
- >
- </File>
- <File
- RelativePath="..\zgeqpf.c"
- >
- </File>
- <File
- RelativePath="..\zgeqr2.c"
- >
- </File>
- <File
- RelativePath="..\zgeqrf.c"
- >
- </File>
- <File
- RelativePath="..\zgesc2.c"
- >
- </File>
- <File
- RelativePath="..\zgesvd.c"
- >
- </File>
- <File
- RelativePath="..\zgetc2.c"
- >
- </File>
- <File
- RelativePath="..\zgetf2.c"
- >
- </File>
- <File
- RelativePath="..\zgetrf.c"
- >
- </File>
- <File
- RelativePath="..\zgetri.c"
- >
- </File>
- <File
- RelativePath="..\zgetrs.c"
- >
- </File>
- <File
- RelativePath="..\zggbak.c"
- >
- </File>
- <File
- RelativePath="..\zggbal.c"
- >
- </File>
- <File
- RelativePath="..\zgges.c"
- >
- </File>
- <File
- RelativePath="..\zggev.c"
- >
- </File>
- <File
- RelativePath="..\zgghrd.c"
- >
- </File>
- <File
- RelativePath="..\zheev.c"
- >
- </File>
- <File
- RelativePath="..\zhetd2.c"
- >
- </File>
- <File
- RelativePath="..\zhetrd.c"
- >
- </File>
- <File
- RelativePath="..\zhgeqz.c"
- >
- </File>
- <File
- RelativePath="..\zhseqr.c"
- >
- </File>
- <File
- RelativePath="..\zlabrd.c"
- >
- </File>
- <File
- RelativePath="..\zlacgv.c"
- >
- </File>
- <File
- RelativePath="..\zlacn2.c"
- >
- </File>
- <File
- RelativePath="..\zlacon.c"
- >
- </File>
- <File
- RelativePath="..\zlacpy.c"
- >
- </File>
- <File
- RelativePath="..\zladiv.c"
- >
- </File>
- <File
- RelativePath="..\zlahqr.c"
- >
- </File>
- <File
- RelativePath="..\zlahr2.c"
- >
- </File>
- <File
- RelativePath="..\zlahrd.c"
- >
- </File>
- <File
- RelativePath="..\zlaic1.c"
- >
- </File>
- <File
- RelativePath="..\zlange.c"
- >
- </File>
- <File
- RelativePath="..\zlanhe.c"
- >
- </File>
- <File
- RelativePath="..\zlanhs.c"
- >
- </File>
- <File
- RelativePath="..\zlaqp2.c"
- >
- </File>
- <File
- RelativePath="..\zlaqps.c"
- >
- </File>
- <File
- RelativePath="..\zlaqr0.c"
- >
- </File>
- <File
- RelativePath="..\zlaqr1.c"
- >
- </File>
- <File
- RelativePath="..\zlaqr2.c"
- >
- </File>
- <File
- RelativePath="..\zlaqr3.c"
- >
- </File>
- <File
- RelativePath="..\zlaqr4.c"
- >
- </File>
- <File
- RelativePath="..\zlaqr5.c"
- >
- </File>
- <File
- RelativePath="..\zlarf.c"
- >
- </File>
- <File
- RelativePath="..\zlarfb.c"
- >
- </File>
- <File
- RelativePath="..\zlarfg.c"
- >
- </File>
- <File
- RelativePath="..\zlarft.c"
- >
- </File>
- <File
- RelativePath="..\zlarfx.c"
- >
- <FileConfiguration
- Name="Release|Win32"
- >
- <Tool
- Name="VCCLCompilerTool"
- Optimization="0"
- />
- </FileConfiguration>
- <FileConfiguration
- Name="Release|x64"
- >
- <Tool
- Name="VCCLCompilerTool"
- Optimization="0"
- />
- </FileConfiguration>
- </File>
- <File
- RelativePath="..\zlartg.c"
- >
- </File>
- <File
- RelativePath="..\zlarz.c"
- >
- </File>
- <File
- RelativePath="..\zlarzb.c"
- >
- </File>
- <File
- RelativePath="..\zlarzt.c"
- >
- </File>
- <File
- RelativePath="..\zlascl.c"
- >
- </File>
- <File
- RelativePath="..\zlaset.c"
- >
- </File>
- <File
- RelativePath="..\zlasr.c"
- >
- </File>
- <File
- RelativePath="..\zlassq.c"
- >
- </File>
- <File
- RelativePath="..\zlaswp.c"
- >
- </File>
- <File
- RelativePath="..\zlatdf.c"
- >
- </File>
- <File
- RelativePath="..\zlatrd.c"
- >
- </File>
- <File
- RelativePath="..\zlatrs.c"
- >
- </File>
- <File
- RelativePath="..\zlatrz.c"
- >
- </File>
- <File
- RelativePath="..\zpotf2.c"
- >
- </File>
- <File
- RelativePath="..\zpotrf.c"
- >
- </File>
- <File
- RelativePath="..\zrot.c"
- >
- </File>
- <File
- RelativePath="..\zsteqr.c"
- >
- </File>
- <File
- RelativePath="..\ztgevc.c"
- >
- </File>
- <File
- RelativePath="..\ztgex2.c"
- >
- </File>
- <File
- RelativePath="..\ztgexc.c"
- >
- </File>
- <File
- RelativePath="..\ztgsen.c"
- >
- </File>
- <File
- RelativePath="..\ztgsy2.c"
- >
- </File>
- <File
- RelativePath="..\ztgsyl.c"
- >
- </File>
- <File
- RelativePath="..\ztrevc.c"
- >
- </File>
- <File
- RelativePath="..\ztrexc.c"
- >
- </File>
- <File
- RelativePath="..\ztrsen.c"
- >
- </File>
- <File
- RelativePath="..\ztrsyl.c"
- >
- </File>
- <File
- RelativePath="..\ztrti2.c"
- >
- </File>
- <File
- RelativePath="..\ztrtri.c"
- >
- </File>
- <File
- RelativePath="..\ztzrzf.c"
- >
- </File>
- <File
- RelativePath="..\zung2l.c"
- >
- </File>
- <File
- RelativePath="..\zung2r.c"
- >
- </File>
- <File
- RelativePath="..\zungbr.c"
- >
- </File>
- <File
- RelativePath="..\zunghr.c"
- >
- </File>
- <File
- RelativePath="..\zungl2.c"
- >
- </File>
- <File
- RelativePath="..\zunglq.c"
- >
- </File>
- <File
- RelativePath="..\zungql.c"
- >
- </File>
- <File
- RelativePath="..\zungqr.c"
- >
- </File>
- <File
- RelativePath="..\zungtr.c"
- >
- </File>
- <File
- RelativePath="..\zunm2r.c"
- >
- </File>
- <File
- RelativePath="..\zunmbr.c"
- >
- </File>
- <File
- RelativePath="..\zunml2.c"
- >
- </File>
- <File
- RelativePath="..\zunmlq.c"
- >
- </File>
- <File
- RelativePath="..\zunmqr.c"
- >
- </File>
- <File
- RelativePath="..\zunmr3.c"
- >
- </File>
- <File
- RelativePath="..\zunmrz.c"
- >
- </File>
- </Filter>
- <Filter
- Name="Header Files"
- Filter="h;hpp;hxx;hm;inl;inc;xsd"
- >
- </Filter>
- <Filter
- Name="Resource Files"
- Filter="rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe;resx"
- >
- </Filter>
- <Filter
- Name="Fortran Files"
- >
- <File
- RelativePath="..\dbdsqr.f"
- >
- </File>
- <File
- RelativePath="..\dgebak.f"
- >
- </File>
- <File
- RelativePath="..\dgebal.f"
- >
- </File>
- <File
- RelativePath="..\dgebd2.f"
- >
- </File>
- <File
- RelativePath="..\dgebrd.f"
- >
- </File>
- <File
- RelativePath="..\dgecon.f"
- >
- </File>
- <File
- RelativePath="..\dgeequ.f"
- >
- </File>
- <File
- RelativePath="..\dgees.f"
- >
- </File>
- <File
- RelativePath="..\dgeesx.f"
- >
- </File>
- <File
- RelativePath="..\dgeev.f"
- >
- </File>
- <File
- RelativePath="..\dgegs.f"
- >
- </File>
- <File
- RelativePath="..\dgehd2.f"
- >
- </File>
- <File
- RelativePath="..\dgehrd.f"
- >
- </File>
- <File
- RelativePath="..\dgelq2.f"
- >
- </File>
- <File
- RelativePath="..\dgelqf.f"
- >
- </File>
- <File
- RelativePath="..\dgels.f"
- >
- </File>
- <File
- RelativePath="..\dgelss.f"
- >
- </File>
- <File
- RelativePath="..\dgelsx.f"
- >
- </File>
- <File
- RelativePath="..\dgelsy.f"
- >
- </File>
- <File
- RelativePath="..\dgeql2.f"
- >
- </File>
- <File
- RelativePath="..\dgeqlf.f"
- >
- </File>
- <File
- RelativePath="..\dgeqp3.f"
- >
- </File>
- <File
- RelativePath="..\dgeqpf.f"
- >
- </File>
- <File
- RelativePath="..\dgeqr2.f"
- >
- </File>
- <File
- RelativePath="..\dgeqrf.f"
- >
- </File>
- <File
- RelativePath="..\dgerfs.f"
- >
- </File>
- <File
- RelativePath="..\dgerq2.f"
- >
- </File>
- <File
- RelativePath="..\dgerqf.f"
- >
- </File>
- <File
- RelativePath="..\dgesc2.f"
- >
- </File>
- <File
- RelativePath="..\dgesv.f"
- >
- </File>
- <File
- RelativePath="..\dgesvd.f"
- >
- </File>
- <File
- RelativePath="..\dgesvx.f"
- >
- </File>
- <File
- RelativePath="..\dgetc2.f"
- >
- </File>
- <File
- RelativePath="..\dgetf2.f"
- >
- </File>
- <File
- RelativePath="..\dgetrf.f"
- >
- </File>
- <File
- RelativePath="..\dgetri.f"
- >
- </File>
- <File
- RelativePath="..\dgetrs.f"
- >
- </File>
- <File
- RelativePath="..\dggbak.f"
- >
- </File>
- <File
- RelativePath="..\dggbal.f"
- >
- </File>
- <File
- RelativePath="..\dgges.f"
- >
- </File>
- <File
- RelativePath="..\dggev.f"
- >
- </File>
- <File
- RelativePath="..\dgghrd.f"
- >
- </File>
- <File
- RelativePath="..\dhgeqz.f"
- >
- </File>
- <File
- RelativePath="..\dhseqr.f"
- >
- </File>
- <File
- RelativePath="..\disnan.f"
- >
- </File>
- <File
- RelativePath="..\dlabad.f"
- >
- </File>
- <File
- RelativePath="..\dlabrd.f"
- >
- </File>
- <File
- RelativePath="..\dlacn2.f"
- >
- </File>
- <File
- RelativePath="..\dlacon.f"
- >
- </File>
- <File
- RelativePath="..\dlacpy.f"
- >
- </File>
- <File
- RelativePath="..\dladiv.f"
- >
- </File>
- <File
- RelativePath="..\dlae2.f"
- >
- </File>
- <File
- RelativePath="..\dlaev2.f"
- >
- </File>
- <File
- RelativePath="..\dlaexc.f"
- >
- </File>
- <File
- RelativePath="..\dlag2.f"
- >
- </File>
- <File
- RelativePath="..\dlagv2.f"
- >
- </File>
- <File
- RelativePath="..\dlahqr.f"
- >
- </File>
- <File
- RelativePath="..\dlahr2.f"
- >
- </File>
- <File
- RelativePath="..\dlahrd.f"
- >
- </File>
- <File
- RelativePath="..\dlaic1.f"
- >
- </File>
- <File
- RelativePath="..\dlaisnan.f"
- >
- </File>
- <File
- RelativePath="..\dlaln2.f"
- >
- </File>
- <File
- RelativePath="..\dlamch.f"
- >
- </File>
- <File
- RelativePath="..\dlange.f"
- >
- </File>
- <File
- RelativePath="..\dlanhs.f"
- >
- </File>
- <File
- RelativePath="..\dlansp.f"
- >
- </File>
- <File
- RelativePath="..\dlanst.f"
- >
- </File>
- <File
- RelativePath="..\dlansy.f"
- >
- </File>
- <File
- RelativePath="..\dlantr.f"
- >
- </File>
- <File
- RelativePath="..\dlanv2.f"
- >
- </File>
- <File
- RelativePath="..\dlapmt.f"
- >
- </File>
- <File
- RelativePath="..\dlapy2.f"
- >
- </File>
- <File
- RelativePath="..\dlapy3.f"
- >
- </File>
- <File
- RelativePath="..\dlaqge.f"
- >
- </File>
- <File
- RelativePath="..\dlaqp2.f"
- >
- </File>
- <File
- RelativePath="..\dlaqps.f"
- >
- </File>
- <File
- RelativePath="..\dlaqr0.f"
- >
- </File>
- <File
- RelativePath="..\dlaqr1.f"
- >
- </File>
- <File
- RelativePath="..\dlaqr2.f"
- >
- </File>
- <File
- RelativePath="..\dlaqr3.f"
- >
- </File>
- <File
- RelativePath="..\dlaqr4.f"
- >
- </File>
- <File
- RelativePath="..\dlaqr5.f"
- >
- </File>
- <File
- RelativePath="..\dlarf.f"
- >
- </File>
- <File
- RelativePath="..\dlarfb.f"
- >
- </File>
- <File
- RelativePath="..\dlarfg.f"
- >
- </File>
- <File
- RelativePath="..\dlarft.f"
- >
- </File>
- <File
- RelativePath="..\dlarfx.f"
- >
- </File>
- <File
- RelativePath="..\dlartg.f"
- >
- </File>
- <File
- RelativePath="..\dlarz.f"
- >
- </File>
- <File
- RelativePath="..\dlarzb.f"
- >
- </File>
- <File
- RelativePath="..\dlarzt.f"
- >
- </File>
- <File
- RelativePath="..\dlas2.f"
- >
- </File>
- <File
- RelativePath="..\dlascl.f"
- >
- </File>
- <File
- RelativePath="..\dlaset.f"
- >
- </File>
- <File
- RelativePath="..\dlasq1.f"
- >
- </File>
- <File
- RelativePath="..\dlasq2.f"
- >
- </File>
- <File
- RelativePath="..\dlasq3.f"
- >
- </File>
- <File
- RelativePath="..\dlasq4.f"
- >
- </File>
- <File
- RelativePath="..\dlasq5.f"
- >
- </File>
- <File
- RelativePath="..\dlasq6.f"
- >
- </File>
- <File
- RelativePath="..\dlasr.f"
- >
- </File>
- <File
- RelativePath="..\dlasrt.f"
- >
- </File>
- <File
- RelativePath="..\dlassq.f"
- >
- </File>
- <File
- RelativePath="..\dlasv2.f"
- >
- </File>
- <File
- RelativePath="..\dlaswp.f"
- >
- </File>
- <File
- RelativePath="..\dlasy2.f"
- >
- </File>
- <File
- RelativePath="..\dlasyf.f"
- >
- </File>
- <File
- RelativePath="..\dlatdf.f"
- >
- </File>
- <File
- RelativePath="..\dlatrd.f"
- >
- </File>
- <File
- RelativePath="..\dlatrs.f"
- >
- </File>
- <File
- RelativePath="..\dlatrz.f"
- >
- </File>
- <File
- RelativePath="..\dlatzm.f"
- >
- </File>
- <File
- RelativePath="..\dlazq3.f"
- >
- </File>
- <File
- RelativePath="..\dlazq4.f"
- >
- </File>
- <File
- RelativePath="..\dopgtr.f"
- >
- </File>
- <File
- RelativePath="..\dorg2l.f"
- >
- </File>
- <File
- RelativePath="..\dorg2r.f"
- >
- </File>
- <File
- RelativePath="..\dorgbr.f"
- >
- </File>
- <File
- RelativePath="..\dorghr.f"
- >
- </File>
- <File
- RelativePath="..\dorgl2.f"
- >
- </File>
- <File
- RelativePath="..\dorglq.f"
- >
- </File>
- <File
- RelativePath="..\dorgql.f"
- >
- </File>
- <File
- RelativePath="..\dorgqr.f"
- >
- </File>
- <File
- RelativePath="..\dorgr2.f"
- >
- </File>
- <File
- RelativePath="..\dorgrq.f"
- >
- </File>
- <File
- RelativePath="..\dorgtr.f"
- >
- </File>
- <File
- RelativePath="..\dorm2l.f"
- >
- </File>
- <File
- RelativePath="..\dorm2r.f"
- >
- </File>
- <File
- RelativePath="..\dormbr.f"
- >
- </File>
- <File
- RelativePath="..\dormhr.f"
- >
- </File>
- <File
- RelativePath="..\dorml2.f"
- >
- </File>
- <File
- RelativePath="..\dormlq.f"
- >
- </File>
- <File
- RelativePath="..\dormql.f"
- >
- </File>
- <File
- RelativePath="..\dormqr.f"
- >
- </File>
- <File
- RelativePath="..\dormr2.f"
- >
- </File>
- <File
- RelativePath="..\dormr3.f"
- >
- </File>
- <File
- RelativePath="..\dormrq.f"
- >
- </File>
- <File
- RelativePath="..\dormrz.f"
- >
- </File>
- <File
- RelativePath="..\dpocon.f"
- >
- </File>
- <File
- RelativePath="..\dpotf2.f"
- >
- </File>
- <File
- RelativePath="..\dpotrf.f"
- >
- </File>
- <File
- RelativePath="..\dpotrs.f"
- >
- </File>
- <File
- RelativePath="..\dpptrf.f"
- >
- </File>
- <File
- RelativePath="..\drscl.f"
- >
- </File>
- <File
- RelativePath="..\dspev.f"
- >
- </File>
- <File
- RelativePath="..\dspgst.f"
- >
- </File>
- <File
- RelativePath="..\dspgv.f"
- >
- </File>
- <File
- RelativePath="..\dsptrd.f"
- >
- </File>
- <File
- RelativePath="..\dsptrf.f"
- >
- </File>
- <File
- RelativePath="..\dsteqr.f"
- >
- </File>
- <File
- RelativePath="..\dsterf.f"
- >
- </File>
- <File
- RelativePath="..\dsycon.f"
- >
- </File>
- <File
- RelativePath="..\dsyev.f"
- >
- </File>
- <File
- RelativePath="..\dsysv.f"
- >
- </File>
- <File
- RelativePath="..\dsytd2.f"
- >
- </File>
- <File
- RelativePath="..\dsytf2.f"
- >
- </File>
- <File
- RelativePath="..\dsytrd.f"
- >
- </File>
- <File
- RelativePath="..\dsytrf.f"
- >
- </File>
- <File
- RelativePath="..\dsytri.f"
- >
- </File>
- <File
- RelativePath="..\dsytrs.f"
- >
- </File>
- <File
- RelativePath="..\dtgevc.f"
- >
- </File>
- <File
- RelativePath="..\dtgex2.f"
- >
- </File>
- <File
- RelativePath="..\dtgexc.f"
- >
- </File>
- <File
- RelativePath="..\dtgsen.f"
- >
- </File>
- <File
- RelativePath="..\dtgsy2.f"
- >
- </File>
- <File
- RelativePath="..\dtgsyl.f"
- >
- </File>
- <File
- RelativePath="..\dtrcon.f"
- >
- </File>
- <File
- RelativePath="..\dtrevc.f"
- >
- </File>
- <File
- RelativePath="..\dtrexc.f"
- >
- </File>
- <File
- RelativePath="..\dtrsen.f"
- >
- </File>
- <File
- RelativePath="..\dtrsyl.f"
- >
- </File>
- <File
- RelativePath="..\dtrti2.f"
- >
- </File>
- <File
- RelativePath="..\dtrtri.f"
- >
- </File>
- <File
- RelativePath="..\dtrtrs.f"
- >
- </File>
- <File
- RelativePath="..\dtzrqf.f"
- >
- </File>
- <File
- RelativePath="..\dtzrzf.f"
- >
- </File>
- <File
- RelativePath="..\dzsum1.f"
- >
- </File>
- <File
- RelativePath="..\ieeeck.f"
- >
- </File>
- <File
- RelativePath="..\ilaenv.f"
- >
- </File>
- <File
- RelativePath="..\iparmq.f"
- >
- </File>
- <File
- RelativePath="..\izmax1.f"
- >
- </File>
- <File
- RelativePath="..\lsame.f"
- >
- </File>
- <File
- RelativePath="..\slamch.f"
- >
- </File>
- <File
- RelativePath="..\xerbla.f"
- >
- </File>
- <File
- RelativePath="..\zbdsqr.f"
- >
- </File>
- <File
- RelativePath="..\zdrot.f"
- >
- </File>
- <File
- RelativePath="..\zdrscl.f"
- >
- </File>
- <File
- RelativePath="..\zgebak.f"
- >
- </File>
- <File
- RelativePath="..\zgebal.f"
- >
- </File>
- <File
- RelativePath="..\zgebd2.f"
- >
- </File>
- <File
- RelativePath="..\zgebrd.f"
- >
- </File>
- <File
- RelativePath="..\zgecon.f"
- >
- </File>
- <File
- RelativePath="..\zgees.f"
- >
- </File>
- <File
- RelativePath="..\zgeev.f"
- >
- </File>
- <File
- RelativePath="..\zgehd2.f"
- >
- </File>
- <File
- RelativePath="..\zgehrd.f"
- >
- </File>
- <File
- RelativePath="..\zgelq2.f"
- >
- </File>
- <File
- RelativePath="..\zgelqf.f"
- >
- </File>
- <File
- RelativePath="..\zgelsy.f"
- >
- </File>
- <File
- RelativePath="..\zgeqp3.f"
- >
- </File>
- <File
- RelativePath="..\zgeqpf.f"
- >
- </File>
- <File
- RelativePath="..\zgeqr2.f"
- >
- </File>
- <File
- RelativePath="..\zgeqrf.f"
- >
- </File>
- <File
- RelativePath="..\zgesc2.f"
- >
- </File>
- <File
- RelativePath="..\zgesvd.f"
- >
- </File>
- <File
- RelativePath="..\zgetc2.f"
- >
- </File>
- <File
- RelativePath="..\zgetf2.f"
- >
- </File>
- <File
- RelativePath="..\zgetrf.f"
- >
- </File>
- <File
- RelativePath="..\zgetri.f"
- >
- </File>
- <File
- RelativePath="..\zgetrs.f"
- >
- </File>
- <File
- RelativePath="..\zggbak.f"
- >
- </File>
- <File
- RelativePath="..\zggbal.f"
- >
- </File>
- <File
- RelativePath="..\zgges.f"
- >
- </File>
- <File
- RelativePath="..\zggev.f"
- >
- </File>
- <File
- RelativePath="..\zgghrd.f"
- >
- </File>
- <File
- RelativePath="..\zheev.f"
- >
- </File>
- <File
- RelativePath="..\zhetd2.f"
- >
- </File>
- <File
- RelativePath="..\zhetrd.f"
- >
- </File>
- <File
- RelativePath="..\zhgeqz.f"
- >
- </File>
- <File
- RelativePath="..\zhseqr.f"
- >
- </File>
- <File
- RelativePath="..\zlabrd.f"
- >
- </File>
- <File
- RelativePath="..\zlacgv.f"
- >
- </File>
- <File
- RelativePath="..\zlacn2.f"
- >
- </File>
- <File
- RelativePath="..\zlacon.f"
- >
- </File>
- <File
- RelativePath="..\zlacpy.f"
- >
- </File>
- <File
- RelativePath="..\zladiv.f"
- >
- </File>
- <File
- RelativePath="..\zlahqr.f"
- >
- </File>
- <File
- RelativePath="..\zlahr2.f"
- >
- </File>
- <File
- RelativePath="..\zlahrd.f"
- >
- </File>
- <File
- RelativePath="..\zlaic1.f"
- >
- </File>
- <File
- RelativePath="..\zlange.f"
- >
- </File>
- <File
- RelativePath="..\zlanhe.f"
- >
- </File>
- <File
- RelativePath="..\zlanhs.f"
- >
- </File>
- <File
- RelativePath="..\zlaqp2.f"
- >
- </File>
- <File
- RelativePath="..\zlaqps.f"
- >
- </File>
- <File
- RelativePath="..\zlaqr0.f"
- >
- </File>
- <File
- RelativePath="..\zlaqr1.f"
- >
- </File>
- <File
- RelativePath="..\zlaqr2.f"
- >
- </File>
- <File
- RelativePath="..\zlaqr3.f"
- >
- </File>
- <File
- RelativePath="..\zlaqr4.f"
- >
- </File>
- <File
- RelativePath="..\zlaqr5.f"
- >
- </File>
- <File
- RelativePath="..\zlarf.f"
- >
- </File>
- <File
- RelativePath="..\zlarfb.f"
- >
- </File>
- <File
- RelativePath="..\zlarfg.f"
- >
- </File>
- <File
- RelativePath="..\zlarft.f"
- >
- </File>
- <File
- RelativePath="..\zlarfx.f"
- >
- </File>
- <File
- RelativePath="..\zlartg.f"
- >
- </File>
- <File
- RelativePath="..\zlarz.f"
- >
- </File>
- <File
- RelativePath="..\zlarzb.f"
- >
- </File>
- <File
- RelativePath="..\zlarzt.f"
- >
- </File>
- <File
- RelativePath="..\zlascl.f"
- >
- </File>
- <File
- RelativePath="..\zlaset.f"
- >
- </File>
- <File
- RelativePath="..\zlasr.f"
- >
- </File>
- <File
- RelativePath="..\zlassq.f"
- >
- </File>
- <File
- RelativePath="..\zlaswp.f"
- >
- </File>
- <File
- RelativePath="..\zlatdf.f"
- >
- </File>
- <File
- RelativePath="..\zlatrd.f"
- >
- </File>
- <File
- RelativePath="..\zlatrs.f"
- >
- </File>
- <File
- RelativePath="..\zlatrz.f"
- >
- </File>
- <File
- RelativePath="..\zpotf2.f"
- >
- </File>
- <File
- RelativePath="..\zpotrf.f"
- >
- </File>
- <File
- RelativePath="..\zrot.f"
- >
- </File>
- <File
- RelativePath="..\zsteqr.f"
- >
- </File>
- <File
- RelativePath="..\ztgevc.f"
- >
- </File>
- <File
- RelativePath="..\ztgex2.f"
- >
- </File>
- <File
- RelativePath="..\ztgexc.f"
- >
- </File>
- <File
- RelativePath="..\ztgsen.f"
- >
- </File>
- <File
- RelativePath="..\ztgsy2.f"
- >
- </File>
- <File
- RelativePath="..\ztgsyl.f"
- >
- </File>
- <File
- RelativePath="..\ztrevc.f"
- >
- </File>
- <File
- RelativePath="..\ztrexc.f"
- >
- </File>
- <File
- RelativePath="..\ztrsen.f"
- >
- </File>
- <File
- RelativePath="..\ztrsyl.f"
- >
- </File>
- <File
- RelativePath="..\ztrti2.f"
- >
- </File>
- <File
- RelativePath="..\ztrtri.f"
- >
- </File>
- <File
- RelativePath="..\ztzrzf.f"
- >
- </File>
- <File
- RelativePath="..\zung2l.f"
- >
- </File>
- <File
- RelativePath="..\zung2r.f"
- >
- </File>
- <File
- RelativePath="..\zungbr.f"
- >
- </File>
- <File
- RelativePath="..\zunghr.f"
- >
- </File>
- <File
- RelativePath="..\zungl2.f"
- >
- </File>
- <File
- RelativePath="..\zunglq.f"
- >
- </File>
- <File
- RelativePath="..\zungql.f"
- >
- </File>
- <File
- RelativePath="..\zungqr.f"
- >
- </File>
- <File
- RelativePath="..\zungtr.f"
- >
- </File>
- <File
- RelativePath="..\zunm2r.f"
- >
- </File>
- <File
- RelativePath="..\zunmbr.f"
- >
- </File>
- <File
- RelativePath="..\zunml2.f"
- >
- </File>
- <File
- RelativePath="..\zunmlq.f"
- >
- </File>
- <File
- RelativePath="..\zunmqr.f"
- >
- </File>
- <File
- RelativePath="..\zunmr3.f"
- >
- </File>
- <File
- RelativePath="..\zunmrz.f"
- >
- </File>
- </Filter>
- <File
- RelativePath="..\..\..\..\bin\libf2c.lib"
- >
- </File>
- <File
- RelativePath="..\Makefile.am"
- >
- </File>
- </Files>
- <Globals>
- </Globals>
-</VisualStudioProject>
diff --git a/src/lib/lapack/lsame.f b/src/lib/lapack/lsame.f
deleted file mode 100644
index bf25d86f..00000000
--- a/src/lib/lapack/lsame.f
+++ /dev/null
@@ -1,87 +0,0 @@
- LOGICAL FUNCTION LSAME( CA, CB )
-*
-* -- LAPACK auxiliary routine (version 3.0) --
-* Univ. of Tennessee, Univ. of California Berkeley, NAG Ltd.,
-* Courant Institute, Argonne National Lab, and Rice University
-* September 30, 1994
-*
-* .. Scalar Arguments ..
- CHARACTER CA, CB
-* ..
-*
-* Purpose
-* =======
-*
-* LSAME returns .TRUE. if CA is the same letter as CB regardless of
-* case.
-*
-* Arguments
-* =========
-*
-* CA (input) CHARACTER*1
-* CB (input) CHARACTER*1
-* CA and CB specify the single characters to be compared.
-*
-* =====================================================================
-*
-* .. Intrinsic Functions ..
- INTRINSIC ICHAR
-* ..
-* .. Local Scalars ..
- INTEGER INTA, INTB, ZCODE
-* ..
-* .. Executable Statements ..
-*
-* Test if the characters are equal
-*
- LSAME = CA.EQ.CB
- IF( LSAME )
- $ RETURN
-*
-* Now test for equivalence if both characters are alphabetic.
-*
- ZCODE = ICHAR( 'Z' )
-*
-* Use 'Z' rather than 'A' so that ASCII can be detected on Prime
-* machines, on which ICHAR returns a value with bit 8 set.
-* ICHAR('A') on Prime machines returns 193 which is the same as
-* ICHAR('A') on an EBCDIC machine.
-*
- INTA = ICHAR( CA )
- INTB = ICHAR( CB )
-*
- IF( ZCODE.EQ.90 .OR. ZCODE.EQ.122 ) THEN
-*
-* ASCII is assumed - ZCODE is the ASCII code of either lower or
-* upper case 'Z'.
-*
- IF( INTA.GE.97 .AND. INTA.LE.122 ) INTA = INTA - 32
- IF( INTB.GE.97 .AND. INTB.LE.122 ) INTB = INTB - 32
-*
- ELSE IF( ZCODE.EQ.233 .OR. ZCODE.EQ.169 ) THEN
-*
-* EBCDIC is assumed - ZCODE is the EBCDIC code of either lower or
-* upper case 'Z'.
-*
- IF( INTA.GE.129 .AND. INTA.LE.137 .OR.
- $ INTA.GE.145 .AND. INTA.LE.153 .OR.
- $ INTA.GE.162 .AND. INTA.LE.169 ) INTA = INTA + 64
- IF( INTB.GE.129 .AND. INTB.LE.137 .OR.
- $ INTB.GE.145 .AND. INTB.LE.153 .OR.
- $ INTB.GE.162 .AND. INTB.LE.169 ) INTB = INTB + 64
-*
- ELSE IF( ZCODE.EQ.218 .OR. ZCODE.EQ.250 ) THEN
-*
-* ASCII is assumed, on Prime machines - ZCODE is the ASCII code
-* plus 128 of either lower or upper case 'Z'.
-*
- IF( INTA.GE.225 .AND. INTA.LE.250 ) INTA = INTA - 32
- IF( INTB.GE.225 .AND. INTB.LE.250 ) INTB = INTB - 32
- END IF
- LSAME = INTA.EQ.INTB
-*
-* RETURN
-*
-* End of LSAME
-*
- END
diff --git a/src/lib/lapack/slamch.f b/src/lib/lapack/slamch.f
deleted file mode 100644
index afb4d368..00000000
--- a/src/lib/lapack/slamch.f
+++ /dev/null
@@ -1,857 +0,0 @@
- REAL FUNCTION SLAMCH( CMACH )
-*
-* -- LAPACK auxiliary routine (version 3.0) --
-* Univ. of Tennessee, Univ. of California Berkeley, NAG Ltd.,
-* Courant Institute, Argonne National Lab, and Rice University
-* October 31, 1992
-*
-* .. Scalar Arguments ..
- CHARACTER CMACH
-* ..
-*
-* Purpose
-* =======
-*
-* SLAMCH determines single precision machine parameters.
-*
-* Arguments
-* =========
-*
-* CMACH (input) CHARACTER*1
-* Specifies the value to be returned by SLAMCH:
-* = 'E' or 'e', SLAMCH := eps
-* = 'S' or 's , SLAMCH := sfmin
-* = 'B' or 'b', SLAMCH := base
-* = 'P' or 'p', SLAMCH := eps*base
-* = 'N' or 'n', SLAMCH := t
-* = 'R' or 'r', SLAMCH := rnd
-* = 'M' or 'm', SLAMCH := emin
-* = 'U' or 'u', SLAMCH := rmin
-* = 'L' or 'l', SLAMCH := emax
-* = 'O' or 'o', SLAMCH := rmax
-*
-* where
-*
-* eps = relative machine precision
-* sfmin = safe minimum, such that 1/sfmin does not overflow
-* base = base of the machine
-* prec = eps*base
-* t = number of (base) digits in the mantissa
-* rnd = 1.0 when rounding occurs in addition, 0.0 otherwise
-* emin = minimum exponent before (gradual) underflow
-* rmin = underflow threshold - base**(emin-1)
-* emax = largest exponent before overflow
-* rmax = overflow threshold - (base**emax)*(1-eps)
-*
-* =====================================================================
-*
-* .. Parameters ..
- REAL ONE, ZERO
- PARAMETER ( ONE = 1.0E+0, ZERO = 0.0E+0 )
-* ..
-* .. Local Scalars ..
- LOGICAL FIRST, LRND
- INTEGER BETA, IMAX, IMIN, IT
- REAL BASE, EMAX, EMIN, EPS, PREC, RMACH, RMAX, RMIN,
- $ RND, SFMIN, SMALL, T
-* ..
-* .. External Functions ..
- LOGICAL LSAME
- EXTERNAL LSAME
-* ..
-* .. External Subroutines ..
- EXTERNAL SLAMC2
-* ..
-* .. Save statement ..
- SAVE FIRST, EPS, SFMIN, BASE, T, RND, EMIN, RMIN,
- $ EMAX, RMAX, PREC
-* ..
-* .. Data statements ..
- DATA FIRST / .TRUE. /
-* ..
-* .. Executable Statements ..
-*
- IF( FIRST ) THEN
- FIRST = .FALSE.
- CALL SLAMC2( BETA, IT, LRND, EPS, IMIN, RMIN, IMAX, RMAX )
- BASE = BETA
- T = IT
- IF( LRND ) THEN
- RND = ONE
- EPS = ( BASE**( 1-IT ) ) / 2
- ELSE
- RND = ZERO
- EPS = BASE**( 1-IT )
- END IF
- PREC = EPS*BASE
- EMIN = IMIN
- EMAX = IMAX
- SFMIN = RMIN
- SMALL = ONE / RMAX
- IF( SMALL.GE.SFMIN ) THEN
-*
-* Use SMALL plus a bit, to avoid the possibility of rounding
-* causing overflow when computing 1/sfmin.
-*
- SFMIN = SMALL*( ONE+EPS )
- END IF
- END IF
-*
- IF( LSAME( CMACH, 'E' ) ) THEN
- RMACH = EPS
- ELSE IF( LSAME( CMACH, 'S' ) ) THEN
- RMACH = SFMIN
- ELSE IF( LSAME( CMACH, 'B' ) ) THEN
- RMACH = BASE
- ELSE IF( LSAME( CMACH, 'P' ) ) THEN
- RMACH = PREC
- ELSE IF( LSAME( CMACH, 'N' ) ) THEN
- RMACH = T
- ELSE IF( LSAME( CMACH, 'R' ) ) THEN
- RMACH = RND
- ELSE IF( LSAME( CMACH, 'M' ) ) THEN
- RMACH = EMIN
- ELSE IF( LSAME( CMACH, 'U' ) ) THEN
- RMACH = RMIN
- ELSE IF( LSAME( CMACH, 'L' ) ) THEN
- RMACH = EMAX
- ELSE IF( LSAME( CMACH, 'O' ) ) THEN
- RMACH = RMAX
- END IF
-*
- SLAMCH = RMACH
- RETURN
-*
-* End of SLAMCH
-*
- END
-*
-************************************************************************
-*
- SUBROUTINE SLAMC1( BETA, T, RND, IEEE1 )
-*
-* -- LAPACK auxiliary routine (version 3.0) --
-* Univ. of Tennessee, Univ. of California Berkeley, NAG Ltd.,
-* Courant Institute, Argonne National Lab, and Rice University
-* October 31, 1992
-*
-* .. Scalar Arguments ..
- LOGICAL IEEE1, RND
- INTEGER BETA, T
-* ..
-*
-* Purpose
-* =======
-*
-* SLAMC1 determines the machine parameters given by BETA, T, RND, and
-* IEEE1.
-*
-* Arguments
-* =========
-*
-* BETA (output) INTEGER
-* The base of the machine.
-*
-* T (output) INTEGER
-* The number of ( BETA ) digits in the mantissa.
-*
-* RND (output) LOGICAL
-* Specifies whether proper rounding ( RND = .TRUE. ) or
-* chopping ( RND = .FALSE. ) occurs in addition. This may not
-* be a reliable guide to the way in which the machine performs
-* its arithmetic.
-*
-* IEEE1 (output) LOGICAL
-* Specifies whether rounding appears to be done in the IEEE
-* 'round to nearest' style.
-*
-* Further Details
-* ===============
-*
-* The routine is based on the routine ENVRON by Malcolm and
-* incorporates suggestions by Gentleman and Marovich. See
-*
-* Malcolm M. A. (1972) Algorithms to reveal properties of
-* floating-point arithmetic. Comms. of the ACM, 15, 949-951.
-*
-* Gentleman W. M. and Marovich S. B. (1974) More on algorithms
-* that reveal properties of floating point arithmetic units.
-* Comms. of the ACM, 17, 276-277.
-*
-* =====================================================================
-*
-* .. Local Scalars ..
- LOGICAL FIRST, LIEEE1, LRND
- INTEGER LBETA, LT
- REAL A, B, C, F, ONE, QTR, SAVEC, T1, T2
-* ..
-* .. External Functions ..
- REAL SLAMC3
- EXTERNAL SLAMC3
-* ..
-* .. Save statement ..
- SAVE FIRST, LIEEE1, LBETA, LRND, LT
-* ..
-* .. Data statements ..
- DATA FIRST / .TRUE. /
-* ..
-* .. Executable Statements ..
-*
- IF( FIRST ) THEN
- FIRST = .FALSE.
- ONE = 1
-*
-* LBETA, LIEEE1, LT and LRND are the local values of BETA,
-* IEEE1, T and RND.
-*
-* Throughout this routine we use the function SLAMC3 to ensure
-* that relevant values are stored and not held in registers, or
-* are not affected by optimizers.
-*
-* Compute a = 2.0**m with the smallest positive integer m such
-* that
-*
-* fl( a + 1.0 ) = a.
-*
- A = 1
- C = 1
-*
-*+ WHILE( C.EQ.ONE )LOOP
- 10 CONTINUE
- IF( C.EQ.ONE ) THEN
- A = 2*A
- C = SLAMC3( A, ONE )
- C = SLAMC3( C, -A )
- GO TO 10
- END IF
-*+ END WHILE
-*
-* Now compute b = 2.0**m with the smallest positive integer m
-* such that
-*
-* fl( a + b ) .gt. a.
-*
- B = 1
- C = SLAMC3( A, B )
-*
-*+ WHILE( C.EQ.A )LOOP
- 20 CONTINUE
- IF( C.EQ.A ) THEN
- B = 2*B
- C = SLAMC3( A, B )
- GO TO 20
- END IF
-*+ END WHILE
-*
-* Now compute the base. a and c are neighbouring floating point
-* numbers in the interval ( beta**t, beta**( t + 1 ) ) and so
-* their difference is beta. Adding 0.25 to c is to ensure that it
-* is truncated to beta and not ( beta - 1 ).
-*
- QTR = ONE / 4
- SAVEC = C
- C = SLAMC3( C, -A )
- LBETA = C + QTR
-*
-* Now determine whether rounding or chopping occurs, by adding a
-* bit less than beta/2 and a bit more than beta/2 to a.
-*
- B = LBETA
- F = SLAMC3( B / 2, -B / 100 )
- C = SLAMC3( F, A )
- IF( C.EQ.A ) THEN
- LRND = .TRUE.
- ELSE
- LRND = .FALSE.
- END IF
- F = SLAMC3( B / 2, B / 100 )
- C = SLAMC3( F, A )
- IF( ( LRND ) .AND. ( C.EQ.A ) )
- $ LRND = .FALSE.
-*
-* Try and decide whether rounding is done in the IEEE 'round to
-* nearest' style. B/2 is half a unit in the last place of the two
-* numbers A and SAVEC. Furthermore, A is even, i.e. has last bit
-* zero, and SAVEC is odd. Thus adding B/2 to A should not change
-* A, but adding B/2 to SAVEC should change SAVEC.
-*
- T1 = SLAMC3( B / 2, A )
- T2 = SLAMC3( B / 2, SAVEC )
- LIEEE1 = ( T1.EQ.A ) .AND. ( T2.GT.SAVEC ) .AND. LRND
-*
-* Now find the mantissa, t. It should be the integer part of
-* log to the base beta of a, however it is safer to determine t
-* by powering. So we find t as the smallest positive integer for
-* which
-*
-* fl( beta**t + 1.0 ) = 1.0.
-*
- LT = 0
- A = 1
- C = 1
-*
-*+ WHILE( C.EQ.ONE )LOOP
- 30 CONTINUE
- IF( C.EQ.ONE ) THEN
- LT = LT + 1
- A = A*LBETA
- C = SLAMC3( A, ONE )
- C = SLAMC3( C, -A )
- GO TO 30
- END IF
-*+ END WHILE
-*
- END IF
-*
- BETA = LBETA
- T = LT
- RND = LRND
- IEEE1 = LIEEE1
- RETURN
-*
-* End of SLAMC1
-*
- END
-*
-************************************************************************
-*
- SUBROUTINE SLAMC2( BETA, T, RND, EPS, EMIN, RMIN, EMAX, RMAX )
-*
-* -- LAPACK auxiliary routine (version 3.0) --
-* Univ. of Tennessee, Univ. of California Berkeley, NAG Ltd.,
-* Courant Institute, Argonne National Lab, and Rice University
-* October 31, 1992
-*
-* .. Scalar Arguments ..
- LOGICAL RND
- INTEGER BETA, EMAX, EMIN, T
- REAL EPS, RMAX, RMIN
-* ..
-*
-* Purpose
-* =======
-*
-* SLAMC2 determines the machine parameters specified in its argument
-* list.
-*
-* Arguments
-* =========
-*
-* BETA (output) INTEGER
-* The base of the machine.
-*
-* T (output) INTEGER
-* The number of ( BETA ) digits in the mantissa.
-*
-* RND (output) LOGICAL
-* Specifies whether proper rounding ( RND = .TRUE. ) or
-* chopping ( RND = .FALSE. ) occurs in addition. This may not
-* be a reliable guide to the way in which the machine performs
-* its arithmetic.
-*
-* EPS (output) REAL
-* The smallest positive number such that
-*
-* fl( 1.0 - EPS ) .LT. 1.0,
-*
-* where fl denotes the computed value.
-*
-* EMIN (output) INTEGER
-* The minimum exponent before (gradual) underflow occurs.
-*
-* RMIN (output) REAL
-* The smallest normalized number for the machine, given by
-* BASE**( EMIN - 1 ), where BASE is the floating point value
-* of BETA.
-*
-* EMAX (output) INTEGER
-* The maximum exponent before overflow occurs.
-*
-* RMAX (output) REAL
-* The largest positive number for the machine, given by
-* BASE**EMAX * ( 1 - EPS ), where BASE is the floating point
-* value of BETA.
-*
-* Further Details
-* ===============
-*
-* The computation of EPS is based on a routine PARANOIA by
-* W. Kahan of the University of California at Berkeley.
-*
-* =====================================================================
-*
-* .. Local Scalars ..
- LOGICAL FIRST, IEEE, IWARN, LIEEE1, LRND
- INTEGER GNMIN, GPMIN, I, LBETA, LEMAX, LEMIN, LT,
- $ NGNMIN, NGPMIN
- REAL A, B, C, HALF, LEPS, LRMAX, LRMIN, ONE, RBASE,
- $ SIXTH, SMALL, THIRD, TWO, ZERO
-* ..
-* .. External Functions ..
- REAL SLAMC3
- EXTERNAL SLAMC3
-* ..
-* .. External Subroutines ..
- EXTERNAL SLAMC1, SLAMC4, SLAMC5
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC ABS, MAX, MIN
-* ..
-* .. Save statement ..
- SAVE FIRST, IWARN, LBETA, LEMAX, LEMIN, LEPS, LRMAX,
- $ LRMIN, LT
-* ..
-* .. Data statements ..
- DATA FIRST / .TRUE. / , IWARN / .FALSE. /
-* ..
-* .. Executable Statements ..
-*
- IF( FIRST ) THEN
- FIRST = .FALSE.
- ZERO = 0
- ONE = 1
- TWO = 2
-*
-* LBETA, LT, LRND, LEPS, LEMIN and LRMIN are the local values of
-* BETA, T, RND, EPS, EMIN and RMIN.
-*
-* Throughout this routine we use the function SLAMC3 to ensure
-* that relevant values are stored and not held in registers, or
-* are not affected by optimizers.
-*
-* SLAMC1 returns the parameters LBETA, LT, LRND and LIEEE1.
-*
- CALL SLAMC1( LBETA, LT, LRND, LIEEE1 )
-*
-* Start to find EPS.
-*
- B = LBETA
- A = B**( -LT )
- LEPS = A
-*
-* Try some tricks to see whether or not this is the correct EPS.
-*
- B = TWO / 3
- HALF = ONE / 2
- SIXTH = SLAMC3( B, -HALF )
- THIRD = SLAMC3( SIXTH, SIXTH )
- B = SLAMC3( THIRD, -HALF )
- B = SLAMC3( B, SIXTH )
- B = ABS( B )
- IF( B.LT.LEPS )
- $ B = LEPS
-*
- LEPS = 1
-*
-*+ WHILE( ( LEPS.GT.B ).AND.( B.GT.ZERO ) )LOOP
- 10 CONTINUE
- IF( ( LEPS.GT.B ) .AND. ( B.GT.ZERO ) ) THEN
- LEPS = B
- C = SLAMC3( HALF*LEPS, ( TWO**5 )*( LEPS**2 ) )
- C = SLAMC3( HALF, -C )
- B = SLAMC3( HALF, C )
- C = SLAMC3( HALF, -B )
- B = SLAMC3( HALF, C )
- GO TO 10
- END IF
-*+ END WHILE
-*
- IF( A.LT.LEPS )
- $ LEPS = A
-*
-* Computation of EPS complete.
-*
-* Now find EMIN. Let A = + or - 1, and + or - (1 + BASE**(-3)).
-* Keep dividing A by BETA until (gradual) underflow occurs. This
-* is detected when we cannot recover the previous A.
-*
- RBASE = ONE / LBETA
- SMALL = ONE
- DO 20 I = 1, 3
- SMALL = SLAMC3( SMALL*RBASE, ZERO )
- 20 CONTINUE
- A = SLAMC3( ONE, SMALL )
- CALL SLAMC4( NGPMIN, ONE, LBETA )
- CALL SLAMC4( NGNMIN, -ONE, LBETA )
- CALL SLAMC4( GPMIN, A, LBETA )
- CALL SLAMC4( GNMIN, -A, LBETA )
- IEEE = .FALSE.
-*
- IF( ( NGPMIN.EQ.NGNMIN ) .AND. ( GPMIN.EQ.GNMIN ) ) THEN
- IF( NGPMIN.EQ.GPMIN ) THEN
- LEMIN = NGPMIN
-* ( Non twos-complement machines, no gradual underflow;
-* e.g., VAX )
- ELSE IF( ( GPMIN-NGPMIN ).EQ.3 ) THEN
- LEMIN = NGPMIN - 1 + LT
- IEEE = .TRUE.
-* ( Non twos-complement machines, with gradual underflow;
-* e.g., IEEE standard followers )
- ELSE
- LEMIN = MIN( NGPMIN, GPMIN )
-* ( A guess; no known machine )
- IWARN = .TRUE.
- END IF
-*
- ELSE IF( ( NGPMIN.EQ.GPMIN ) .AND. ( NGNMIN.EQ.GNMIN ) ) THEN
- IF( ABS( NGPMIN-NGNMIN ).EQ.1 ) THEN
- LEMIN = MAX( NGPMIN, NGNMIN )
-* ( Twos-complement machines, no gradual underflow;
-* e.g., CYBER 205 )
- ELSE
- LEMIN = MIN( NGPMIN, NGNMIN )
-* ( A guess; no known machine )
- IWARN = .TRUE.
- END IF
-*
- ELSE IF( ( ABS( NGPMIN-NGNMIN ).EQ.1 ) .AND.
- $ ( GPMIN.EQ.GNMIN ) ) THEN
- IF( ( GPMIN-MIN( NGPMIN, NGNMIN ) ).EQ.3 ) THEN
- LEMIN = MAX( NGPMIN, NGNMIN ) - 1 + LT
-* ( Twos-complement machines with gradual underflow;
-* no known machine )
- ELSE
- LEMIN = MIN( NGPMIN, NGNMIN )
-* ( A guess; no known machine )
- IWARN = .TRUE.
- END IF
-*
- ELSE
- LEMIN = MIN( NGPMIN, NGNMIN, GPMIN, GNMIN )
-* ( A guess; no known machine )
- IWARN = .TRUE.
- END IF
-***
-* Comment out this if block if EMIN is ok
- IF( IWARN ) THEN
- FIRST = .TRUE.
- WRITE( 6, FMT = 9999 )LEMIN
- END IF
-***
-*
-* Assume IEEE arithmetic if we found denormalised numbers above,
-* or if arithmetic seems to round in the IEEE style, determined
-* in routine SLAMC1. A true IEEE machine should have both things
-* true; however, faulty machines may have one or the other.
-*
- IEEE = IEEE .OR. LIEEE1
-*
-* Compute RMIN by successive division by BETA. We could compute
-* RMIN as BASE**( EMIN - 1 ), but some machines underflow during
-* this computation.
-*
- LRMIN = 1
- DO 30 I = 1, 1 - LEMIN
- LRMIN = SLAMC3( LRMIN*RBASE, ZERO )
- 30 CONTINUE
-*
-* Finally, call SLAMC5 to compute EMAX and RMAX.
-*
- CALL SLAMC5( LBETA, LT, LEMIN, IEEE, LEMAX, LRMAX )
- END IF
-*
- BETA = LBETA
- T = LT
- RND = LRND
- EPS = LEPS
- EMIN = LEMIN
- RMIN = LRMIN
- EMAX = LEMAX
- RMAX = LRMAX
-*
- RETURN
-*
- 9999 FORMAT( / / ' WARNING. The value EMIN may be incorrect:-',
- $ ' EMIN = ', I8, /
- $ ' If, after inspection, the value EMIN looks',
- $ ' acceptable please comment out ',
- $ / ' the IF block as marked within the code of routine',
- $ ' SLAMC2,', / ' otherwise supply EMIN explicitly.', / )
-*
-* End of SLAMC2
-*
- END
-*
-************************************************************************
-*
- REAL FUNCTION SLAMC3( A, B )
-*
-* -- LAPACK auxiliary routine (version 3.0) --
-* Univ. of Tennessee, Univ. of California Berkeley, NAG Ltd.,
-* Courant Institute, Argonne National Lab, and Rice University
-* October 31, 1992
-*
-* .. Scalar Arguments ..
- REAL A, B
-* ..
-*
-* Purpose
-* =======
-*
-* SLAMC3 is intended to force A and B to be stored prior to doing
-* the addition of A and B , for use in situations where optimizers
-* might hold one of these in a register.
-*
-* Arguments
-* =========
-*
-* A, B (input) REAL
-* The values A and B.
-*
-* =====================================================================
-*
-* .. Executable Statements ..
-*
- SLAMC3 = A + B
-*
- RETURN
-*
-* End of SLAMC3
-*
- END
-*
-************************************************************************
-*
- SUBROUTINE SLAMC4( EMIN, START, BASE )
-*
-* -- LAPACK auxiliary routine (version 3.0) --
-* Univ. of Tennessee, Univ. of California Berkeley, NAG Ltd.,
-* Courant Institute, Argonne National Lab, and Rice University
-* October 31, 1992
-*
-* .. Scalar Arguments ..
- INTEGER BASE, EMIN
- REAL START
-* ..
-*
-* Purpose
-* =======
-*
-* SLAMC4 is a service routine for SLAMC2.
-*
-* Arguments
-* =========
-*
-* EMIN (output) EMIN
-* The minimum exponent before (gradual) underflow, computed by
-* setting A = START and dividing by BASE until the previous A
-* can not be recovered.
-*
-* START (input) REAL
-* The starting point for determining EMIN.
-*
-* BASE (input) INTEGER
-* The base of the machine.
-*
-* =====================================================================
-*
-* .. Local Scalars ..
- INTEGER I
- REAL A, B1, B2, C1, C2, D1, D2, ONE, RBASE, ZERO
-* ..
-* .. External Functions ..
- REAL SLAMC3
- EXTERNAL SLAMC3
-* ..
-* .. Executable Statements ..
-*
- A = START
- ONE = 1
- RBASE = ONE / BASE
- ZERO = 0
- EMIN = 1
- B1 = SLAMC3( A*RBASE, ZERO )
- C1 = A
- C2 = A
- D1 = A
- D2 = A
-*+ WHILE( ( C1.EQ.A ).AND.( C2.EQ.A ).AND.
-* $ ( D1.EQ.A ).AND.( D2.EQ.A ) )LOOP
- 10 CONTINUE
- IF( ( C1.EQ.A ) .AND. ( C2.EQ.A ) .AND. ( D1.EQ.A ) .AND.
- $ ( D2.EQ.A ) ) THEN
- EMIN = EMIN - 1
- A = B1
- B1 = SLAMC3( A / BASE, ZERO )
- C1 = SLAMC3( B1*BASE, ZERO )
- D1 = ZERO
- DO 20 I = 1, BASE
- D1 = D1 + B1
- 20 CONTINUE
- B2 = SLAMC3( A*RBASE, ZERO )
- C2 = SLAMC3( B2 / RBASE, ZERO )
- D2 = ZERO
- DO 30 I = 1, BASE
- D2 = D2 + B2
- 30 CONTINUE
- GO TO 10
- END IF
-*+ END WHILE
-*
- RETURN
-*
-* End of SLAMC4
-*
- END
-*
-************************************************************************
-*
- SUBROUTINE SLAMC5( BETA, P, EMIN, IEEE, EMAX, RMAX )
-*
-* -- LAPACK auxiliary routine (version 3.0) --
-* Univ. of Tennessee, Univ. of California Berkeley, NAG Ltd.,
-* Courant Institute, Argonne National Lab, and Rice University
-* October 31, 1992
-*
-* .. Scalar Arguments ..
- LOGICAL IEEE
- INTEGER BETA, EMAX, EMIN, P
- REAL RMAX
-* ..
-*
-* Purpose
-* =======
-*
-* SLAMC5 attempts to compute RMAX, the largest machine floating-point
-* number, without overflow. It assumes that EMAX + abs(EMIN) sum
-* approximately to a power of 2. It will fail on machines where this
-* assumption does not hold, for example, the Cyber 205 (EMIN = -28625,
-* EMAX = 28718). It will also fail if the value supplied for EMIN is
-* too large (i.e. too close to zero), probably with overflow.
-*
-* Arguments
-* =========
-*
-* BETA (input) INTEGER
-* The base of floating-point arithmetic.
-*
-* P (input) INTEGER
-* The number of base BETA digits in the mantissa of a
-* floating-point value.
-*
-* EMIN (input) INTEGER
-* The minimum exponent before (gradual) underflow.
-*
-* IEEE (input) LOGICAL
-* A logical flag specifying whether or not the arithmetic
-* system is thought to comply with the IEEE standard.
-*
-* EMAX (output) INTEGER
-* The largest exponent before overflow
-*
-* RMAX (output) REAL
-* The largest machine floating-point number.
-*
-* =====================================================================
-*
-* .. Parameters ..
- REAL ZERO, ONE
- PARAMETER ( ZERO = 0.0E0, ONE = 1.0E0 )
-* ..
-* .. Local Scalars ..
- INTEGER EXBITS, EXPSUM, I, LEXP, NBITS, TRY, UEXP
- REAL OLDY, RECBAS, Y, Z
-* ..
-* .. External Functions ..
- REAL SLAMC3
- EXTERNAL SLAMC3
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC MOD
-* ..
-* .. Executable Statements ..
-*
-* First compute LEXP and UEXP, two powers of 2 that bound
-* abs(EMIN). We then assume that EMAX + abs(EMIN) will sum
-* approximately to the bound that is closest to abs(EMIN).
-* (EMAX is the exponent of the required number RMAX).
-*
- LEXP = 1
- EXBITS = 1
- 10 CONTINUE
- TRY = LEXP*2
- IF( TRY.LE.( -EMIN ) ) THEN
- LEXP = TRY
- EXBITS = EXBITS + 1
- GO TO 10
- END IF
- IF( LEXP.EQ.-EMIN ) THEN
- UEXP = LEXP
- ELSE
- UEXP = TRY
- EXBITS = EXBITS + 1
- END IF
-*
-* Now -LEXP is less than or equal to EMIN, and -UEXP is greater
-* than or equal to EMIN. EXBITS is the number of bits needed to
-* store the exponent.
-*
- IF( ( UEXP+EMIN ).GT.( -LEXP-EMIN ) ) THEN
- EXPSUM = 2*LEXP
- ELSE
- EXPSUM = 2*UEXP
- END IF
-*
-* EXPSUM is the exponent range, approximately equal to
-* EMAX - EMIN + 1 .
-*
- EMAX = EXPSUM + EMIN - 1
- NBITS = 1 + EXBITS + P
-*
-* NBITS is the total number of bits needed to store a
-* floating-point number.
-*
- IF( ( MOD( NBITS, 2 ).EQ.1 ) .AND. ( BETA.EQ.2 ) ) THEN
-*
-* Either there are an odd number of bits used to store a
-* floating-point number, which is unlikely, or some bits are
-* not used in the representation of numbers, which is possible,
-* (e.g. Cray machines) or the mantissa has an implicit bit,
-* (e.g. IEEE machines, Dec Vax machines), which is perhaps the
-* most likely. We have to assume the last alternative.
-* If this is true, then we need to reduce EMAX by one because
-* there must be some way of representing zero in an implicit-bit
-* system. On machines like Cray, we are reducing EMAX by one
-* unnecessarily.
-*
- EMAX = EMAX - 1
- END IF
-*
- IF( IEEE ) THEN
-*
-* Assume we are on an IEEE machine which reserves one exponent
-* for infinity and NaN.
-*
- EMAX = EMAX - 1
- END IF
-*
-* Now create RMAX, the largest machine number, which should
-* be equal to (1.0 - BETA**(-P)) * BETA**EMAX .
-*
-* First compute 1.0 - BETA**(-P), being careful that the
-* result is less than 1.0 .
-*
- RECBAS = ONE / BETA
- Z = BETA - ONE
- Y = ZERO
- DO 20 I = 1, P
- Z = Z*RECBAS
- IF( Y.LT.ONE )
- $ OLDY = Y
- Y = SLAMC3( Y, Z )
- 20 CONTINUE
- IF( Y.GE.ONE )
- $ Y = OLDY
-*
-* Now multiply by BETA**EMAX to get RMAX.
-*
- DO 30 I = 1, EMAX
- Y = SLAMC3( Y*BETA, ZERO )
- 30 CONTINUE
-*
- RMAX = Y
- RETURN
-*
-* End of SLAMC5
-*
- END
diff --git a/src/lib/lapack/xerbla.f b/src/lib/lapack/xerbla.f
deleted file mode 100644
index c8c9231b..00000000
--- a/src/lib/lapack/xerbla.f
+++ /dev/null
@@ -1,45 +0,0 @@
- SUBROUTINE XERBLA( SRNAME, INFO )
-*
-* -- LAPACK auxiliary routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- CHARACTER*6 SRNAME
- INTEGER INFO
-* ..
-*
-* Purpose
-* =======
-*
-* XERBLA is an error handler for the LAPACK routines.
-* It is called by an LAPACK routine if an input parameter has an
-* invalid value. A message is printed and execution stops.
-*
-* Installers may consider modifying the STOP statement in order to
-* call system-specific exception-handling facilities.
-*
-* Arguments
-* =========
-*
-* SRNAME (input) CHARACTER*6
-* The name of the routine which called XERBLA.
-*
-* INFO (input) INTEGER
-* The position of the invalid parameter in the parameter list
-* of the calling routine.
-*
-* =====================================================================
-*
-* .. Executable Statements ..
-*
- WRITE( *, FMT = 9999 )SRNAME, INFO
-*
- STOP
-*
- 9999 FORMAT( ' ** On entry to ', A6, ' parameter number ', I2, ' had ',
- $ 'an illegal value' )
-*
-* End of XERBLA
-*
- END
diff --git a/src/lib/lapack/zbdsqr.f b/src/lib/lapack/zbdsqr.f
deleted file mode 100644
index f9086be5..00000000
--- a/src/lib/lapack/zbdsqr.f
+++ /dev/null
@@ -1,742 +0,0 @@
- SUBROUTINE ZBDSQR( UPLO, N, NCVT, NRU, NCC, D, E, VT, LDVT, U,
- $ LDU, C, LDC, RWORK, INFO )
-*
-* -- LAPACK routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- CHARACTER UPLO
- INTEGER INFO, LDC, LDU, LDVT, N, NCC, NCVT, NRU
-* ..
-* .. Array Arguments ..
- DOUBLE PRECISION D( * ), E( * ), RWORK( * )
- COMPLEX*16 C( LDC, * ), U( LDU, * ), VT( LDVT, * )
-* ..
-*
-* Purpose
-* =======
-*
-* ZBDSQR computes the singular values and, optionally, the right and/or
-* left singular vectors from the singular value decomposition (SVD) of
-* a real N-by-N (upper or lower) bidiagonal matrix B using the implicit
-* zero-shift QR algorithm. The SVD of B has the form
-*
-* B = Q * S * P**H
-*
-* where S is the diagonal matrix of singular values, Q is an orthogonal
-* matrix of left singular vectors, and P is an orthogonal matrix of
-* right singular vectors. If left singular vectors are requested, this
-* subroutine actually returns U*Q instead of Q, and, if right singular
-* vectors are requested, this subroutine returns P**H*VT instead of
-* P**H, for given complex input matrices U and VT. When U and VT are
-* the unitary matrices that reduce a general matrix A to bidiagonal
-* form: A = U*B*VT, as computed by ZGEBRD, then
-*
-* A = (U*Q) * S * (P**H*VT)
-*
-* is the SVD of A. Optionally, the subroutine may also compute Q**H*C
-* for a given complex input matrix C.
-*
-* See "Computing Small Singular Values of Bidiagonal Matrices With
-* Guaranteed High Relative Accuracy," by J. Demmel and W. Kahan,
-* LAPACK Working Note #3 (or SIAM J. Sci. Statist. Comput. vol. 11,
-* no. 5, pp. 873-912, Sept 1990) and
-* "Accurate singular values and differential qd algorithms," by
-* B. Parlett and V. Fernando, Technical Report CPAM-554, Mathematics
-* Department, University of California at Berkeley, July 1992
-* for a detailed description of the algorithm.
-*
-* Arguments
-* =========
-*
-* UPLO (input) CHARACTER*1
-* = 'U': B is upper bidiagonal;
-* = 'L': B is lower bidiagonal.
-*
-* N (input) INTEGER
-* The order of the matrix B. N >= 0.
-*
-* NCVT (input) INTEGER
-* The number of columns of the matrix VT. NCVT >= 0.
-*
-* NRU (input) INTEGER
-* The number of rows of the matrix U. NRU >= 0.
-*
-* NCC (input) INTEGER
-* The number of columns of the matrix C. NCC >= 0.
-*
-* D (input/output) DOUBLE PRECISION array, dimension (N)
-* On entry, the n diagonal elements of the bidiagonal matrix B.
-* On exit, if INFO=0, the singular values of B in decreasing
-* order.
-*
-* E (input/output) DOUBLE PRECISION array, dimension (N-1)
-* On entry, the N-1 offdiagonal elements of the bidiagonal
-* matrix B.
-* On exit, if INFO = 0, E is destroyed; if INFO > 0, D and E
-* will contain the diagonal and superdiagonal elements of a
-* bidiagonal matrix orthogonally equivalent to the one given
-* as input.
-*
-* VT (input/output) COMPLEX*16 array, dimension (LDVT, NCVT)
-* On entry, an N-by-NCVT matrix VT.
-* On exit, VT is overwritten by P**H * VT.
-* Not referenced if NCVT = 0.
-*
-* LDVT (input) INTEGER
-* The leading dimension of the array VT.
-* LDVT >= max(1,N) if NCVT > 0; LDVT >= 1 if NCVT = 0.
-*
-* U (input/output) COMPLEX*16 array, dimension (LDU, N)
-* On entry, an NRU-by-N matrix U.
-* On exit, U is overwritten by U * Q.
-* Not referenced if NRU = 0.
-*
-* LDU (input) INTEGER
-* The leading dimension of the array U. LDU >= max(1,NRU).
-*
-* C (input/output) COMPLEX*16 array, dimension (LDC, NCC)
-* On entry, an N-by-NCC matrix C.
-* On exit, C is overwritten by Q**H * C.
-* Not referenced if NCC = 0.
-*
-* LDC (input) INTEGER
-* The leading dimension of the array C.
-* LDC >= max(1,N) if NCC > 0; LDC >=1 if NCC = 0.
-*
-* RWORK (workspace) DOUBLE PRECISION array, dimension (2*N)
-* if NCVT = NRU = NCC = 0, (max(1, 4*N-4)) otherwise
-*
-* INFO (output) INTEGER
-* = 0: successful exit
-* < 0: If INFO = -i, the i-th argument had an illegal value
-* > 0: the algorithm did not converge; D and E contain the
-* elements of a bidiagonal matrix which is orthogonally
-* similar to the input matrix B; if INFO = i, i
-* elements of E have not converged to zero.
-*
-* Internal Parameters
-* ===================
-*
-* TOLMUL DOUBLE PRECISION, default = max(10,min(100,EPS**(-1/8)))
-* TOLMUL controls the convergence criterion of the QR loop.
-* If it is positive, TOLMUL*EPS is the desired relative
-* precision in the computed singular values.
-* If it is negative, abs(TOLMUL*EPS*sigma_max) is the
-* desired absolute accuracy in the computed singular
-* values (corresponds to relative accuracy
-* abs(TOLMUL*EPS) in the largest singular value.
-* abs(TOLMUL) should be between 1 and 1/EPS, and preferably
-* between 10 (for fast convergence) and .1/EPS
-* (for there to be some accuracy in the results).
-* Default is to lose at either one eighth or 2 of the
-* available decimal digits in each computed singular value
-* (whichever is smaller).
-*
-* MAXITR INTEGER, default = 6
-* MAXITR controls the maximum number of passes of the
-* algorithm through its inner loop. The algorithms stops
-* (and so fails to converge) if the number of passes
-* through the inner loop exceeds MAXITR*N**2.
-*
-* =====================================================================
-*
-* .. Parameters ..
- DOUBLE PRECISION ZERO
- PARAMETER ( ZERO = 0.0D0 )
- DOUBLE PRECISION ONE
- PARAMETER ( ONE = 1.0D0 )
- DOUBLE PRECISION NEGONE
- PARAMETER ( NEGONE = -1.0D0 )
- DOUBLE PRECISION HNDRTH
- PARAMETER ( HNDRTH = 0.01D0 )
- DOUBLE PRECISION TEN
- PARAMETER ( TEN = 10.0D0 )
- DOUBLE PRECISION HNDRD
- PARAMETER ( HNDRD = 100.0D0 )
- DOUBLE PRECISION MEIGTH
- PARAMETER ( MEIGTH = -0.125D0 )
- INTEGER MAXITR
- PARAMETER ( MAXITR = 6 )
-* ..
-* .. Local Scalars ..
- LOGICAL LOWER, ROTATE
- INTEGER I, IDIR, ISUB, ITER, J, LL, LLL, M, MAXIT, NM1,
- $ NM12, NM13, OLDLL, OLDM
- DOUBLE PRECISION ABSE, ABSS, COSL, COSR, CS, EPS, F, G, H, MU,
- $ OLDCS, OLDSN, R, SHIFT, SIGMN, SIGMX, SINL,
- $ SINR, SLL, SMAX, SMIN, SMINL, SMINOA,
- $ SN, THRESH, TOL, TOLMUL, UNFL
-* ..
-* .. External Functions ..
- LOGICAL LSAME
- DOUBLE PRECISION DLAMCH
- EXTERNAL LSAME, DLAMCH
-* ..
-* .. External Subroutines ..
- EXTERNAL DLARTG, DLAS2, DLASQ1, DLASV2, XERBLA, ZDROT,
- $ ZDSCAL, ZLASR, ZSWAP
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC ABS, DBLE, MAX, MIN, SIGN, SQRT
-* ..
-* .. Executable Statements ..
-*
-* Test the input parameters.
-*
- INFO = 0
- LOWER = LSAME( UPLO, 'L' )
- IF( .NOT.LSAME( UPLO, 'U' ) .AND. .NOT.LOWER ) THEN
- INFO = -1
- ELSE IF( N.LT.0 ) THEN
- INFO = -2
- ELSE IF( NCVT.LT.0 ) THEN
- INFO = -3
- ELSE IF( NRU.LT.0 ) THEN
- INFO = -4
- ELSE IF( NCC.LT.0 ) THEN
- INFO = -5
- ELSE IF( ( NCVT.EQ.0 .AND. LDVT.LT.1 ) .OR.
- $ ( NCVT.GT.0 .AND. LDVT.LT.MAX( 1, N ) ) ) THEN
- INFO = -9
- ELSE IF( LDU.LT.MAX( 1, NRU ) ) THEN
- INFO = -11
- ELSE IF( ( NCC.EQ.0 .AND. LDC.LT.1 ) .OR.
- $ ( NCC.GT.0 .AND. LDC.LT.MAX( 1, N ) ) ) THEN
- INFO = -13
- END IF
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'ZBDSQR', -INFO )
- RETURN
- END IF
- IF( N.EQ.0 )
- $ RETURN
- IF( N.EQ.1 )
- $ GO TO 160
-*
-* ROTATE is true if any singular vectors desired, false otherwise
-*
- ROTATE = ( NCVT.GT.0 ) .OR. ( NRU.GT.0 ) .OR. ( NCC.GT.0 )
-*
-* If no singular vectors desired, use qd algorithm
-*
- IF( .NOT.ROTATE ) THEN
- CALL DLASQ1( N, D, E, RWORK, INFO )
- RETURN
- END IF
-*
- NM1 = N - 1
- NM12 = NM1 + NM1
- NM13 = NM12 + NM1
- IDIR = 0
-*
-* Get machine constants
-*
- EPS = DLAMCH( 'Epsilon' )
- UNFL = DLAMCH( 'Safe minimum' )
-*
-* If matrix lower bidiagonal, rotate to be upper bidiagonal
-* by applying Givens rotations on the left
-*
- IF( LOWER ) THEN
- DO 10 I = 1, N - 1
- CALL DLARTG( D( I ), E( I ), CS, SN, R )
- D( I ) = R
- E( I ) = SN*D( I+1 )
- D( I+1 ) = CS*D( I+1 )
- RWORK( I ) = CS
- RWORK( NM1+I ) = SN
- 10 CONTINUE
-*
-* Update singular vectors if desired
-*
- IF( NRU.GT.0 )
- $ CALL ZLASR( 'R', 'V', 'F', NRU, N, RWORK( 1 ), RWORK( N ),
- $ U, LDU )
- IF( NCC.GT.0 )
- $ CALL ZLASR( 'L', 'V', 'F', N, NCC, RWORK( 1 ), RWORK( N ),
- $ C, LDC )
- END IF
-*
-* Compute singular values to relative accuracy TOL
-* (By setting TOL to be negative, algorithm will compute
-* singular values to absolute accuracy ABS(TOL)*norm(input matrix))
-*
- TOLMUL = MAX( TEN, MIN( HNDRD, EPS**MEIGTH ) )
- TOL = TOLMUL*EPS
-*
-* Compute approximate maximum, minimum singular values
-*
- SMAX = ZERO
- DO 20 I = 1, N
- SMAX = MAX( SMAX, ABS( D( I ) ) )
- 20 CONTINUE
- DO 30 I = 1, N - 1
- SMAX = MAX( SMAX, ABS( E( I ) ) )
- 30 CONTINUE
- SMINL = ZERO
- IF( TOL.GE.ZERO ) THEN
-*
-* Relative accuracy desired
-*
- SMINOA = ABS( D( 1 ) )
- IF( SMINOA.EQ.ZERO )
- $ GO TO 50
- MU = SMINOA
- DO 40 I = 2, N
- MU = ABS( D( I ) )*( MU / ( MU+ABS( E( I-1 ) ) ) )
- SMINOA = MIN( SMINOA, MU )
- IF( SMINOA.EQ.ZERO )
- $ GO TO 50
- 40 CONTINUE
- 50 CONTINUE
- SMINOA = SMINOA / SQRT( DBLE( N ) )
- THRESH = MAX( TOL*SMINOA, MAXITR*N*N*UNFL )
- ELSE
-*
-* Absolute accuracy desired
-*
- THRESH = MAX( ABS( TOL )*SMAX, MAXITR*N*N*UNFL )
- END IF
-*
-* Prepare for main iteration loop for the singular values
-* (MAXIT is the maximum number of passes through the inner
-* loop permitted before nonconvergence signalled.)
-*
- MAXIT = MAXITR*N*N
- ITER = 0
- OLDLL = -1
- OLDM = -1
-*
-* M points to last element of unconverged part of matrix
-*
- M = N
-*
-* Begin main iteration loop
-*
- 60 CONTINUE
-*
-* Check for convergence or exceeding iteration count
-*
- IF( M.LE.1 )
- $ GO TO 160
- IF( ITER.GT.MAXIT )
- $ GO TO 200
-*
-* Find diagonal block of matrix to work on
-*
- IF( TOL.LT.ZERO .AND. ABS( D( M ) ).LE.THRESH )
- $ D( M ) = ZERO
- SMAX = ABS( D( M ) )
- SMIN = SMAX
- DO 70 LLL = 1, M - 1
- LL = M - LLL
- ABSS = ABS( D( LL ) )
- ABSE = ABS( E( LL ) )
- IF( TOL.LT.ZERO .AND. ABSS.LE.THRESH )
- $ D( LL ) = ZERO
- IF( ABSE.LE.THRESH )
- $ GO TO 80
- SMIN = MIN( SMIN, ABSS )
- SMAX = MAX( SMAX, ABSS, ABSE )
- 70 CONTINUE
- LL = 0
- GO TO 90
- 80 CONTINUE
- E( LL ) = ZERO
-*
-* Matrix splits since E(LL) = 0
-*
- IF( LL.EQ.M-1 ) THEN
-*
-* Convergence of bottom singular value, return to top of loop
-*
- M = M - 1
- GO TO 60
- END IF
- 90 CONTINUE
- LL = LL + 1
-*
-* E(LL) through E(M-1) are nonzero, E(LL-1) is zero
-*
- IF( LL.EQ.M-1 ) THEN
-*
-* 2 by 2 block, handle separately
-*
- CALL DLASV2( D( M-1 ), E( M-1 ), D( M ), SIGMN, SIGMX, SINR,
- $ COSR, SINL, COSL )
- D( M-1 ) = SIGMX
- E( M-1 ) = ZERO
- D( M ) = SIGMN
-*
-* Compute singular vectors, if desired
-*
- IF( NCVT.GT.0 )
- $ CALL ZDROT( NCVT, VT( M-1, 1 ), LDVT, VT( M, 1 ), LDVT,
- $ COSR, SINR )
- IF( NRU.GT.0 )
- $ CALL ZDROT( NRU, U( 1, M-1 ), 1, U( 1, M ), 1, COSL, SINL )
- IF( NCC.GT.0 )
- $ CALL ZDROT( NCC, C( M-1, 1 ), LDC, C( M, 1 ), LDC, COSL,
- $ SINL )
- M = M - 2
- GO TO 60
- END IF
-*
-* If working on new submatrix, choose shift direction
-* (from larger end diagonal element towards smaller)
-*
- IF( LL.GT.OLDM .OR. M.LT.OLDLL ) THEN
- IF( ABS( D( LL ) ).GE.ABS( D( M ) ) ) THEN
-*
-* Chase bulge from top (big end) to bottom (small end)
-*
- IDIR = 1
- ELSE
-*
-* Chase bulge from bottom (big end) to top (small end)
-*
- IDIR = 2
- END IF
- END IF
-*
-* Apply convergence tests
-*
- IF( IDIR.EQ.1 ) THEN
-*
-* Run convergence test in forward direction
-* First apply standard test to bottom of matrix
-*
- IF( ABS( E( M-1 ) ).LE.ABS( TOL )*ABS( D( M ) ) .OR.
- $ ( TOL.LT.ZERO .AND. ABS( E( M-1 ) ).LE.THRESH ) ) THEN
- E( M-1 ) = ZERO
- GO TO 60
- END IF
-*
- IF( TOL.GE.ZERO ) THEN
-*
-* If relative accuracy desired,
-* apply convergence criterion forward
-*
- MU = ABS( D( LL ) )
- SMINL = MU
- DO 100 LLL = LL, M - 1
- IF( ABS( E( LLL ) ).LE.TOL*MU ) THEN
- E( LLL ) = ZERO
- GO TO 60
- END IF
- MU = ABS( D( LLL+1 ) )*( MU / ( MU+ABS( E( LLL ) ) ) )
- SMINL = MIN( SMINL, MU )
- 100 CONTINUE
- END IF
-*
- ELSE
-*
-* Run convergence test in backward direction
-* First apply standard test to top of matrix
-*
- IF( ABS( E( LL ) ).LE.ABS( TOL )*ABS( D( LL ) ) .OR.
- $ ( TOL.LT.ZERO .AND. ABS( E( LL ) ).LE.THRESH ) ) THEN
- E( LL ) = ZERO
- GO TO 60
- END IF
-*
- IF( TOL.GE.ZERO ) THEN
-*
-* If relative accuracy desired,
-* apply convergence criterion backward
-*
- MU = ABS( D( M ) )
- SMINL = MU
- DO 110 LLL = M - 1, LL, -1
- IF( ABS( E( LLL ) ).LE.TOL*MU ) THEN
- E( LLL ) = ZERO
- GO TO 60
- END IF
- MU = ABS( D( LLL ) )*( MU / ( MU+ABS( E( LLL ) ) ) )
- SMINL = MIN( SMINL, MU )
- 110 CONTINUE
- END IF
- END IF
- OLDLL = LL
- OLDM = M
-*
-* Compute shift. First, test if shifting would ruin relative
-* accuracy, and if so set the shift to zero.
-*
- IF( TOL.GE.ZERO .AND. N*TOL*( SMINL / SMAX ).LE.
- $ MAX( EPS, HNDRTH*TOL ) ) THEN
-*
-* Use a zero shift to avoid loss of relative accuracy
-*
- SHIFT = ZERO
- ELSE
-*
-* Compute the shift from 2-by-2 block at end of matrix
-*
- IF( IDIR.EQ.1 ) THEN
- SLL = ABS( D( LL ) )
- CALL DLAS2( D( M-1 ), E( M-1 ), D( M ), SHIFT, R )
- ELSE
- SLL = ABS( D( M ) )
- CALL DLAS2( D( LL ), E( LL ), D( LL+1 ), SHIFT, R )
- END IF
-*
-* Test if shift negligible, and if so set to zero
-*
- IF( SLL.GT.ZERO ) THEN
- IF( ( SHIFT / SLL )**2.LT.EPS )
- $ SHIFT = ZERO
- END IF
- END IF
-*
-* Increment iteration count
-*
- ITER = ITER + M - LL
-*
-* If SHIFT = 0, do simplified QR iteration
-*
- IF( SHIFT.EQ.ZERO ) THEN
- IF( IDIR.EQ.1 ) THEN
-*
-* Chase bulge from top to bottom
-* Save cosines and sines for later singular vector updates
-*
- CS = ONE
- OLDCS = ONE
- DO 120 I = LL, M - 1
- CALL DLARTG( D( I )*CS, E( I ), CS, SN, R )
- IF( I.GT.LL )
- $ E( I-1 ) = OLDSN*R
- CALL DLARTG( OLDCS*R, D( I+1 )*SN, OLDCS, OLDSN, D( I ) )
- RWORK( I-LL+1 ) = CS
- RWORK( I-LL+1+NM1 ) = SN
- RWORK( I-LL+1+NM12 ) = OLDCS
- RWORK( I-LL+1+NM13 ) = OLDSN
- 120 CONTINUE
- H = D( M )*CS
- D( M ) = H*OLDCS
- E( M-1 ) = H*OLDSN
-*
-* Update singular vectors
-*
- IF( NCVT.GT.0 )
- $ CALL ZLASR( 'L', 'V', 'F', M-LL+1, NCVT, RWORK( 1 ),
- $ RWORK( N ), VT( LL, 1 ), LDVT )
- IF( NRU.GT.0 )
- $ CALL ZLASR( 'R', 'V', 'F', NRU, M-LL+1, RWORK( NM12+1 ),
- $ RWORK( NM13+1 ), U( 1, LL ), LDU )
- IF( NCC.GT.0 )
- $ CALL ZLASR( 'L', 'V', 'F', M-LL+1, NCC, RWORK( NM12+1 ),
- $ RWORK( NM13+1 ), C( LL, 1 ), LDC )
-*
-* Test convergence
-*
- IF( ABS( E( M-1 ) ).LE.THRESH )
- $ E( M-1 ) = ZERO
-*
- ELSE
-*
-* Chase bulge from bottom to top
-* Save cosines and sines for later singular vector updates
-*
- CS = ONE
- OLDCS = ONE
- DO 130 I = M, LL + 1, -1
- CALL DLARTG( D( I )*CS, E( I-1 ), CS, SN, R )
- IF( I.LT.M )
- $ E( I ) = OLDSN*R
- CALL DLARTG( OLDCS*R, D( I-1 )*SN, OLDCS, OLDSN, D( I ) )
- RWORK( I-LL ) = CS
- RWORK( I-LL+NM1 ) = -SN
- RWORK( I-LL+NM12 ) = OLDCS
- RWORK( I-LL+NM13 ) = -OLDSN
- 130 CONTINUE
- H = D( LL )*CS
- D( LL ) = H*OLDCS
- E( LL ) = H*OLDSN
-*
-* Update singular vectors
-*
- IF( NCVT.GT.0 )
- $ CALL ZLASR( 'L', 'V', 'B', M-LL+1, NCVT, RWORK( NM12+1 ),
- $ RWORK( NM13+1 ), VT( LL, 1 ), LDVT )
- IF( NRU.GT.0 )
- $ CALL ZLASR( 'R', 'V', 'B', NRU, M-LL+1, RWORK( 1 ),
- $ RWORK( N ), U( 1, LL ), LDU )
- IF( NCC.GT.0 )
- $ CALL ZLASR( 'L', 'V', 'B', M-LL+1, NCC, RWORK( 1 ),
- $ RWORK( N ), C( LL, 1 ), LDC )
-*
-* Test convergence
-*
- IF( ABS( E( LL ) ).LE.THRESH )
- $ E( LL ) = ZERO
- END IF
- ELSE
-*
-* Use nonzero shift
-*
- IF( IDIR.EQ.1 ) THEN
-*
-* Chase bulge from top to bottom
-* Save cosines and sines for later singular vector updates
-*
- F = ( ABS( D( LL ) )-SHIFT )*
- $ ( SIGN( ONE, D( LL ) )+SHIFT / D( LL ) )
- G = E( LL )
- DO 140 I = LL, M - 1
- CALL DLARTG( F, G, COSR, SINR, R )
- IF( I.GT.LL )
- $ E( I-1 ) = R
- F = COSR*D( I ) + SINR*E( I )
- E( I ) = COSR*E( I ) - SINR*D( I )
- G = SINR*D( I+1 )
- D( I+1 ) = COSR*D( I+1 )
- CALL DLARTG( F, G, COSL, SINL, R )
- D( I ) = R
- F = COSL*E( I ) + SINL*D( I+1 )
- D( I+1 ) = COSL*D( I+1 ) - SINL*E( I )
- IF( I.LT.M-1 ) THEN
- G = SINL*E( I+1 )
- E( I+1 ) = COSL*E( I+1 )
- END IF
- RWORK( I-LL+1 ) = COSR
- RWORK( I-LL+1+NM1 ) = SINR
- RWORK( I-LL+1+NM12 ) = COSL
- RWORK( I-LL+1+NM13 ) = SINL
- 140 CONTINUE
- E( M-1 ) = F
-*
-* Update singular vectors
-*
- IF( NCVT.GT.0 )
- $ CALL ZLASR( 'L', 'V', 'F', M-LL+1, NCVT, RWORK( 1 ),
- $ RWORK( N ), VT( LL, 1 ), LDVT )
- IF( NRU.GT.0 )
- $ CALL ZLASR( 'R', 'V', 'F', NRU, M-LL+1, RWORK( NM12+1 ),
- $ RWORK( NM13+1 ), U( 1, LL ), LDU )
- IF( NCC.GT.0 )
- $ CALL ZLASR( 'L', 'V', 'F', M-LL+1, NCC, RWORK( NM12+1 ),
- $ RWORK( NM13+1 ), C( LL, 1 ), LDC )
-*
-* Test convergence
-*
- IF( ABS( E( M-1 ) ).LE.THRESH )
- $ E( M-1 ) = ZERO
-*
- ELSE
-*
-* Chase bulge from bottom to top
-* Save cosines and sines for later singular vector updates
-*
- F = ( ABS( D( M ) )-SHIFT )*( SIGN( ONE, D( M ) )+SHIFT /
- $ D( M ) )
- G = E( M-1 )
- DO 150 I = M, LL + 1, -1
- CALL DLARTG( F, G, COSR, SINR, R )
- IF( I.LT.M )
- $ E( I ) = R
- F = COSR*D( I ) + SINR*E( I-1 )
- E( I-1 ) = COSR*E( I-1 ) - SINR*D( I )
- G = SINR*D( I-1 )
- D( I-1 ) = COSR*D( I-1 )
- CALL DLARTG( F, G, COSL, SINL, R )
- D( I ) = R
- F = COSL*E( I-1 ) + SINL*D( I-1 )
- D( I-1 ) = COSL*D( I-1 ) - SINL*E( I-1 )
- IF( I.GT.LL+1 ) THEN
- G = SINL*E( I-2 )
- E( I-2 ) = COSL*E( I-2 )
- END IF
- RWORK( I-LL ) = COSR
- RWORK( I-LL+NM1 ) = -SINR
- RWORK( I-LL+NM12 ) = COSL
- RWORK( I-LL+NM13 ) = -SINL
- 150 CONTINUE
- E( LL ) = F
-*
-* Test convergence
-*
- IF( ABS( E( LL ) ).LE.THRESH )
- $ E( LL ) = ZERO
-*
-* Update singular vectors if desired
-*
- IF( NCVT.GT.0 )
- $ CALL ZLASR( 'L', 'V', 'B', M-LL+1, NCVT, RWORK( NM12+1 ),
- $ RWORK( NM13+1 ), VT( LL, 1 ), LDVT )
- IF( NRU.GT.0 )
- $ CALL ZLASR( 'R', 'V', 'B', NRU, M-LL+1, RWORK( 1 ),
- $ RWORK( N ), U( 1, LL ), LDU )
- IF( NCC.GT.0 )
- $ CALL ZLASR( 'L', 'V', 'B', M-LL+1, NCC, RWORK( 1 ),
- $ RWORK( N ), C( LL, 1 ), LDC )
- END IF
- END IF
-*
-* QR iteration finished, go back and check convergence
-*
- GO TO 60
-*
-* All singular values converged, so make them positive
-*
- 160 CONTINUE
- DO 170 I = 1, N
- IF( D( I ).LT.ZERO ) THEN
- D( I ) = -D( I )
-*
-* Change sign of singular vectors, if desired
-*
- IF( NCVT.GT.0 )
- $ CALL ZDSCAL( NCVT, NEGONE, VT( I, 1 ), LDVT )
- END IF
- 170 CONTINUE
-*
-* Sort the singular values into decreasing order (insertion sort on
-* singular values, but only one transposition per singular vector)
-*
- DO 190 I = 1, N - 1
-*
-* Scan for smallest D(I)
-*
- ISUB = 1
- SMIN = D( 1 )
- DO 180 J = 2, N + 1 - I
- IF( D( J ).LE.SMIN ) THEN
- ISUB = J
- SMIN = D( J )
- END IF
- 180 CONTINUE
- IF( ISUB.NE.N+1-I ) THEN
-*
-* Swap singular values and vectors
-*
- D( ISUB ) = D( N+1-I )
- D( N+1-I ) = SMIN
- IF( NCVT.GT.0 )
- $ CALL ZSWAP( NCVT, VT( ISUB, 1 ), LDVT, VT( N+1-I, 1 ),
- $ LDVT )
- IF( NRU.GT.0 )
- $ CALL ZSWAP( NRU, U( 1, ISUB ), 1, U( 1, N+1-I ), 1 )
- IF( NCC.GT.0 )
- $ CALL ZSWAP( NCC, C( ISUB, 1 ), LDC, C( N+1-I, 1 ), LDC )
- END IF
- 190 CONTINUE
- GO TO 220
-*
-* Maximum number of iterations exceeded, failure to converge
-*
- 200 CONTINUE
- INFO = 0
- DO 210 I = 1, N - 1
- IF( E( I ).NE.ZERO )
- $ INFO = INFO + 1
- 210 CONTINUE
- 220 CONTINUE
- RETURN
-*
-* End of ZBDSQR
-*
- END
diff --git a/src/lib/lapack/zdrot.f b/src/lib/lapack/zdrot.f
deleted file mode 100644
index 3b946e99..00000000
--- a/src/lib/lapack/zdrot.f
+++ /dev/null
@@ -1,96 +0,0 @@
- SUBROUTINE ZDROT( N, CX, INCX, CY, INCY, C, S )
-*
-* .. Scalar Arguments ..
- INTEGER INCX, INCY, N
- DOUBLE PRECISION C, S
-* ..
-* .. Array Arguments ..
- COMPLEX*16 CX( * ), CY( * )
-* ..
-*
-* Purpose
-* =======
-*
-* Applies a plane rotation, where the cos and sin (c and s) are real
-* and the vectors cx and cy are complex.
-* jack dongarra, linpack, 3/11/78.
-*
-* Arguments
-* ==========
-*
-* N (input) INTEGER
-* On entry, N specifies the order of the vectors cx and cy.
-* N must be at least zero.
-* Unchanged on exit.
-*
-* CX (input) COMPLEX*16 array, dimension at least
-* ( 1 + ( N - 1 )*abs( INCX ) ).
-* Before entry, the incremented array CX must contain the n
-* element vector cx. On exit, CX is overwritten by the updated
-* vector cx.
-*
-* INCX (input) INTEGER
-* On entry, INCX specifies the increment for the elements of
-* CX. INCX must not be zero.
-* Unchanged on exit.
-*
-* CY (input) COMPLEX*16 array, dimension at least
-* ( 1 + ( N - 1 )*abs( INCY ) ).
-* Before entry, the incremented array CY must contain the n
-* element vector cy. On exit, CY is overwritten by the updated
-* vector cy.
-*
-* INCY (input) INTEGER
-* On entry, INCY specifies the increment for the elements of
-* CY. INCY must not be zero.
-* Unchanged on exit.
-*
-* C (input) DOUBLE PRECISION
-* On entry, C specifies the cosine, cos.
-* Unchanged on exit.
-*
-* S (input) DOUBLE PRECISION
-* On entry, S specifies the sine, sin.
-* Unchanged on exit.
-*
-* =====================================================================
-*
-* .. Local Scalars ..
- INTEGER I, IX, IY
- COMPLEX*16 CTEMP
-* ..
-* .. Executable Statements ..
-*
- IF( N.LE.0 )
- $ RETURN
- IF( INCX.EQ.1 .AND. INCY.EQ.1 )
- $ GO TO 20
-*
-* code for unequal increments or equal increments not equal
-* to 1
-*
- IX = 1
- IY = 1
- IF( INCX.LT.0 )
- $ IX = ( -N+1 )*INCX + 1
- IF( INCY.LT.0 )
- $ IY = ( -N+1 )*INCY + 1
- DO 10 I = 1, N
- CTEMP = C*CX( IX ) + S*CY( IY )
- CY( IY ) = C*CY( IY ) - S*CX( IX )
- CX( IX ) = CTEMP
- IX = IX + INCX
- IY = IY + INCY
- 10 CONTINUE
- RETURN
-*
-* code for both increments equal to 1
-*
- 20 CONTINUE
- DO 30 I = 1, N
- CTEMP = C*CX( I ) + S*CY( I )
- CY( I ) = C*CY( I ) - S*CX( I )
- CX( I ) = CTEMP
- 30 CONTINUE
- RETURN
- END
diff --git a/src/lib/lapack/zdrscl.f b/src/lib/lapack/zdrscl.f
deleted file mode 100644
index 11686d0b..00000000
--- a/src/lib/lapack/zdrscl.f
+++ /dev/null
@@ -1,114 +0,0 @@
- SUBROUTINE ZDRSCL( N, SA, SX, INCX )
-*
-* -- LAPACK auxiliary routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- INTEGER INCX, N
- DOUBLE PRECISION SA
-* ..
-* .. Array Arguments ..
- COMPLEX*16 SX( * )
-* ..
-*
-* Purpose
-* =======
-*
-* ZDRSCL multiplies an n-element complex vector x by the real scalar
-* 1/a. This is done without overflow or underflow as long as
-* the final result x/a does not overflow or underflow.
-*
-* Arguments
-* =========
-*
-* N (input) INTEGER
-* The number of components of the vector x.
-*
-* SA (input) DOUBLE PRECISION
-* The scalar a which is used to divide each component of x.
-* SA must be >= 0, or the subroutine will divide by zero.
-*
-* SX (input/output) COMPLEX*16 array, dimension
-* (1+(N-1)*abs(INCX))
-* The n-element vector x.
-*
-* INCX (input) INTEGER
-* The increment between successive values of the vector SX.
-* > 0: SX(1) = X(1) and SX(1+(i-1)*INCX) = x(i), 1< i<= n
-*
-* =====================================================================
-*
-* .. Parameters ..
- DOUBLE PRECISION ZERO, ONE
- PARAMETER ( ZERO = 0.0D+0, ONE = 1.0D+0 )
-* ..
-* .. Local Scalars ..
- LOGICAL DONE
- DOUBLE PRECISION BIGNUM, CDEN, CDEN1, CNUM, CNUM1, MUL, SMLNUM
-* ..
-* .. External Functions ..
- DOUBLE PRECISION DLAMCH
- EXTERNAL DLAMCH
-* ..
-* .. External Subroutines ..
- EXTERNAL DLABAD, ZDSCAL
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC ABS
-* ..
-* .. Executable Statements ..
-*
-* Quick return if possible
-*
- IF( N.LE.0 )
- $ RETURN
-*
-* Get machine parameters
-*
- SMLNUM = DLAMCH( 'S' )
- BIGNUM = ONE / SMLNUM
- CALL DLABAD( SMLNUM, BIGNUM )
-*
-* Initialize the denominator to SA and the numerator to 1.
-*
- CDEN = SA
- CNUM = ONE
-*
- 10 CONTINUE
- CDEN1 = CDEN*SMLNUM
- CNUM1 = CNUM / BIGNUM
- IF( ABS( CDEN1 ).GT.ABS( CNUM ) .AND. CNUM.NE.ZERO ) THEN
-*
-* Pre-multiply X by SMLNUM if CDEN is large compared to CNUM.
-*
- MUL = SMLNUM
- DONE = .FALSE.
- CDEN = CDEN1
- ELSE IF( ABS( CNUM1 ).GT.ABS( CDEN ) ) THEN
-*
-* Pre-multiply X by BIGNUM if CDEN is small compared to CNUM.
-*
- MUL = BIGNUM
- DONE = .FALSE.
- CNUM = CNUM1
- ELSE
-*
-* Multiply X by CNUM / CDEN and return.
-*
- MUL = CNUM / CDEN
- DONE = .TRUE.
- END IF
-*
-* Scale the vector X by MUL
-*
- CALL ZDSCAL( N, MUL, SX, INCX )
-*
- IF( .NOT.DONE )
- $ GO TO 10
-*
- RETURN
-*
-* End of ZDRSCL
-*
- END
diff --git a/src/lib/lapack/zgebak.f b/src/lib/lapack/zgebak.f
deleted file mode 100644
index 1023601d..00000000
--- a/src/lib/lapack/zgebak.f
+++ /dev/null
@@ -1,189 +0,0 @@
- SUBROUTINE ZGEBAK( JOB, SIDE, N, ILO, IHI, SCALE, M, V, LDV,
- $ INFO )
-*
-* -- LAPACK routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- CHARACTER JOB, SIDE
- INTEGER IHI, ILO, INFO, LDV, M, N
-* ..
-* .. Array Arguments ..
- DOUBLE PRECISION SCALE( * )
- COMPLEX*16 V( LDV, * )
-* ..
-*
-* Purpose
-* =======
-*
-* ZGEBAK forms the right or left eigenvectors of a complex general
-* matrix by backward transformation on the computed eigenvectors of the
-* balanced matrix output by ZGEBAL.
-*
-* Arguments
-* =========
-*
-* JOB (input) CHARACTER*1
-* Specifies the type of backward transformation required:
-* = 'N', do nothing, return immediately;
-* = 'P', do backward transformation for permutation only;
-* = 'S', do backward transformation for scaling only;
-* = 'B', do backward transformations for both permutation and
-* scaling.
-* JOB must be the same as the argument JOB supplied to ZGEBAL.
-*
-* SIDE (input) CHARACTER*1
-* = 'R': V contains right eigenvectors;
-* = 'L': V contains left eigenvectors.
-*
-* N (input) INTEGER
-* The number of rows of the matrix V. N >= 0.
-*
-* ILO (input) INTEGER
-* IHI (input) INTEGER
-* The integers ILO and IHI determined by ZGEBAL.
-* 1 <= ILO <= IHI <= N, if N > 0; ILO=1 and IHI=0, if N=0.
-*
-* SCALE (input) DOUBLE PRECISION array, dimension (N)
-* Details of the permutation and scaling factors, as returned
-* by ZGEBAL.
-*
-* M (input) INTEGER
-* The number of columns of the matrix V. M >= 0.
-*
-* V (input/output) COMPLEX*16 array, dimension (LDV,M)
-* On entry, the matrix of right or left eigenvectors to be
-* transformed, as returned by ZHSEIN or ZTREVC.
-* On exit, V is overwritten by the transformed eigenvectors.
-*
-* LDV (input) INTEGER
-* The leading dimension of the array V. LDV >= max(1,N).
-*
-* INFO (output) INTEGER
-* = 0: successful exit
-* < 0: if INFO = -i, the i-th argument had an illegal value.
-*
-* =====================================================================
-*
-* .. Parameters ..
- DOUBLE PRECISION ONE
- PARAMETER ( ONE = 1.0D+0 )
-* ..
-* .. Local Scalars ..
- LOGICAL LEFTV, RIGHTV
- INTEGER I, II, K
- DOUBLE PRECISION S
-* ..
-* .. External Functions ..
- LOGICAL LSAME
- EXTERNAL LSAME
-* ..
-* .. External Subroutines ..
- EXTERNAL XERBLA, ZDSCAL, ZSWAP
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC MAX, MIN
-* ..
-* .. Executable Statements ..
-*
-* Decode and Test the input parameters
-*
- RIGHTV = LSAME( SIDE, 'R' )
- LEFTV = LSAME( SIDE, 'L' )
-*
- INFO = 0
- IF( .NOT.LSAME( JOB, 'N' ) .AND. .NOT.LSAME( JOB, 'P' ) .AND.
- $ .NOT.LSAME( JOB, 'S' ) .AND. .NOT.LSAME( JOB, 'B' ) ) THEN
- INFO = -1
- ELSE IF( .NOT.RIGHTV .AND. .NOT.LEFTV ) THEN
- INFO = -2
- ELSE IF( N.LT.0 ) THEN
- INFO = -3
- ELSE IF( ILO.LT.1 .OR. ILO.GT.MAX( 1, N ) ) THEN
- INFO = -4
- ELSE IF( IHI.LT.MIN( ILO, N ) .OR. IHI.GT.N ) THEN
- INFO = -5
- ELSE IF( M.LT.0 ) THEN
- INFO = -7
- ELSE IF( LDV.LT.MAX( 1, N ) ) THEN
- INFO = -9
- END IF
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'ZGEBAK', -INFO )
- RETURN
- END IF
-*
-* Quick return if possible
-*
- IF( N.EQ.0 )
- $ RETURN
- IF( M.EQ.0 )
- $ RETURN
- IF( LSAME( JOB, 'N' ) )
- $ RETURN
-*
- IF( ILO.EQ.IHI )
- $ GO TO 30
-*
-* Backward balance
-*
- IF( LSAME( JOB, 'S' ) .OR. LSAME( JOB, 'B' ) ) THEN
-*
- IF( RIGHTV ) THEN
- DO 10 I = ILO, IHI
- S = SCALE( I )
- CALL ZDSCAL( M, S, V( I, 1 ), LDV )
- 10 CONTINUE
- END IF
-*
- IF( LEFTV ) THEN
- DO 20 I = ILO, IHI
- S = ONE / SCALE( I )
- CALL ZDSCAL( M, S, V( I, 1 ), LDV )
- 20 CONTINUE
- END IF
-*
- END IF
-*
-* Backward permutation
-*
-* For I = ILO-1 step -1 until 1,
-* IHI+1 step 1 until N do --
-*
- 30 CONTINUE
- IF( LSAME( JOB, 'P' ) .OR. LSAME( JOB, 'B' ) ) THEN
- IF( RIGHTV ) THEN
- DO 40 II = 1, N
- I = II
- IF( I.GE.ILO .AND. I.LE.IHI )
- $ GO TO 40
- IF( I.LT.ILO )
- $ I = ILO - II
- K = SCALE( I )
- IF( K.EQ.I )
- $ GO TO 40
- CALL ZSWAP( M, V( I, 1 ), LDV, V( K, 1 ), LDV )
- 40 CONTINUE
- END IF
-*
- IF( LEFTV ) THEN
- DO 50 II = 1, N
- I = II
- IF( I.GE.ILO .AND. I.LE.IHI )
- $ GO TO 50
- IF( I.LT.ILO )
- $ I = ILO - II
- K = SCALE( I )
- IF( K.EQ.I )
- $ GO TO 50
- CALL ZSWAP( M, V( I, 1 ), LDV, V( K, 1 ), LDV )
- 50 CONTINUE
- END IF
- END IF
-*
- RETURN
-*
-* End of ZGEBAK
-*
- END
diff --git a/src/lib/lapack/zgebal.f b/src/lib/lapack/zgebal.f
deleted file mode 100644
index 67ac2e14..00000000
--- a/src/lib/lapack/zgebal.f
+++ /dev/null
@@ -1,330 +0,0 @@
- SUBROUTINE ZGEBAL( JOB, N, A, LDA, ILO, IHI, SCALE, INFO )
-*
-* -- LAPACK routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- CHARACTER JOB
- INTEGER IHI, ILO, INFO, LDA, N
-* ..
-* .. Array Arguments ..
- DOUBLE PRECISION SCALE( * )
- COMPLEX*16 A( LDA, * )
-* ..
-*
-* Purpose
-* =======
-*
-* ZGEBAL balances a general complex matrix A. This involves, first,
-* permuting A by a similarity transformation to isolate eigenvalues
-* in the first 1 to ILO-1 and last IHI+1 to N elements on the
-* diagonal; and second, applying a diagonal similarity transformation
-* to rows and columns ILO to IHI to make the rows and columns as
-* close in norm as possible. Both steps are optional.
-*
-* Balancing may reduce the 1-norm of the matrix, and improve the
-* accuracy of the computed eigenvalues and/or eigenvectors.
-*
-* Arguments
-* =========
-*
-* JOB (input) CHARACTER*1
-* Specifies the operations to be performed on A:
-* = 'N': none: simply set ILO = 1, IHI = N, SCALE(I) = 1.0
-* for i = 1,...,N;
-* = 'P': permute only;
-* = 'S': scale only;
-* = 'B': both permute and scale.
-*
-* N (input) INTEGER
-* The order of the matrix A. N >= 0.
-*
-* A (input/output) COMPLEX*16 array, dimension (LDA,N)
-* On entry, the input matrix A.
-* On exit, A is overwritten by the balanced matrix.
-* If JOB = 'N', A is not referenced.
-* See Further Details.
-*
-* LDA (input) INTEGER
-* The leading dimension of the array A. LDA >= max(1,N).
-*
-* ILO (output) INTEGER
-* IHI (output) INTEGER
-* ILO and IHI are set to integers such that on exit
-* A(i,j) = 0 if i > j and j = 1,...,ILO-1 or I = IHI+1,...,N.
-* If JOB = 'N' or 'S', ILO = 1 and IHI = N.
-*
-* SCALE (output) DOUBLE PRECISION array, dimension (N)
-* Details of the permutations and scaling factors applied to
-* A. If P(j) is the index of the row and column interchanged
-* with row and column j and D(j) is the scaling factor
-* applied to row and column j, then
-* SCALE(j) = P(j) for j = 1,...,ILO-1
-* = D(j) for j = ILO,...,IHI
-* = P(j) for j = IHI+1,...,N.
-* The order in which the interchanges are made is N to IHI+1,
-* then 1 to ILO-1.
-*
-* INFO (output) INTEGER
-* = 0: successful exit.
-* < 0: if INFO = -i, the i-th argument had an illegal value.
-*
-* Further Details
-* ===============
-*
-* The permutations consist of row and column interchanges which put
-* the matrix in the form
-*
-* ( T1 X Y )
-* P A P = ( 0 B Z )
-* ( 0 0 T2 )
-*
-* where T1 and T2 are upper triangular matrices whose eigenvalues lie
-* along the diagonal. The column indices ILO and IHI mark the starting
-* and ending columns of the submatrix B. Balancing consists of applying
-* a diagonal similarity transformation inv(D) * B * D to make the
-* 1-norms of each row of B and its corresponding column nearly equal.
-* The output matrix is
-*
-* ( T1 X*D Y )
-* ( 0 inv(D)*B*D inv(D)*Z ).
-* ( 0 0 T2 )
-*
-* Information about the permutations P and the diagonal matrix D is
-* returned in the vector SCALE.
-*
-* This subroutine is based on the EISPACK routine CBAL.
-*
-* Modified by Tzu-Yi Chen, Computer Science Division, University of
-* California at Berkeley, USA
-*
-* =====================================================================
-*
-* .. Parameters ..
- DOUBLE PRECISION ZERO, ONE
- PARAMETER ( ZERO = 0.0D+0, ONE = 1.0D+0 )
- DOUBLE PRECISION SCLFAC
- PARAMETER ( SCLFAC = 2.0D+0 )
- DOUBLE PRECISION FACTOR
- PARAMETER ( FACTOR = 0.95D+0 )
-* ..
-* .. Local Scalars ..
- LOGICAL NOCONV
- INTEGER I, ICA, IEXC, IRA, J, K, L, M
- DOUBLE PRECISION C, CA, F, G, R, RA, S, SFMAX1, SFMAX2, SFMIN1,
- $ SFMIN2
- COMPLEX*16 CDUM
-* ..
-* .. External Functions ..
- LOGICAL LSAME
- INTEGER IZAMAX
- DOUBLE PRECISION DLAMCH
- EXTERNAL LSAME, IZAMAX, DLAMCH
-* ..
-* .. External Subroutines ..
- EXTERNAL XERBLA, ZDSCAL, ZSWAP
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC ABS, DBLE, DIMAG, MAX, MIN
-* ..
-* .. Statement Functions ..
- DOUBLE PRECISION CABS1
-* ..
-* .. Statement Function definitions ..
- CABS1( CDUM ) = ABS( DBLE( CDUM ) ) + ABS( DIMAG( CDUM ) )
-* ..
-* .. Executable Statements ..
-*
-* Test the input parameters
-*
- INFO = 0
- IF( .NOT.LSAME( JOB, 'N' ) .AND. .NOT.LSAME( JOB, 'P' ) .AND.
- $ .NOT.LSAME( JOB, 'S' ) .AND. .NOT.LSAME( JOB, 'B' ) ) THEN
- INFO = -1
- ELSE IF( N.LT.0 ) THEN
- INFO = -2
- ELSE IF( LDA.LT.MAX( 1, N ) ) THEN
- INFO = -4
- END IF
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'ZGEBAL', -INFO )
- RETURN
- END IF
-*
- K = 1
- L = N
-*
- IF( N.EQ.0 )
- $ GO TO 210
-*
- IF( LSAME( JOB, 'N' ) ) THEN
- DO 10 I = 1, N
- SCALE( I ) = ONE
- 10 CONTINUE
- GO TO 210
- END IF
-*
- IF( LSAME( JOB, 'S' ) )
- $ GO TO 120
-*
-* Permutation to isolate eigenvalues if possible
-*
- GO TO 50
-*
-* Row and column exchange.
-*
- 20 CONTINUE
- SCALE( M ) = J
- IF( J.EQ.M )
- $ GO TO 30
-*
- CALL ZSWAP( L, A( 1, J ), 1, A( 1, M ), 1 )
- CALL ZSWAP( N-K+1, A( J, K ), LDA, A( M, K ), LDA )
-*
- 30 CONTINUE
- GO TO ( 40, 80 )IEXC
-*
-* Search for rows isolating an eigenvalue and push them down.
-*
- 40 CONTINUE
- IF( L.EQ.1 )
- $ GO TO 210
- L = L - 1
-*
- 50 CONTINUE
- DO 70 J = L, 1, -1
-*
- DO 60 I = 1, L
- IF( I.EQ.J )
- $ GO TO 60
- IF( DBLE( A( J, I ) ).NE.ZERO .OR. DIMAG( A( J, I ) ).NE.
- $ ZERO )GO TO 70
- 60 CONTINUE
-*
- M = L
- IEXC = 1
- GO TO 20
- 70 CONTINUE
-*
- GO TO 90
-*
-* Search for columns isolating an eigenvalue and push them left.
-*
- 80 CONTINUE
- K = K + 1
-*
- 90 CONTINUE
- DO 110 J = K, L
-*
- DO 100 I = K, L
- IF( I.EQ.J )
- $ GO TO 100
- IF( DBLE( A( I, J ) ).NE.ZERO .OR. DIMAG( A( I, J ) ).NE.
- $ ZERO )GO TO 110
- 100 CONTINUE
-*
- M = K
- IEXC = 2
- GO TO 20
- 110 CONTINUE
-*
- 120 CONTINUE
- DO 130 I = K, L
- SCALE( I ) = ONE
- 130 CONTINUE
-*
- IF( LSAME( JOB, 'P' ) )
- $ GO TO 210
-*
-* Balance the submatrix in rows K to L.
-*
-* Iterative loop for norm reduction
-*
- SFMIN1 = DLAMCH( 'S' ) / DLAMCH( 'P' )
- SFMAX1 = ONE / SFMIN1
- SFMIN2 = SFMIN1*SCLFAC
- SFMAX2 = ONE / SFMIN2
- 140 CONTINUE
- NOCONV = .FALSE.
-*
- DO 200 I = K, L
- C = ZERO
- R = ZERO
-*
- DO 150 J = K, L
- IF( J.EQ.I )
- $ GO TO 150
- C = C + CABS1( A( J, I ) )
- R = R + CABS1( A( I, J ) )
- 150 CONTINUE
- ICA = IZAMAX( L, A( 1, I ), 1 )
- CA = ABS( A( ICA, I ) )
- IRA = IZAMAX( N-K+1, A( I, K ), LDA )
- RA = ABS( A( I, IRA+K-1 ) )
-*
-* Guard against zero C or R due to underflow.
-*
- IF( C.EQ.ZERO .OR. R.EQ.ZERO )
- $ GO TO 200
- G = R / SCLFAC
- F = ONE
- S = C + R
- 160 CONTINUE
- IF( C.GE.G .OR. MAX( F, C, CA ).GE.SFMAX2 .OR.
- $ MIN( R, G, RA ).LE.SFMIN2 )GO TO 170
- F = F*SCLFAC
- C = C*SCLFAC
- CA = CA*SCLFAC
- R = R / SCLFAC
- G = G / SCLFAC
- RA = RA / SCLFAC
- GO TO 160
-*
- 170 CONTINUE
- G = C / SCLFAC
- 180 CONTINUE
- IF( G.LT.R .OR. MAX( R, RA ).GE.SFMAX2 .OR.
- $ MIN( F, C, G, CA ).LE.SFMIN2 )GO TO 190
- F = F / SCLFAC
- C = C / SCLFAC
- G = G / SCLFAC
- CA = CA / SCLFAC
- R = R*SCLFAC
- RA = RA*SCLFAC
- GO TO 180
-*
-* Now balance.
-*
- 190 CONTINUE
- IF( ( C+R ).GE.FACTOR*S )
- $ GO TO 200
- IF( F.LT.ONE .AND. SCALE( I ).LT.ONE ) THEN
- IF( F*SCALE( I ).LE.SFMIN1 )
- $ GO TO 200
- END IF
- IF( F.GT.ONE .AND. SCALE( I ).GT.ONE ) THEN
- IF( SCALE( I ).GE.SFMAX1 / F )
- $ GO TO 200
- END IF
- G = ONE / F
- SCALE( I ) = SCALE( I )*F
- NOCONV = .TRUE.
-*
- CALL ZDSCAL( N-K+1, G, A( I, K ), LDA )
- CALL ZDSCAL( L, F, A( 1, I ), 1 )
-*
- 200 CONTINUE
-*
- IF( NOCONV )
- $ GO TO 140
-*
- 210 CONTINUE
- ILO = K
- IHI = L
-*
- RETURN
-*
-* End of ZGEBAL
-*
- END
diff --git a/src/lib/lapack/zgebd2.f b/src/lib/lapack/zgebd2.f
deleted file mode 100644
index 5ba52e87..00000000
--- a/src/lib/lapack/zgebd2.f
+++ /dev/null
@@ -1,250 +0,0 @@
- SUBROUTINE ZGEBD2( M, N, A, LDA, D, E, TAUQ, TAUP, WORK, INFO )
-*
-* -- LAPACK routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- INTEGER INFO, LDA, M, N
-* ..
-* .. Array Arguments ..
- DOUBLE PRECISION D( * ), E( * )
- COMPLEX*16 A( LDA, * ), TAUP( * ), TAUQ( * ), WORK( * )
-* ..
-*
-* Purpose
-* =======
-*
-* ZGEBD2 reduces a complex general m by n matrix A to upper or lower
-* real bidiagonal form B by a unitary transformation: Q' * A * P = B.
-*
-* If m >= n, B is upper bidiagonal; if m < n, B is lower bidiagonal.
-*
-* Arguments
-* =========
-*
-* M (input) INTEGER
-* The number of rows in the matrix A. M >= 0.
-*
-* N (input) INTEGER
-* The number of columns in the matrix A. N >= 0.
-*
-* A (input/output) COMPLEX*16 array, dimension (LDA,N)
-* On entry, the m by n general matrix to be reduced.
-* On exit,
-* if m >= n, the diagonal and the first superdiagonal are
-* overwritten with the upper bidiagonal matrix B; the
-* elements below the diagonal, with the array TAUQ, represent
-* the unitary matrix Q as a product of elementary
-* reflectors, and the elements above the first superdiagonal,
-* with the array TAUP, represent the unitary matrix P as
-* a product of elementary reflectors;
-* if m < n, the diagonal and the first subdiagonal are
-* overwritten with the lower bidiagonal matrix B; the
-* elements below the first subdiagonal, with the array TAUQ,
-* represent the unitary matrix Q as a product of
-* elementary reflectors, and the elements above the diagonal,
-* with the array TAUP, represent the unitary matrix P as
-* a product of elementary reflectors.
-* See Further Details.
-*
-* LDA (input) INTEGER
-* The leading dimension of the array A. LDA >= max(1,M).
-*
-* D (output) DOUBLE PRECISION array, dimension (min(M,N))
-* The diagonal elements of the bidiagonal matrix B:
-* D(i) = A(i,i).
-*
-* E (output) DOUBLE PRECISION array, dimension (min(M,N)-1)
-* The off-diagonal elements of the bidiagonal matrix B:
-* if m >= n, E(i) = A(i,i+1) for i = 1,2,...,n-1;
-* if m < n, E(i) = A(i+1,i) for i = 1,2,...,m-1.
-*
-* TAUQ (output) COMPLEX*16 array dimension (min(M,N))
-* The scalar factors of the elementary reflectors which
-* represent the unitary matrix Q. See Further Details.
-*
-* TAUP (output) COMPLEX*16 array, dimension (min(M,N))
-* The scalar factors of the elementary reflectors which
-* represent the unitary matrix P. See Further Details.
-*
-* WORK (workspace) COMPLEX*16 array, dimension (max(M,N))
-*
-* INFO (output) INTEGER
-* = 0: successful exit
-* < 0: if INFO = -i, the i-th argument had an illegal value.
-*
-* Further Details
-* ===============
-*
-* The matrices Q and P are represented as products of elementary
-* reflectors:
-*
-* If m >= n,
-*
-* Q = H(1) H(2) . . . H(n) and P = G(1) G(2) . . . G(n-1)
-*
-* Each H(i) and G(i) has the form:
-*
-* H(i) = I - tauq * v * v' and G(i) = I - taup * u * u'
-*
-* where tauq and taup are complex scalars, and v and u are complex
-* vectors; v(1:i-1) = 0, v(i) = 1, and v(i+1:m) is stored on exit in
-* A(i+1:m,i); u(1:i) = 0, u(i+1) = 1, and u(i+2:n) is stored on exit in
-* A(i,i+2:n); tauq is stored in TAUQ(i) and taup in TAUP(i).
-*
-* If m < n,
-*
-* Q = H(1) H(2) . . . H(m-1) and P = G(1) G(2) . . . G(m)
-*
-* Each H(i) and G(i) has the form:
-*
-* H(i) = I - tauq * v * v' and G(i) = I - taup * u * u'
-*
-* where tauq and taup are complex scalars, v and u are complex vectors;
-* v(1:i) = 0, v(i+1) = 1, and v(i+2:m) is stored on exit in A(i+2:m,i);
-* u(1:i-1) = 0, u(i) = 1, and u(i+1:n) is stored on exit in A(i,i+1:n);
-* tauq is stored in TAUQ(i) and taup in TAUP(i).
-*
-* The contents of A on exit are illustrated by the following examples:
-*
-* m = 6 and n = 5 (m > n): m = 5 and n = 6 (m < n):
-*
-* ( d e u1 u1 u1 ) ( d u1 u1 u1 u1 u1 )
-* ( v1 d e u2 u2 ) ( e d u2 u2 u2 u2 )
-* ( v1 v2 d e u3 ) ( v1 e d u3 u3 u3 )
-* ( v1 v2 v3 d e ) ( v1 v2 e d u4 u4 )
-* ( v1 v2 v3 v4 d ) ( v1 v2 v3 e d u5 )
-* ( v1 v2 v3 v4 v5 )
-*
-* where d and e denote diagonal and off-diagonal elements of B, vi
-* denotes an element of the vector defining H(i), and ui an element of
-* the vector defining G(i).
-*
-* =====================================================================
-*
-* .. Parameters ..
- COMPLEX*16 ZERO, ONE
- PARAMETER ( ZERO = ( 0.0D+0, 0.0D+0 ),
- $ ONE = ( 1.0D+0, 0.0D+0 ) )
-* ..
-* .. Local Scalars ..
- INTEGER I
- COMPLEX*16 ALPHA
-* ..
-* .. External Subroutines ..
- EXTERNAL XERBLA, ZLACGV, ZLARF, ZLARFG
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC DCONJG, MAX, MIN
-* ..
-* .. Executable Statements ..
-*
-* Test the input parameters
-*
- INFO = 0
- IF( M.LT.0 ) THEN
- INFO = -1
- ELSE IF( N.LT.0 ) THEN
- INFO = -2
- ELSE IF( LDA.LT.MAX( 1, M ) ) THEN
- INFO = -4
- END IF
- IF( INFO.LT.0 ) THEN
- CALL XERBLA( 'ZGEBD2', -INFO )
- RETURN
- END IF
-*
- IF( M.GE.N ) THEN
-*
-* Reduce to upper bidiagonal form
-*
- DO 10 I = 1, N
-*
-* Generate elementary reflector H(i) to annihilate A(i+1:m,i)
-*
- ALPHA = A( I, I )
- CALL ZLARFG( M-I+1, ALPHA, A( MIN( I+1, M ), I ), 1,
- $ TAUQ( I ) )
- D( I ) = ALPHA
- A( I, I ) = ONE
-*
-* Apply H(i)' to A(i:m,i+1:n) from the left
-*
- IF( I.LT.N )
- $ CALL ZLARF( 'Left', M-I+1, N-I, A( I, I ), 1,
- $ DCONJG( TAUQ( I ) ), A( I, I+1 ), LDA, WORK )
- A( I, I ) = D( I )
-*
- IF( I.LT.N ) THEN
-*
-* Generate elementary reflector G(i) to annihilate
-* A(i,i+2:n)
-*
- CALL ZLACGV( N-I, A( I, I+1 ), LDA )
- ALPHA = A( I, I+1 )
- CALL ZLARFG( N-I, ALPHA, A( I, MIN( I+2, N ) ), LDA,
- $ TAUP( I ) )
- E( I ) = ALPHA
- A( I, I+1 ) = ONE
-*
-* Apply G(i) to A(i+1:m,i+1:n) from the right
-*
- CALL ZLARF( 'Right', M-I, N-I, A( I, I+1 ), LDA,
- $ TAUP( I ), A( I+1, I+1 ), LDA, WORK )
- CALL ZLACGV( N-I, A( I, I+1 ), LDA )
- A( I, I+1 ) = E( I )
- ELSE
- TAUP( I ) = ZERO
- END IF
- 10 CONTINUE
- ELSE
-*
-* Reduce to lower bidiagonal form
-*
- DO 20 I = 1, M
-*
-* Generate elementary reflector G(i) to annihilate A(i,i+1:n)
-*
- CALL ZLACGV( N-I+1, A( I, I ), LDA )
- ALPHA = A( I, I )
- CALL ZLARFG( N-I+1, ALPHA, A( I, MIN( I+1, N ) ), LDA,
- $ TAUP( I ) )
- D( I ) = ALPHA
- A( I, I ) = ONE
-*
-* Apply G(i) to A(i+1:m,i:n) from the right
-*
- IF( I.LT.M )
- $ CALL ZLARF( 'Right', M-I, N-I+1, A( I, I ), LDA,
- $ TAUP( I ), A( I+1, I ), LDA, WORK )
- CALL ZLACGV( N-I+1, A( I, I ), LDA )
- A( I, I ) = D( I )
-*
- IF( I.LT.M ) THEN
-*
-* Generate elementary reflector H(i) to annihilate
-* A(i+2:m,i)
-*
- ALPHA = A( I+1, I )
- CALL ZLARFG( M-I, ALPHA, A( MIN( I+2, M ), I ), 1,
- $ TAUQ( I ) )
- E( I ) = ALPHA
- A( I+1, I ) = ONE
-*
-* Apply H(i)' to A(i+1:m,i+1:n) from the left
-*
- CALL ZLARF( 'Left', M-I, N-I, A( I+1, I ), 1,
- $ DCONJG( TAUQ( I ) ), A( I+1, I+1 ), LDA,
- $ WORK )
- A( I+1, I ) = E( I )
- ELSE
- TAUQ( I ) = ZERO
- END IF
- 20 CONTINUE
- END IF
- RETURN
-*
-* End of ZGEBD2
-*
- END
diff --git a/src/lib/lapack/zgebrd.f b/src/lib/lapack/zgebrd.f
deleted file mode 100644
index 4f97bd7e..00000000
--- a/src/lib/lapack/zgebrd.f
+++ /dev/null
@@ -1,268 +0,0 @@
- SUBROUTINE ZGEBRD( M, N, A, LDA, D, E, TAUQ, TAUP, WORK, LWORK,
- $ INFO )
-*
-* -- LAPACK routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- INTEGER INFO, LDA, LWORK, M, N
-* ..
-* .. Array Arguments ..
- DOUBLE PRECISION D( * ), E( * )
- COMPLEX*16 A( LDA, * ), TAUP( * ), TAUQ( * ), WORK( * )
-* ..
-*
-* Purpose
-* =======
-*
-* ZGEBRD reduces a general complex M-by-N matrix A to upper or lower
-* bidiagonal form B by a unitary transformation: Q**H * A * P = B.
-*
-* If m >= n, B is upper bidiagonal; if m < n, B is lower bidiagonal.
-*
-* Arguments
-* =========
-*
-* M (input) INTEGER
-* The number of rows in the matrix A. M >= 0.
-*
-* N (input) INTEGER
-* The number of columns in the matrix A. N >= 0.
-*
-* A (input/output) COMPLEX*16 array, dimension (LDA,N)
-* On entry, the M-by-N general matrix to be reduced.
-* On exit,
-* if m >= n, the diagonal and the first superdiagonal are
-* overwritten with the upper bidiagonal matrix B; the
-* elements below the diagonal, with the array TAUQ, represent
-* the unitary matrix Q as a product of elementary
-* reflectors, and the elements above the first superdiagonal,
-* with the array TAUP, represent the unitary matrix P as
-* a product of elementary reflectors;
-* if m < n, the diagonal and the first subdiagonal are
-* overwritten with the lower bidiagonal matrix B; the
-* elements below the first subdiagonal, with the array TAUQ,
-* represent the unitary matrix Q as a product of
-* elementary reflectors, and the elements above the diagonal,
-* with the array TAUP, represent the unitary matrix P as
-* a product of elementary reflectors.
-* See Further Details.
-*
-* LDA (input) INTEGER
-* The leading dimension of the array A. LDA >= max(1,M).
-*
-* D (output) DOUBLE PRECISION array, dimension (min(M,N))
-* The diagonal elements of the bidiagonal matrix B:
-* D(i) = A(i,i).
-*
-* E (output) DOUBLE PRECISION array, dimension (min(M,N)-1)
-* The off-diagonal elements of the bidiagonal matrix B:
-* if m >= n, E(i) = A(i,i+1) for i = 1,2,...,n-1;
-* if m < n, E(i) = A(i+1,i) for i = 1,2,...,m-1.
-*
-* TAUQ (output) COMPLEX*16 array dimension (min(M,N))
-* The scalar factors of the elementary reflectors which
-* represent the unitary matrix Q. See Further Details.
-*
-* TAUP (output) COMPLEX*16 array, dimension (min(M,N))
-* The scalar factors of the elementary reflectors which
-* represent the unitary matrix P. See Further Details.
-*
-* WORK (workspace/output) COMPLEX*16 array, dimension (MAX(1,LWORK))
-* On exit, if INFO = 0, WORK(1) returns the optimal LWORK.
-*
-* LWORK (input) INTEGER
-* The length of the array WORK. LWORK >= max(1,M,N).
-* For optimum performance LWORK >= (M+N)*NB, where NB
-* is the optimal blocksize.
-*
-* If LWORK = -1, then a workspace query is assumed; the routine
-* only calculates the optimal size of the WORK array, returns
-* this value as the first entry of the WORK array, and no error
-* message related to LWORK is issued by XERBLA.
-*
-* INFO (output) INTEGER
-* = 0: successful exit.
-* < 0: if INFO = -i, the i-th argument had an illegal value.
-*
-* Further Details
-* ===============
-*
-* The matrices Q and P are represented as products of elementary
-* reflectors:
-*
-* If m >= n,
-*
-* Q = H(1) H(2) . . . H(n) and P = G(1) G(2) . . . G(n-1)
-*
-* Each H(i) and G(i) has the form:
-*
-* H(i) = I - tauq * v * v' and G(i) = I - taup * u * u'
-*
-* where tauq and taup are complex scalars, and v and u are complex
-* vectors; v(1:i-1) = 0, v(i) = 1, and v(i+1:m) is stored on exit in
-* A(i+1:m,i); u(1:i) = 0, u(i+1) = 1, and u(i+2:n) is stored on exit in
-* A(i,i+2:n); tauq is stored in TAUQ(i) and taup in TAUP(i).
-*
-* If m < n,
-*
-* Q = H(1) H(2) . . . H(m-1) and P = G(1) G(2) . . . G(m)
-*
-* Each H(i) and G(i) has the form:
-*
-* H(i) = I - tauq * v * v' and G(i) = I - taup * u * u'
-*
-* where tauq and taup are complex scalars, and v and u are complex
-* vectors; v(1:i) = 0, v(i+1) = 1, and v(i+2:m) is stored on exit in
-* A(i+2:m,i); u(1:i-1) = 0, u(i) = 1, and u(i+1:n) is stored on exit in
-* A(i,i+1:n); tauq is stored in TAUQ(i) and taup in TAUP(i).
-*
-* The contents of A on exit are illustrated by the following examples:
-*
-* m = 6 and n = 5 (m > n): m = 5 and n = 6 (m < n):
-*
-* ( d e u1 u1 u1 ) ( d u1 u1 u1 u1 u1 )
-* ( v1 d e u2 u2 ) ( e d u2 u2 u2 u2 )
-* ( v1 v2 d e u3 ) ( v1 e d u3 u3 u3 )
-* ( v1 v2 v3 d e ) ( v1 v2 e d u4 u4 )
-* ( v1 v2 v3 v4 d ) ( v1 v2 v3 e d u5 )
-* ( v1 v2 v3 v4 v5 )
-*
-* where d and e denote diagonal and off-diagonal elements of B, vi
-* denotes an element of the vector defining H(i), and ui an element of
-* the vector defining G(i).
-*
-* =====================================================================
-*
-* .. Parameters ..
- COMPLEX*16 ONE
- PARAMETER ( ONE = ( 1.0D+0, 0.0D+0 ) )
-* ..
-* .. Local Scalars ..
- LOGICAL LQUERY
- INTEGER I, IINFO, J, LDWRKX, LDWRKY, LWKOPT, MINMN, NB,
- $ NBMIN, NX
- DOUBLE PRECISION WS
-* ..
-* .. External Subroutines ..
- EXTERNAL XERBLA, ZGEBD2, ZGEMM, ZLABRD
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC DBLE, MAX, MIN
-* ..
-* .. External Functions ..
- INTEGER ILAENV
- EXTERNAL ILAENV
-* ..
-* .. Executable Statements ..
-*
-* Test the input parameters
-*
- INFO = 0
- NB = MAX( 1, ILAENV( 1, 'ZGEBRD', ' ', M, N, -1, -1 ) )
- LWKOPT = ( M+N )*NB
- WORK( 1 ) = DBLE( LWKOPT )
- LQUERY = ( LWORK.EQ.-1 )
- IF( M.LT.0 ) THEN
- INFO = -1
- ELSE IF( N.LT.0 ) THEN
- INFO = -2
- ELSE IF( LDA.LT.MAX( 1, M ) ) THEN
- INFO = -4
- ELSE IF( LWORK.LT.MAX( 1, M, N ) .AND. .NOT.LQUERY ) THEN
- INFO = -10
- END IF
- IF( INFO.LT.0 ) THEN
- CALL XERBLA( 'ZGEBRD', -INFO )
- RETURN
- ELSE IF( LQUERY ) THEN
- RETURN
- END IF
-*
-* Quick return if possible
-*
- MINMN = MIN( M, N )
- IF( MINMN.EQ.0 ) THEN
- WORK( 1 ) = 1
- RETURN
- END IF
-*
- WS = MAX( M, N )
- LDWRKX = M
- LDWRKY = N
-*
- IF( NB.GT.1 .AND. NB.LT.MINMN ) THEN
-*
-* Set the crossover point NX.
-*
- NX = MAX( NB, ILAENV( 3, 'ZGEBRD', ' ', M, N, -1, -1 ) )
-*
-* Determine when to switch from blocked to unblocked code.
-*
- IF( NX.LT.MINMN ) THEN
- WS = ( M+N )*NB
- IF( LWORK.LT.WS ) THEN
-*
-* Not enough work space for the optimal NB, consider using
-* a smaller block size.
-*
- NBMIN = ILAENV( 2, 'ZGEBRD', ' ', M, N, -1, -1 )
- IF( LWORK.GE.( M+N )*NBMIN ) THEN
- NB = LWORK / ( M+N )
- ELSE
- NB = 1
- NX = MINMN
- END IF
- END IF
- END IF
- ELSE
- NX = MINMN
- END IF
-*
- DO 30 I = 1, MINMN - NX, NB
-*
-* Reduce rows and columns i:i+ib-1 to bidiagonal form and return
-* the matrices X and Y which are needed to update the unreduced
-* part of the matrix
-*
- CALL ZLABRD( M-I+1, N-I+1, NB, A( I, I ), LDA, D( I ), E( I ),
- $ TAUQ( I ), TAUP( I ), WORK, LDWRKX,
- $ WORK( LDWRKX*NB+1 ), LDWRKY )
-*
-* Update the trailing submatrix A(i+ib:m,i+ib:n), using
-* an update of the form A := A - V*Y' - X*U'
-*
- CALL ZGEMM( 'No transpose', 'Conjugate transpose', M-I-NB+1,
- $ N-I-NB+1, NB, -ONE, A( I+NB, I ), LDA,
- $ WORK( LDWRKX*NB+NB+1 ), LDWRKY, ONE,
- $ A( I+NB, I+NB ), LDA )
- CALL ZGEMM( 'No transpose', 'No transpose', M-I-NB+1, N-I-NB+1,
- $ NB, -ONE, WORK( NB+1 ), LDWRKX, A( I, I+NB ), LDA,
- $ ONE, A( I+NB, I+NB ), LDA )
-*
-* Copy diagonal and off-diagonal elements of B back into A
-*
- IF( M.GE.N ) THEN
- DO 10 J = I, I + NB - 1
- A( J, J ) = D( J )
- A( J, J+1 ) = E( J )
- 10 CONTINUE
- ELSE
- DO 20 J = I, I + NB - 1
- A( J, J ) = D( J )
- A( J+1, J ) = E( J )
- 20 CONTINUE
- END IF
- 30 CONTINUE
-*
-* Use unblocked code to reduce the remainder of the matrix
-*
- CALL ZGEBD2( M-I+1, N-I+1, A( I, I ), LDA, D( I ), E( I ),
- $ TAUQ( I ), TAUP( I ), WORK, IINFO )
- WORK( 1 ) = WS
- RETURN
-*
-* End of ZGEBRD
-*
- END
diff --git a/src/lib/lapack/zgecon.f b/src/lib/lapack/zgecon.f
deleted file mode 100644
index cfaaca35..00000000
--- a/src/lib/lapack/zgecon.f
+++ /dev/null
@@ -1,193 +0,0 @@
- SUBROUTINE ZGECON( NORM, N, A, LDA, ANORM, RCOND, WORK, RWORK,
- $ INFO )
-*
-* -- LAPACK routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* Modified to call ZLACN2 in place of ZLACON, 10 Feb 03, SJH.
-*
-* .. Scalar Arguments ..
- CHARACTER NORM
- INTEGER INFO, LDA, N
- DOUBLE PRECISION ANORM, RCOND
-* ..
-* .. Array Arguments ..
- DOUBLE PRECISION RWORK( * )
- COMPLEX*16 A( LDA, * ), WORK( * )
-* ..
-*
-* Purpose
-* =======
-*
-* ZGECON estimates the reciprocal of the condition number of a general
-* complex matrix A, in either the 1-norm or the infinity-norm, using
-* the LU factorization computed by ZGETRF.
-*
-* An estimate is obtained for norm(inv(A)), and the reciprocal of the
-* condition number is computed as
-* RCOND = 1 / ( norm(A) * norm(inv(A)) ).
-*
-* Arguments
-* =========
-*
-* NORM (input) CHARACTER*1
-* Specifies whether the 1-norm condition number or the
-* infinity-norm condition number is required:
-* = '1' or 'O': 1-norm;
-* = 'I': Infinity-norm.
-*
-* N (input) INTEGER
-* The order of the matrix A. N >= 0.
-*
-* A (input) COMPLEX*16 array, dimension (LDA,N)
-* The factors L and U from the factorization A = P*L*U
-* as computed by ZGETRF.
-*
-* LDA (input) INTEGER
-* The leading dimension of the array A. LDA >= max(1,N).
-*
-* ANORM (input) DOUBLE PRECISION
-* If NORM = '1' or 'O', the 1-norm of the original matrix A.
-* If NORM = 'I', the infinity-norm of the original matrix A.
-*
-* RCOND (output) DOUBLE PRECISION
-* The reciprocal of the condition number of the matrix A,
-* computed as RCOND = 1/(norm(A) * norm(inv(A))).
-*
-* WORK (workspace) COMPLEX*16 array, dimension (2*N)
-*
-* RWORK (workspace) DOUBLE PRECISION array, dimension (2*N)
-*
-* INFO (output) INTEGER
-* = 0: successful exit
-* < 0: if INFO = -i, the i-th argument had an illegal value
-*
-* =====================================================================
-*
-* .. Parameters ..
- DOUBLE PRECISION ONE, ZERO
- PARAMETER ( ONE = 1.0D+0, ZERO = 0.0D+0 )
-* ..
-* .. Local Scalars ..
- LOGICAL ONENRM
- CHARACTER NORMIN
- INTEGER IX, KASE, KASE1
- DOUBLE PRECISION AINVNM, SCALE, SL, SMLNUM, SU
- COMPLEX*16 ZDUM
-* ..
-* .. Local Arrays ..
- INTEGER ISAVE( 3 )
-* ..
-* .. External Functions ..
- LOGICAL LSAME
- INTEGER IZAMAX
- DOUBLE PRECISION DLAMCH
- EXTERNAL LSAME, IZAMAX, DLAMCH
-* ..
-* .. External Subroutines ..
- EXTERNAL XERBLA, ZDRSCL, ZLACN2, ZLATRS
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC ABS, DBLE, DIMAG, MAX
-* ..
-* .. Statement Functions ..
- DOUBLE PRECISION CABS1
-* ..
-* .. Statement Function definitions ..
- CABS1( ZDUM ) = ABS( DBLE( ZDUM ) ) + ABS( DIMAG( ZDUM ) )
-* ..
-* .. Executable Statements ..
-*
-* Test the input parameters.
-*
- INFO = 0
- ONENRM = NORM.EQ.'1' .OR. LSAME( NORM, 'O' )
- IF( .NOT.ONENRM .AND. .NOT.LSAME( NORM, 'I' ) ) THEN
- INFO = -1
- ELSE IF( N.LT.0 ) THEN
- INFO = -2
- ELSE IF( LDA.LT.MAX( 1, N ) ) THEN
- INFO = -4
- ELSE IF( ANORM.LT.ZERO ) THEN
- INFO = -5
- END IF
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'ZGECON', -INFO )
- RETURN
- END IF
-*
-* Quick return if possible
-*
- RCOND = ZERO
- IF( N.EQ.0 ) THEN
- RCOND = ONE
- RETURN
- ELSE IF( ANORM.EQ.ZERO ) THEN
- RETURN
- END IF
-*
- SMLNUM = DLAMCH( 'Safe minimum' )
-*
-* Estimate the norm of inv(A).
-*
- AINVNM = ZERO
- NORMIN = 'N'
- IF( ONENRM ) THEN
- KASE1 = 1
- ELSE
- KASE1 = 2
- END IF
- KASE = 0
- 10 CONTINUE
- CALL ZLACN2( N, WORK( N+1 ), WORK, AINVNM, KASE, ISAVE )
- IF( KASE.NE.0 ) THEN
- IF( KASE.EQ.KASE1 ) THEN
-*
-* Multiply by inv(L).
-*
- CALL ZLATRS( 'Lower', 'No transpose', 'Unit', NORMIN, N, A,
- $ LDA, WORK, SL, RWORK, INFO )
-*
-* Multiply by inv(U).
-*
- CALL ZLATRS( 'Upper', 'No transpose', 'Non-unit', NORMIN, N,
- $ A, LDA, WORK, SU, RWORK( N+1 ), INFO )
- ELSE
-*
-* Multiply by inv(U').
-*
- CALL ZLATRS( 'Upper', 'Conjugate transpose', 'Non-unit',
- $ NORMIN, N, A, LDA, WORK, SU, RWORK( N+1 ),
- $ INFO )
-*
-* Multiply by inv(L').
-*
- CALL ZLATRS( 'Lower', 'Conjugate transpose', 'Unit', NORMIN,
- $ N, A, LDA, WORK, SL, RWORK, INFO )
- END IF
-*
-* Divide X by 1/(SL*SU) if doing so will not cause overflow.
-*
- SCALE = SL*SU
- NORMIN = 'Y'
- IF( SCALE.NE.ONE ) THEN
- IX = IZAMAX( N, WORK, 1 )
- IF( SCALE.LT.CABS1( WORK( IX ) )*SMLNUM .OR. SCALE.EQ.ZERO )
- $ GO TO 20
- CALL ZDRSCL( N, SCALE, WORK, 1 )
- END IF
- GO TO 10
- END IF
-*
-* Compute the estimate of the reciprocal condition number.
-*
- IF( AINVNM.NE.ZERO )
- $ RCOND = ( ONE / AINVNM ) / ANORM
-*
- 20 CONTINUE
- RETURN
-*
-* End of ZGECON
-*
- END
diff --git a/src/lib/lapack/zgees.f b/src/lib/lapack/zgees.f
deleted file mode 100644
index ade5f9f2..00000000
--- a/src/lib/lapack/zgees.f
+++ /dev/null
@@ -1,324 +0,0 @@
- SUBROUTINE ZGEES( JOBVS, SORT, SELECT, N, A, LDA, SDIM, W, VS,
- $ LDVS, WORK, LWORK, RWORK, BWORK, INFO )
-*
-* -- LAPACK driver routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- CHARACTER JOBVS, SORT
- INTEGER INFO, LDA, LDVS, LWORK, N, SDIM
-* ..
-* .. Array Arguments ..
- LOGICAL BWORK( * )
- DOUBLE PRECISION RWORK( * )
- COMPLEX*16 A( LDA, * ), VS( LDVS, * ), W( * ), WORK( * )
-* ..
-* .. Function Arguments ..
- LOGICAL SELECT
- EXTERNAL SELECT
-* ..
-*
-* Purpose
-* =======
-*
-* ZGEES computes for an N-by-N complex nonsymmetric matrix A, the
-* eigenvalues, the Schur form T, and, optionally, the matrix of Schur
-* vectors Z. This gives the Schur factorization A = Z*T*(Z**H).
-*
-* Optionally, it also orders the eigenvalues on the diagonal of the
-* Schur form so that selected eigenvalues are at the top left.
-* The leading columns of Z then form an orthonormal basis for the
-* invariant subspace corresponding to the selected eigenvalues.
-*
-* A complex matrix is in Schur form if it is upper triangular.
-*
-* Arguments
-* =========
-*
-* JOBVS (input) CHARACTER*1
-* = 'N': Schur vectors are not computed;
-* = 'V': Schur vectors are computed.
-*
-* SORT (input) CHARACTER*1
-* Specifies whether or not to order the eigenvalues on the
-* diagonal of the Schur form.
-* = 'N': Eigenvalues are not ordered:
-* = 'S': Eigenvalues are ordered (see SELECT).
-*
-* SELECT (external procedure) LOGICAL FUNCTION of one COMPLEX*16 argument
-* SELECT must be declared EXTERNAL in the calling subroutine.
-* If SORT = 'S', SELECT is used to select eigenvalues to order
-* to the top left of the Schur form.
-* IF SORT = 'N', SELECT is not referenced.
-* The eigenvalue W(j) is selected if SELECT(W(j)) is true.
-*
-* N (input) INTEGER
-* The order of the matrix A. N >= 0.
-*
-* A (input/output) COMPLEX*16 array, dimension (LDA,N)
-* On entry, the N-by-N matrix A.
-* On exit, A has been overwritten by its Schur form T.
-*
-* LDA (input) INTEGER
-* The leading dimension of the array A. LDA >= max(1,N).
-*
-* SDIM (output) INTEGER
-* If SORT = 'N', SDIM = 0.
-* If SORT = 'S', SDIM = number of eigenvalues for which
-* SELECT is true.
-*
-* W (output) COMPLEX*16 array, dimension (N)
-* W contains the computed eigenvalues, in the same order that
-* they appear on the diagonal of the output Schur form T.
-*
-* VS (output) COMPLEX*16 array, dimension (LDVS,N)
-* If JOBVS = 'V', VS contains the unitary matrix Z of Schur
-* vectors.
-* If JOBVS = 'N', VS is not referenced.
-*
-* LDVS (input) INTEGER
-* The leading dimension of the array VS. LDVS >= 1; if
-* JOBVS = 'V', LDVS >= N.
-*
-* WORK (workspace/output) COMPLEX*16 array, dimension (MAX(1,LWORK))
-* On exit, if INFO = 0, WORK(1) returns the optimal LWORK.
-*
-* LWORK (input) INTEGER
-* The dimension of the array WORK. LWORK >= max(1,2*N).
-* For good performance, LWORK must generally be larger.
-*
-* If LWORK = -1, then a workspace query is assumed; the routine
-* only calculates the optimal size of the WORK array, returns
-* this value as the first entry of the WORK array, and no error
-* message related to LWORK is issued by XERBLA.
-*
-* RWORK (workspace) DOUBLE PRECISION array, dimension (N)
-*
-* BWORK (workspace) LOGICAL array, dimension (N)
-* Not referenced if SORT = 'N'.
-*
-* INFO (output) INTEGER
-* = 0: successful exit
-* < 0: if INFO = -i, the i-th argument had an illegal value.
-* > 0: if INFO = i, and i is
-* <= N: the QR algorithm failed to compute all the
-* eigenvalues; elements 1:ILO-1 and i+1:N of W
-* contain those eigenvalues which have converged;
-* if JOBVS = 'V', VS contains the matrix which
-* reduces A to its partially converged Schur form.
-* = N+1: the eigenvalues could not be reordered because
-* some eigenvalues were too close to separate (the
-* problem is very ill-conditioned);
-* = N+2: after reordering, roundoff changed values of
-* some complex eigenvalues so that leading
-* eigenvalues in the Schur form no longer satisfy
-* SELECT = .TRUE.. This could also be caused by
-* underflow due to scaling.
-*
-* =====================================================================
-*
-* .. Parameters ..
- DOUBLE PRECISION ZERO, ONE
- PARAMETER ( ZERO = 0.0D0, ONE = 1.0D0 )
-* ..
-* .. Local Scalars ..
- LOGICAL LQUERY, SCALEA, WANTST, WANTVS
- INTEGER HSWORK, I, IBAL, ICOND, IERR, IEVAL, IHI, ILO,
- $ ITAU, IWRK, MAXWRK, MINWRK
- DOUBLE PRECISION ANRM, BIGNUM, CSCALE, EPS, S, SEP, SMLNUM
-* ..
-* .. Local Arrays ..
- DOUBLE PRECISION DUM( 1 )
-* ..
-* .. External Subroutines ..
- EXTERNAL DLABAD, XERBLA, ZCOPY, ZGEBAK, ZGEBAL, ZGEHRD,
- $ ZHSEQR, ZLACPY, ZLASCL, ZTRSEN, ZUNGHR
-* ..
-* .. External Functions ..
- LOGICAL LSAME
- INTEGER ILAENV
- DOUBLE PRECISION DLAMCH, ZLANGE
- EXTERNAL LSAME, ILAENV, DLAMCH, ZLANGE
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC MAX, SQRT
-* ..
-* .. Executable Statements ..
-*
-* Test the input arguments
-*
- INFO = 0
- LQUERY = ( LWORK.EQ.-1 )
- WANTVS = LSAME( JOBVS, 'V' )
- WANTST = LSAME( SORT, 'S' )
- IF( ( .NOT.WANTVS ) .AND. ( .NOT.LSAME( JOBVS, 'N' ) ) ) THEN
- INFO = -1
- ELSE IF( ( .NOT.WANTST ) .AND. ( .NOT.LSAME( SORT, 'N' ) ) ) THEN
- INFO = -2
- ELSE IF( N.LT.0 ) THEN
- INFO = -4
- ELSE IF( LDA.LT.MAX( 1, N ) ) THEN
- INFO = -6
- ELSE IF( LDVS.LT.1 .OR. ( WANTVS .AND. LDVS.LT.N ) ) THEN
- INFO = -10
- END IF
-*
-* Compute workspace
-* (Note: Comments in the code beginning "Workspace:" describe the
-* minimal amount of workspace needed at that point in the code,
-* as well as the preferred amount for good performance.
-* CWorkspace refers to complex workspace, and RWorkspace to real
-* workspace. NB refers to the optimal block size for the
-* immediately following subroutine, as returned by ILAENV.
-* HSWORK refers to the workspace preferred by ZHSEQR, as
-* calculated below. HSWORK is computed assuming ILO=1 and IHI=N,
-* the worst case.)
-*
- IF( INFO.EQ.0 ) THEN
- IF( N.EQ.0 ) THEN
- MINWRK = 1
- MAXWRK = 1
- ELSE
- MAXWRK = N + N*ILAENV( 1, 'ZGEHRD', ' ', N, 1, N, 0 )
- MINWRK = 2*N
-*
- CALL ZHSEQR( 'S', JOBVS, N, 1, N, A, LDA, W, VS, LDVS,
- $ WORK, -1, IEVAL )
- HSWORK = WORK( 1 )
-*
- IF( .NOT.WANTVS ) THEN
- MAXWRK = MAX( MAXWRK, HSWORK )
- ELSE
- MAXWRK = MAX( MAXWRK, N + ( N - 1 )*ILAENV( 1, 'ZUNGHR',
- $ ' ', N, 1, N, -1 ) )
- MAXWRK = MAX( MAXWRK, HSWORK )
- END IF
- END IF
- WORK( 1 ) = MAXWRK
-*
- IF( LWORK.LT.MINWRK .AND. .NOT.LQUERY ) THEN
- INFO = -12
- END IF
- END IF
-*
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'ZGEES ', -INFO )
- RETURN
- ELSE IF( LQUERY ) THEN
- RETURN
- END IF
-*
-* Quick return if possible
-*
- IF( N.EQ.0 ) THEN
- SDIM = 0
- RETURN
- END IF
-*
-* Get machine constants
-*
- EPS = DLAMCH( 'P' )
- SMLNUM = DLAMCH( 'S' )
- BIGNUM = ONE / SMLNUM
- CALL DLABAD( SMLNUM, BIGNUM )
- SMLNUM = SQRT( SMLNUM ) / EPS
- BIGNUM = ONE / SMLNUM
-*
-* Scale A if max element outside range [SMLNUM,BIGNUM]
-*
- ANRM = ZLANGE( 'M', N, N, A, LDA, DUM )
- SCALEA = .FALSE.
- IF( ANRM.GT.ZERO .AND. ANRM.LT.SMLNUM ) THEN
- SCALEA = .TRUE.
- CSCALE = SMLNUM
- ELSE IF( ANRM.GT.BIGNUM ) THEN
- SCALEA = .TRUE.
- CSCALE = BIGNUM
- END IF
- IF( SCALEA )
- $ CALL ZLASCL( 'G', 0, 0, ANRM, CSCALE, N, N, A, LDA, IERR )
-*
-* Permute the matrix to make it more nearly triangular
-* (CWorkspace: none)
-* (RWorkspace: need N)
-*
- IBAL = 1
- CALL ZGEBAL( 'P', N, A, LDA, ILO, IHI, RWORK( IBAL ), IERR )
-*
-* Reduce to upper Hessenberg form
-* (CWorkspace: need 2*N, prefer N+N*NB)
-* (RWorkspace: none)
-*
- ITAU = 1
- IWRK = N + ITAU
- CALL ZGEHRD( N, ILO, IHI, A, LDA, WORK( ITAU ), WORK( IWRK ),
- $ LWORK-IWRK+1, IERR )
-*
- IF( WANTVS ) THEN
-*
-* Copy Householder vectors to VS
-*
- CALL ZLACPY( 'L', N, N, A, LDA, VS, LDVS )
-*
-* Generate unitary matrix in VS
-* (CWorkspace: need 2*N-1, prefer N+(N-1)*NB)
-* (RWorkspace: none)
-*
- CALL ZUNGHR( N, ILO, IHI, VS, LDVS, WORK( ITAU ), WORK( IWRK ),
- $ LWORK-IWRK+1, IERR )
- END IF
-*
- SDIM = 0
-*
-* Perform QR iteration, accumulating Schur vectors in VS if desired
-* (CWorkspace: need 1, prefer HSWORK (see comments) )
-* (RWorkspace: none)
-*
- IWRK = ITAU
- CALL ZHSEQR( 'S', JOBVS, N, ILO, IHI, A, LDA, W, VS, LDVS,
- $ WORK( IWRK ), LWORK-IWRK+1, IEVAL )
- IF( IEVAL.GT.0 )
- $ INFO = IEVAL
-*
-* Sort eigenvalues if desired
-*
- IF( WANTST .AND. INFO.EQ.0 ) THEN
- IF( SCALEA )
- $ CALL ZLASCL( 'G', 0, 0, CSCALE, ANRM, N, 1, W, N, IERR )
- DO 10 I = 1, N
- BWORK( I ) = SELECT( W( I ) )
- 10 CONTINUE
-*
-* Reorder eigenvalues and transform Schur vectors
-* (CWorkspace: none)
-* (RWorkspace: none)
-*
- CALL ZTRSEN( 'N', JOBVS, BWORK, N, A, LDA, VS, LDVS, W, SDIM,
- $ S, SEP, WORK( IWRK ), LWORK-IWRK+1, ICOND )
- END IF
-*
- IF( WANTVS ) THEN
-*
-* Undo balancing
-* (CWorkspace: none)
-* (RWorkspace: need N)
-*
- CALL ZGEBAK( 'P', 'R', N, ILO, IHI, RWORK( IBAL ), N, VS, LDVS,
- $ IERR )
- END IF
-*
- IF( SCALEA ) THEN
-*
-* Undo scaling for the Schur form of A
-*
- CALL ZLASCL( 'U', 0, 0, CSCALE, ANRM, N, N, A, LDA, IERR )
- CALL ZCOPY( N, A, LDA+1, W, 1 )
- END IF
-*
- WORK( 1 ) = MAXWRK
- RETURN
-*
-* End of ZGEES
-*
- END
diff --git a/src/lib/lapack/zgeev.f b/src/lib/lapack/zgeev.f
deleted file mode 100644
index 0fa66307..00000000
--- a/src/lib/lapack/zgeev.f
+++ /dev/null
@@ -1,396 +0,0 @@
- SUBROUTINE ZGEEV( JOBVL, JOBVR, N, A, LDA, W, VL, LDVL, VR, LDVR,
- $ WORK, LWORK, RWORK, INFO )
-*
-* -- LAPACK driver routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- CHARACTER JOBVL, JOBVR
- INTEGER INFO, LDA, LDVL, LDVR, LWORK, N
-* ..
-* .. Array Arguments ..
- DOUBLE PRECISION RWORK( * )
- COMPLEX*16 A( LDA, * ), VL( LDVL, * ), VR( LDVR, * ),
- $ W( * ), WORK( * )
-* ..
-*
-* Purpose
-* =======
-*
-* ZGEEV computes for an N-by-N complex nonsymmetric matrix A, the
-* eigenvalues and, optionally, the left and/or right eigenvectors.
-*
-* The right eigenvector v(j) of A satisfies
-* A * v(j) = lambda(j) * v(j)
-* where lambda(j) is its eigenvalue.
-* The left eigenvector u(j) of A satisfies
-* u(j)**H * A = lambda(j) * u(j)**H
-* where u(j)**H denotes the conjugate transpose of u(j).
-*
-* The computed eigenvectors are normalized to have Euclidean norm
-* equal to 1 and largest component real.
-*
-* Arguments
-* =========
-*
-* JOBVL (input) CHARACTER*1
-* = 'N': left eigenvectors of A are not computed;
-* = 'V': left eigenvectors of are computed.
-*
-* JOBVR (input) CHARACTER*1
-* = 'N': right eigenvectors of A are not computed;
-* = 'V': right eigenvectors of A are computed.
-*
-* N (input) INTEGER
-* The order of the matrix A. N >= 0.
-*
-* A (input/output) COMPLEX*16 array, dimension (LDA,N)
-* On entry, the N-by-N matrix A.
-* On exit, A has been overwritten.
-*
-* LDA (input) INTEGER
-* The leading dimension of the array A. LDA >= max(1,N).
-*
-* W (output) COMPLEX*16 array, dimension (N)
-* W contains the computed eigenvalues.
-*
-* VL (output) COMPLEX*16 array, dimension (LDVL,N)
-* If JOBVL = 'V', the left eigenvectors u(j) are stored one
-* after another in the columns of VL, in the same order
-* as their eigenvalues.
-* If JOBVL = 'N', VL is not referenced.
-* u(j) = VL(:,j), the j-th column of VL.
-*
-* LDVL (input) INTEGER
-* The leading dimension of the array VL. LDVL >= 1; if
-* JOBVL = 'V', LDVL >= N.
-*
-* VR (output) COMPLEX*16 array, dimension (LDVR,N)
-* If JOBVR = 'V', the right eigenvectors v(j) are stored one
-* after another in the columns of VR, in the same order
-* as their eigenvalues.
-* If JOBVR = 'N', VR is not referenced.
-* v(j) = VR(:,j), the j-th column of VR.
-*
-* LDVR (input) INTEGER
-* The leading dimension of the array VR. LDVR >= 1; if
-* JOBVR = 'V', LDVR >= N.
-*
-* WORK (workspace/output) COMPLEX*16 array, dimension (MAX(1,LWORK))
-* On exit, if INFO = 0, WORK(1) returns the optimal LWORK.
-*
-* LWORK (input) INTEGER
-* The dimension of the array WORK. LWORK >= max(1,2*N).
-* For good performance, LWORK must generally be larger.
-*
-* If LWORK = -1, then a workspace query is assumed; the routine
-* only calculates the optimal size of the WORK array, returns
-* this value as the first entry of the WORK array, and no error
-* message related to LWORK is issued by XERBLA.
-*
-* RWORK (workspace) DOUBLE PRECISION array, dimension (2*N)
-*
-* INFO (output) INTEGER
-* = 0: successful exit
-* < 0: if INFO = -i, the i-th argument had an illegal value.
-* > 0: if INFO = i, the QR algorithm failed to compute all the
-* eigenvalues, and no eigenvectors have been computed;
-* elements and i+1:N of W contain eigenvalues which have
-* converged.
-*
-* =====================================================================
-*
-* .. Parameters ..
- DOUBLE PRECISION ZERO, ONE
- PARAMETER ( ZERO = 0.0D0, ONE = 1.0D0 )
-* ..
-* .. Local Scalars ..
- LOGICAL LQUERY, SCALEA, WANTVL, WANTVR
- CHARACTER SIDE
- INTEGER HSWORK, I, IBAL, IERR, IHI, ILO, IRWORK, ITAU,
- $ IWRK, K, MAXWRK, MINWRK, NOUT
- DOUBLE PRECISION ANRM, BIGNUM, CSCALE, EPS, SCL, SMLNUM
- COMPLEX*16 TMP
-* ..
-* .. Local Arrays ..
- LOGICAL SELECT( 1 )
- DOUBLE PRECISION DUM( 1 )
-* ..
-* .. External Subroutines ..
- EXTERNAL DLABAD, XERBLA, ZDSCAL, ZGEBAK, ZGEBAL, ZGEHRD,
- $ ZHSEQR, ZLACPY, ZLASCL, ZSCAL, ZTREVC, ZUNGHR
-* ..
-* .. External Functions ..
- LOGICAL LSAME
- INTEGER IDAMAX, ILAENV
- DOUBLE PRECISION DLAMCH, DZNRM2, ZLANGE
- EXTERNAL LSAME, IDAMAX, ILAENV, DLAMCH, DZNRM2, ZLANGE
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC DBLE, DCMPLX, DCONJG, DIMAG, MAX, SQRT
-* ..
-* .. Executable Statements ..
-*
-* Test the input arguments
-*
- INFO = 0
- LQUERY = ( LWORK.EQ.-1 )
- WANTVL = LSAME( JOBVL, 'V' )
- WANTVR = LSAME( JOBVR, 'V' )
- IF( ( .NOT.WANTVL ) .AND. ( .NOT.LSAME( JOBVL, 'N' ) ) ) THEN
- INFO = -1
- ELSE IF( ( .NOT.WANTVR ) .AND. ( .NOT.LSAME( JOBVR, 'N' ) ) ) THEN
- INFO = -2
- ELSE IF( N.LT.0 ) THEN
- INFO = -3
- ELSE IF( LDA.LT.MAX( 1, N ) ) THEN
- INFO = -5
- ELSE IF( LDVL.LT.1 .OR. ( WANTVL .AND. LDVL.LT.N ) ) THEN
- INFO = -8
- ELSE IF( LDVR.LT.1 .OR. ( WANTVR .AND. LDVR.LT.N ) ) THEN
- INFO = -10
- END IF
-*
-* Compute workspace
-* (Note: Comments in the code beginning "Workspace:" describe the
-* minimal amount of workspace needed at that point in the code,
-* as well as the preferred amount for good performance.
-* CWorkspace refers to complex workspace, and RWorkspace to real
-* workspace. NB refers to the optimal block size for the
-* immediately following subroutine, as returned by ILAENV.
-* HSWORK refers to the workspace preferred by ZHSEQR, as
-* calculated below. HSWORK is computed assuming ILO=1 and IHI=N,
-* the worst case.)
-*
- IF( INFO.EQ.0 ) THEN
- IF( N.EQ.0 ) THEN
- MINWRK = 1
- MAXWRK = 1
- ELSE
- MAXWRK = N + N*ILAENV( 1, 'ZGEHRD', ' ', N, 1, N, 0 )
- MINWRK = 2*N
- IF( WANTVL ) THEN
- MAXWRK = MAX( MAXWRK, N + ( N - 1 )*ILAENV( 1, 'ZUNGHR',
- $ ' ', N, 1, N, -1 ) )
- CALL ZHSEQR( 'S', 'V', N, 1, N, A, LDA, W, VL, LDVL,
- $ WORK, -1, INFO )
- ELSE IF( WANTVR ) THEN
- MAXWRK = MAX( MAXWRK, N + ( N - 1 )*ILAENV( 1, 'ZUNGHR',
- $ ' ', N, 1, N, -1 ) )
- CALL ZHSEQR( 'S', 'V', N, 1, N, A, LDA, W, VR, LDVR,
- $ WORK, -1, INFO )
- ELSE
- CALL ZHSEQR( 'E', 'N', N, 1, N, A, LDA, W, VR, LDVR,
- $ WORK, -1, INFO )
- END IF
- HSWORK = WORK( 1 )
- MAXWRK = MAX( MAXWRK, HSWORK, MINWRK )
- END IF
- WORK( 1 ) = MAXWRK
-*
- IF( LWORK.LT.MINWRK .AND. .NOT.LQUERY ) THEN
- INFO = -12
- END IF
- END IF
-*
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'ZGEEV ', -INFO )
- RETURN
- ELSE IF( LQUERY ) THEN
- RETURN
- END IF
-*
-* Quick return if possible
-*
- IF( N.EQ.0 )
- $ RETURN
-*
-* Get machine constants
-*
- EPS = DLAMCH( 'P' )
- SMLNUM = DLAMCH( 'S' )
- BIGNUM = ONE / SMLNUM
- CALL DLABAD( SMLNUM, BIGNUM )
- SMLNUM = SQRT( SMLNUM ) / EPS
- BIGNUM = ONE / SMLNUM
-*
-* Scale A if max element outside range [SMLNUM,BIGNUM]
-*
- ANRM = ZLANGE( 'M', N, N, A, LDA, DUM )
- SCALEA = .FALSE.
- IF( ANRM.GT.ZERO .AND. ANRM.LT.SMLNUM ) THEN
- SCALEA = .TRUE.
- CSCALE = SMLNUM
- ELSE IF( ANRM.GT.BIGNUM ) THEN
- SCALEA = .TRUE.
- CSCALE = BIGNUM
- END IF
- IF( SCALEA )
- $ CALL ZLASCL( 'G', 0, 0, ANRM, CSCALE, N, N, A, LDA, IERR )
-*
-* Balance the matrix
-* (CWorkspace: none)
-* (RWorkspace: need N)
-*
- IBAL = 1
- CALL ZGEBAL( 'B', N, A, LDA, ILO, IHI, RWORK( IBAL ), IERR )
-*
-* Reduce to upper Hessenberg form
-* (CWorkspace: need 2*N, prefer N+N*NB)
-* (RWorkspace: none)
-*
- ITAU = 1
- IWRK = ITAU + N
- CALL ZGEHRD( N, ILO, IHI, A, LDA, WORK( ITAU ), WORK( IWRK ),
- $ LWORK-IWRK+1, IERR )
-*
- IF( WANTVL ) THEN
-*
-* Want left eigenvectors
-* Copy Householder vectors to VL
-*
- SIDE = 'L'
- CALL ZLACPY( 'L', N, N, A, LDA, VL, LDVL )
-*
-* Generate unitary matrix in VL
-* (CWorkspace: need 2*N-1, prefer N+(N-1)*NB)
-* (RWorkspace: none)
-*
- CALL ZUNGHR( N, ILO, IHI, VL, LDVL, WORK( ITAU ), WORK( IWRK ),
- $ LWORK-IWRK+1, IERR )
-*
-* Perform QR iteration, accumulating Schur vectors in VL
-* (CWorkspace: need 1, prefer HSWORK (see comments) )
-* (RWorkspace: none)
-*
- IWRK = ITAU
- CALL ZHSEQR( 'S', 'V', N, ILO, IHI, A, LDA, W, VL, LDVL,
- $ WORK( IWRK ), LWORK-IWRK+1, INFO )
-*
- IF( WANTVR ) THEN
-*
-* Want left and right eigenvectors
-* Copy Schur vectors to VR
-*
- SIDE = 'B'
- CALL ZLACPY( 'F', N, N, VL, LDVL, VR, LDVR )
- END IF
-*
- ELSE IF( WANTVR ) THEN
-*
-* Want right eigenvectors
-* Copy Householder vectors to VR
-*
- SIDE = 'R'
- CALL ZLACPY( 'L', N, N, A, LDA, VR, LDVR )
-*
-* Generate unitary matrix in VR
-* (CWorkspace: need 2*N-1, prefer N+(N-1)*NB)
-* (RWorkspace: none)
-*
- CALL ZUNGHR( N, ILO, IHI, VR, LDVR, WORK( ITAU ), WORK( IWRK ),
- $ LWORK-IWRK+1, IERR )
-*
-* Perform QR iteration, accumulating Schur vectors in VR
-* (CWorkspace: need 1, prefer HSWORK (see comments) )
-* (RWorkspace: none)
-*
- IWRK = ITAU
- CALL ZHSEQR( 'S', 'V', N, ILO, IHI, A, LDA, W, VR, LDVR,
- $ WORK( IWRK ), LWORK-IWRK+1, INFO )
-*
- ELSE
-*
-* Compute eigenvalues only
-* (CWorkspace: need 1, prefer HSWORK (see comments) )
-* (RWorkspace: none)
-*
- IWRK = ITAU
- CALL ZHSEQR( 'E', 'N', N, ILO, IHI, A, LDA, W, VR, LDVR,
- $ WORK( IWRK ), LWORK-IWRK+1, INFO )
- END IF
-*
-* If INFO > 0 from ZHSEQR, then quit
-*
- IF( INFO.GT.0 )
- $ GO TO 50
-*
- IF( WANTVL .OR. WANTVR ) THEN
-*
-* Compute left and/or right eigenvectors
-* (CWorkspace: need 2*N)
-* (RWorkspace: need 2*N)
-*
- IRWORK = IBAL + N
- CALL ZTREVC( SIDE, 'B', SELECT, N, A, LDA, VL, LDVL, VR, LDVR,
- $ N, NOUT, WORK( IWRK ), RWORK( IRWORK ), IERR )
- END IF
-*
- IF( WANTVL ) THEN
-*
-* Undo balancing of left eigenvectors
-* (CWorkspace: none)
-* (RWorkspace: need N)
-*
- CALL ZGEBAK( 'B', 'L', N, ILO, IHI, RWORK( IBAL ), N, VL, LDVL,
- $ IERR )
-*
-* Normalize left eigenvectors and make largest component real
-*
- DO 20 I = 1, N
- SCL = ONE / DZNRM2( N, VL( 1, I ), 1 )
- CALL ZDSCAL( N, SCL, VL( 1, I ), 1 )
- DO 10 K = 1, N
- RWORK( IRWORK+K-1 ) = DBLE( VL( K, I ) )**2 +
- $ DIMAG( VL( K, I ) )**2
- 10 CONTINUE
- K = IDAMAX( N, RWORK( IRWORK ), 1 )
- TMP = DCONJG( VL( K, I ) ) / SQRT( RWORK( IRWORK+K-1 ) )
- CALL ZSCAL( N, TMP, VL( 1, I ), 1 )
- VL( K, I ) = DCMPLX( DBLE( VL( K, I ) ), ZERO )
- 20 CONTINUE
- END IF
-*
- IF( WANTVR ) THEN
-*
-* Undo balancing of right eigenvectors
-* (CWorkspace: none)
-* (RWorkspace: need N)
-*
- CALL ZGEBAK( 'B', 'R', N, ILO, IHI, RWORK( IBAL ), N, VR, LDVR,
- $ IERR )
-*
-* Normalize right eigenvectors and make largest component real
-*
- DO 40 I = 1, N
- SCL = ONE / DZNRM2( N, VR( 1, I ), 1 )
- CALL ZDSCAL( N, SCL, VR( 1, I ), 1 )
- DO 30 K = 1, N
- RWORK( IRWORK+K-1 ) = DBLE( VR( K, I ) )**2 +
- $ DIMAG( VR( K, I ) )**2
- 30 CONTINUE
- K = IDAMAX( N, RWORK( IRWORK ), 1 )
- TMP = DCONJG( VR( K, I ) ) / SQRT( RWORK( IRWORK+K-1 ) )
- CALL ZSCAL( N, TMP, VR( 1, I ), 1 )
- VR( K, I ) = DCMPLX( DBLE( VR( K, I ) ), ZERO )
- 40 CONTINUE
- END IF
-*
-* Undo scaling if necessary
-*
- 50 CONTINUE
- IF( SCALEA ) THEN
- CALL ZLASCL( 'G', 0, 0, CSCALE, ANRM, N-INFO, 1, W( INFO+1 ),
- $ MAX( N-INFO, 1 ), IERR )
- IF( INFO.GT.0 ) THEN
- CALL ZLASCL( 'G', 0, 0, CSCALE, ANRM, ILO-1, 1, W, N, IERR )
- END IF
- END IF
-*
- WORK( 1 ) = MAXWRK
- RETURN
-*
-* End of ZGEEV
-*
- END
diff --git a/src/lib/lapack/zgehd2.f b/src/lib/lapack/zgehd2.f
deleted file mode 100644
index c73f4200..00000000
--- a/src/lib/lapack/zgehd2.f
+++ /dev/null
@@ -1,148 +0,0 @@
- SUBROUTINE ZGEHD2( N, ILO, IHI, A, LDA, TAU, WORK, INFO )
-*
-* -- LAPACK routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- INTEGER IHI, ILO, INFO, LDA, N
-* ..
-* .. Array Arguments ..
- COMPLEX*16 A( LDA, * ), TAU( * ), WORK( * )
-* ..
-*
-* Purpose
-* =======
-*
-* ZGEHD2 reduces a complex general matrix A to upper Hessenberg form H
-* by a unitary similarity transformation: Q' * A * Q = H .
-*
-* Arguments
-* =========
-*
-* N (input) INTEGER
-* The order of the matrix A. N >= 0.
-*
-* ILO (input) INTEGER
-* IHI (input) INTEGER
-* It is assumed that A is already upper triangular in rows
-* and columns 1:ILO-1 and IHI+1:N. ILO and IHI are normally
-* set by a previous call to ZGEBAL; otherwise they should be
-* set to 1 and N respectively. See Further Details.
-* 1 <= ILO <= IHI <= max(1,N).
-*
-* A (input/output) COMPLEX*16 array, dimension (LDA,N)
-* On entry, the n by n general matrix to be reduced.
-* On exit, the upper triangle and the first subdiagonal of A
-* are overwritten with the upper Hessenberg matrix H, and the
-* elements below the first subdiagonal, with the array TAU,
-* represent the unitary matrix Q as a product of elementary
-* reflectors. See Further Details.
-*
-* LDA (input) INTEGER
-* The leading dimension of the array A. LDA >= max(1,N).
-*
-* TAU (output) COMPLEX*16 array, dimension (N-1)
-* The scalar factors of the elementary reflectors (see Further
-* Details).
-*
-* WORK (workspace) COMPLEX*16 array, dimension (N)
-*
-* INFO (output) INTEGER
-* = 0: successful exit
-* < 0: if INFO = -i, the i-th argument had an illegal value.
-*
-* Further Details
-* ===============
-*
-* The matrix Q is represented as a product of (ihi-ilo) elementary
-* reflectors
-*
-* Q = H(ilo) H(ilo+1) . . . H(ihi-1).
-*
-* Each H(i) has the form
-*
-* H(i) = I - tau * v * v'
-*
-* where tau is a complex scalar, and v is a complex vector with
-* v(1:i) = 0, v(i+1) = 1 and v(ihi+1:n) = 0; v(i+2:ihi) is stored on
-* exit in A(i+2:ihi,i), and tau in TAU(i).
-*
-* The contents of A are illustrated by the following example, with
-* n = 7, ilo = 2 and ihi = 6:
-*
-* on entry, on exit,
-*
-* ( a a a a a a a ) ( a a h h h h a )
-* ( a a a a a a ) ( a h h h h a )
-* ( a a a a a a ) ( h h h h h h )
-* ( a a a a a a ) ( v2 h h h h h )
-* ( a a a a a a ) ( v2 v3 h h h h )
-* ( a a a a a a ) ( v2 v3 v4 h h h )
-* ( a ) ( a )
-*
-* where a denotes an element of the original matrix A, h denotes a
-* modified element of the upper Hessenberg matrix H, and vi denotes an
-* element of the vector defining H(i).
-*
-* =====================================================================
-*
-* .. Parameters ..
- COMPLEX*16 ONE
- PARAMETER ( ONE = ( 1.0D+0, 0.0D+0 ) )
-* ..
-* .. Local Scalars ..
- INTEGER I
- COMPLEX*16 ALPHA
-* ..
-* .. External Subroutines ..
- EXTERNAL XERBLA, ZLARF, ZLARFG
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC DCONJG, MAX, MIN
-* ..
-* .. Executable Statements ..
-*
-* Test the input parameters
-*
- INFO = 0
- IF( N.LT.0 ) THEN
- INFO = -1
- ELSE IF( ILO.LT.1 .OR. ILO.GT.MAX( 1, N ) ) THEN
- INFO = -2
- ELSE IF( IHI.LT.MIN( ILO, N ) .OR. IHI.GT.N ) THEN
- INFO = -3
- ELSE IF( LDA.LT.MAX( 1, N ) ) THEN
- INFO = -5
- END IF
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'ZGEHD2', -INFO )
- RETURN
- END IF
-*
- DO 10 I = ILO, IHI - 1
-*
-* Compute elementary reflector H(i) to annihilate A(i+2:ihi,i)
-*
- ALPHA = A( I+1, I )
- CALL ZLARFG( IHI-I, ALPHA, A( MIN( I+2, N ), I ), 1, TAU( I ) )
- A( I+1, I ) = ONE
-*
-* Apply H(i) to A(1:ihi,i+1:ihi) from the right
-*
- CALL ZLARF( 'Right', IHI, IHI-I, A( I+1, I ), 1, TAU( I ),
- $ A( 1, I+1 ), LDA, WORK )
-*
-* Apply H(i)' to A(i+1:ihi,i+1:n) from the left
-*
- CALL ZLARF( 'Left', IHI-I, N-I, A( I+1, I ), 1,
- $ DCONJG( TAU( I ) ), A( I+1, I+1 ), LDA, WORK )
-*
- A( I+1, I ) = ALPHA
- 10 CONTINUE
-*
- RETURN
-*
-* End of ZGEHD2
-*
- END
diff --git a/src/lib/lapack/zgehrd.f b/src/lib/lapack/zgehrd.f
deleted file mode 100644
index 83c1aa32..00000000
--- a/src/lib/lapack/zgehrd.f
+++ /dev/null
@@ -1,273 +0,0 @@
- SUBROUTINE ZGEHRD( N, ILO, IHI, A, LDA, TAU, WORK, LWORK, INFO )
-*
-* -- LAPACK routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- INTEGER IHI, ILO, INFO, LDA, LWORK, N
-* ..
-* .. Array Arguments ..
- COMPLEX*16 A( LDA, * ), TAU( * ), WORK( * )
-* ..
-*
-* Purpose
-* =======
-*
-* ZGEHRD reduces a complex general matrix A to upper Hessenberg form H by
-* an unitary similarity transformation: Q' * A * Q = H .
-*
-* Arguments
-* =========
-*
-* N (input) INTEGER
-* The order of the matrix A. N >= 0.
-*
-* ILO (input) INTEGER
-* IHI (input) INTEGER
-* It is assumed that A is already upper triangular in rows
-* and columns 1:ILO-1 and IHI+1:N. ILO and IHI are normally
-* set by a previous call to ZGEBAL; otherwise they should be
-* set to 1 and N respectively. See Further Details.
-* 1 <= ILO <= IHI <= N, if N > 0; ILO=1 and IHI=0, if N=0.
-*
-* A (input/output) COMPLEX*16 array, dimension (LDA,N)
-* On entry, the N-by-N general matrix to be reduced.
-* On exit, the upper triangle and the first subdiagonal of A
-* are overwritten with the upper Hessenberg matrix H, and the
-* elements below the first subdiagonal, with the array TAU,
-* represent the unitary matrix Q as a product of elementary
-* reflectors. See Further Details.
-*
-* LDA (input) INTEGER
-* The leading dimension of the array A. LDA >= max(1,N).
-*
-* TAU (output) COMPLEX*16 array, dimension (N-1)
-* The scalar factors of the elementary reflectors (see Further
-* Details). Elements 1:ILO-1 and IHI:N-1 of TAU are set to
-* zero.
-*
-* WORK (workspace/output) COMPLEX*16 array, dimension (LWORK)
-* On exit, if INFO = 0, WORK(1) returns the optimal LWORK.
-*
-* LWORK (input) INTEGER
-* The length of the array WORK. LWORK >= max(1,N).
-* For optimum performance LWORK >= N*NB, where NB is the
-* optimal blocksize.
-*
-* If LWORK = -1, then a workspace query is assumed; the routine
-* only calculates the optimal size of the WORK array, returns
-* this value as the first entry of the WORK array, and no error
-* message related to LWORK is issued by XERBLA.
-*
-* INFO (output) INTEGER
-* = 0: successful exit
-* < 0: if INFO = -i, the i-th argument had an illegal value.
-*
-* Further Details
-* ===============
-*
-* The matrix Q is represented as a product of (ihi-ilo) elementary
-* reflectors
-*
-* Q = H(ilo) H(ilo+1) . . . H(ihi-1).
-*
-* Each H(i) has the form
-*
-* H(i) = I - tau * v * v'
-*
-* where tau is a complex scalar, and v is a complex vector with
-* v(1:i) = 0, v(i+1) = 1 and v(ihi+1:n) = 0; v(i+2:ihi) is stored on
-* exit in A(i+2:ihi,i), and tau in TAU(i).
-*
-* The contents of A are illustrated by the following example, with
-* n = 7, ilo = 2 and ihi = 6:
-*
-* on entry, on exit,
-*
-* ( a a a a a a a ) ( a a h h h h a )
-* ( a a a a a a ) ( a h h h h a )
-* ( a a a a a a ) ( h h h h h h )
-* ( a a a a a a ) ( v2 h h h h h )
-* ( a a a a a a ) ( v2 v3 h h h h )
-* ( a a a a a a ) ( v2 v3 v4 h h h )
-* ( a ) ( a )
-*
-* where a denotes an element of the original matrix A, h denotes a
-* modified element of the upper Hessenberg matrix H, and vi denotes an
-* element of the vector defining H(i).
-*
-* This file is a slight modification of LAPACK-3.0's ZGEHRD
-* subroutine incorporating improvements proposed by Quintana-Orti and
-* Van de Geijn (2005).
-*
-* =====================================================================
-*
-* .. Parameters ..
- INTEGER NBMAX, LDT
- PARAMETER ( NBMAX = 64, LDT = NBMAX+1 )
- COMPLEX*16 ZERO, ONE
- PARAMETER ( ZERO = ( 0.0D+0, 0.0D+0 ),
- $ ONE = ( 1.0D+0, 0.0D+0 ) )
-* ..
-* .. Local Scalars ..
- LOGICAL LQUERY
- INTEGER I, IB, IINFO, IWS, J, LDWORK, LWKOPT, NB,
- $ NBMIN, NH, NX
- COMPLEX*16 EI
-* ..
-* .. Local Arrays ..
- COMPLEX*16 T( LDT, NBMAX )
-* ..
-* .. External Subroutines ..
- EXTERNAL ZAXPY, ZGEHD2, ZGEMM, ZLAHR2, ZLARFB, ZTRMM,
- $ XERBLA
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC MAX, MIN
-* ..
-* .. External Functions ..
- INTEGER ILAENV
- EXTERNAL ILAENV
-* ..
-* .. Executable Statements ..
-*
-* Test the input parameters
-*
- INFO = 0
- NB = MIN( NBMAX, ILAENV( 1, 'ZGEHRD', ' ', N, ILO, IHI, -1 ) )
- LWKOPT = N*NB
- WORK( 1 ) = LWKOPT
- LQUERY = ( LWORK.EQ.-1 )
- IF( N.LT.0 ) THEN
- INFO = -1
- ELSE IF( ILO.LT.1 .OR. ILO.GT.MAX( 1, N ) ) THEN
- INFO = -2
- ELSE IF( IHI.LT.MIN( ILO, N ) .OR. IHI.GT.N ) THEN
- INFO = -3
- ELSE IF( LDA.LT.MAX( 1, N ) ) THEN
- INFO = -5
- ELSE IF( LWORK.LT.MAX( 1, N ) .AND. .NOT.LQUERY ) THEN
- INFO = -8
- END IF
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'ZGEHRD', -INFO )
- RETURN
- ELSE IF( LQUERY ) THEN
- RETURN
- END IF
-*
-* Set elements 1:ILO-1 and IHI:N-1 of TAU to zero
-*
- DO 10 I = 1, ILO - 1
- TAU( I ) = ZERO
- 10 CONTINUE
- DO 20 I = MAX( 1, IHI ), N - 1
- TAU( I ) = ZERO
- 20 CONTINUE
-*
-* Quick return if possible
-*
- NH = IHI - ILO + 1
- IF( NH.LE.1 ) THEN
- WORK( 1 ) = 1
- RETURN
- END IF
-*
-* Determine the block size
-*
- NB = MIN( NBMAX, ILAENV( 1, 'ZGEHRD', ' ', N, ILO, IHI, -1 ) )
- NBMIN = 2
- IWS = 1
- IF( NB.GT.1 .AND. NB.LT.NH ) THEN
-*
-* Determine when to cross over from blocked to unblocked code
-* (last block is always handled by unblocked code)
-*
- NX = MAX( NB, ILAENV( 3, 'ZGEHRD', ' ', N, ILO, IHI, -1 ) )
- IF( NX.LT.NH ) THEN
-*
-* Determine if workspace is large enough for blocked code
-*
- IWS = N*NB
- IF( LWORK.LT.IWS ) THEN
-*
-* Not enough workspace to use optimal NB: determine the
-* minimum value of NB, and reduce NB or force use of
-* unblocked code
-*
- NBMIN = MAX( 2, ILAENV( 2, 'ZGEHRD', ' ', N, ILO, IHI,
- $ -1 ) )
- IF( LWORK.GE.N*NBMIN ) THEN
- NB = LWORK / N
- ELSE
- NB = 1
- END IF
- END IF
- END IF
- END IF
- LDWORK = N
-*
- IF( NB.LT.NBMIN .OR. NB.GE.NH ) THEN
-*
-* Use unblocked code below
-*
- I = ILO
-*
- ELSE
-*
-* Use blocked code
-*
- DO 40 I = ILO, IHI - 1 - NX, NB
- IB = MIN( NB, IHI-I )
-*
-* Reduce columns i:i+ib-1 to Hessenberg form, returning the
-* matrices V and T of the block reflector H = I - V*T*V'
-* which performs the reduction, and also the matrix Y = A*V*T
-*
- CALL ZLAHR2( IHI, I, IB, A( 1, I ), LDA, TAU( I ), T, LDT,
- $ WORK, LDWORK )
-*
-* Apply the block reflector H to A(1:ihi,i+ib:ihi) from the
-* right, computing A := A - Y * V'. V(i+ib,ib-1) must be set
-* to 1
-*
- EI = A( I+IB, I+IB-1 )
- A( I+IB, I+IB-1 ) = ONE
- CALL ZGEMM( 'No transpose', 'Conjugate transpose',
- $ IHI, IHI-I-IB+1,
- $ IB, -ONE, WORK, LDWORK, A( I+IB, I ), LDA, ONE,
- $ A( 1, I+IB ), LDA )
- A( I+IB, I+IB-1 ) = EI
-*
-* Apply the block reflector H to A(1:i,i+1:i+ib-1) from the
-* right
-*
- CALL ZTRMM( 'Right', 'Lower', 'Conjugate transpose',
- $ 'Unit', I, IB-1,
- $ ONE, A( I+1, I ), LDA, WORK, LDWORK )
- DO 30 J = 0, IB-2
- CALL ZAXPY( I, -ONE, WORK( LDWORK*J+1 ), 1,
- $ A( 1, I+J+1 ), 1 )
- 30 CONTINUE
-*
-* Apply the block reflector H to A(i+1:ihi,i+ib:n) from the
-* left
-*
- CALL ZLARFB( 'Left', 'Conjugate transpose', 'Forward',
- $ 'Columnwise',
- $ IHI-I, N-I-IB+1, IB, A( I+1, I ), LDA, T, LDT,
- $ A( I+1, I+IB ), LDA, WORK, LDWORK )
- 40 CONTINUE
- END IF
-*
-* Use unblocked code to reduce the rest of the matrix
-*
- CALL ZGEHD2( N, I, IHI, A, LDA, TAU, WORK, IINFO )
- WORK( 1 ) = IWS
-*
- RETURN
-*
-* End of ZGEHRD
-*
- END
diff --git a/src/lib/lapack/zgelq2.f b/src/lib/lapack/zgelq2.f
deleted file mode 100644
index dc387af0..00000000
--- a/src/lib/lapack/zgelq2.f
+++ /dev/null
@@ -1,123 +0,0 @@
- SUBROUTINE ZGELQ2( M, N, A, LDA, TAU, WORK, INFO )
-*
-* -- LAPACK routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- INTEGER INFO, LDA, M, N
-* ..
-* .. Array Arguments ..
- COMPLEX*16 A( LDA, * ), TAU( * ), WORK( * )
-* ..
-*
-* Purpose
-* =======
-*
-* ZGELQ2 computes an LQ factorization of a complex m by n matrix A:
-* A = L * Q.
-*
-* Arguments
-* =========
-*
-* M (input) INTEGER
-* The number of rows of the matrix A. M >= 0.
-*
-* N (input) INTEGER
-* The number of columns of the matrix A. N >= 0.
-*
-* A (input/output) COMPLEX*16 array, dimension (LDA,N)
-* On entry, the m by n matrix A.
-* On exit, the elements on and below the diagonal of the array
-* contain the m by min(m,n) lower trapezoidal matrix L (L is
-* lower triangular if m <= n); the elements above the diagonal,
-* with the array TAU, represent the unitary matrix Q as a
-* product of elementary reflectors (see Further Details).
-*
-* LDA (input) INTEGER
-* The leading dimension of the array A. LDA >= max(1,M).
-*
-* TAU (output) COMPLEX*16 array, dimension (min(M,N))
-* The scalar factors of the elementary reflectors (see Further
-* Details).
-*
-* WORK (workspace) COMPLEX*16 array, dimension (M)
-*
-* INFO (output) INTEGER
-* = 0: successful exit
-* < 0: if INFO = -i, the i-th argument had an illegal value
-*
-* Further Details
-* ===============
-*
-* The matrix Q is represented as a product of elementary reflectors
-*
-* Q = H(k)' . . . H(2)' H(1)', where k = min(m,n).
-*
-* Each H(i) has the form
-*
-* H(i) = I - tau * v * v'
-*
-* where tau is a complex scalar, and v is a complex vector with
-* v(1:i-1) = 0 and v(i) = 1; conjg(v(i+1:n)) is stored on exit in
-* A(i,i+1:n), and tau in TAU(i).
-*
-* =====================================================================
-*
-* .. Parameters ..
- COMPLEX*16 ONE
- PARAMETER ( ONE = ( 1.0D+0, 0.0D+0 ) )
-* ..
-* .. Local Scalars ..
- INTEGER I, K
- COMPLEX*16 ALPHA
-* ..
-* .. External Subroutines ..
- EXTERNAL XERBLA, ZLACGV, ZLARF, ZLARFG
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC MAX, MIN
-* ..
-* .. Executable Statements ..
-*
-* Test the input arguments
-*
- INFO = 0
- IF( M.LT.0 ) THEN
- INFO = -1
- ELSE IF( N.LT.0 ) THEN
- INFO = -2
- ELSE IF( LDA.LT.MAX( 1, M ) ) THEN
- INFO = -4
- END IF
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'ZGELQ2', -INFO )
- RETURN
- END IF
-*
- K = MIN( M, N )
-*
- DO 10 I = 1, K
-*
-* Generate elementary reflector H(i) to annihilate A(i,i+1:n)
-*
- CALL ZLACGV( N-I+1, A( I, I ), LDA )
- ALPHA = A( I, I )
- CALL ZLARFG( N-I+1, ALPHA, A( I, MIN( I+1, N ) ), LDA,
- $ TAU( I ) )
- IF( I.LT.M ) THEN
-*
-* Apply H(i) to A(i+1:m,i:n) from the right
-*
- A( I, I ) = ONE
- CALL ZLARF( 'Right', M-I, N-I+1, A( I, I ), LDA, TAU( I ),
- $ A( I+1, I ), LDA, WORK )
- END IF
- A( I, I ) = ALPHA
- CALL ZLACGV( N-I+1, A( I, I ), LDA )
- 10 CONTINUE
- RETURN
-*
-* End of ZGELQ2
-*
- END
diff --git a/src/lib/lapack/zgelqf.f b/src/lib/lapack/zgelqf.f
deleted file mode 100644
index 5dac50dc..00000000
--- a/src/lib/lapack/zgelqf.f
+++ /dev/null
@@ -1,195 +0,0 @@
- SUBROUTINE ZGELQF( M, N, A, LDA, TAU, WORK, LWORK, INFO )
-*
-* -- LAPACK routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- INTEGER INFO, LDA, LWORK, M, N
-* ..
-* .. Array Arguments ..
- COMPLEX*16 A( LDA, * ), TAU( * ), WORK( * )
-* ..
-*
-* Purpose
-* =======
-*
-* ZGELQF computes an LQ factorization of a complex M-by-N matrix A:
-* A = L * Q.
-*
-* Arguments
-* =========
-*
-* M (input) INTEGER
-* The number of rows of the matrix A. M >= 0.
-*
-* N (input) INTEGER
-* The number of columns of the matrix A. N >= 0.
-*
-* A (input/output) COMPLEX*16 array, dimension (LDA,N)
-* On entry, the M-by-N matrix A.
-* On exit, the elements on and below the diagonal of the array
-* contain the m-by-min(m,n) lower trapezoidal matrix L (L is
-* lower triangular if m <= n); the elements above the diagonal,
-* with the array TAU, represent the unitary matrix Q as a
-* product of elementary reflectors (see Further Details).
-*
-* LDA (input) INTEGER
-* The leading dimension of the array A. LDA >= max(1,M).
-*
-* TAU (output) COMPLEX*16 array, dimension (min(M,N))
-* The scalar factors of the elementary reflectors (see Further
-* Details).
-*
-* WORK (workspace/output) COMPLEX*16 array, dimension (MAX(1,LWORK))
-* On exit, if INFO = 0, WORK(1) returns the optimal LWORK.
-*
-* LWORK (input) INTEGER
-* The dimension of the array WORK. LWORK >= max(1,M).
-* For optimum performance LWORK >= M*NB, where NB is the
-* optimal blocksize.
-*
-* If LWORK = -1, then a workspace query is assumed; the routine
-* only calculates the optimal size of the WORK array, returns
-* this value as the first entry of the WORK array, and no error
-* message related to LWORK is issued by XERBLA.
-*
-* INFO (output) INTEGER
-* = 0: successful exit
-* < 0: if INFO = -i, the i-th argument had an illegal value
-*
-* Further Details
-* ===============
-*
-* The matrix Q is represented as a product of elementary reflectors
-*
-* Q = H(k)' . . . H(2)' H(1)', where k = min(m,n).
-*
-* Each H(i) has the form
-*
-* H(i) = I - tau * v * v'
-*
-* where tau is a complex scalar, and v is a complex vector with
-* v(1:i-1) = 0 and v(i) = 1; conjg(v(i+1:n)) is stored on exit in
-* A(i,i+1:n), and tau in TAU(i).
-*
-* =====================================================================
-*
-* .. Local Scalars ..
- LOGICAL LQUERY
- INTEGER I, IB, IINFO, IWS, K, LDWORK, LWKOPT, NB,
- $ NBMIN, NX
-* ..
-* .. External Subroutines ..
- EXTERNAL XERBLA, ZGELQ2, ZLARFB, ZLARFT
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC MAX, MIN
-* ..
-* .. External Functions ..
- INTEGER ILAENV
- EXTERNAL ILAENV
-* ..
-* .. Executable Statements ..
-*
-* Test the input arguments
-*
- INFO = 0
- NB = ILAENV( 1, 'ZGELQF', ' ', M, N, -1, -1 )
- LWKOPT = M*NB
- WORK( 1 ) = LWKOPT
- LQUERY = ( LWORK.EQ.-1 )
- IF( M.LT.0 ) THEN
- INFO = -1
- ELSE IF( N.LT.0 ) THEN
- INFO = -2
- ELSE IF( LDA.LT.MAX( 1, M ) ) THEN
- INFO = -4
- ELSE IF( LWORK.LT.MAX( 1, M ) .AND. .NOT.LQUERY ) THEN
- INFO = -7
- END IF
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'ZGELQF', -INFO )
- RETURN
- ELSE IF( LQUERY ) THEN
- RETURN
- END IF
-*
-* Quick return if possible
-*
- K = MIN( M, N )
- IF( K.EQ.0 ) THEN
- WORK( 1 ) = 1
- RETURN
- END IF
-*
- NBMIN = 2
- NX = 0
- IWS = M
- IF( NB.GT.1 .AND. NB.LT.K ) THEN
-*
-* Determine when to cross over from blocked to unblocked code.
-*
- NX = MAX( 0, ILAENV( 3, 'ZGELQF', ' ', M, N, -1, -1 ) )
- IF( NX.LT.K ) THEN
-*
-* Determine if workspace is large enough for blocked code.
-*
- LDWORK = M
- IWS = LDWORK*NB
- IF( LWORK.LT.IWS ) THEN
-*
-* Not enough workspace to use optimal NB: reduce NB and
-* determine the minimum value of NB.
-*
- NB = LWORK / LDWORK
- NBMIN = MAX( 2, ILAENV( 2, 'ZGELQF', ' ', M, N, -1,
- $ -1 ) )
- END IF
- END IF
- END IF
-*
- IF( NB.GE.NBMIN .AND. NB.LT.K .AND. NX.LT.K ) THEN
-*
-* Use blocked code initially
-*
- DO 10 I = 1, K - NX, NB
- IB = MIN( K-I+1, NB )
-*
-* Compute the LQ factorization of the current block
-* A(i:i+ib-1,i:n)
-*
- CALL ZGELQ2( IB, N-I+1, A( I, I ), LDA, TAU( I ), WORK,
- $ IINFO )
- IF( I+IB.LE.M ) THEN
-*
-* Form the triangular factor of the block reflector
-* H = H(i) H(i+1) . . . H(i+ib-1)
-*
- CALL ZLARFT( 'Forward', 'Rowwise', N-I+1, IB, A( I, I ),
- $ LDA, TAU( I ), WORK, LDWORK )
-*
-* Apply H to A(i+ib:m,i:n) from the right
-*
- CALL ZLARFB( 'Right', 'No transpose', 'Forward',
- $ 'Rowwise', M-I-IB+1, N-I+1, IB, A( I, I ),
- $ LDA, WORK, LDWORK, A( I+IB, I ), LDA,
- $ WORK( IB+1 ), LDWORK )
- END IF
- 10 CONTINUE
- ELSE
- I = 1
- END IF
-*
-* Use unblocked code to factor the last or only block.
-*
- IF( I.LE.K )
- $ CALL ZGELQ2( M-I+1, N-I+1, A( I, I ), LDA, TAU( I ), WORK,
- $ IINFO )
-*
- WORK( 1 ) = IWS
- RETURN
-*
-* End of ZGELQF
-*
- END
diff --git a/src/lib/lapack/zgelsy.f b/src/lib/lapack/zgelsy.f
deleted file mode 100644
index 95aece58..00000000
--- a/src/lib/lapack/zgelsy.f
+++ /dev/null
@@ -1,385 +0,0 @@
- SUBROUTINE ZGELSY( M, N, NRHS, A, LDA, B, LDB, JPVT, RCOND, RANK,
- $ WORK, LWORK, RWORK, INFO )
-*
-* -- LAPACK driver routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- INTEGER INFO, LDA, LDB, LWORK, M, N, NRHS, RANK
- DOUBLE PRECISION RCOND
-* ..
-* .. Array Arguments ..
- INTEGER JPVT( * )
- DOUBLE PRECISION RWORK( * )
- COMPLEX*16 A( LDA, * ), B( LDB, * ), WORK( * )
-* ..
-*
-* Purpose
-* =======
-*
-* ZGELSY computes the minimum-norm solution to a complex linear least
-* squares problem:
-* minimize || A * X - B ||
-* using a complete orthogonal factorization of A. A is an M-by-N
-* matrix which may be rank-deficient.
-*
-* Several right hand side vectors b and solution vectors x can be
-* handled in a single call; they are stored as the columns of the
-* M-by-NRHS right hand side matrix B and the N-by-NRHS solution
-* matrix X.
-*
-* The routine first computes a QR factorization with column pivoting:
-* A * P = Q * [ R11 R12 ]
-* [ 0 R22 ]
-* with R11 defined as the largest leading submatrix whose estimated
-* condition number is less than 1/RCOND. The order of R11, RANK,
-* is the effective rank of A.
-*
-* Then, R22 is considered to be negligible, and R12 is annihilated
-* by unitary transformations from the right, arriving at the
-* complete orthogonal factorization:
-* A * P = Q * [ T11 0 ] * Z
-* [ 0 0 ]
-* The minimum-norm solution is then
-* X = P * Z' [ inv(T11)*Q1'*B ]
-* [ 0 ]
-* where Q1 consists of the first RANK columns of Q.
-*
-* This routine is basically identical to the original xGELSX except
-* three differences:
-* o The permutation of matrix B (the right hand side) is faster and
-* more simple.
-* o The call to the subroutine xGEQPF has been substituted by the
-* the call to the subroutine xGEQP3. This subroutine is a Blas-3
-* version of the QR factorization with column pivoting.
-* o Matrix B (the right hand side) is updated with Blas-3.
-*
-* Arguments
-* =========
-*
-* M (input) INTEGER
-* The number of rows of the matrix A. M >= 0.
-*
-* N (input) INTEGER
-* The number of columns of the matrix A. N >= 0.
-*
-* NRHS (input) INTEGER
-* The number of right hand sides, i.e., the number of
-* columns of matrices B and X. NRHS >= 0.
-*
-* A (input/output) COMPLEX*16 array, dimension (LDA,N)
-* On entry, the M-by-N matrix A.
-* On exit, A has been overwritten by details of its
-* complete orthogonal factorization.
-*
-* LDA (input) INTEGER
-* The leading dimension of the array A. LDA >= max(1,M).
-*
-* B (input/output) COMPLEX*16 array, dimension (LDB,NRHS)
-* On entry, the M-by-NRHS right hand side matrix B.
-* On exit, the N-by-NRHS solution matrix X.
-*
-* LDB (input) INTEGER
-* The leading dimension of the array B. LDB >= max(1,M,N).
-*
-* JPVT (input/output) INTEGER array, dimension (N)
-* On entry, if JPVT(i) .ne. 0, the i-th column of A is permuted
-* to the front of AP, otherwise column i is a free column.
-* On exit, if JPVT(i) = k, then the i-th column of A*P
-* was the k-th column of A.
-*
-* RCOND (input) DOUBLE PRECISION
-* RCOND is used to determine the effective rank of A, which
-* is defined as the order of the largest leading triangular
-* submatrix R11 in the QR factorization with pivoting of A,
-* whose estimated condition number < 1/RCOND.
-*
-* RANK (output) INTEGER
-* The effective rank of A, i.e., the order of the submatrix
-* R11. This is the same as the order of the submatrix T11
-* in the complete orthogonal factorization of A.
-*
-* WORK (workspace/output) COMPLEX*16 array, dimension (MAX(1,LWORK))
-* On exit, if INFO = 0, WORK(1) returns the optimal LWORK.
-*
-* LWORK (input) INTEGER
-* The dimension of the array WORK.
-* The unblocked strategy requires that:
-* LWORK >= MN + MAX( 2*MN, N+1, MN+NRHS )
-* where MN = min(M,N).
-* The block algorithm requires that:
-* LWORK >= MN + MAX( 2*MN, NB*(N+1), MN+MN*NB, MN+NB*NRHS )
-* where NB is an upper bound on the blocksize returned
-* by ILAENV for the routines ZGEQP3, ZTZRZF, CTZRQF, ZUNMQR,
-* and ZUNMRZ.
-*
-* If LWORK = -1, then a workspace query is assumed; the routine
-* only calculates the optimal size of the WORK array, returns
-* this value as the first entry of the WORK array, and no error
-* message related to LWORK is issued by XERBLA.
-*
-* RWORK (workspace) DOUBLE PRECISION array, dimension (2*N)
-*
-* INFO (output) INTEGER
-* = 0: successful exit
-* < 0: if INFO = -i, the i-th argument had an illegal value
-*
-* Further Details
-* ===============
-*
-* Based on contributions by
-* A. Petitet, Computer Science Dept., Univ. of Tenn., Knoxville, USA
-* E. Quintana-Orti, Depto. de Informatica, Universidad Jaime I, Spain
-* G. Quintana-Orti, Depto. de Informatica, Universidad Jaime I, Spain
-*
-* =====================================================================
-*
-* .. Parameters ..
- INTEGER IMAX, IMIN
- PARAMETER ( IMAX = 1, IMIN = 2 )
- DOUBLE PRECISION ZERO, ONE
- PARAMETER ( ZERO = 0.0D+0, ONE = 1.0D+0 )
- COMPLEX*16 CZERO, CONE
- PARAMETER ( CZERO = ( 0.0D+0, 0.0D+0 ),
- $ CONE = ( 1.0D+0, 0.0D+0 ) )
-* ..
-* .. Local Scalars ..
- LOGICAL LQUERY
- INTEGER I, IASCL, IBSCL, ISMAX, ISMIN, J, LWKOPT, MN,
- $ NB, NB1, NB2, NB3, NB4
- DOUBLE PRECISION ANRM, BIGNUM, BNRM, SMAX, SMAXPR, SMIN, SMINPR,
- $ SMLNUM, WSIZE
- COMPLEX*16 C1, C2, S1, S2
-* ..
-* .. External Subroutines ..
- EXTERNAL DLABAD, XERBLA, ZCOPY, ZGEQP3, ZLAIC1, ZLASCL,
- $ ZLASET, ZTRSM, ZTZRZF, ZUNMQR, ZUNMRZ
-* ..
-* .. External Functions ..
- INTEGER ILAENV
- DOUBLE PRECISION DLAMCH, ZLANGE
- EXTERNAL ILAENV, DLAMCH, ZLANGE
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC ABS, DBLE, DCMPLX, MAX, MIN
-* ..
-* .. Executable Statements ..
-*
- MN = MIN( M, N )
- ISMIN = MN + 1
- ISMAX = 2*MN + 1
-*
-* Test the input arguments.
-*
- INFO = 0
- NB1 = ILAENV( 1, 'ZGEQRF', ' ', M, N, -1, -1 )
- NB2 = ILAENV( 1, 'ZGERQF', ' ', M, N, -1, -1 )
- NB3 = ILAENV( 1, 'ZUNMQR', ' ', M, N, NRHS, -1 )
- NB4 = ILAENV( 1, 'ZUNMRQ', ' ', M, N, NRHS, -1 )
- NB = MAX( NB1, NB2, NB3, NB4 )
- LWKOPT = MAX( 1, MN+2*N+NB*( N+1 ), 2*MN+NB*NRHS )
- WORK( 1 ) = DCMPLX( LWKOPT )
- LQUERY = ( LWORK.EQ.-1 )
- IF( M.LT.0 ) THEN
- INFO = -1
- ELSE IF( N.LT.0 ) THEN
- INFO = -2
- ELSE IF( NRHS.LT.0 ) THEN
- INFO = -3
- ELSE IF( LDA.LT.MAX( 1, M ) ) THEN
- INFO = -5
- ELSE IF( LDB.LT.MAX( 1, M, N ) ) THEN
- INFO = -7
- ELSE IF( LWORK.LT.( MN+MAX( 2*MN, N+1, MN+NRHS ) ) .AND. .NOT.
- $ LQUERY ) THEN
- INFO = -12
- END IF
-*
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'ZGELSY', -INFO )
- RETURN
- ELSE IF( LQUERY ) THEN
- RETURN
- END IF
-*
-* Quick return if possible
-*
- IF( MIN( M, N, NRHS ).EQ.0 ) THEN
- RANK = 0
- RETURN
- END IF
-*
-* Get machine parameters
-*
- SMLNUM = DLAMCH( 'S' ) / DLAMCH( 'P' )
- BIGNUM = ONE / SMLNUM
- CALL DLABAD( SMLNUM, BIGNUM )
-*
-* Scale A, B if max entries outside range [SMLNUM,BIGNUM]
-*
- ANRM = ZLANGE( 'M', M, N, A, LDA, RWORK )
- IASCL = 0
- IF( ANRM.GT.ZERO .AND. ANRM.LT.SMLNUM ) THEN
-*
-* Scale matrix norm up to SMLNUM
-*
- CALL ZLASCL( 'G', 0, 0, ANRM, SMLNUM, M, N, A, LDA, INFO )
- IASCL = 1
- ELSE IF( ANRM.GT.BIGNUM ) THEN
-*
-* Scale matrix norm down to BIGNUM
-*
- CALL ZLASCL( 'G', 0, 0, ANRM, BIGNUM, M, N, A, LDA, INFO )
- IASCL = 2
- ELSE IF( ANRM.EQ.ZERO ) THEN
-*
-* Matrix all zero. Return zero solution.
-*
- CALL ZLASET( 'F', MAX( M, N ), NRHS, CZERO, CZERO, B, LDB )
- RANK = 0
- GO TO 70
- END IF
-*
- BNRM = ZLANGE( 'M', M, NRHS, B, LDB, RWORK )
- IBSCL = 0
- IF( BNRM.GT.ZERO .AND. BNRM.LT.SMLNUM ) THEN
-*
-* Scale matrix norm up to SMLNUM
-*
- CALL ZLASCL( 'G', 0, 0, BNRM, SMLNUM, M, NRHS, B, LDB, INFO )
- IBSCL = 1
- ELSE IF( BNRM.GT.BIGNUM ) THEN
-*
-* Scale matrix norm down to BIGNUM
-*
- CALL ZLASCL( 'G', 0, 0, BNRM, BIGNUM, M, NRHS, B, LDB, INFO )
- IBSCL = 2
- END IF
-*
-* Compute QR factorization with column pivoting of A:
-* A * P = Q * R
-*
- CALL ZGEQP3( M, N, A, LDA, JPVT, WORK( 1 ), WORK( MN+1 ),
- $ LWORK-MN, RWORK, INFO )
- WSIZE = MN + DBLE( WORK( MN+1 ) )
-*
-* complex workspace: MN+NB*(N+1). real workspace 2*N.
-* Details of Householder rotations stored in WORK(1:MN).
-*
-* Determine RANK using incremental condition estimation
-*
- WORK( ISMIN ) = CONE
- WORK( ISMAX ) = CONE
- SMAX = ABS( A( 1, 1 ) )
- SMIN = SMAX
- IF( ABS( A( 1, 1 ) ).EQ.ZERO ) THEN
- RANK = 0
- CALL ZLASET( 'F', MAX( M, N ), NRHS, CZERO, CZERO, B, LDB )
- GO TO 70
- ELSE
- RANK = 1
- END IF
-*
- 10 CONTINUE
- IF( RANK.LT.MN ) THEN
- I = RANK + 1
- CALL ZLAIC1( IMIN, RANK, WORK( ISMIN ), SMIN, A( 1, I ),
- $ A( I, I ), SMINPR, S1, C1 )
- CALL ZLAIC1( IMAX, RANK, WORK( ISMAX ), SMAX, A( 1, I ),
- $ A( I, I ), SMAXPR, S2, C2 )
-*
- IF( SMAXPR*RCOND.LE.SMINPR ) THEN
- DO 20 I = 1, RANK
- WORK( ISMIN+I-1 ) = S1*WORK( ISMIN+I-1 )
- WORK( ISMAX+I-1 ) = S2*WORK( ISMAX+I-1 )
- 20 CONTINUE
- WORK( ISMIN+RANK ) = C1
- WORK( ISMAX+RANK ) = C2
- SMIN = SMINPR
- SMAX = SMAXPR
- RANK = RANK + 1
- GO TO 10
- END IF
- END IF
-*
-* complex workspace: 3*MN.
-*
-* Logically partition R = [ R11 R12 ]
-* [ 0 R22 ]
-* where R11 = R(1:RANK,1:RANK)
-*
-* [R11,R12] = [ T11, 0 ] * Y
-*
-c IF( RANK.LT.N )
-c $ CALL ZTZRZF( RANK, N, A, LDA, WORK( MN+1 ), WORK( 2*MN+1 ),
-c $ LWORK-2*MN, INFO )
-*
-* complex workspace: 2*MN.
-* Details of Householder rotations stored in WORK(MN+1:2*MN)
-*
-* B(1:M,1:NRHS) := Q' * B(1:M,1:NRHS)
-*
- CALL ZUNMQR( 'Left', 'Conjugate transpose', M, NRHS, MN, A, LDA,
- $ WORK( 1 ), B, LDB, WORK( 2*MN+1 ), LWORK-2*MN, INFO )
- WSIZE = MAX( WSIZE, 2*MN+DBLE( WORK( 2*MN+1 ) ) )
-*
-* complex workspace: 2*MN+NB*NRHS.
-*
-* B(1:RANK,1:NRHS) := inv(T11) * B(1:RANK,1:NRHS)
-*
- CALL ZTRSM( 'Left', 'Upper', 'No transpose', 'Non-unit', RANK,
- $ NRHS, CONE, A, LDA, B, LDB )
-*
- DO 40 J = 1, NRHS
- DO 30 I = RANK + 1, N
- B( I, J ) = CZERO
- 30 CONTINUE
- 40 CONTINUE
-*
-* B(1:N,1:NRHS) := Y' * B(1:N,1:NRHS)
-*
-c IF( RANK.LT.N ) THEN
-c CALL ZUNMRZ( 'Left', 'Conjugate transpose', N, NRHS, RANK,
-c $ N-RANK, A, LDA, WORK( MN+1 ), B, LDB,
-c $ WORK( 2*MN+1 ), LWORK-2*MN, INFO )
-c END IF
-*
-* complex workspace: 2*MN+NRHS.
-*
-* B(1:N,1:NRHS) := P * B(1:N,1:NRHS)
-*
- DO 60 J = 1, NRHS
- DO 50 I = 1, N
- WORK( JPVT( I ) ) = B( I, J )
- 50 CONTINUE
- CALL ZCOPY( N, WORK( 1 ), 1, B( 1, J ), 1 )
- 60 CONTINUE
-*
-* complex workspace: N.
-*
-* Undo scaling
-*
- IF( IASCL.EQ.1 ) THEN
- CALL ZLASCL( 'G', 0, 0, ANRM, SMLNUM, N, NRHS, B, LDB, INFO )
- CALL ZLASCL( 'U', 0, 0, SMLNUM, ANRM, RANK, RANK, A, LDA,
- $ INFO )
- ELSE IF( IASCL.EQ.2 ) THEN
- CALL ZLASCL( 'G', 0, 0, ANRM, BIGNUM, N, NRHS, B, LDB, INFO )
- CALL ZLASCL( 'U', 0, 0, BIGNUM, ANRM, RANK, RANK, A, LDA,
- $ INFO )
- END IF
- IF( IBSCL.EQ.1 ) THEN
- CALL ZLASCL( 'G', 0, 0, SMLNUM, BNRM, N, NRHS, B, LDB, INFO )
- ELSE IF( IBSCL.EQ.2 ) THEN
- CALL ZLASCL( 'G', 0, 0, BIGNUM, BNRM, N, NRHS, B, LDB, INFO )
- END IF
-*
- 70 CONTINUE
- WORK( 1 ) = DCMPLX( LWKOPT )
-*
- RETURN
-*
-* End of ZGELSY
-*
- END
diff --git a/src/lib/lapack/zgeqp3.f b/src/lib/lapack/zgeqp3.f
deleted file mode 100644
index 32bf3367..00000000
--- a/src/lib/lapack/zgeqp3.f
+++ /dev/null
@@ -1,293 +0,0 @@
- SUBROUTINE ZGEQP3( M, N, A, LDA, JPVT, TAU, WORK, LWORK, RWORK,
- $ INFO )
-*
-* -- LAPACK routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- INTEGER INFO, LDA, LWORK, M, N
-* ..
-* .. Array Arguments ..
- INTEGER JPVT( * )
- DOUBLE PRECISION RWORK( * )
- COMPLEX*16 A( LDA, * ), TAU( * ), WORK( * )
-* ..
-*
-* Purpose
-* =======
-*
-* ZGEQP3 computes a QR factorization with column pivoting of a
-* matrix A: A*P = Q*R using Level 3 BLAS.
-*
-* Arguments
-* =========
-*
-* M (input) INTEGER
-* The number of rows of the matrix A. M >= 0.
-*
-* N (input) INTEGER
-* The number of columns of the matrix A. N >= 0.
-*
-* A (input/output) COMPLEX*16 array, dimension (LDA,N)
-* On entry, the M-by-N matrix A.
-* On exit, the upper triangle of the array contains the
-* min(M,N)-by-N upper trapezoidal matrix R; the elements below
-* the diagonal, together with the array TAU, represent the
-* unitary matrix Q as a product of min(M,N) elementary
-* reflectors.
-*
-* LDA (input) INTEGER
-* The leading dimension of the array A. LDA >= max(1,M).
-*
-* JPVT (input/output) INTEGER array, dimension (N)
-* On entry, if JPVT(J).ne.0, the J-th column of A is permuted
-* to the front of A*P (a leading column); if JPVT(J)=0,
-* the J-th column of A is a free column.
-* On exit, if JPVT(J)=K, then the J-th column of A*P was the
-* the K-th column of A.
-*
-* TAU (output) COMPLEX*16 array, dimension (min(M,N))
-* The scalar factors of the elementary reflectors.
-*
-* WORK (workspace/output) COMPLEX*16 array, dimension (MAX(1,LWORK))
-* On exit, if INFO=0, WORK(1) returns the optimal LWORK.
-*
-* LWORK (input) INTEGER
-* The dimension of the array WORK. LWORK >= N+1.
-* For optimal performance LWORK >= ( N+1 )*NB, where NB
-* is the optimal blocksize.
-*
-* If LWORK = -1, then a workspace query is assumed; the routine
-* only calculates the optimal size of the WORK array, returns
-* this value as the first entry of the WORK array, and no error
-* message related to LWORK is issued by XERBLA.
-*
-* RWORK (workspace) DOUBLE PRECISION array, dimension (2*N)
-*
-* INFO (output) INTEGER
-* = 0: successful exit.
-* < 0: if INFO = -i, the i-th argument had an illegal value.
-*
-* Further Details
-* ===============
-*
-* The matrix Q is represented as a product of elementary reflectors
-*
-* Q = H(1) H(2) . . . H(k), where k = min(m,n).
-*
-* Each H(i) has the form
-*
-* H(i) = I - tau * v * v'
-*
-* where tau is a real/complex scalar, and v is a real/complex vector
-* with v(1:i-1) = 0 and v(i) = 1; v(i+1:m) is stored on exit in
-* A(i+1:m,i), and tau in TAU(i).
-*
-* Based on contributions by
-* G. Quintana-Orti, Depto. de Informatica, Universidad Jaime I, Spain
-* X. Sun, Computer Science Dept., Duke University, USA
-*
-* =====================================================================
-*
-* .. Parameters ..
- INTEGER INB, INBMIN, IXOVER
- PARAMETER ( INB = 1, INBMIN = 2, IXOVER = 3 )
-* ..
-* .. Local Scalars ..
- LOGICAL LQUERY
- INTEGER FJB, IWS, J, JB, LWKOPT, MINMN, MINWS, NA, NB,
- $ NBMIN, NFXD, NX, SM, SMINMN, SN, TOPBMN
-* ..
-* .. External Subroutines ..
- EXTERNAL XERBLA, ZGEQRF, ZLAQP2, ZLAQPS, ZSWAP, ZUNMQR
-* ..
-* .. External Functions ..
- INTEGER ILAENV
- DOUBLE PRECISION DZNRM2
- EXTERNAL ILAENV, DZNRM2
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC INT, MAX, MIN
-* ..
-* .. Executable Statements ..
-*
-* Test input arguments
-* ====================
-*
- INFO = 0
- LQUERY = ( LWORK.EQ.-1 )
- IF( M.LT.0 ) THEN
- INFO = -1
- ELSE IF( N.LT.0 ) THEN
- INFO = -2
- ELSE IF( LDA.LT.MAX( 1, M ) ) THEN
- INFO = -4
- END IF
-*
- IF( INFO.EQ.0 ) THEN
- MINMN = MIN( M, N )
- IF( MINMN.EQ.0 ) THEN
- IWS = 1
- LWKOPT = 1
- ELSE
- IWS = N + 1
- NB = ILAENV( INB, 'ZGEQRF', ' ', M, N, -1, -1 )
- LWKOPT = ( N + 1 )*NB
- END IF
- WORK( 1 ) = LWKOPT
-*
- IF( ( LWORK.LT.IWS ) .AND. .NOT.LQUERY ) THEN
- INFO = -8
- END IF
- END IF
-*
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'ZGEQP3', -INFO )
- RETURN
- ELSE IF( LQUERY ) THEN
- RETURN
- END IF
-*
-* Quick return if possible.
-*
- IF( MINMN.EQ.0 ) THEN
- RETURN
- END IF
-*
-* Move initial columns up front.
-*
- NFXD = 1
- DO 10 J = 1, N
- IF( JPVT( J ).NE.0 ) THEN
- IF( J.NE.NFXD ) THEN
- CALL ZSWAP( M, A( 1, J ), 1, A( 1, NFXD ), 1 )
- JPVT( J ) = JPVT( NFXD )
- JPVT( NFXD ) = J
- ELSE
- JPVT( J ) = J
- END IF
- NFXD = NFXD + 1
- ELSE
- JPVT( J ) = J
- END IF
- 10 CONTINUE
- NFXD = NFXD - 1
-*
-* Factorize fixed columns
-* =======================
-*
-* Compute the QR factorization of fixed columns and update
-* remaining columns.
-*
- IF( NFXD.GT.0 ) THEN
- NA = MIN( M, NFXD )
-*CC CALL ZGEQR2( M, NA, A, LDA, TAU, WORK, INFO )
- CALL ZGEQRF( M, NA, A, LDA, TAU, WORK, LWORK, INFO )
- IWS = MAX( IWS, INT( WORK( 1 ) ) )
- IF( NA.LT.N ) THEN
-*CC CALL ZUNM2R( 'Left', 'Conjugate Transpose', M, N-NA,
-*CC $ NA, A, LDA, TAU, A( 1, NA+1 ), LDA, WORK,
-*CC $ INFO )
- CALL ZUNMQR( 'Left', 'Conjugate Transpose', M, N-NA, NA, A,
- $ LDA, TAU, A( 1, NA+1 ), LDA, WORK, LWORK,
- $ INFO )
- IWS = MAX( IWS, INT( WORK( 1 ) ) )
- END IF
- END IF
-*
-* Factorize free columns
-* ======================
-*
- IF( NFXD.LT.MINMN ) THEN
-*
- SM = M - NFXD
- SN = N - NFXD
- SMINMN = MINMN - NFXD
-*
-* Determine the block size.
-*
- NB = ILAENV( INB, 'ZGEQRF', ' ', SM, SN, -1, -1 )
- NBMIN = 2
- NX = 0
-*
- IF( ( NB.GT.1 ) .AND. ( NB.LT.SMINMN ) ) THEN
-*
-* Determine when to cross over from blocked to unblocked code.
-*
- NX = MAX( 0, ILAENV( IXOVER, 'ZGEQRF', ' ', SM, SN, -1,
- $ -1 ) )
-*
-*
- IF( NX.LT.SMINMN ) THEN
-*
-* Determine if workspace is large enough for blocked code.
-*
- MINWS = ( SN+1 )*NB
- IWS = MAX( IWS, MINWS )
- IF( LWORK.LT.MINWS ) THEN
-*
-* Not enough workspace to use optimal NB: Reduce NB and
-* determine the minimum value of NB.
-*
- NB = LWORK / ( SN+1 )
- NBMIN = MAX( 2, ILAENV( INBMIN, 'ZGEQRF', ' ', SM, SN,
- $ -1, -1 ) )
-*
-*
- END IF
- END IF
- END IF
-*
-* Initialize partial column norms. The first N elements of work
-* store the exact column norms.
-*
- DO 20 J = NFXD + 1, N
- RWORK( J ) = DZNRM2( SM, A( NFXD+1, J ), 1 )
- RWORK( N+J ) = RWORK( J )
- 20 CONTINUE
-*
- IF( ( NB.GE.NBMIN ) .AND. ( NB.LT.SMINMN ) .AND.
- $ ( NX.LT.SMINMN ) ) THEN
-*
-* Use blocked code initially.
-*
- J = NFXD + 1
-*
-* Compute factorization: while loop.
-*
-*
- TOPBMN = MINMN - NX
- 30 CONTINUE
- IF( J.LE.TOPBMN ) THEN
- JB = MIN( NB, TOPBMN-J+1 )
-*
-* Factorize JB columns among columns J:N.
-*
- CALL ZLAQPS( M, N-J+1, J-1, JB, FJB, A( 1, J ), LDA,
- $ JPVT( J ), TAU( J ), RWORK( J ),
- $ RWORK( N+J ), WORK( 1 ), WORK( JB+1 ),
- $ N-J+1 )
-*
- J = J + FJB
- GO TO 30
- END IF
- ELSE
- J = NFXD + 1
- END IF
-*
-* Use unblocked code to factor the last or only block.
-*
-*
- IF( J.LE.MINMN )
- $ CALL ZLAQP2( M, N-J+1, J-1, A( 1, J ), LDA, JPVT( J ),
- $ TAU( J ), RWORK( J ), RWORK( N+J ), WORK( 1 ) )
-*
- END IF
-*
- WORK( 1 ) = IWS
- RETURN
-*
-* End of ZGEQP3
-*
- END
diff --git a/src/lib/lapack/zgeqpf.f b/src/lib/lapack/zgeqpf.f
deleted file mode 100644
index 6d4f86f0..00000000
--- a/src/lib/lapack/zgeqpf.f
+++ /dev/null
@@ -1,234 +0,0 @@
- SUBROUTINE ZGEQPF( M, N, A, LDA, JPVT, TAU, WORK, RWORK, INFO )
-*
-* -- LAPACK deprecated driver routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- INTEGER INFO, LDA, M, N
-* ..
-* .. Array Arguments ..
- INTEGER JPVT( * )
- DOUBLE PRECISION RWORK( * )
- COMPLEX*16 A( LDA, * ), TAU( * ), WORK( * )
-* ..
-*
-* Purpose
-* =======
-*
-* This routine is deprecated and has been replaced by routine ZGEQP3.
-*
-* ZGEQPF computes a QR factorization with column pivoting of a
-* complex M-by-N matrix A: A*P = Q*R.
-*
-* Arguments
-* =========
-*
-* M (input) INTEGER
-* The number of rows of the matrix A. M >= 0.
-*
-* N (input) INTEGER
-* The number of columns of the matrix A. N >= 0
-*
-* A (input/output) COMPLEX*16 array, dimension (LDA,N)
-* On entry, the M-by-N matrix A.
-* On exit, the upper triangle of the array contains the
-* min(M,N)-by-N upper triangular matrix R; the elements
-* below the diagonal, together with the array TAU,
-* represent the unitary matrix Q as a product of
-* min(m,n) elementary reflectors.
-*
-* LDA (input) INTEGER
-* The leading dimension of the array A. LDA >= max(1,M).
-*
-* JPVT (input/output) INTEGER array, dimension (N)
-* On entry, if JPVT(i) .ne. 0, the i-th column of A is permuted
-* to the front of A*P (a leading column); if JPVT(i) = 0,
-* the i-th column of A is a free column.
-* On exit, if JPVT(i) = k, then the i-th column of A*P
-* was the k-th column of A.
-*
-* TAU (output) COMPLEX*16 array, dimension (min(M,N))
-* The scalar factors of the elementary reflectors.
-*
-* WORK (workspace) COMPLEX*16 array, dimension (N)
-*
-* RWORK (workspace) DOUBLE PRECISION array, dimension (2*N)
-*
-* INFO (output) INTEGER
-* = 0: successful exit
-* < 0: if INFO = -i, the i-th argument had an illegal value
-*
-* Further Details
-* ===============
-*
-* The matrix Q is represented as a product of elementary reflectors
-*
-* Q = H(1) H(2) . . . H(n)
-*
-* Each H(i) has the form
-*
-* H = I - tau * v * v'
-*
-* where tau is a complex scalar, and v is a complex vector with
-* v(1:i-1) = 0 and v(i) = 1; v(i+1:m) is stored on exit in A(i+1:m,i).
-*
-* The matrix P is represented in jpvt as follows: If
-* jpvt(j) = i
-* then the jth column of P is the ith canonical unit vector.
-*
-* Partial column norm updating strategy modified by
-* Z. Drmac and Z. Bujanovic, Dept. of Mathematics,
-* University of Zagreb, Croatia.
-* June 2006.
-* For more details see LAPACK Working Note 176.
-*
-* =====================================================================
-*
-* .. Parameters ..
- DOUBLE PRECISION ZERO, ONE
- PARAMETER ( ZERO = 0.0D+0, ONE = 1.0D+0 )
-* ..
-* .. Local Scalars ..
- INTEGER I, ITEMP, J, MA, MN, PVT
- DOUBLE PRECISION TEMP, TEMP2, TOL3Z
- COMPLEX*16 AII
-* ..
-* .. External Subroutines ..
- EXTERNAL XERBLA, ZGEQR2, ZLARF, ZLARFG, ZSWAP, ZUNM2R
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC ABS, DCMPLX, DCONJG, MAX, MIN, SQRT
-* ..
-* .. External Functions ..
- INTEGER IDAMAX
- DOUBLE PRECISION DLAMCH, DZNRM2
- EXTERNAL IDAMAX, DLAMCH, DZNRM2
-* ..
-* .. Executable Statements ..
-*
-* Test the input arguments
-*
- INFO = 0
- IF( M.LT.0 ) THEN
- INFO = -1
- ELSE IF( N.LT.0 ) THEN
- INFO = -2
- ELSE IF( LDA.LT.MAX( 1, M ) ) THEN
- INFO = -4
- END IF
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'ZGEQPF', -INFO )
- RETURN
- END IF
-*
- MN = MIN( M, N )
- TOL3Z = SQRT(DLAMCH('Epsilon'))
-*
-* Move initial columns up front
-*
- ITEMP = 1
- DO 10 I = 1, N
- IF( JPVT( I ).NE.0 ) THEN
- IF( I.NE.ITEMP ) THEN
- CALL ZSWAP( M, A( 1, I ), 1, A( 1, ITEMP ), 1 )
- JPVT( I ) = JPVT( ITEMP )
- JPVT( ITEMP ) = I
- ELSE
- JPVT( I ) = I
- END IF
- ITEMP = ITEMP + 1
- ELSE
- JPVT( I ) = I
- END IF
- 10 CONTINUE
- ITEMP = ITEMP - 1
-*
-* Compute the QR factorization and update remaining columns
-*
- IF( ITEMP.GT.0 ) THEN
- MA = MIN( ITEMP, M )
- CALL ZGEQR2( M, MA, A, LDA, TAU, WORK, INFO )
- IF( MA.LT.N ) THEN
- CALL ZUNM2R( 'Left', 'Conjugate transpose', M, N-MA, MA, A,
- $ LDA, TAU, A( 1, MA+1 ), LDA, WORK, INFO )
- END IF
- END IF
-*
- IF( ITEMP.LT.MN ) THEN
-*
-* Initialize partial column norms. The first n elements of
-* work store the exact column norms.
-*
- DO 20 I = ITEMP + 1, N
- RWORK( I ) = DZNRM2( M-ITEMP, A( ITEMP+1, I ), 1 )
- RWORK( N+I ) = RWORK( I )
- 20 CONTINUE
-*
-* Compute factorization
-*
- DO 40 I = ITEMP + 1, MN
-*
-* Determine ith pivot column and swap if necessary
-*
- PVT = ( I-1 ) + IDAMAX( N-I+1, RWORK( I ), 1 )
-*
- IF( PVT.NE.I ) THEN
- CALL ZSWAP( M, A( 1, PVT ), 1, A( 1, I ), 1 )
- ITEMP = JPVT( PVT )
- JPVT( PVT ) = JPVT( I )
- JPVT( I ) = ITEMP
- RWORK( PVT ) = RWORK( I )
- RWORK( N+PVT ) = RWORK( N+I )
- END IF
-*
-* Generate elementary reflector H(i)
-*
- AII = A( I, I )
- CALL ZLARFG( M-I+1, AII, A( MIN( I+1, M ), I ), 1,
- $ TAU( I ) )
- A( I, I ) = AII
-*
- IF( I.LT.N ) THEN
-*
-* Apply H(i) to A(i:m,i+1:n) from the left
-*
- AII = A( I, I )
- A( I, I ) = DCMPLX( ONE )
- CALL ZLARF( 'Left', M-I+1, N-I, A( I, I ), 1,
- $ DCONJG( TAU( I ) ), A( I, I+1 ), LDA, WORK )
- A( I, I ) = AII
- END IF
-*
-* Update partial column norms
-*
- DO 30 J = I + 1, N
- IF( RWORK( J ).NE.ZERO ) THEN
-*
-* NOTE: The following 4 lines follow from the analysis in
-* Lapack Working Note 176.
-*
- TEMP = ABS( A( I, J ) ) / RWORK( J )
- TEMP = MAX( ZERO, ( ONE+TEMP )*( ONE-TEMP ) )
- TEMP2 = TEMP*( RWORK( J ) / RWORK( N+J ) )**2
- IF( TEMP2 .LE. TOL3Z ) THEN
- IF( M-I.GT.0 ) THEN
- RWORK( J ) = DZNRM2( M-I, A( I+1, J ), 1 )
- RWORK( N+J ) = RWORK( J )
- ELSE
- RWORK( J ) = ZERO
- RWORK( N+J ) = ZERO
- END IF
- ELSE
- RWORK( J ) = RWORK( J )*SQRT( TEMP )
- END IF
- END IF
- 30 CONTINUE
-*
- 40 CONTINUE
- END IF
- RETURN
-*
-* End of ZGEQPF
-*
- END
diff --git a/src/lib/lapack/zgeqr2.f b/src/lib/lapack/zgeqr2.f
deleted file mode 100644
index 962ab588..00000000
--- a/src/lib/lapack/zgeqr2.f
+++ /dev/null
@@ -1,121 +0,0 @@
- SUBROUTINE ZGEQR2( M, N, A, LDA, TAU, WORK, INFO )
-*
-* -- LAPACK routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- INTEGER INFO, LDA, M, N
-* ..
-* .. Array Arguments ..
- COMPLEX*16 A( LDA, * ), TAU( * ), WORK( * )
-* ..
-*
-* Purpose
-* =======
-*
-* ZGEQR2 computes a QR factorization of a complex m by n matrix A:
-* A = Q * R.
-*
-* Arguments
-* =========
-*
-* M (input) INTEGER
-* The number of rows of the matrix A. M >= 0.
-*
-* N (input) INTEGER
-* The number of columns of the matrix A. N >= 0.
-*
-* A (input/output) COMPLEX*16 array, dimension (LDA,N)
-* On entry, the m by n matrix A.
-* On exit, the elements on and above the diagonal of the array
-* contain the min(m,n) by n upper trapezoidal matrix R (R is
-* upper triangular if m >= n); the elements below the diagonal,
-* with the array TAU, represent the unitary matrix Q as a
-* product of elementary reflectors (see Further Details).
-*
-* LDA (input) INTEGER
-* The leading dimension of the array A. LDA >= max(1,M).
-*
-* TAU (output) COMPLEX*16 array, dimension (min(M,N))
-* The scalar factors of the elementary reflectors (see Further
-* Details).
-*
-* WORK (workspace) COMPLEX*16 array, dimension (N)
-*
-* INFO (output) INTEGER
-* = 0: successful exit
-* < 0: if INFO = -i, the i-th argument had an illegal value
-*
-* Further Details
-* ===============
-*
-* The matrix Q is represented as a product of elementary reflectors
-*
-* Q = H(1) H(2) . . . H(k), where k = min(m,n).
-*
-* Each H(i) has the form
-*
-* H(i) = I - tau * v * v'
-*
-* where tau is a complex scalar, and v is a complex vector with
-* v(1:i-1) = 0 and v(i) = 1; v(i+1:m) is stored on exit in A(i+1:m,i),
-* and tau in TAU(i).
-*
-* =====================================================================
-*
-* .. Parameters ..
- COMPLEX*16 ONE
- PARAMETER ( ONE = ( 1.0D+0, 0.0D+0 ) )
-* ..
-* .. Local Scalars ..
- INTEGER I, K
- COMPLEX*16 ALPHA
-* ..
-* .. External Subroutines ..
- EXTERNAL XERBLA, ZLARF, ZLARFG
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC DCONJG, MAX, MIN
-* ..
-* .. Executable Statements ..
-*
-* Test the input arguments
-*
- INFO = 0
- IF( M.LT.0 ) THEN
- INFO = -1
- ELSE IF( N.LT.0 ) THEN
- INFO = -2
- ELSE IF( LDA.LT.MAX( 1, M ) ) THEN
- INFO = -4
- END IF
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'ZGEQR2', -INFO )
- RETURN
- END IF
-*
- K = MIN( M, N )
-*
- DO 10 I = 1, K
-*
-* Generate elementary reflector H(i) to annihilate A(i+1:m,i)
-*
- CALL ZLARFG( M-I+1, A( I, I ), A( MIN( I+1, M ), I ), 1,
- $ TAU( I ) )
- IF( I.LT.N ) THEN
-*
-* Apply H(i)' to A(i:m,i+1:n) from the left
-*
- ALPHA = A( I, I )
- A( I, I ) = ONE
- CALL ZLARF( 'Left', M-I+1, N-I, A( I, I ), 1,
- $ DCONJG( TAU( I ) ), A( I, I+1 ), LDA, WORK )
- A( I, I ) = ALPHA
- END IF
- 10 CONTINUE
- RETURN
-*
-* End of ZGEQR2
-*
- END
diff --git a/src/lib/lapack/zgeqrf.f b/src/lib/lapack/zgeqrf.f
deleted file mode 100644
index d11c9245..00000000
--- a/src/lib/lapack/zgeqrf.f
+++ /dev/null
@@ -1,196 +0,0 @@
- SUBROUTINE ZGEQRF( M, N, A, LDA, TAU, WORK, LWORK, INFO )
-*
-* -- LAPACK routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- INTEGER INFO, LDA, LWORK, M, N
-* ..
-* .. Array Arguments ..
- COMPLEX*16 A( LDA, * ), TAU( * ), WORK( * )
-* ..
-*
-* Purpose
-* =======
-*
-* ZGEQRF computes a QR factorization of a complex M-by-N matrix A:
-* A = Q * R.
-*
-* Arguments
-* =========
-*
-* M (input) INTEGER
-* The number of rows of the matrix A. M >= 0.
-*
-* N (input) INTEGER
-* The number of columns of the matrix A. N >= 0.
-*
-* A (input/output) COMPLEX*16 array, dimension (LDA,N)
-* On entry, the M-by-N matrix A.
-* On exit, the elements on and above the diagonal of the array
-* contain the min(M,N)-by-N upper trapezoidal matrix R (R is
-* upper triangular if m >= n); the elements below the diagonal,
-* with the array TAU, represent the unitary matrix Q as a
-* product of min(m,n) elementary reflectors (see Further
-* Details).
-*
-* LDA (input) INTEGER
-* The leading dimension of the array A. LDA >= max(1,M).
-*
-* TAU (output) COMPLEX*16 array, dimension (min(M,N))
-* The scalar factors of the elementary reflectors (see Further
-* Details).
-*
-* WORK (workspace/output) COMPLEX*16 array, dimension (MAX(1,LWORK))
-* On exit, if INFO = 0, WORK(1) returns the optimal LWORK.
-*
-* LWORK (input) INTEGER
-* The dimension of the array WORK. LWORK >= max(1,N).
-* For optimum performance LWORK >= N*NB, where NB is
-* the optimal blocksize.
-*
-* If LWORK = -1, then a workspace query is assumed; the routine
-* only calculates the optimal size of the WORK array, returns
-* this value as the first entry of the WORK array, and no error
-* message related to LWORK is issued by XERBLA.
-*
-* INFO (output) INTEGER
-* = 0: successful exit
-* < 0: if INFO = -i, the i-th argument had an illegal value
-*
-* Further Details
-* ===============
-*
-* The matrix Q is represented as a product of elementary reflectors
-*
-* Q = H(1) H(2) . . . H(k), where k = min(m,n).
-*
-* Each H(i) has the form
-*
-* H(i) = I - tau * v * v'
-*
-* where tau is a complex scalar, and v is a complex vector with
-* v(1:i-1) = 0 and v(i) = 1; v(i+1:m) is stored on exit in A(i+1:m,i),
-* and tau in TAU(i).
-*
-* =====================================================================
-*
-* .. Local Scalars ..
- LOGICAL LQUERY
- INTEGER I, IB, IINFO, IWS, K, LDWORK, LWKOPT, NB,
- $ NBMIN, NX
-* ..
-* .. External Subroutines ..
- EXTERNAL XERBLA, ZGEQR2, ZLARFB, ZLARFT
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC MAX, MIN
-* ..
-* .. External Functions ..
- INTEGER ILAENV
- EXTERNAL ILAENV
-* ..
-* .. Executable Statements ..
-*
-* Test the input arguments
-*
- INFO = 0
- NB = ILAENV( 1, 'ZGEQRF', ' ', M, N, -1, -1 )
- LWKOPT = N*NB
- WORK( 1 ) = LWKOPT
- LQUERY = ( LWORK.EQ.-1 )
- IF( M.LT.0 ) THEN
- INFO = -1
- ELSE IF( N.LT.0 ) THEN
- INFO = -2
- ELSE IF( LDA.LT.MAX( 1, M ) ) THEN
- INFO = -4
- ELSE IF( LWORK.LT.MAX( 1, N ) .AND. .NOT.LQUERY ) THEN
- INFO = -7
- END IF
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'ZGEQRF', -INFO )
- RETURN
- ELSE IF( LQUERY ) THEN
- RETURN
- END IF
-*
-* Quick return if possible
-*
- K = MIN( M, N )
- IF( K.EQ.0 ) THEN
- WORK( 1 ) = 1
- RETURN
- END IF
-*
- NBMIN = 2
- NX = 0
- IWS = N
- IF( NB.GT.1 .AND. NB.LT.K ) THEN
-*
-* Determine when to cross over from blocked to unblocked code.
-*
- NX = MAX( 0, ILAENV( 3, 'ZGEQRF', ' ', M, N, -1, -1 ) )
- IF( NX.LT.K ) THEN
-*
-* Determine if workspace is large enough for blocked code.
-*
- LDWORK = N
- IWS = LDWORK*NB
- IF( LWORK.LT.IWS ) THEN
-*
-* Not enough workspace to use optimal NB: reduce NB and
-* determine the minimum value of NB.
-*
- NB = LWORK / LDWORK
- NBMIN = MAX( 2, ILAENV( 2, 'ZGEQRF', ' ', M, N, -1,
- $ -1 ) )
- END IF
- END IF
- END IF
-*
- IF( NB.GE.NBMIN .AND. NB.LT.K .AND. NX.LT.K ) THEN
-*
-* Use blocked code initially
-*
- DO 10 I = 1, K - NX, NB
- IB = MIN( K-I+1, NB )
-*
-* Compute the QR factorization of the current block
-* A(i:m,i:i+ib-1)
-*
- CALL ZGEQR2( M-I+1, IB, A( I, I ), LDA, TAU( I ), WORK,
- $ IINFO )
- IF( I+IB.LE.N ) THEN
-*
-* Form the triangular factor of the block reflector
-* H = H(i) H(i+1) . . . H(i+ib-1)
-*
- CALL ZLARFT( 'Forward', 'Columnwise', M-I+1, IB,
- $ A( I, I ), LDA, TAU( I ), WORK, LDWORK )
-*
-* Apply H' to A(i:m,i+ib:n) from the left
-*
- CALL ZLARFB( 'Left', 'Conjugate transpose', 'Forward',
- $ 'Columnwise', M-I+1, N-I-IB+1, IB,
- $ A( I, I ), LDA, WORK, LDWORK, A( I, I+IB ),
- $ LDA, WORK( IB+1 ), LDWORK )
- END IF
- 10 CONTINUE
- ELSE
- I = 1
- END IF
-*
-* Use unblocked code to factor the last or only block.
-*
- IF( I.LE.K )
- $ CALL ZGEQR2( M-I+1, N-I+1, A( I, I ), LDA, TAU( I ), WORK,
- $ IINFO )
-*
- WORK( 1 ) = IWS
- RETURN
-*
-* End of ZGEQRF
-*
- END
diff --git a/src/lib/lapack/zgesc2.f b/src/lib/lapack/zgesc2.f
deleted file mode 100644
index d4d51337..00000000
--- a/src/lib/lapack/zgesc2.f
+++ /dev/null
@@ -1,133 +0,0 @@
- SUBROUTINE ZGESC2( N, A, LDA, RHS, IPIV, JPIV, SCALE )
-*
-* -- LAPACK auxiliary routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- INTEGER LDA, N
- DOUBLE PRECISION SCALE
-* ..
-* .. Array Arguments ..
- INTEGER IPIV( * ), JPIV( * )
- COMPLEX*16 A( LDA, * ), RHS( * )
-* ..
-*
-* Purpose
-* =======
-*
-* ZGESC2 solves a system of linear equations
-*
-* A * X = scale* RHS
-*
-* with a general N-by-N matrix A using the LU factorization with
-* complete pivoting computed by ZGETC2.
-*
-*
-* Arguments
-* =========
-*
-* N (input) INTEGER
-* The number of columns of the matrix A.
-*
-* A (input) COMPLEX*16 array, dimension (LDA, N)
-* On entry, the LU part of the factorization of the n-by-n
-* matrix A computed by ZGETC2: A = P * L * U * Q
-*
-* LDA (input) INTEGER
-* The leading dimension of the array A. LDA >= max(1, N).
-*
-* RHS (input/output) COMPLEX*16 array, dimension N.
-* On entry, the right hand side vector b.
-* On exit, the solution vector X.
-*
-* IPIV (input) INTEGER array, dimension (N).
-* The pivot indices; for 1 <= i <= N, row i of the
-* matrix has been interchanged with row IPIV(i).
-*
-* JPIV (input) INTEGER array, dimension (N).
-* The pivot indices; for 1 <= j <= N, column j of the
-* matrix has been interchanged with column JPIV(j).
-*
-* SCALE (output) DOUBLE PRECISION
-* On exit, SCALE contains the scale factor. SCALE is chosen
-* 0 <= SCALE <= 1 to prevent owerflow in the solution.
-*
-* Further Details
-* ===============
-*
-* Based on contributions by
-* Bo Kagstrom and Peter Poromaa, Department of Computing Science,
-* Umea University, S-901 87 Umea, Sweden.
-*
-* =====================================================================
-*
-* .. Parameters ..
- DOUBLE PRECISION ZERO, ONE, TWO
- PARAMETER ( ZERO = 0.0D+0, ONE = 1.0D+0, TWO = 2.0D+0 )
-* ..
-* .. Local Scalars ..
- INTEGER I, J
- DOUBLE PRECISION BIGNUM, EPS, SMLNUM
- COMPLEX*16 TEMP
-* ..
-* .. External Subroutines ..
- EXTERNAL ZLASWP, ZSCAL
-* ..
-* .. External Functions ..
- INTEGER IZAMAX
- DOUBLE PRECISION DLAMCH
- EXTERNAL IZAMAX, DLAMCH
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC ABS, DBLE, DCMPLX
-* ..
-* .. Executable Statements ..
-*
-* Set constant to control overflow
-*
- EPS = DLAMCH( 'P' )
- SMLNUM = DLAMCH( 'S' ) / EPS
- BIGNUM = ONE / SMLNUM
- CALL DLABAD( SMLNUM, BIGNUM )
-*
-* Apply permutations IPIV to RHS
-*
- CALL ZLASWP( 1, RHS, LDA, 1, N-1, IPIV, 1 )
-*
-* Solve for L part
-*
- DO 20 I = 1, N - 1
- DO 10 J = I + 1, N
- RHS( J ) = RHS( J ) - A( J, I )*RHS( I )
- 10 CONTINUE
- 20 CONTINUE
-*
-* Solve for U part
-*
- SCALE = ONE
-*
-* Check for scaling
-*
- I = IZAMAX( N, RHS, 1 )
- IF( TWO*SMLNUM*ABS( RHS( I ) ).GT.ABS( A( N, N ) ) ) THEN
- TEMP = DCMPLX( ONE / TWO, ZERO ) / ABS( RHS( I ) )
- CALL ZSCAL( N, TEMP, RHS( 1 ), 1 )
- SCALE = SCALE*DBLE( TEMP )
- END IF
- DO 40 I = N, 1, -1
- TEMP = DCMPLX( ONE, ZERO ) / A( I, I )
- RHS( I ) = RHS( I )*TEMP
- DO 30 J = I + 1, N
- RHS( I ) = RHS( I ) - RHS( J )*( A( I, J )*TEMP )
- 30 CONTINUE
- 40 CONTINUE
-*
-* Apply permutations JPIV to the solution (RHS)
-*
- CALL ZLASWP( 1, RHS, LDA, 1, N-1, JPIV, -1 )
- RETURN
-*
-* End of ZGESC2
-*
- END
diff --git a/src/lib/lapack/zgesvd.f b/src/lib/lapack/zgesvd.f
deleted file mode 100644
index 7b238d8b..00000000
--- a/src/lib/lapack/zgesvd.f
+++ /dev/null
@@ -1,3602 +0,0 @@
- SUBROUTINE ZGESVD( JOBU, JOBVT, M, N, A, LDA, S, U, LDU, VT, LDVT,
- $ WORK, LWORK, RWORK, INFO )
-*
-* -- LAPACK driver routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- CHARACTER JOBU, JOBVT
- INTEGER INFO, LDA, LDU, LDVT, LWORK, M, N
-* ..
-* .. Array Arguments ..
- DOUBLE PRECISION RWORK( * ), S( * )
- COMPLEX*16 A( LDA, * ), U( LDU, * ), VT( LDVT, * ),
- $ WORK( * )
-* ..
-*
-* Purpose
-* =======
-*
-* ZGESVD computes the singular value decomposition (SVD) of a complex
-* M-by-N matrix A, optionally computing the left and/or right singular
-* vectors. The SVD is written
-*
-* A = U * SIGMA * conjugate-transpose(V)
-*
-* where SIGMA is an M-by-N matrix which is zero except for its
-* min(m,n) diagonal elements, U is an M-by-M unitary matrix, and
-* V is an N-by-N unitary matrix. The diagonal elements of SIGMA
-* are the singular values of A; they are real and non-negative, and
-* are returned in descending order. The first min(m,n) columns of
-* U and V are the left and right singular vectors of A.
-*
-* Note that the routine returns V**H, not V.
-*
-* Arguments
-* =========
-*
-* JOBU (input) CHARACTER*1
-* Specifies options for computing all or part of the matrix U:
-* = 'A': all M columns of U are returned in array U:
-* = 'S': the first min(m,n) columns of U (the left singular
-* vectors) are returned in the array U;
-* = 'O': the first min(m,n) columns of U (the left singular
-* vectors) are overwritten on the array A;
-* = 'N': no columns of U (no left singular vectors) are
-* computed.
-*
-* JOBVT (input) CHARACTER*1
-* Specifies options for computing all or part of the matrix
-* V**H:
-* = 'A': all N rows of V**H are returned in the array VT;
-* = 'S': the first min(m,n) rows of V**H (the right singular
-* vectors) are returned in the array VT;
-* = 'O': the first min(m,n) rows of V**H (the right singular
-* vectors) are overwritten on the array A;
-* = 'N': no rows of V**H (no right singular vectors) are
-* computed.
-*
-* JOBVT and JOBU cannot both be 'O'.
-*
-* M (input) INTEGER
-* The number of rows of the input matrix A. M >= 0.
-*
-* N (input) INTEGER
-* The number of columns of the input matrix A. N >= 0.
-*
-* A (input/output) COMPLEX*16 array, dimension (LDA,N)
-* On entry, the M-by-N matrix A.
-* On exit,
-* if JOBU = 'O', A is overwritten with the first min(m,n)
-* columns of U (the left singular vectors,
-* stored columnwise);
-* if JOBVT = 'O', A is overwritten with the first min(m,n)
-* rows of V**H (the right singular vectors,
-* stored rowwise);
-* if JOBU .ne. 'O' and JOBVT .ne. 'O', the contents of A
-* are destroyed.
-*
-* LDA (input) INTEGER
-* The leading dimension of the array A. LDA >= max(1,M).
-*
-* S (output) DOUBLE PRECISION array, dimension (min(M,N))
-* The singular values of A, sorted so that S(i) >= S(i+1).
-*
-* U (output) COMPLEX*16 array, dimension (LDU,UCOL)
-* (LDU,M) if JOBU = 'A' or (LDU,min(M,N)) if JOBU = 'S'.
-* If JOBU = 'A', U contains the M-by-M unitary matrix U;
-* if JOBU = 'S', U contains the first min(m,n) columns of U
-* (the left singular vectors, stored columnwise);
-* if JOBU = 'N' or 'O', U is not referenced.
-*
-* LDU (input) INTEGER
-* The leading dimension of the array U. LDU >= 1; if
-* JOBU = 'S' or 'A', LDU >= M.
-*
-* VT (output) COMPLEX*16 array, dimension (LDVT,N)
-* If JOBVT = 'A', VT contains the N-by-N unitary matrix
-* V**H;
-* if JOBVT = 'S', VT contains the first min(m,n) rows of
-* V**H (the right singular vectors, stored rowwise);
-* if JOBVT = 'N' or 'O', VT is not referenced.
-*
-* LDVT (input) INTEGER
-* The leading dimension of the array VT. LDVT >= 1; if
-* JOBVT = 'A', LDVT >= N; if JOBVT = 'S', LDVT >= min(M,N).
-*
-* WORK (workspace/output) COMPLEX*16 array, dimension (MAX(1,LWORK))
-* On exit, if INFO = 0, WORK(1) returns the optimal LWORK.
-*
-* LWORK (input) INTEGER
-* The dimension of the array WORK.
-* LWORK >= MAX(1,2*MIN(M,N)+MAX(M,N)).
-* For good performance, LWORK should generally be larger.
-*
-* If LWORK = -1, then a workspace query is assumed; the routine
-* only calculates the optimal size of the WORK array, returns
-* this value as the first entry of the WORK array, and no error
-* message related to LWORK is issued by XERBLA.
-*
-* RWORK (workspace) DOUBLE PRECISION array, dimension (5*min(M,N))
-* On exit, if INFO > 0, RWORK(1:MIN(M,N)-1) contains the
-* unconverged superdiagonal elements of an upper bidiagonal
-* matrix B whose diagonal is in S (not necessarily sorted).
-* B satisfies A = U * B * VT, so it has the same singular
-* values as A, and singular vectors related by U and VT.
-*
-* INFO (output) INTEGER
-* = 0: successful exit.
-* < 0: if INFO = -i, the i-th argument had an illegal value.
-* > 0: if ZBDSQR did not converge, INFO specifies how many
-* superdiagonals of an intermediate bidiagonal form B
-* did not converge to zero. See the description of RWORK
-* above for details.
-*
-* =====================================================================
-*
-* .. Parameters ..
- COMPLEX*16 CZERO, CONE
- PARAMETER ( CZERO = ( 0.0D0, 0.0D0 ),
- $ CONE = ( 1.0D0, 0.0D0 ) )
- DOUBLE PRECISION ZERO, ONE
- PARAMETER ( ZERO = 0.0D0, ONE = 1.0D0 )
-* ..
-* .. Local Scalars ..
- LOGICAL LQUERY, WNTUA, WNTUAS, WNTUN, WNTUO, WNTUS,
- $ WNTVA, WNTVAS, WNTVN, WNTVO, WNTVS
- INTEGER BLK, CHUNK, I, IE, IERR, IR, IRWORK, ISCL,
- $ ITAU, ITAUP, ITAUQ, IU, IWORK, LDWRKR, LDWRKU,
- $ MAXWRK, MINMN, MINWRK, MNTHR, NCU, NCVT, NRU,
- $ NRVT, WRKBL
- DOUBLE PRECISION ANRM, BIGNUM, EPS, SMLNUM
-* ..
-* .. Local Arrays ..
- DOUBLE PRECISION DUM( 1 )
- COMPLEX*16 CDUM( 1 )
-* ..
-* .. External Subroutines ..
- EXTERNAL DLASCL, XERBLA, ZBDSQR, ZGEBRD, ZGELQF, ZGEMM,
- $ ZGEQRF, ZLACPY, ZLASCL, ZLASET, ZUNGBR, ZUNGLQ,
- $ ZUNGQR, ZUNMBR
-* ..
-* .. External Functions ..
- LOGICAL LSAME
- INTEGER ILAENV
- DOUBLE PRECISION DLAMCH, ZLANGE
- EXTERNAL LSAME, ILAENV, DLAMCH, ZLANGE
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC MAX, MIN, SQRT
-* ..
-* .. Executable Statements ..
-*
-* Test the input arguments
-*
- INFO = 0
- MINMN = MIN( M, N )
- WNTUA = LSAME( JOBU, 'A' )
- WNTUS = LSAME( JOBU, 'S' )
- WNTUAS = WNTUA .OR. WNTUS
- WNTUO = LSAME( JOBU, 'O' )
- WNTUN = LSAME( JOBU, 'N' )
- WNTVA = LSAME( JOBVT, 'A' )
- WNTVS = LSAME( JOBVT, 'S' )
- WNTVAS = WNTVA .OR. WNTVS
- WNTVO = LSAME( JOBVT, 'O' )
- WNTVN = LSAME( JOBVT, 'N' )
- LQUERY = ( LWORK.EQ.-1 )
-*
- IF( .NOT.( WNTUA .OR. WNTUS .OR. WNTUO .OR. WNTUN ) ) THEN
- INFO = -1
- ELSE IF( .NOT.( WNTVA .OR. WNTVS .OR. WNTVO .OR. WNTVN ) .OR.
- $ ( WNTVO .AND. WNTUO ) ) THEN
- INFO = -2
- ELSE IF( M.LT.0 ) THEN
- INFO = -3
- ELSE IF( N.LT.0 ) THEN
- INFO = -4
- ELSE IF( LDA.LT.MAX( 1, M ) ) THEN
- INFO = -6
- ELSE IF( LDU.LT.1 .OR. ( WNTUAS .AND. LDU.LT.M ) ) THEN
- INFO = -9
- ELSE IF( LDVT.LT.1 .OR. ( WNTVA .AND. LDVT.LT.N ) .OR.
- $ ( WNTVS .AND. LDVT.LT.MINMN ) ) THEN
- INFO = -11
- END IF
-*
-* Compute workspace
-* (Note: Comments in the code beginning "Workspace:" describe the
-* minimal amount of workspace needed at that point in the code,
-* as well as the preferred amount for good performance.
-* CWorkspace refers to complex workspace, and RWorkspace to
-* real workspace. NB refers to the optimal block size for the
-* immediately following subroutine, as returned by ILAENV.)
-*
- IF( INFO.EQ.0 ) THEN
- MINWRK = 1
- MAXWRK = 1
- IF( M.GE.N .AND. MINMN.GT.0 ) THEN
-*
-* Space needed for ZBDSQR is BDSPAC = 5*N
-*
- MNTHR = ILAENV( 6, 'ZGESVD', JOBU // JOBVT, M, N, 0, 0 )
- IF( M.GE.MNTHR ) THEN
- IF( WNTUN ) THEN
-*
-* Path 1 (M much larger than N, JOBU='N')
-*
- MAXWRK = N + N*ILAENV( 1, 'ZGEQRF', ' ', M, N, -1,
- $ -1 )
- MAXWRK = MAX( MAXWRK, 2*N+2*N*
- $ ILAENV( 1, 'ZGEBRD', ' ', N, N, -1, -1 ) )
- IF( WNTVO .OR. WNTVAS )
- $ MAXWRK = MAX( MAXWRK, 2*N+( N-1 )*
- $ ILAENV( 1, 'ZUNGBR', 'P', N, N, N, -1 ) )
- MINWRK = 3*N
- ELSE IF( WNTUO .AND. WNTVN ) THEN
-*
-* Path 2 (M much larger than N, JOBU='O', JOBVT='N')
-*
- WRKBL = N + N*ILAENV( 1, 'ZGEQRF', ' ', M, N, -1, -1 )
- WRKBL = MAX( WRKBL, N+N*ILAENV( 1, 'ZUNGQR', ' ', M,
- $ N, N, -1 ) )
- WRKBL = MAX( WRKBL, 2*N+2*N*
- $ ILAENV( 1, 'ZGEBRD', ' ', N, N, -1, -1 ) )
- WRKBL = MAX( WRKBL, 2*N+N*
- $ ILAENV( 1, 'ZUNGBR', 'Q', N, N, N, -1 ) )
- MAXWRK = MAX( N*N+WRKBL, N*N+M*N )
- MINWRK = 2*N + M
- ELSE IF( WNTUO .AND. WNTVAS ) THEN
-*
-* Path 3 (M much larger than N, JOBU='O', JOBVT='S' or
-* 'A')
-*
- WRKBL = N + N*ILAENV( 1, 'ZGEQRF', ' ', M, N, -1, -1 )
- WRKBL = MAX( WRKBL, N+N*ILAENV( 1, 'ZUNGQR', ' ', M,
- $ N, N, -1 ) )
- WRKBL = MAX( WRKBL, 2*N+2*N*
- $ ILAENV( 1, 'ZGEBRD', ' ', N, N, -1, -1 ) )
- WRKBL = MAX( WRKBL, 2*N+N*
- $ ILAENV( 1, 'ZUNGBR', 'Q', N, N, N, -1 ) )
- WRKBL = MAX( WRKBL, 2*N+( N-1 )*
- $ ILAENV( 1, 'ZUNGBR', 'P', N, N, N, -1 ) )
- MAXWRK = MAX( N*N+WRKBL, N*N+M*N )
- MINWRK = 2*N + M
- ELSE IF( WNTUS .AND. WNTVN ) THEN
-*
-* Path 4 (M much larger than N, JOBU='S', JOBVT='N')
-*
- WRKBL = N + N*ILAENV( 1, 'ZGEQRF', ' ', M, N, -1, -1 )
- WRKBL = MAX( WRKBL, N+N*ILAENV( 1, 'ZUNGQR', ' ', M,
- $ N, N, -1 ) )
- WRKBL = MAX( WRKBL, 2*N+2*N*
- $ ILAENV( 1, 'ZGEBRD', ' ', N, N, -1, -1 ) )
- WRKBL = MAX( WRKBL, 2*N+N*
- $ ILAENV( 1, 'ZUNGBR', 'Q', N, N, N, -1 ) )
- MAXWRK = N*N + WRKBL
- MINWRK = 2*N + M
- ELSE IF( WNTUS .AND. WNTVO ) THEN
-*
-* Path 5 (M much larger than N, JOBU='S', JOBVT='O')
-*
- WRKBL = N + N*ILAENV( 1, 'ZGEQRF', ' ', M, N, -1, -1 )
- WRKBL = MAX( WRKBL, N+N*ILAENV( 1, 'ZUNGQR', ' ', M,
- $ N, N, -1 ) )
- WRKBL = MAX( WRKBL, 2*N+2*N*
- $ ILAENV( 1, 'ZGEBRD', ' ', N, N, -1, -1 ) )
- WRKBL = MAX( WRKBL, 2*N+N*
- $ ILAENV( 1, 'ZUNGBR', 'Q', N, N, N, -1 ) )
- WRKBL = MAX( WRKBL, 2*N+( N-1 )*
- $ ILAENV( 1, 'ZUNGBR', 'P', N, N, N, -1 ) )
- MAXWRK = 2*N*N + WRKBL
- MINWRK = 2*N + M
- ELSE IF( WNTUS .AND. WNTVAS ) THEN
-*
-* Path 6 (M much larger than N, JOBU='S', JOBVT='S' or
-* 'A')
-*
- WRKBL = N + N*ILAENV( 1, 'ZGEQRF', ' ', M, N, -1, -1 )
- WRKBL = MAX( WRKBL, N+N*ILAENV( 1, 'ZUNGQR', ' ', M,
- $ N, N, -1 ) )
- WRKBL = MAX( WRKBL, 2*N+2*N*
- $ ILAENV( 1, 'ZGEBRD', ' ', N, N, -1, -1 ) )
- WRKBL = MAX( WRKBL, 2*N+N*
- $ ILAENV( 1, 'ZUNGBR', 'Q', N, N, N, -1 ) )
- WRKBL = MAX( WRKBL, 2*N+( N-1 )*
- $ ILAENV( 1, 'ZUNGBR', 'P', N, N, N, -1 ) )
- MAXWRK = N*N + WRKBL
- MINWRK = 2*N + M
- ELSE IF( WNTUA .AND. WNTVN ) THEN
-*
-* Path 7 (M much larger than N, JOBU='A', JOBVT='N')
-*
- WRKBL = N + N*ILAENV( 1, 'ZGEQRF', ' ', M, N, -1, -1 )
- WRKBL = MAX( WRKBL, N+M*ILAENV( 1, 'ZUNGQR', ' ', M,
- $ M, N, -1 ) )
- WRKBL = MAX( WRKBL, 2*N+2*N*
- $ ILAENV( 1, 'ZGEBRD', ' ', N, N, -1, -1 ) )
- WRKBL = MAX( WRKBL, 2*N+N*
- $ ILAENV( 1, 'ZUNGBR', 'Q', N, N, N, -1 ) )
- MAXWRK = N*N + WRKBL
- MINWRK = 2*N + M
- ELSE IF( WNTUA .AND. WNTVO ) THEN
-*
-* Path 8 (M much larger than N, JOBU='A', JOBVT='O')
-*
- WRKBL = N + N*ILAENV( 1, 'ZGEQRF', ' ', M, N, -1, -1 )
- WRKBL = MAX( WRKBL, N+M*ILAENV( 1, 'ZUNGQR', ' ', M,
- $ M, N, -1 ) )
- WRKBL = MAX( WRKBL, 2*N+2*N*
- $ ILAENV( 1, 'ZGEBRD', ' ', N, N, -1, -1 ) )
- WRKBL = MAX( WRKBL, 2*N+N*
- $ ILAENV( 1, 'ZUNGBR', 'Q', N, N, N, -1 ) )
- WRKBL = MAX( WRKBL, 2*N+( N-1 )*
- $ ILAENV( 1, 'ZUNGBR', 'P', N, N, N, -1 ) )
- MAXWRK = 2*N*N + WRKBL
- MINWRK = 2*N + M
- ELSE IF( WNTUA .AND. WNTVAS ) THEN
-*
-* Path 9 (M much larger than N, JOBU='A', JOBVT='S' or
-* 'A')
-*
- WRKBL = N + N*ILAENV( 1, 'ZGEQRF', ' ', M, N, -1, -1 )
- WRKBL = MAX( WRKBL, N+M*ILAENV( 1, 'ZUNGQR', ' ', M,
- $ M, N, -1 ) )
- WRKBL = MAX( WRKBL, 2*N+2*N*
- $ ILAENV( 1, 'ZGEBRD', ' ', N, N, -1, -1 ) )
- WRKBL = MAX( WRKBL, 2*N+N*
- $ ILAENV( 1, 'ZUNGBR', 'Q', N, N, N, -1 ) )
- WRKBL = MAX( WRKBL, 2*N+( N-1 )*
- $ ILAENV( 1, 'ZUNGBR', 'P', N, N, N, -1 ) )
- MAXWRK = N*N + WRKBL
- MINWRK = 2*N + M
- END IF
- ELSE
-*
-* Path 10 (M at least N, but not much larger)
-*
- MAXWRK = 2*N + ( M+N )*ILAENV( 1, 'ZGEBRD', ' ', M, N,
- $ -1, -1 )
- IF( WNTUS .OR. WNTUO )
- $ MAXWRK = MAX( MAXWRK, 2*N+N*
- $ ILAENV( 1, 'ZUNGBR', 'Q', M, N, N, -1 ) )
- IF( WNTUA )
- $ MAXWRK = MAX( MAXWRK, 2*N+M*
- $ ILAENV( 1, 'ZUNGBR', 'Q', M, M, N, -1 ) )
- IF( .NOT.WNTVN )
- $ MAXWRK = MAX( MAXWRK, 2*N+( N-1 )*
- $ ILAENV( 1, 'ZUNGBR', 'P', N, N, N, -1 ) )
- MINWRK = 2*N + M
- END IF
- ELSE IF( MINMN.GT.0 ) THEN
-*
-* Space needed for ZBDSQR is BDSPAC = 5*M
-*
- MNTHR = ILAENV( 6, 'ZGESVD', JOBU // JOBVT, M, N, 0, 0 )
- IF( N.GE.MNTHR ) THEN
- IF( WNTVN ) THEN
-*
-* Path 1t(N much larger than M, JOBVT='N')
-*
- MAXWRK = M + M*ILAENV( 1, 'ZGELQF', ' ', M, N, -1,
- $ -1 )
- MAXWRK = MAX( MAXWRK, 2*M+2*M*
- $ ILAENV( 1, 'ZGEBRD', ' ', M, M, -1, -1 ) )
- IF( WNTUO .OR. WNTUAS )
- $ MAXWRK = MAX( MAXWRK, 2*M+M*
- $ ILAENV( 1, 'ZUNGBR', 'Q', M, M, M, -1 ) )
- MINWRK = 3*M
- ELSE IF( WNTVO .AND. WNTUN ) THEN
-*
-* Path 2t(N much larger than M, JOBU='N', JOBVT='O')
-*
- WRKBL = M + M*ILAENV( 1, 'ZGELQF', ' ', M, N, -1, -1 )
- WRKBL = MAX( WRKBL, M+M*ILAENV( 1, 'ZUNGLQ', ' ', M,
- $ N, M, -1 ) )
- WRKBL = MAX( WRKBL, 2*M+2*M*
- $ ILAENV( 1, 'ZGEBRD', ' ', M, M, -1, -1 ) )
- WRKBL = MAX( WRKBL, 2*M+( M-1 )*
- $ ILAENV( 1, 'ZUNGBR', 'P', M, M, M, -1 ) )
- MAXWRK = MAX( M*M+WRKBL, M*M+M*N )
- MINWRK = 2*M + N
- ELSE IF( WNTVO .AND. WNTUAS ) THEN
-*
-* Path 3t(N much larger than M, JOBU='S' or 'A',
-* JOBVT='O')
-*
- WRKBL = M + M*ILAENV( 1, 'ZGELQF', ' ', M, N, -1, -1 )
- WRKBL = MAX( WRKBL, M+M*ILAENV( 1, 'ZUNGLQ', ' ', M,
- $ N, M, -1 ) )
- WRKBL = MAX( WRKBL, 2*M+2*M*
- $ ILAENV( 1, 'ZGEBRD', ' ', M, M, -1, -1 ) )
- WRKBL = MAX( WRKBL, 2*M+( M-1 )*
- $ ILAENV( 1, 'ZUNGBR', 'P', M, M, M, -1 ) )
- WRKBL = MAX( WRKBL, 2*M+M*
- $ ILAENV( 1, 'ZUNGBR', 'Q', M, M, M, -1 ) )
- MAXWRK = MAX( M*M+WRKBL, M*M+M*N )
- MINWRK = 2*M + N
- ELSE IF( WNTVS .AND. WNTUN ) THEN
-*
-* Path 4t(N much larger than M, JOBU='N', JOBVT='S')
-*
- WRKBL = M + M*ILAENV( 1, 'ZGELQF', ' ', M, N, -1, -1 )
- WRKBL = MAX( WRKBL, M+M*ILAENV( 1, 'ZUNGLQ', ' ', M,
- $ N, M, -1 ) )
- WRKBL = MAX( WRKBL, 2*M+2*M*
- $ ILAENV( 1, 'ZGEBRD', ' ', M, M, -1, -1 ) )
- WRKBL = MAX( WRKBL, 2*M+( M-1 )*
- $ ILAENV( 1, 'ZUNGBR', 'P', M, M, M, -1 ) )
- MAXWRK = M*M + WRKBL
- MINWRK = 2*M + N
- ELSE IF( WNTVS .AND. WNTUO ) THEN
-*
-* Path 5t(N much larger than M, JOBU='O', JOBVT='S')
-*
- WRKBL = M + M*ILAENV( 1, 'ZGELQF', ' ', M, N, -1, -1 )
- WRKBL = MAX( WRKBL, M+M*ILAENV( 1, 'ZUNGLQ', ' ', M,
- $ N, M, -1 ) )
- WRKBL = MAX( WRKBL, 2*M+2*M*
- $ ILAENV( 1, 'ZGEBRD', ' ', M, M, -1, -1 ) )
- WRKBL = MAX( WRKBL, 2*M+( M-1 )*
- $ ILAENV( 1, 'ZUNGBR', 'P', M, M, M, -1 ) )
- WRKBL = MAX( WRKBL, 2*M+M*
- $ ILAENV( 1, 'ZUNGBR', 'Q', M, M, M, -1 ) )
- MAXWRK = 2*M*M + WRKBL
- MINWRK = 2*M + N
- ELSE IF( WNTVS .AND. WNTUAS ) THEN
-*
-* Path 6t(N much larger than M, JOBU='S' or 'A',
-* JOBVT='S')
-*
- WRKBL = M + M*ILAENV( 1, 'ZGELQF', ' ', M, N, -1, -1 )
- WRKBL = MAX( WRKBL, M+M*ILAENV( 1, 'ZUNGLQ', ' ', M,
- $ N, M, -1 ) )
- WRKBL = MAX( WRKBL, 2*M+2*M*
- $ ILAENV( 1, 'ZGEBRD', ' ', M, M, -1, -1 ) )
- WRKBL = MAX( WRKBL, 2*M+( M-1 )*
- $ ILAENV( 1, 'ZUNGBR', 'P', M, M, M, -1 ) )
- WRKBL = MAX( WRKBL, 2*M+M*
- $ ILAENV( 1, 'ZUNGBR', 'Q', M, M, M, -1 ) )
- MAXWRK = M*M + WRKBL
- MINWRK = 2*M + N
- ELSE IF( WNTVA .AND. WNTUN ) THEN
-*
-* Path 7t(N much larger than M, JOBU='N', JOBVT='A')
-*
- WRKBL = M + M*ILAENV( 1, 'ZGELQF', ' ', M, N, -1, -1 )
- WRKBL = MAX( WRKBL, M+N*ILAENV( 1, 'ZUNGLQ', ' ', N,
- $ N, M, -1 ) )
- WRKBL = MAX( WRKBL, 2*M+2*M*
- $ ILAENV( 1, 'ZGEBRD', ' ', M, M, -1, -1 ) )
- WRKBL = MAX( WRKBL, 2*M+( M-1 )*
- $ ILAENV( 1, 'ZUNGBR', 'P', M, M, M, -1 ) )
- MAXWRK = M*M + WRKBL
- MINWRK = 2*M + N
- ELSE IF( WNTVA .AND. WNTUO ) THEN
-*
-* Path 8t(N much larger than M, JOBU='O', JOBVT='A')
-*
- WRKBL = M + M*ILAENV( 1, 'ZGELQF', ' ', M, N, -1, -1 )
- WRKBL = MAX( WRKBL, M+N*ILAENV( 1, 'ZUNGLQ', ' ', N,
- $ N, M, -1 ) )
- WRKBL = MAX( WRKBL, 2*M+2*M*
- $ ILAENV( 1, 'ZGEBRD', ' ', M, M, -1, -1 ) )
- WRKBL = MAX( WRKBL, 2*M+( M-1 )*
- $ ILAENV( 1, 'ZUNGBR', 'P', M, M, M, -1 ) )
- WRKBL = MAX( WRKBL, 2*M+M*
- $ ILAENV( 1, 'ZUNGBR', 'Q', M, M, M, -1 ) )
- MAXWRK = 2*M*M + WRKBL
- MINWRK = 2*M + N
- ELSE IF( WNTVA .AND. WNTUAS ) THEN
-*
-* Path 9t(N much larger than M, JOBU='S' or 'A',
-* JOBVT='A')
-*
- WRKBL = M + M*ILAENV( 1, 'ZGELQF', ' ', M, N, -1, -1 )
- WRKBL = MAX( WRKBL, M+N*ILAENV( 1, 'ZUNGLQ', ' ', N,
- $ N, M, -1 ) )
- WRKBL = MAX( WRKBL, 2*M+2*M*
- $ ILAENV( 1, 'ZGEBRD', ' ', M, M, -1, -1 ) )
- WRKBL = MAX( WRKBL, 2*M+( M-1 )*
- $ ILAENV( 1, 'ZUNGBR', 'P', M, M, M, -1 ) )
- WRKBL = MAX( WRKBL, 2*M+M*
- $ ILAENV( 1, 'ZUNGBR', 'Q', M, M, M, -1 ) )
- MAXWRK = M*M + WRKBL
- MINWRK = 2*M + N
- END IF
- ELSE
-*
-* Path 10t(N greater than M, but not much larger)
-*
- MAXWRK = 2*M + ( M+N )*ILAENV( 1, 'ZGEBRD', ' ', M, N,
- $ -1, -1 )
- IF( WNTVS .OR. WNTVO )
- $ MAXWRK = MAX( MAXWRK, 2*M+M*
- $ ILAENV( 1, 'ZUNGBR', 'P', M, N, M, -1 ) )
- IF( WNTVA )
- $ MAXWRK = MAX( MAXWRK, 2*M+N*
- $ ILAENV( 1, 'ZUNGBR', 'P', N, N, M, -1 ) )
- IF( .NOT.WNTUN )
- $ MAXWRK = MAX( MAXWRK, 2*M+( M-1 )*
- $ ILAENV( 1, 'ZUNGBR', 'Q', M, M, M, -1 ) )
- MINWRK = 2*M + N
- END IF
- END IF
- MAXWRK = MAX( MAXWRK, MINWRK )
- WORK( 1 ) = MAXWRK
-*
- IF( LWORK.LT.MINWRK .AND. .NOT.LQUERY ) THEN
- INFO = -13
- END IF
- END IF
-*
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'ZGESVD', -INFO )
- RETURN
- ELSE IF( LQUERY ) THEN
- RETURN
- END IF
-*
-* Quick return if possible
-*
- IF( M.EQ.0 .OR. N.EQ.0 ) THEN
- RETURN
- END IF
-*
-* Get machine constants
-*
- EPS = DLAMCH( 'P' )
- SMLNUM = SQRT( DLAMCH( 'S' ) ) / EPS
- BIGNUM = ONE / SMLNUM
-*
-* Scale A if max element outside range [SMLNUM,BIGNUM]
-*
- ANRM = ZLANGE( 'M', M, N, A, LDA, DUM )
- ISCL = 0
- IF( ANRM.GT.ZERO .AND. ANRM.LT.SMLNUM ) THEN
- ISCL = 1
- CALL ZLASCL( 'G', 0, 0, ANRM, SMLNUM, M, N, A, LDA, IERR )
- ELSE IF( ANRM.GT.BIGNUM ) THEN
- ISCL = 1
- CALL ZLASCL( 'G', 0, 0, ANRM, BIGNUM, M, N, A, LDA, IERR )
- END IF
-*
- IF( M.GE.N ) THEN
-*
-* A has at least as many rows as columns. If A has sufficiently
-* more rows than columns, first reduce using the QR
-* decomposition (if sufficient workspace available)
-*
- IF( M.GE.MNTHR ) THEN
-*
- IF( WNTUN ) THEN
-*
-* Path 1 (M much larger than N, JOBU='N')
-* No left singular vectors to be computed
-*
- ITAU = 1
- IWORK = ITAU + N
-*
-* Compute A=Q*R
-* (CWorkspace: need 2*N, prefer N+N*NB)
-* (RWorkspace: need 0)
-*
- CALL ZGEQRF( M, N, A, LDA, WORK( ITAU ), WORK( IWORK ),
- $ LWORK-IWORK+1, IERR )
-*
-* Zero out below R
-*
- CALL ZLASET( 'L', N-1, N-1, CZERO, CZERO, A( 2, 1 ),
- $ LDA )
- IE = 1
- ITAUQ = 1
- ITAUP = ITAUQ + N
- IWORK = ITAUP + N
-*
-* Bidiagonalize R in A
-* (CWorkspace: need 3*N, prefer 2*N+2*N*NB)
-* (RWorkspace: need N)
-*
- CALL ZGEBRD( N, N, A, LDA, S, RWORK( IE ), WORK( ITAUQ ),
- $ WORK( ITAUP ), WORK( IWORK ), LWORK-IWORK+1,
- $ IERR )
- NCVT = 0
- IF( WNTVO .OR. WNTVAS ) THEN
-*
-* If right singular vectors desired, generate P'.
-* (CWorkspace: need 3*N-1, prefer 2*N+(N-1)*NB)
-* (RWorkspace: 0)
-*
- CALL ZUNGBR( 'P', N, N, N, A, LDA, WORK( ITAUP ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
- NCVT = N
- END IF
- IRWORK = IE + N
-*
-* Perform bidiagonal QR iteration, computing right
-* singular vectors of A in A if desired
-* (CWorkspace: 0)
-* (RWorkspace: need BDSPAC)
-*
- CALL ZBDSQR( 'U', N, NCVT, 0, 0, S, RWORK( IE ), A, LDA,
- $ CDUM, 1, CDUM, 1, RWORK( IRWORK ), INFO )
-*
-* If right singular vectors desired in VT, copy them there
-*
- IF( WNTVAS )
- $ CALL ZLACPY( 'F', N, N, A, LDA, VT, LDVT )
-*
- ELSE IF( WNTUO .AND. WNTVN ) THEN
-*
-* Path 2 (M much larger than N, JOBU='O', JOBVT='N')
-* N left singular vectors to be overwritten on A and
-* no right singular vectors to be computed
-*
- IF( LWORK.GE.N*N+3*N ) THEN
-*
-* Sufficient workspace for a fast algorithm
-*
- IR = 1
- IF( LWORK.GE.MAX( WRKBL, LDA*N )+LDA*N ) THEN
-*
-* WORK(IU) is LDA by N, WORK(IR) is LDA by N
-*
- LDWRKU = LDA
- LDWRKR = LDA
- ELSE IF( LWORK.GE.MAX( WRKBL, LDA*N )+N*N ) THEN
-*
-* WORK(IU) is LDA by N, WORK(IR) is N by N
-*
- LDWRKU = LDA
- LDWRKR = N
- ELSE
-*
-* WORK(IU) is LDWRKU by N, WORK(IR) is N by N
-*
- LDWRKU = ( LWORK-N*N ) / N
- LDWRKR = N
- END IF
- ITAU = IR + LDWRKR*N
- IWORK = ITAU + N
-*
-* Compute A=Q*R
-* (CWorkspace: need N*N+2*N, prefer N*N+N+N*NB)
-* (RWorkspace: 0)
-*
- CALL ZGEQRF( M, N, A, LDA, WORK( ITAU ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
-*
-* Copy R to WORK(IR) and zero out below it
-*
- CALL ZLACPY( 'U', N, N, A, LDA, WORK( IR ), LDWRKR )
- CALL ZLASET( 'L', N-1, N-1, CZERO, CZERO,
- $ WORK( IR+1 ), LDWRKR )
-*
-* Generate Q in A
-* (CWorkspace: need N*N+2*N, prefer N*N+N+N*NB)
-* (RWorkspace: 0)
-*
- CALL ZUNGQR( M, N, N, A, LDA, WORK( ITAU ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
- IE = 1
- ITAUQ = ITAU
- ITAUP = ITAUQ + N
- IWORK = ITAUP + N
-*
-* Bidiagonalize R in WORK(IR)
-* (CWorkspace: need N*N+3*N, prefer N*N+2*N+2*N*NB)
-* (RWorkspace: need N)
-*
- CALL ZGEBRD( N, N, WORK( IR ), LDWRKR, S, RWORK( IE ),
- $ WORK( ITAUQ ), WORK( ITAUP ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
-*
-* Generate left vectors bidiagonalizing R
-* (CWorkspace: need N*N+3*N, prefer N*N+2*N+N*NB)
-* (RWorkspace: need 0)
-*
- CALL ZUNGBR( 'Q', N, N, N, WORK( IR ), LDWRKR,
- $ WORK( ITAUQ ), WORK( IWORK ),
- $ LWORK-IWORK+1, IERR )
- IRWORK = IE + N
-*
-* Perform bidiagonal QR iteration, computing left
-* singular vectors of R in WORK(IR)
-* (CWorkspace: need N*N)
-* (RWorkspace: need BDSPAC)
-*
- CALL ZBDSQR( 'U', N, 0, N, 0, S, RWORK( IE ), CDUM, 1,
- $ WORK( IR ), LDWRKR, CDUM, 1,
- $ RWORK( IRWORK ), INFO )
- IU = ITAUQ
-*
-* Multiply Q in A by left singular vectors of R in
-* WORK(IR), storing result in WORK(IU) and copying to A
-* (CWorkspace: need N*N+N, prefer N*N+M*N)
-* (RWorkspace: 0)
-*
- DO 10 I = 1, M, LDWRKU
- CHUNK = MIN( M-I+1, LDWRKU )
- CALL ZGEMM( 'N', 'N', CHUNK, N, N, CONE, A( I, 1 ),
- $ LDA, WORK( IR ), LDWRKR, CZERO,
- $ WORK( IU ), LDWRKU )
- CALL ZLACPY( 'F', CHUNK, N, WORK( IU ), LDWRKU,
- $ A( I, 1 ), LDA )
- 10 CONTINUE
-*
- ELSE
-*
-* Insufficient workspace for a fast algorithm
-*
- IE = 1
- ITAUQ = 1
- ITAUP = ITAUQ + N
- IWORK = ITAUP + N
-*
-* Bidiagonalize A
-* (CWorkspace: need 2*N+M, prefer 2*N+(M+N)*NB)
-* (RWorkspace: N)
-*
- CALL ZGEBRD( M, N, A, LDA, S, RWORK( IE ),
- $ WORK( ITAUQ ), WORK( ITAUP ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
-*
-* Generate left vectors bidiagonalizing A
-* (CWorkspace: need 3*N, prefer 2*N+N*NB)
-* (RWorkspace: 0)
-*
- CALL ZUNGBR( 'Q', M, N, N, A, LDA, WORK( ITAUQ ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
- IRWORK = IE + N
-*
-* Perform bidiagonal QR iteration, computing left
-* singular vectors of A in A
-* (CWorkspace: need 0)
-* (RWorkspace: need BDSPAC)
-*
- CALL ZBDSQR( 'U', N, 0, M, 0, S, RWORK( IE ), CDUM, 1,
- $ A, LDA, CDUM, 1, RWORK( IRWORK ), INFO )
-*
- END IF
-*
- ELSE IF( WNTUO .AND. WNTVAS ) THEN
-*
-* Path 3 (M much larger than N, JOBU='O', JOBVT='S' or 'A')
-* N left singular vectors to be overwritten on A and
-* N right singular vectors to be computed in VT
-*
- IF( LWORK.GE.N*N+3*N ) THEN
-*
-* Sufficient workspace for a fast algorithm
-*
- IR = 1
- IF( LWORK.GE.MAX( WRKBL, LDA*N )+LDA*N ) THEN
-*
-* WORK(IU) is LDA by N and WORK(IR) is LDA by N
-*
- LDWRKU = LDA
- LDWRKR = LDA
- ELSE IF( LWORK.GE.MAX( WRKBL, LDA*N )+N*N ) THEN
-*
-* WORK(IU) is LDA by N and WORK(IR) is N by N
-*
- LDWRKU = LDA
- LDWRKR = N
- ELSE
-*
-* WORK(IU) is LDWRKU by N and WORK(IR) is N by N
-*
- LDWRKU = ( LWORK-N*N ) / N
- LDWRKR = N
- END IF
- ITAU = IR + LDWRKR*N
- IWORK = ITAU + N
-*
-* Compute A=Q*R
-* (CWorkspace: need N*N+2*N, prefer N*N+N+N*NB)
-* (RWorkspace: 0)
-*
- CALL ZGEQRF( M, N, A, LDA, WORK( ITAU ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
-*
-* Copy R to VT, zeroing out below it
-*
- CALL ZLACPY( 'U', N, N, A, LDA, VT, LDVT )
- IF( N.GT.1 )
- $ CALL ZLASET( 'L', N-1, N-1, CZERO, CZERO,
- $ VT( 2, 1 ), LDVT )
-*
-* Generate Q in A
-* (CWorkspace: need N*N+2*N, prefer N*N+N+N*NB)
-* (RWorkspace: 0)
-*
- CALL ZUNGQR( M, N, N, A, LDA, WORK( ITAU ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
- IE = 1
- ITAUQ = ITAU
- ITAUP = ITAUQ + N
- IWORK = ITAUP + N
-*
-* Bidiagonalize R in VT, copying result to WORK(IR)
-* (CWorkspace: need N*N+3*N, prefer N*N+2*N+2*N*NB)
-* (RWorkspace: need N)
-*
- CALL ZGEBRD( N, N, VT, LDVT, S, RWORK( IE ),
- $ WORK( ITAUQ ), WORK( ITAUP ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
- CALL ZLACPY( 'L', N, N, VT, LDVT, WORK( IR ), LDWRKR )
-*
-* Generate left vectors bidiagonalizing R in WORK(IR)
-* (CWorkspace: need N*N+3*N, prefer N*N+2*N+N*NB)
-* (RWorkspace: 0)
-*
- CALL ZUNGBR( 'Q', N, N, N, WORK( IR ), LDWRKR,
- $ WORK( ITAUQ ), WORK( IWORK ),
- $ LWORK-IWORK+1, IERR )
-*
-* Generate right vectors bidiagonalizing R in VT
-* (CWorkspace: need N*N+3*N-1, prefer N*N+2*N+(N-1)*NB)
-* (RWorkspace: 0)
-*
- CALL ZUNGBR( 'P', N, N, N, VT, LDVT, WORK( ITAUP ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
- IRWORK = IE + N
-*
-* Perform bidiagonal QR iteration, computing left
-* singular vectors of R in WORK(IR) and computing right
-* singular vectors of R in VT
-* (CWorkspace: need N*N)
-* (RWorkspace: need BDSPAC)
-*
- CALL ZBDSQR( 'U', N, N, N, 0, S, RWORK( IE ), VT,
- $ LDVT, WORK( IR ), LDWRKR, CDUM, 1,
- $ RWORK( IRWORK ), INFO )
- IU = ITAUQ
-*
-* Multiply Q in A by left singular vectors of R in
-* WORK(IR), storing result in WORK(IU) and copying to A
-* (CWorkspace: need N*N+N, prefer N*N+M*N)
-* (RWorkspace: 0)
-*
- DO 20 I = 1, M, LDWRKU
- CHUNK = MIN( M-I+1, LDWRKU )
- CALL ZGEMM( 'N', 'N', CHUNK, N, N, CONE, A( I, 1 ),
- $ LDA, WORK( IR ), LDWRKR, CZERO,
- $ WORK( IU ), LDWRKU )
- CALL ZLACPY( 'F', CHUNK, N, WORK( IU ), LDWRKU,
- $ A( I, 1 ), LDA )
- 20 CONTINUE
-*
- ELSE
-*
-* Insufficient workspace for a fast algorithm
-*
- ITAU = 1
- IWORK = ITAU + N
-*
-* Compute A=Q*R
-* (CWorkspace: need 2*N, prefer N+N*NB)
-* (RWorkspace: 0)
-*
- CALL ZGEQRF( M, N, A, LDA, WORK( ITAU ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
-*
-* Copy R to VT, zeroing out below it
-*
- CALL ZLACPY( 'U', N, N, A, LDA, VT, LDVT )
- IF( N.GT.1 )
- $ CALL ZLASET( 'L', N-1, N-1, CZERO, CZERO,
- $ VT( 2, 1 ), LDVT )
-*
-* Generate Q in A
-* (CWorkspace: need 2*N, prefer N+N*NB)
-* (RWorkspace: 0)
-*
- CALL ZUNGQR( M, N, N, A, LDA, WORK( ITAU ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
- IE = 1
- ITAUQ = ITAU
- ITAUP = ITAUQ + N
- IWORK = ITAUP + N
-*
-* Bidiagonalize R in VT
-* (CWorkspace: need 3*N, prefer 2*N+2*N*NB)
-* (RWorkspace: N)
-*
- CALL ZGEBRD( N, N, VT, LDVT, S, RWORK( IE ),
- $ WORK( ITAUQ ), WORK( ITAUP ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
-*
-* Multiply Q in A by left vectors bidiagonalizing R
-* (CWorkspace: need 2*N+M, prefer 2*N+M*NB)
-* (RWorkspace: 0)
-*
- CALL ZUNMBR( 'Q', 'R', 'N', M, N, N, VT, LDVT,
- $ WORK( ITAUQ ), A, LDA, WORK( IWORK ),
- $ LWORK-IWORK+1, IERR )
-*
-* Generate right vectors bidiagonalizing R in VT
-* (CWorkspace: need 3*N-1, prefer 2*N+(N-1)*NB)
-* (RWorkspace: 0)
-*
- CALL ZUNGBR( 'P', N, N, N, VT, LDVT, WORK( ITAUP ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
- IRWORK = IE + N
-*
-* Perform bidiagonal QR iteration, computing left
-* singular vectors of A in A and computing right
-* singular vectors of A in VT
-* (CWorkspace: 0)
-* (RWorkspace: need BDSPAC)
-*
- CALL ZBDSQR( 'U', N, N, M, 0, S, RWORK( IE ), VT,
- $ LDVT, A, LDA, CDUM, 1, RWORK( IRWORK ),
- $ INFO )
-*
- END IF
-*
- ELSE IF( WNTUS ) THEN
-*
- IF( WNTVN ) THEN
-*
-* Path 4 (M much larger than N, JOBU='S', JOBVT='N')
-* N left singular vectors to be computed in U and
-* no right singular vectors to be computed
-*
- IF( LWORK.GE.N*N+3*N ) THEN
-*
-* Sufficient workspace for a fast algorithm
-*
- IR = 1
- IF( LWORK.GE.WRKBL+LDA*N ) THEN
-*
-* WORK(IR) is LDA by N
-*
- LDWRKR = LDA
- ELSE
-*
-* WORK(IR) is N by N
-*
- LDWRKR = N
- END IF
- ITAU = IR + LDWRKR*N
- IWORK = ITAU + N
-*
-* Compute A=Q*R
-* (CWorkspace: need N*N+2*N, prefer N*N+N+N*NB)
-* (RWorkspace: 0)
-*
- CALL ZGEQRF( M, N, A, LDA, WORK( ITAU ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
-*
-* Copy R to WORK(IR), zeroing out below it
-*
- CALL ZLACPY( 'U', N, N, A, LDA, WORK( IR ),
- $ LDWRKR )
- CALL ZLASET( 'L', N-1, N-1, CZERO, CZERO,
- $ WORK( IR+1 ), LDWRKR )
-*
-* Generate Q in A
-* (CWorkspace: need N*N+2*N, prefer N*N+N+N*NB)
-* (RWorkspace: 0)
-*
- CALL ZUNGQR( M, N, N, A, LDA, WORK( ITAU ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
- IE = 1
- ITAUQ = ITAU
- ITAUP = ITAUQ + N
- IWORK = ITAUP + N
-*
-* Bidiagonalize R in WORK(IR)
-* (CWorkspace: need N*N+3*N, prefer N*N+2*N+2*N*NB)
-* (RWorkspace: need N)
-*
- CALL ZGEBRD( N, N, WORK( IR ), LDWRKR, S,
- $ RWORK( IE ), WORK( ITAUQ ),
- $ WORK( ITAUP ), WORK( IWORK ),
- $ LWORK-IWORK+1, IERR )
-*
-* Generate left vectors bidiagonalizing R in WORK(IR)
-* (CWorkspace: need N*N+3*N, prefer N*N+2*N+N*NB)
-* (RWorkspace: 0)
-*
- CALL ZUNGBR( 'Q', N, N, N, WORK( IR ), LDWRKR,
- $ WORK( ITAUQ ), WORK( IWORK ),
- $ LWORK-IWORK+1, IERR )
- IRWORK = IE + N
-*
-* Perform bidiagonal QR iteration, computing left
-* singular vectors of R in WORK(IR)
-* (CWorkspace: need N*N)
-* (RWorkspace: need BDSPAC)
-*
- CALL ZBDSQR( 'U', N, 0, N, 0, S, RWORK( IE ), CDUM,
- $ 1, WORK( IR ), LDWRKR, CDUM, 1,
- $ RWORK( IRWORK ), INFO )
-*
-* Multiply Q in A by left singular vectors of R in
-* WORK(IR), storing result in U
-* (CWorkspace: need N*N)
-* (RWorkspace: 0)
-*
- CALL ZGEMM( 'N', 'N', M, N, N, CONE, A, LDA,
- $ WORK( IR ), LDWRKR, CZERO, U, LDU )
-*
- ELSE
-*
-* Insufficient workspace for a fast algorithm
-*
- ITAU = 1
- IWORK = ITAU + N
-*
-* Compute A=Q*R, copying result to U
-* (CWorkspace: need 2*N, prefer N+N*NB)
-* (RWorkspace: 0)
-*
- CALL ZGEQRF( M, N, A, LDA, WORK( ITAU ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
- CALL ZLACPY( 'L', M, N, A, LDA, U, LDU )
-*
-* Generate Q in U
-* (CWorkspace: need 2*N, prefer N+N*NB)
-* (RWorkspace: 0)
-*
- CALL ZUNGQR( M, N, N, U, LDU, WORK( ITAU ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
- IE = 1
- ITAUQ = ITAU
- ITAUP = ITAUQ + N
- IWORK = ITAUP + N
-*
-* Zero out below R in A
-*
- CALL ZLASET( 'L', N-1, N-1, CZERO, CZERO,
- $ A( 2, 1 ), LDA )
-*
-* Bidiagonalize R in A
-* (CWorkspace: need 3*N, prefer 2*N+2*N*NB)
-* (RWorkspace: need N)
-*
- CALL ZGEBRD( N, N, A, LDA, S, RWORK( IE ),
- $ WORK( ITAUQ ), WORK( ITAUP ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
-*
-* Multiply Q in U by left vectors bidiagonalizing R
-* (CWorkspace: need 2*N+M, prefer 2*N+M*NB)
-* (RWorkspace: 0)
-*
- CALL ZUNMBR( 'Q', 'R', 'N', M, N, N, A, LDA,
- $ WORK( ITAUQ ), U, LDU, WORK( IWORK ),
- $ LWORK-IWORK+1, IERR )
- IRWORK = IE + N
-*
-* Perform bidiagonal QR iteration, computing left
-* singular vectors of A in U
-* (CWorkspace: 0)
-* (RWorkspace: need BDSPAC)
-*
- CALL ZBDSQR( 'U', N, 0, M, 0, S, RWORK( IE ), CDUM,
- $ 1, U, LDU, CDUM, 1, RWORK( IRWORK ),
- $ INFO )
-*
- END IF
-*
- ELSE IF( WNTVO ) THEN
-*
-* Path 5 (M much larger than N, JOBU='S', JOBVT='O')
-* N left singular vectors to be computed in U and
-* N right singular vectors to be overwritten on A
-*
- IF( LWORK.GE.2*N*N+3*N ) THEN
-*
-* Sufficient workspace for a fast algorithm
-*
- IU = 1
- IF( LWORK.GE.WRKBL+2*LDA*N ) THEN
-*
-* WORK(IU) is LDA by N and WORK(IR) is LDA by N
-*
- LDWRKU = LDA
- IR = IU + LDWRKU*N
- LDWRKR = LDA
- ELSE IF( LWORK.GE.WRKBL+( LDA+N )*N ) THEN
-*
-* WORK(IU) is LDA by N and WORK(IR) is N by N
-*
- LDWRKU = LDA
- IR = IU + LDWRKU*N
- LDWRKR = N
- ELSE
-*
-* WORK(IU) is N by N and WORK(IR) is N by N
-*
- LDWRKU = N
- IR = IU + LDWRKU*N
- LDWRKR = N
- END IF
- ITAU = IR + LDWRKR*N
- IWORK = ITAU + N
-*
-* Compute A=Q*R
-* (CWorkspace: need 2*N*N+2*N, prefer 2*N*N+N+N*NB)
-* (RWorkspace: 0)
-*
- CALL ZGEQRF( M, N, A, LDA, WORK( ITAU ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
-*
-* Copy R to WORK(IU), zeroing out below it
-*
- CALL ZLACPY( 'U', N, N, A, LDA, WORK( IU ),
- $ LDWRKU )
- CALL ZLASET( 'L', N-1, N-1, CZERO, CZERO,
- $ WORK( IU+1 ), LDWRKU )
-*
-* Generate Q in A
-* (CWorkspace: need 2*N*N+2*N, prefer 2*N*N+N+N*NB)
-* (RWorkspace: 0)
-*
- CALL ZUNGQR( M, N, N, A, LDA, WORK( ITAU ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
- IE = 1
- ITAUQ = ITAU
- ITAUP = ITAUQ + N
- IWORK = ITAUP + N
-*
-* Bidiagonalize R in WORK(IU), copying result to
-* WORK(IR)
-* (CWorkspace: need 2*N*N+3*N,
-* prefer 2*N*N+2*N+2*N*NB)
-* (RWorkspace: need N)
-*
- CALL ZGEBRD( N, N, WORK( IU ), LDWRKU, S,
- $ RWORK( IE ), WORK( ITAUQ ),
- $ WORK( ITAUP ), WORK( IWORK ),
- $ LWORK-IWORK+1, IERR )
- CALL ZLACPY( 'U', N, N, WORK( IU ), LDWRKU,
- $ WORK( IR ), LDWRKR )
-*
-* Generate left bidiagonalizing vectors in WORK(IU)
-* (CWorkspace: need 2*N*N+3*N, prefer 2*N*N+2*N+N*NB)
-* (RWorkspace: 0)
-*
- CALL ZUNGBR( 'Q', N, N, N, WORK( IU ), LDWRKU,
- $ WORK( ITAUQ ), WORK( IWORK ),
- $ LWORK-IWORK+1, IERR )
-*
-* Generate right bidiagonalizing vectors in WORK(IR)
-* (CWorkspace: need 2*N*N+3*N-1,
-* prefer 2*N*N+2*N+(N-1)*NB)
-* (RWorkspace: 0)
-*
- CALL ZUNGBR( 'P', N, N, N, WORK( IR ), LDWRKR,
- $ WORK( ITAUP ), WORK( IWORK ),
- $ LWORK-IWORK+1, IERR )
- IRWORK = IE + N
-*
-* Perform bidiagonal QR iteration, computing left
-* singular vectors of R in WORK(IU) and computing
-* right singular vectors of R in WORK(IR)
-* (CWorkspace: need 2*N*N)
-* (RWorkspace: need BDSPAC)
-*
- CALL ZBDSQR( 'U', N, N, N, 0, S, RWORK( IE ),
- $ WORK( IR ), LDWRKR, WORK( IU ),
- $ LDWRKU, CDUM, 1, RWORK( IRWORK ),
- $ INFO )
-*
-* Multiply Q in A by left singular vectors of R in
-* WORK(IU), storing result in U
-* (CWorkspace: need N*N)
-* (RWorkspace: 0)
-*
- CALL ZGEMM( 'N', 'N', M, N, N, CONE, A, LDA,
- $ WORK( IU ), LDWRKU, CZERO, U, LDU )
-*
-* Copy right singular vectors of R to A
-* (CWorkspace: need N*N)
-* (RWorkspace: 0)
-*
- CALL ZLACPY( 'F', N, N, WORK( IR ), LDWRKR, A,
- $ LDA )
-*
- ELSE
-*
-* Insufficient workspace for a fast algorithm
-*
- ITAU = 1
- IWORK = ITAU + N
-*
-* Compute A=Q*R, copying result to U
-* (CWorkspace: need 2*N, prefer N+N*NB)
-* (RWorkspace: 0)
-*
- CALL ZGEQRF( M, N, A, LDA, WORK( ITAU ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
- CALL ZLACPY( 'L', M, N, A, LDA, U, LDU )
-*
-* Generate Q in U
-* (CWorkspace: need 2*N, prefer N+N*NB)
-* (RWorkspace: 0)
-*
- CALL ZUNGQR( M, N, N, U, LDU, WORK( ITAU ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
- IE = 1
- ITAUQ = ITAU
- ITAUP = ITAUQ + N
- IWORK = ITAUP + N
-*
-* Zero out below R in A
-*
- CALL ZLASET( 'L', N-1, N-1, CZERO, CZERO,
- $ A( 2, 1 ), LDA )
-*
-* Bidiagonalize R in A
-* (CWorkspace: need 3*N, prefer 2*N+2*N*NB)
-* (RWorkspace: need N)
-*
- CALL ZGEBRD( N, N, A, LDA, S, RWORK( IE ),
- $ WORK( ITAUQ ), WORK( ITAUP ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
-*
-* Multiply Q in U by left vectors bidiagonalizing R
-* (CWorkspace: need 2*N+M, prefer 2*N+M*NB)
-* (RWorkspace: 0)
-*
- CALL ZUNMBR( 'Q', 'R', 'N', M, N, N, A, LDA,
- $ WORK( ITAUQ ), U, LDU, WORK( IWORK ),
- $ LWORK-IWORK+1, IERR )
-*
-* Generate right vectors bidiagonalizing R in A
-* (CWorkspace: need 3*N-1, prefer 2*N+(N-1)*NB)
-* (RWorkspace: 0)
-*
- CALL ZUNGBR( 'P', N, N, N, A, LDA, WORK( ITAUP ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
- IRWORK = IE + N
-*
-* Perform bidiagonal QR iteration, computing left
-* singular vectors of A in U and computing right
-* singular vectors of A in A
-* (CWorkspace: 0)
-* (RWorkspace: need BDSPAC)
-*
- CALL ZBDSQR( 'U', N, N, M, 0, S, RWORK( IE ), A,
- $ LDA, U, LDU, CDUM, 1, RWORK( IRWORK ),
- $ INFO )
-*
- END IF
-*
- ELSE IF( WNTVAS ) THEN
-*
-* Path 6 (M much larger than N, JOBU='S', JOBVT='S'
-* or 'A')
-* N left singular vectors to be computed in U and
-* N right singular vectors to be computed in VT
-*
- IF( LWORK.GE.N*N+3*N ) THEN
-*
-* Sufficient workspace for a fast algorithm
-*
- IU = 1
- IF( LWORK.GE.WRKBL+LDA*N ) THEN
-*
-* WORK(IU) is LDA by N
-*
- LDWRKU = LDA
- ELSE
-*
-* WORK(IU) is N by N
-*
- LDWRKU = N
- END IF
- ITAU = IU + LDWRKU*N
- IWORK = ITAU + N
-*
-* Compute A=Q*R
-* (CWorkspace: need N*N+2*N, prefer N*N+N+N*NB)
-* (RWorkspace: 0)
-*
- CALL ZGEQRF( M, N, A, LDA, WORK( ITAU ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
-*
-* Copy R to WORK(IU), zeroing out below it
-*
- CALL ZLACPY( 'U', N, N, A, LDA, WORK( IU ),
- $ LDWRKU )
- CALL ZLASET( 'L', N-1, N-1, CZERO, CZERO,
- $ WORK( IU+1 ), LDWRKU )
-*
-* Generate Q in A
-* (CWorkspace: need N*N+2*N, prefer N*N+N+N*NB)
-* (RWorkspace: 0)
-*
- CALL ZUNGQR( M, N, N, A, LDA, WORK( ITAU ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
- IE = 1
- ITAUQ = ITAU
- ITAUP = ITAUQ + N
- IWORK = ITAUP + N
-*
-* Bidiagonalize R in WORK(IU), copying result to VT
-* (CWorkspace: need N*N+3*N, prefer N*N+2*N+2*N*NB)
-* (RWorkspace: need N)
-*
- CALL ZGEBRD( N, N, WORK( IU ), LDWRKU, S,
- $ RWORK( IE ), WORK( ITAUQ ),
- $ WORK( ITAUP ), WORK( IWORK ),
- $ LWORK-IWORK+1, IERR )
- CALL ZLACPY( 'U', N, N, WORK( IU ), LDWRKU, VT,
- $ LDVT )
-*
-* Generate left bidiagonalizing vectors in WORK(IU)
-* (CWorkspace: need N*N+3*N, prefer N*N+2*N+N*NB)
-* (RWorkspace: 0)
-*
- CALL ZUNGBR( 'Q', N, N, N, WORK( IU ), LDWRKU,
- $ WORK( ITAUQ ), WORK( IWORK ),
- $ LWORK-IWORK+1, IERR )
-*
-* Generate right bidiagonalizing vectors in VT
-* (CWorkspace: need N*N+3*N-1,
-* prefer N*N+2*N+(N-1)*NB)
-* (RWorkspace: 0)
-*
- CALL ZUNGBR( 'P', N, N, N, VT, LDVT, WORK( ITAUP ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
- IRWORK = IE + N
-*
-* Perform bidiagonal QR iteration, computing left
-* singular vectors of R in WORK(IU) and computing
-* right singular vectors of R in VT
-* (CWorkspace: need N*N)
-* (RWorkspace: need BDSPAC)
-*
- CALL ZBDSQR( 'U', N, N, N, 0, S, RWORK( IE ), VT,
- $ LDVT, WORK( IU ), LDWRKU, CDUM, 1,
- $ RWORK( IRWORK ), INFO )
-*
-* Multiply Q in A by left singular vectors of R in
-* WORK(IU), storing result in U
-* (CWorkspace: need N*N)
-* (RWorkspace: 0)
-*
- CALL ZGEMM( 'N', 'N', M, N, N, CONE, A, LDA,
- $ WORK( IU ), LDWRKU, CZERO, U, LDU )
-*
- ELSE
-*
-* Insufficient workspace for a fast algorithm
-*
- ITAU = 1
- IWORK = ITAU + N
-*
-* Compute A=Q*R, copying result to U
-* (CWorkspace: need 2*N, prefer N+N*NB)
-* (RWorkspace: 0)
-*
- CALL ZGEQRF( M, N, A, LDA, WORK( ITAU ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
- CALL ZLACPY( 'L', M, N, A, LDA, U, LDU )
-*
-* Generate Q in U
-* (CWorkspace: need 2*N, prefer N+N*NB)
-* (RWorkspace: 0)
-*
- CALL ZUNGQR( M, N, N, U, LDU, WORK( ITAU ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
-*
-* Copy R to VT, zeroing out below it
-*
- CALL ZLACPY( 'U', N, N, A, LDA, VT, LDVT )
- IF( N.GT.1 )
- $ CALL ZLASET( 'L', N-1, N-1, CZERO, CZERO,
- $ VT( 2, 1 ), LDVT )
- IE = 1
- ITAUQ = ITAU
- ITAUP = ITAUQ + N
- IWORK = ITAUP + N
-*
-* Bidiagonalize R in VT
-* (CWorkspace: need 3*N, prefer 2*N+2*N*NB)
-* (RWorkspace: need N)
-*
- CALL ZGEBRD( N, N, VT, LDVT, S, RWORK( IE ),
- $ WORK( ITAUQ ), WORK( ITAUP ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
-*
-* Multiply Q in U by left bidiagonalizing vectors
-* in VT
-* (CWorkspace: need 2*N+M, prefer 2*N+M*NB)
-* (RWorkspace: 0)
-*
- CALL ZUNMBR( 'Q', 'R', 'N', M, N, N, VT, LDVT,
- $ WORK( ITAUQ ), U, LDU, WORK( IWORK ),
- $ LWORK-IWORK+1, IERR )
-*
-* Generate right bidiagonalizing vectors in VT
-* (CWorkspace: need 3*N-1, prefer 2*N+(N-1)*NB)
-* (RWorkspace: 0)
-*
- CALL ZUNGBR( 'P', N, N, N, VT, LDVT, WORK( ITAUP ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
- IRWORK = IE + N
-*
-* Perform bidiagonal QR iteration, computing left
-* singular vectors of A in U and computing right
-* singular vectors of A in VT
-* (CWorkspace: 0)
-* (RWorkspace: need BDSPAC)
-*
- CALL ZBDSQR( 'U', N, N, M, 0, S, RWORK( IE ), VT,
- $ LDVT, U, LDU, CDUM, 1,
- $ RWORK( IRWORK ), INFO )
-*
- END IF
-*
- END IF
-*
- ELSE IF( WNTUA ) THEN
-*
- IF( WNTVN ) THEN
-*
-* Path 7 (M much larger than N, JOBU='A', JOBVT='N')
-* M left singular vectors to be computed in U and
-* no right singular vectors to be computed
-*
- IF( LWORK.GE.N*N+MAX( N+M, 3*N ) ) THEN
-*
-* Sufficient workspace for a fast algorithm
-*
- IR = 1
- IF( LWORK.GE.WRKBL+LDA*N ) THEN
-*
-* WORK(IR) is LDA by N
-*
- LDWRKR = LDA
- ELSE
-*
-* WORK(IR) is N by N
-*
- LDWRKR = N
- END IF
- ITAU = IR + LDWRKR*N
- IWORK = ITAU + N
-*
-* Compute A=Q*R, copying result to U
-* (CWorkspace: need N*N+2*N, prefer N*N+N+N*NB)
-* (RWorkspace: 0)
-*
- CALL ZGEQRF( M, N, A, LDA, WORK( ITAU ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
- CALL ZLACPY( 'L', M, N, A, LDA, U, LDU )
-*
-* Copy R to WORK(IR), zeroing out below it
-*
- CALL ZLACPY( 'U', N, N, A, LDA, WORK( IR ),
- $ LDWRKR )
- CALL ZLASET( 'L', N-1, N-1, CZERO, CZERO,
- $ WORK( IR+1 ), LDWRKR )
-*
-* Generate Q in U
-* (CWorkspace: need N*N+N+M, prefer N*N+N+M*NB)
-* (RWorkspace: 0)
-*
- CALL ZUNGQR( M, M, N, U, LDU, WORK( ITAU ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
- IE = 1
- ITAUQ = ITAU
- ITAUP = ITAUQ + N
- IWORK = ITAUP + N
-*
-* Bidiagonalize R in WORK(IR)
-* (CWorkspace: need N*N+3*N, prefer N*N+2*N+2*N*NB)
-* (RWorkspace: need N)
-*
- CALL ZGEBRD( N, N, WORK( IR ), LDWRKR, S,
- $ RWORK( IE ), WORK( ITAUQ ),
- $ WORK( ITAUP ), WORK( IWORK ),
- $ LWORK-IWORK+1, IERR )
-*
-* Generate left bidiagonalizing vectors in WORK(IR)
-* (CWorkspace: need N*N+3*N, prefer N*N+2*N+N*NB)
-* (RWorkspace: 0)
-*
- CALL ZUNGBR( 'Q', N, N, N, WORK( IR ), LDWRKR,
- $ WORK( ITAUQ ), WORK( IWORK ),
- $ LWORK-IWORK+1, IERR )
- IRWORK = IE + N
-*
-* Perform bidiagonal QR iteration, computing left
-* singular vectors of R in WORK(IR)
-* (CWorkspace: need N*N)
-* (RWorkspace: need BDSPAC)
-*
- CALL ZBDSQR( 'U', N, 0, N, 0, S, RWORK( IE ), CDUM,
- $ 1, WORK( IR ), LDWRKR, CDUM, 1,
- $ RWORK( IRWORK ), INFO )
-*
-* Multiply Q in U by left singular vectors of R in
-* WORK(IR), storing result in A
-* (CWorkspace: need N*N)
-* (RWorkspace: 0)
-*
- CALL ZGEMM( 'N', 'N', M, N, N, CONE, U, LDU,
- $ WORK( IR ), LDWRKR, CZERO, A, LDA )
-*
-* Copy left singular vectors of A from A to U
-*
- CALL ZLACPY( 'F', M, N, A, LDA, U, LDU )
-*
- ELSE
-*
-* Insufficient workspace for a fast algorithm
-*
- ITAU = 1
- IWORK = ITAU + N
-*
-* Compute A=Q*R, copying result to U
-* (CWorkspace: need 2*N, prefer N+N*NB)
-* (RWorkspace: 0)
-*
- CALL ZGEQRF( M, N, A, LDA, WORK( ITAU ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
- CALL ZLACPY( 'L', M, N, A, LDA, U, LDU )
-*
-* Generate Q in U
-* (CWorkspace: need N+M, prefer N+M*NB)
-* (RWorkspace: 0)
-*
- CALL ZUNGQR( M, M, N, U, LDU, WORK( ITAU ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
- IE = 1
- ITAUQ = ITAU
- ITAUP = ITAUQ + N
- IWORK = ITAUP + N
-*
-* Zero out below R in A
-*
- CALL ZLASET( 'L', N-1, N-1, CZERO, CZERO,
- $ A( 2, 1 ), LDA )
-*
-* Bidiagonalize R in A
-* (CWorkspace: need 3*N, prefer 2*N+2*N*NB)
-* (RWorkspace: need N)
-*
- CALL ZGEBRD( N, N, A, LDA, S, RWORK( IE ),
- $ WORK( ITAUQ ), WORK( ITAUP ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
-*
-* Multiply Q in U by left bidiagonalizing vectors
-* in A
-* (CWorkspace: need 2*N+M, prefer 2*N+M*NB)
-* (RWorkspace: 0)
-*
- CALL ZUNMBR( 'Q', 'R', 'N', M, N, N, A, LDA,
- $ WORK( ITAUQ ), U, LDU, WORK( IWORK ),
- $ LWORK-IWORK+1, IERR )
- IRWORK = IE + N
-*
-* Perform bidiagonal QR iteration, computing left
-* singular vectors of A in U
-* (CWorkspace: 0)
-* (RWorkspace: need BDSPAC)
-*
- CALL ZBDSQR( 'U', N, 0, M, 0, S, RWORK( IE ), CDUM,
- $ 1, U, LDU, CDUM, 1, RWORK( IRWORK ),
- $ INFO )
-*
- END IF
-*
- ELSE IF( WNTVO ) THEN
-*
-* Path 8 (M much larger than N, JOBU='A', JOBVT='O')
-* M left singular vectors to be computed in U and
-* N right singular vectors to be overwritten on A
-*
- IF( LWORK.GE.2*N*N+MAX( N+M, 3*N ) ) THEN
-*
-* Sufficient workspace for a fast algorithm
-*
- IU = 1
- IF( LWORK.GE.WRKBL+2*LDA*N ) THEN
-*
-* WORK(IU) is LDA by N and WORK(IR) is LDA by N
-*
- LDWRKU = LDA
- IR = IU + LDWRKU*N
- LDWRKR = LDA
- ELSE IF( LWORK.GE.WRKBL+( LDA+N )*N ) THEN
-*
-* WORK(IU) is LDA by N and WORK(IR) is N by N
-*
- LDWRKU = LDA
- IR = IU + LDWRKU*N
- LDWRKR = N
- ELSE
-*
-* WORK(IU) is N by N and WORK(IR) is N by N
-*
- LDWRKU = N
- IR = IU + LDWRKU*N
- LDWRKR = N
- END IF
- ITAU = IR + LDWRKR*N
- IWORK = ITAU + N
-*
-* Compute A=Q*R, copying result to U
-* (CWorkspace: need 2*N*N+2*N, prefer 2*N*N+N+N*NB)
-* (RWorkspace: 0)
-*
- CALL ZGEQRF( M, N, A, LDA, WORK( ITAU ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
- CALL ZLACPY( 'L', M, N, A, LDA, U, LDU )
-*
-* Generate Q in U
-* (CWorkspace: need 2*N*N+N+M, prefer 2*N*N+N+M*NB)
-* (RWorkspace: 0)
-*
- CALL ZUNGQR( M, M, N, U, LDU, WORK( ITAU ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
-*
-* Copy R to WORK(IU), zeroing out below it
-*
- CALL ZLACPY( 'U', N, N, A, LDA, WORK( IU ),
- $ LDWRKU )
- CALL ZLASET( 'L', N-1, N-1, CZERO, CZERO,
- $ WORK( IU+1 ), LDWRKU )
- IE = 1
- ITAUQ = ITAU
- ITAUP = ITAUQ + N
- IWORK = ITAUP + N
-*
-* Bidiagonalize R in WORK(IU), copying result to
-* WORK(IR)
-* (CWorkspace: need 2*N*N+3*N,
-* prefer 2*N*N+2*N+2*N*NB)
-* (RWorkspace: need N)
-*
- CALL ZGEBRD( N, N, WORK( IU ), LDWRKU, S,
- $ RWORK( IE ), WORK( ITAUQ ),
- $ WORK( ITAUP ), WORK( IWORK ),
- $ LWORK-IWORK+1, IERR )
- CALL ZLACPY( 'U', N, N, WORK( IU ), LDWRKU,
- $ WORK( IR ), LDWRKR )
-*
-* Generate left bidiagonalizing vectors in WORK(IU)
-* (CWorkspace: need 2*N*N+3*N, prefer 2*N*N+2*N+N*NB)
-* (RWorkspace: 0)
-*
- CALL ZUNGBR( 'Q', N, N, N, WORK( IU ), LDWRKU,
- $ WORK( ITAUQ ), WORK( IWORK ),
- $ LWORK-IWORK+1, IERR )
-*
-* Generate right bidiagonalizing vectors in WORK(IR)
-* (CWorkspace: need 2*N*N+3*N-1,
-* prefer 2*N*N+2*N+(N-1)*NB)
-* (RWorkspace: 0)
-*
- CALL ZUNGBR( 'P', N, N, N, WORK( IR ), LDWRKR,
- $ WORK( ITAUP ), WORK( IWORK ),
- $ LWORK-IWORK+1, IERR )
- IRWORK = IE + N
-*
-* Perform bidiagonal QR iteration, computing left
-* singular vectors of R in WORK(IU) and computing
-* right singular vectors of R in WORK(IR)
-* (CWorkspace: need 2*N*N)
-* (RWorkspace: need BDSPAC)
-*
- CALL ZBDSQR( 'U', N, N, N, 0, S, RWORK( IE ),
- $ WORK( IR ), LDWRKR, WORK( IU ),
- $ LDWRKU, CDUM, 1, RWORK( IRWORK ),
- $ INFO )
-*
-* Multiply Q in U by left singular vectors of R in
-* WORK(IU), storing result in A
-* (CWorkspace: need N*N)
-* (RWorkspace: 0)
-*
- CALL ZGEMM( 'N', 'N', M, N, N, CONE, U, LDU,
- $ WORK( IU ), LDWRKU, CZERO, A, LDA )
-*
-* Copy left singular vectors of A from A to U
-*
- CALL ZLACPY( 'F', M, N, A, LDA, U, LDU )
-*
-* Copy right singular vectors of R from WORK(IR) to A
-*
- CALL ZLACPY( 'F', N, N, WORK( IR ), LDWRKR, A,
- $ LDA )
-*
- ELSE
-*
-* Insufficient workspace for a fast algorithm
-*
- ITAU = 1
- IWORK = ITAU + N
-*
-* Compute A=Q*R, copying result to U
-* (CWorkspace: need 2*N, prefer N+N*NB)
-* (RWorkspace: 0)
-*
- CALL ZGEQRF( M, N, A, LDA, WORK( ITAU ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
- CALL ZLACPY( 'L', M, N, A, LDA, U, LDU )
-*
-* Generate Q in U
-* (CWorkspace: need N+M, prefer N+M*NB)
-* (RWorkspace: 0)
-*
- CALL ZUNGQR( M, M, N, U, LDU, WORK( ITAU ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
- IE = 1
- ITAUQ = ITAU
- ITAUP = ITAUQ + N
- IWORK = ITAUP + N
-*
-* Zero out below R in A
-*
- CALL ZLASET( 'L', N-1, N-1, CZERO, CZERO,
- $ A( 2, 1 ), LDA )
-*
-* Bidiagonalize R in A
-* (CWorkspace: need 3*N, prefer 2*N+2*N*NB)
-* (RWorkspace: need N)
-*
- CALL ZGEBRD( N, N, A, LDA, S, RWORK( IE ),
- $ WORK( ITAUQ ), WORK( ITAUP ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
-*
-* Multiply Q in U by left bidiagonalizing vectors
-* in A
-* (CWorkspace: need 2*N+M, prefer 2*N+M*NB)
-* (RWorkspace: 0)
-*
- CALL ZUNMBR( 'Q', 'R', 'N', M, N, N, A, LDA,
- $ WORK( ITAUQ ), U, LDU, WORK( IWORK ),
- $ LWORK-IWORK+1, IERR )
-*
-* Generate right bidiagonalizing vectors in A
-* (CWorkspace: need 3*N-1, prefer 2*N+(N-1)*NB)
-* (RWorkspace: 0)
-*
- CALL ZUNGBR( 'P', N, N, N, A, LDA, WORK( ITAUP ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
- IRWORK = IE + N
-*
-* Perform bidiagonal QR iteration, computing left
-* singular vectors of A in U and computing right
-* singular vectors of A in A
-* (CWorkspace: 0)
-* (RWorkspace: need BDSPAC)
-*
- CALL ZBDSQR( 'U', N, N, M, 0, S, RWORK( IE ), A,
- $ LDA, U, LDU, CDUM, 1, RWORK( IRWORK ),
- $ INFO )
-*
- END IF
-*
- ELSE IF( WNTVAS ) THEN
-*
-* Path 9 (M much larger than N, JOBU='A', JOBVT='S'
-* or 'A')
-* M left singular vectors to be computed in U and
-* N right singular vectors to be computed in VT
-*
- IF( LWORK.GE.N*N+MAX( N+M, 3*N ) ) THEN
-*
-* Sufficient workspace for a fast algorithm
-*
- IU = 1
- IF( LWORK.GE.WRKBL+LDA*N ) THEN
-*
-* WORK(IU) is LDA by N
-*
- LDWRKU = LDA
- ELSE
-*
-* WORK(IU) is N by N
-*
- LDWRKU = N
- END IF
- ITAU = IU + LDWRKU*N
- IWORK = ITAU + N
-*
-* Compute A=Q*R, copying result to U
-* (CWorkspace: need N*N+2*N, prefer N*N+N+N*NB)
-* (RWorkspace: 0)
-*
- CALL ZGEQRF( M, N, A, LDA, WORK( ITAU ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
- CALL ZLACPY( 'L', M, N, A, LDA, U, LDU )
-*
-* Generate Q in U
-* (CWorkspace: need N*N+N+M, prefer N*N+N+M*NB)
-* (RWorkspace: 0)
-*
- CALL ZUNGQR( M, M, N, U, LDU, WORK( ITAU ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
-*
-* Copy R to WORK(IU), zeroing out below it
-*
- CALL ZLACPY( 'U', N, N, A, LDA, WORK( IU ),
- $ LDWRKU )
- CALL ZLASET( 'L', N-1, N-1, CZERO, CZERO,
- $ WORK( IU+1 ), LDWRKU )
- IE = 1
- ITAUQ = ITAU
- ITAUP = ITAUQ + N
- IWORK = ITAUP + N
-*
-* Bidiagonalize R in WORK(IU), copying result to VT
-* (CWorkspace: need N*N+3*N, prefer N*N+2*N+2*N*NB)
-* (RWorkspace: need N)
-*
- CALL ZGEBRD( N, N, WORK( IU ), LDWRKU, S,
- $ RWORK( IE ), WORK( ITAUQ ),
- $ WORK( ITAUP ), WORK( IWORK ),
- $ LWORK-IWORK+1, IERR )
- CALL ZLACPY( 'U', N, N, WORK( IU ), LDWRKU, VT,
- $ LDVT )
-*
-* Generate left bidiagonalizing vectors in WORK(IU)
-* (CWorkspace: need N*N+3*N, prefer N*N+2*N+N*NB)
-* (RWorkspace: 0)
-*
- CALL ZUNGBR( 'Q', N, N, N, WORK( IU ), LDWRKU,
- $ WORK( ITAUQ ), WORK( IWORK ),
- $ LWORK-IWORK+1, IERR )
-*
-* Generate right bidiagonalizing vectors in VT
-* (CWorkspace: need N*N+3*N-1,
-* prefer N*N+2*N+(N-1)*NB)
-* (RWorkspace: need 0)
-*
- CALL ZUNGBR( 'P', N, N, N, VT, LDVT, WORK( ITAUP ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
- IRWORK = IE + N
-*
-* Perform bidiagonal QR iteration, computing left
-* singular vectors of R in WORK(IU) and computing
-* right singular vectors of R in VT
-* (CWorkspace: need N*N)
-* (RWorkspace: need BDSPAC)
-*
- CALL ZBDSQR( 'U', N, N, N, 0, S, RWORK( IE ), VT,
- $ LDVT, WORK( IU ), LDWRKU, CDUM, 1,
- $ RWORK( IRWORK ), INFO )
-*
-* Multiply Q in U by left singular vectors of R in
-* WORK(IU), storing result in A
-* (CWorkspace: need N*N)
-* (RWorkspace: 0)
-*
- CALL ZGEMM( 'N', 'N', M, N, N, CONE, U, LDU,
- $ WORK( IU ), LDWRKU, CZERO, A, LDA )
-*
-* Copy left singular vectors of A from A to U
-*
- CALL ZLACPY( 'F', M, N, A, LDA, U, LDU )
-*
- ELSE
-*
-* Insufficient workspace for a fast algorithm
-*
- ITAU = 1
- IWORK = ITAU + N
-*
-* Compute A=Q*R, copying result to U
-* (CWorkspace: need 2*N, prefer N+N*NB)
-* (RWorkspace: 0)
-*
- CALL ZGEQRF( M, N, A, LDA, WORK( ITAU ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
- CALL ZLACPY( 'L', M, N, A, LDA, U, LDU )
-*
-* Generate Q in U
-* (CWorkspace: need N+M, prefer N+M*NB)
-* (RWorkspace: 0)
-*
- CALL ZUNGQR( M, M, N, U, LDU, WORK( ITAU ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
-*
-* Copy R from A to VT, zeroing out below it
-*
- CALL ZLACPY( 'U', N, N, A, LDA, VT, LDVT )
- IF( N.GT.1 )
- $ CALL ZLASET( 'L', N-1, N-1, CZERO, CZERO,
- $ VT( 2, 1 ), LDVT )
- IE = 1
- ITAUQ = ITAU
- ITAUP = ITAUQ + N
- IWORK = ITAUP + N
-*
-* Bidiagonalize R in VT
-* (CWorkspace: need 3*N, prefer 2*N+2*N*NB)
-* (RWorkspace: need N)
-*
- CALL ZGEBRD( N, N, VT, LDVT, S, RWORK( IE ),
- $ WORK( ITAUQ ), WORK( ITAUP ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
-*
-* Multiply Q in U by left bidiagonalizing vectors
-* in VT
-* (CWorkspace: need 2*N+M, prefer 2*N+M*NB)
-* (RWorkspace: 0)
-*
- CALL ZUNMBR( 'Q', 'R', 'N', M, N, N, VT, LDVT,
- $ WORK( ITAUQ ), U, LDU, WORK( IWORK ),
- $ LWORK-IWORK+1, IERR )
-*
-* Generate right bidiagonalizing vectors in VT
-* (CWorkspace: need 3*N-1, prefer 2*N+(N-1)*NB)
-* (RWorkspace: 0)
-*
- CALL ZUNGBR( 'P', N, N, N, VT, LDVT, WORK( ITAUP ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
- IRWORK = IE + N
-*
-* Perform bidiagonal QR iteration, computing left
-* singular vectors of A in U and computing right
-* singular vectors of A in VT
-* (CWorkspace: 0)
-* (RWorkspace: need BDSPAC)
-*
- CALL ZBDSQR( 'U', N, N, M, 0, S, RWORK( IE ), VT,
- $ LDVT, U, LDU, CDUM, 1,
- $ RWORK( IRWORK ), INFO )
-*
- END IF
-*
- END IF
-*
- END IF
-*
- ELSE
-*
-* M .LT. MNTHR
-*
-* Path 10 (M at least N, but not much larger)
-* Reduce to bidiagonal form without QR decomposition
-*
- IE = 1
- ITAUQ = 1
- ITAUP = ITAUQ + N
- IWORK = ITAUP + N
-*
-* Bidiagonalize A
-* (CWorkspace: need 2*N+M, prefer 2*N+(M+N)*NB)
-* (RWorkspace: need N)
-*
- CALL ZGEBRD( M, N, A, LDA, S, RWORK( IE ), WORK( ITAUQ ),
- $ WORK( ITAUP ), WORK( IWORK ), LWORK-IWORK+1,
- $ IERR )
- IF( WNTUAS ) THEN
-*
-* If left singular vectors desired in U, copy result to U
-* and generate left bidiagonalizing vectors in U
-* (CWorkspace: need 2*N+NCU, prefer 2*N+NCU*NB)
-* (RWorkspace: 0)
-*
- CALL ZLACPY( 'L', M, N, A, LDA, U, LDU )
- IF( WNTUS )
- $ NCU = N
- IF( WNTUA )
- $ NCU = M
- CALL ZUNGBR( 'Q', M, NCU, N, U, LDU, WORK( ITAUQ ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
- END IF
- IF( WNTVAS ) THEN
-*
-* If right singular vectors desired in VT, copy result to
-* VT and generate right bidiagonalizing vectors in VT
-* (CWorkspace: need 3*N-1, prefer 2*N+(N-1)*NB)
-* (RWorkspace: 0)
-*
- CALL ZLACPY( 'U', N, N, A, LDA, VT, LDVT )
- CALL ZUNGBR( 'P', N, N, N, VT, LDVT, WORK( ITAUP ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
- END IF
- IF( WNTUO ) THEN
-*
-* If left singular vectors desired in A, generate left
-* bidiagonalizing vectors in A
-* (CWorkspace: need 3*N, prefer 2*N+N*NB)
-* (RWorkspace: 0)
-*
- CALL ZUNGBR( 'Q', M, N, N, A, LDA, WORK( ITAUQ ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
- END IF
- IF( WNTVO ) THEN
-*
-* If right singular vectors desired in A, generate right
-* bidiagonalizing vectors in A
-* (CWorkspace: need 3*N-1, prefer 2*N+(N-1)*NB)
-* (RWorkspace: 0)
-*
- CALL ZUNGBR( 'P', N, N, N, A, LDA, WORK( ITAUP ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
- END IF
- IRWORK = IE + N
- IF( WNTUAS .OR. WNTUO )
- $ NRU = M
- IF( WNTUN )
- $ NRU = 0
- IF( WNTVAS .OR. WNTVO )
- $ NCVT = N
- IF( WNTVN )
- $ NCVT = 0
- IF( ( .NOT.WNTUO ) .AND. ( .NOT.WNTVO ) ) THEN
-*
-* Perform bidiagonal QR iteration, if desired, computing
-* left singular vectors in U and computing right singular
-* vectors in VT
-* (CWorkspace: 0)
-* (RWorkspace: need BDSPAC)
-*
- CALL ZBDSQR( 'U', N, NCVT, NRU, 0, S, RWORK( IE ), VT,
- $ LDVT, U, LDU, CDUM, 1, RWORK( IRWORK ),
- $ INFO )
- ELSE IF( ( .NOT.WNTUO ) .AND. WNTVO ) THEN
-*
-* Perform bidiagonal QR iteration, if desired, computing
-* left singular vectors in U and computing right singular
-* vectors in A
-* (CWorkspace: 0)
-* (RWorkspace: need BDSPAC)
-*
- CALL ZBDSQR( 'U', N, NCVT, NRU, 0, S, RWORK( IE ), A,
- $ LDA, U, LDU, CDUM, 1, RWORK( IRWORK ),
- $ INFO )
- ELSE
-*
-* Perform bidiagonal QR iteration, if desired, computing
-* left singular vectors in A and computing right singular
-* vectors in VT
-* (CWorkspace: 0)
-* (RWorkspace: need BDSPAC)
-*
- CALL ZBDSQR( 'U', N, NCVT, NRU, 0, S, RWORK( IE ), VT,
- $ LDVT, A, LDA, CDUM, 1, RWORK( IRWORK ),
- $ INFO )
- END IF
-*
- END IF
-*
- ELSE
-*
-* A has more columns than rows. If A has sufficiently more
-* columns than rows, first reduce using the LQ decomposition (if
-* sufficient workspace available)
-*
- IF( N.GE.MNTHR ) THEN
-*
- IF( WNTVN ) THEN
-*
-* Path 1t(N much larger than M, JOBVT='N')
-* No right singular vectors to be computed
-*
- ITAU = 1
- IWORK = ITAU + M
-*
-* Compute A=L*Q
-* (CWorkspace: need 2*M, prefer M+M*NB)
-* (RWorkspace: 0)
-*
- CALL ZGELQF( M, N, A, LDA, WORK( ITAU ), WORK( IWORK ),
- $ LWORK-IWORK+1, IERR )
-*
-* Zero out above L
-*
- CALL ZLASET( 'U', M-1, M-1, CZERO, CZERO, A( 1, 2 ),
- $ LDA )
- IE = 1
- ITAUQ = 1
- ITAUP = ITAUQ + M
- IWORK = ITAUP + M
-*
-* Bidiagonalize L in A
-* (CWorkspace: need 3*M, prefer 2*M+2*M*NB)
-* (RWorkspace: need M)
-*
- CALL ZGEBRD( M, M, A, LDA, S, RWORK( IE ), WORK( ITAUQ ),
- $ WORK( ITAUP ), WORK( IWORK ), LWORK-IWORK+1,
- $ IERR )
- IF( WNTUO .OR. WNTUAS ) THEN
-*
-* If left singular vectors desired, generate Q
-* (CWorkspace: need 3*M, prefer 2*M+M*NB)
-* (RWorkspace: 0)
-*
- CALL ZUNGBR( 'Q', M, M, M, A, LDA, WORK( ITAUQ ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
- END IF
- IRWORK = IE + M
- NRU = 0
- IF( WNTUO .OR. WNTUAS )
- $ NRU = M
-*
-* Perform bidiagonal QR iteration, computing left singular
-* vectors of A in A if desired
-* (CWorkspace: 0)
-* (RWorkspace: need BDSPAC)
-*
- CALL ZBDSQR( 'U', M, 0, NRU, 0, S, RWORK( IE ), CDUM, 1,
- $ A, LDA, CDUM, 1, RWORK( IRWORK ), INFO )
-*
-* If left singular vectors desired in U, copy them there
-*
- IF( WNTUAS )
- $ CALL ZLACPY( 'F', M, M, A, LDA, U, LDU )
-*
- ELSE IF( WNTVO .AND. WNTUN ) THEN
-*
-* Path 2t(N much larger than M, JOBU='N', JOBVT='O')
-* M right singular vectors to be overwritten on A and
-* no left singular vectors to be computed
-*
- IF( LWORK.GE.M*M+3*M ) THEN
-*
-* Sufficient workspace for a fast algorithm
-*
- IR = 1
- IF( LWORK.GE.MAX( WRKBL, LDA*N )+LDA*M ) THEN
-*
-* WORK(IU) is LDA by N and WORK(IR) is LDA by M
-*
- LDWRKU = LDA
- CHUNK = N
- LDWRKR = LDA
- ELSE IF( LWORK.GE.MAX( WRKBL, LDA*N )+M*M ) THEN
-*
-* WORK(IU) is LDA by N and WORK(IR) is M by M
-*
- LDWRKU = LDA
- CHUNK = N
- LDWRKR = M
- ELSE
-*
-* WORK(IU) is M by CHUNK and WORK(IR) is M by M
-*
- LDWRKU = M
- CHUNK = ( LWORK-M*M ) / M
- LDWRKR = M
- END IF
- ITAU = IR + LDWRKR*M
- IWORK = ITAU + M
-*
-* Compute A=L*Q
-* (CWorkspace: need M*M+2*M, prefer M*M+M+M*NB)
-* (RWorkspace: 0)
-*
- CALL ZGELQF( M, N, A, LDA, WORK( ITAU ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
-*
-* Copy L to WORK(IR) and zero out above it
-*
- CALL ZLACPY( 'L', M, M, A, LDA, WORK( IR ), LDWRKR )
- CALL ZLASET( 'U', M-1, M-1, CZERO, CZERO,
- $ WORK( IR+LDWRKR ), LDWRKR )
-*
-* Generate Q in A
-* (CWorkspace: need M*M+2*M, prefer M*M+M+M*NB)
-* (RWorkspace: 0)
-*
- CALL ZUNGLQ( M, N, M, A, LDA, WORK( ITAU ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
- IE = 1
- ITAUQ = ITAU
- ITAUP = ITAUQ + M
- IWORK = ITAUP + M
-*
-* Bidiagonalize L in WORK(IR)
-* (CWorkspace: need M*M+3*M, prefer M*M+2*M+2*M*NB)
-* (RWorkspace: need M)
-*
- CALL ZGEBRD( M, M, WORK( IR ), LDWRKR, S, RWORK( IE ),
- $ WORK( ITAUQ ), WORK( ITAUP ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
-*
-* Generate right vectors bidiagonalizing L
-* (CWorkspace: need M*M+3*M-1, prefer M*M+2*M+(M-1)*NB)
-* (RWorkspace: 0)
-*
- CALL ZUNGBR( 'P', M, M, M, WORK( IR ), LDWRKR,
- $ WORK( ITAUP ), WORK( IWORK ),
- $ LWORK-IWORK+1, IERR )
- IRWORK = IE + M
-*
-* Perform bidiagonal QR iteration, computing right
-* singular vectors of L in WORK(IR)
-* (CWorkspace: need M*M)
-* (RWorkspace: need BDSPAC)
-*
- CALL ZBDSQR( 'U', M, M, 0, 0, S, RWORK( IE ),
- $ WORK( IR ), LDWRKR, CDUM, 1, CDUM, 1,
- $ RWORK( IRWORK ), INFO )
- IU = ITAUQ
-*
-* Multiply right singular vectors of L in WORK(IR) by Q
-* in A, storing result in WORK(IU) and copying to A
-* (CWorkspace: need M*M+M, prefer M*M+M*N)
-* (RWorkspace: 0)
-*
- DO 30 I = 1, N, CHUNK
- BLK = MIN( N-I+1, CHUNK )
- CALL ZGEMM( 'N', 'N', M, BLK, M, CONE, WORK( IR ),
- $ LDWRKR, A( 1, I ), LDA, CZERO,
- $ WORK( IU ), LDWRKU )
- CALL ZLACPY( 'F', M, BLK, WORK( IU ), LDWRKU,
- $ A( 1, I ), LDA )
- 30 CONTINUE
-*
- ELSE
-*
-* Insufficient workspace for a fast algorithm
-*
- IE = 1
- ITAUQ = 1
- ITAUP = ITAUQ + M
- IWORK = ITAUP + M
-*
-* Bidiagonalize A
-* (CWorkspace: need 2*M+N, prefer 2*M+(M+N)*NB)
-* (RWorkspace: need M)
-*
- CALL ZGEBRD( M, N, A, LDA, S, RWORK( IE ),
- $ WORK( ITAUQ ), WORK( ITAUP ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
-*
-* Generate right vectors bidiagonalizing A
-* (CWorkspace: need 3*M, prefer 2*M+M*NB)
-* (RWorkspace: 0)
-*
- CALL ZUNGBR( 'P', M, N, M, A, LDA, WORK( ITAUP ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
- IRWORK = IE + M
-*
-* Perform bidiagonal QR iteration, computing right
-* singular vectors of A in A
-* (CWorkspace: 0)
-* (RWorkspace: need BDSPAC)
-*
- CALL ZBDSQR( 'L', M, N, 0, 0, S, RWORK( IE ), A, LDA,
- $ CDUM, 1, CDUM, 1, RWORK( IRWORK ), INFO )
-*
- END IF
-*
- ELSE IF( WNTVO .AND. WNTUAS ) THEN
-*
-* Path 3t(N much larger than M, JOBU='S' or 'A', JOBVT='O')
-* M right singular vectors to be overwritten on A and
-* M left singular vectors to be computed in U
-*
- IF( LWORK.GE.M*M+3*M ) THEN
-*
-* Sufficient workspace for a fast algorithm
-*
- IR = 1
- IF( LWORK.GE.MAX( WRKBL, LDA*N )+LDA*M ) THEN
-*
-* WORK(IU) is LDA by N and WORK(IR) is LDA by M
-*
- LDWRKU = LDA
- CHUNK = N
- LDWRKR = LDA
- ELSE IF( LWORK.GE.MAX( WRKBL, LDA*N )+M*M ) THEN
-*
-* WORK(IU) is LDA by N and WORK(IR) is M by M
-*
- LDWRKU = LDA
- CHUNK = N
- LDWRKR = M
- ELSE
-*
-* WORK(IU) is M by CHUNK and WORK(IR) is M by M
-*
- LDWRKU = M
- CHUNK = ( LWORK-M*M ) / M
- LDWRKR = M
- END IF
- ITAU = IR + LDWRKR*M
- IWORK = ITAU + M
-*
-* Compute A=L*Q
-* (CWorkspace: need M*M+2*M, prefer M*M+M+M*NB)
-* (RWorkspace: 0)
-*
- CALL ZGELQF( M, N, A, LDA, WORK( ITAU ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
-*
-* Copy L to U, zeroing about above it
-*
- CALL ZLACPY( 'L', M, M, A, LDA, U, LDU )
- CALL ZLASET( 'U', M-1, M-1, CZERO, CZERO, U( 1, 2 ),
- $ LDU )
-*
-* Generate Q in A
-* (CWorkspace: need M*M+2*M, prefer M*M+M+M*NB)
-* (RWorkspace: 0)
-*
- CALL ZUNGLQ( M, N, M, A, LDA, WORK( ITAU ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
- IE = 1
- ITAUQ = ITAU
- ITAUP = ITAUQ + M
- IWORK = ITAUP + M
-*
-* Bidiagonalize L in U, copying result to WORK(IR)
-* (CWorkspace: need M*M+3*M, prefer M*M+2*M+2*M*NB)
-* (RWorkspace: need M)
-*
- CALL ZGEBRD( M, M, U, LDU, S, RWORK( IE ),
- $ WORK( ITAUQ ), WORK( ITAUP ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
- CALL ZLACPY( 'U', M, M, U, LDU, WORK( IR ), LDWRKR )
-*
-* Generate right vectors bidiagonalizing L in WORK(IR)
-* (CWorkspace: need M*M+3*M-1, prefer M*M+2*M+(M-1)*NB)
-* (RWorkspace: 0)
-*
- CALL ZUNGBR( 'P', M, M, M, WORK( IR ), LDWRKR,
- $ WORK( ITAUP ), WORK( IWORK ),
- $ LWORK-IWORK+1, IERR )
-*
-* Generate left vectors bidiagonalizing L in U
-* (CWorkspace: need M*M+3*M, prefer M*M+2*M+M*NB)
-* (RWorkspace: 0)
-*
- CALL ZUNGBR( 'Q', M, M, M, U, LDU, WORK( ITAUQ ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
- IRWORK = IE + M
-*
-* Perform bidiagonal QR iteration, computing left
-* singular vectors of L in U, and computing right
-* singular vectors of L in WORK(IR)
-* (CWorkspace: need M*M)
-* (RWorkspace: need BDSPAC)
-*
- CALL ZBDSQR( 'U', M, M, M, 0, S, RWORK( IE ),
- $ WORK( IR ), LDWRKR, U, LDU, CDUM, 1,
- $ RWORK( IRWORK ), INFO )
- IU = ITAUQ
-*
-* Multiply right singular vectors of L in WORK(IR) by Q
-* in A, storing result in WORK(IU) and copying to A
-* (CWorkspace: need M*M+M, prefer M*M+M*N))
-* (RWorkspace: 0)
-*
- DO 40 I = 1, N, CHUNK
- BLK = MIN( N-I+1, CHUNK )
- CALL ZGEMM( 'N', 'N', M, BLK, M, CONE, WORK( IR ),
- $ LDWRKR, A( 1, I ), LDA, CZERO,
- $ WORK( IU ), LDWRKU )
- CALL ZLACPY( 'F', M, BLK, WORK( IU ), LDWRKU,
- $ A( 1, I ), LDA )
- 40 CONTINUE
-*
- ELSE
-*
-* Insufficient workspace for a fast algorithm
-*
- ITAU = 1
- IWORK = ITAU + M
-*
-* Compute A=L*Q
-* (CWorkspace: need 2*M, prefer M+M*NB)
-* (RWorkspace: 0)
-*
- CALL ZGELQF( M, N, A, LDA, WORK( ITAU ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
-*
-* Copy L to U, zeroing out above it
-*
- CALL ZLACPY( 'L', M, M, A, LDA, U, LDU )
- CALL ZLASET( 'U', M-1, M-1, CZERO, CZERO, U( 1, 2 ),
- $ LDU )
-*
-* Generate Q in A
-* (CWorkspace: need 2*M, prefer M+M*NB)
-* (RWorkspace: 0)
-*
- CALL ZUNGLQ( M, N, M, A, LDA, WORK( ITAU ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
- IE = 1
- ITAUQ = ITAU
- ITAUP = ITAUQ + M
- IWORK = ITAUP + M
-*
-* Bidiagonalize L in U
-* (CWorkspace: need 3*M, prefer 2*M+2*M*NB)
-* (RWorkspace: need M)
-*
- CALL ZGEBRD( M, M, U, LDU, S, RWORK( IE ),
- $ WORK( ITAUQ ), WORK( ITAUP ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
-*
-* Multiply right vectors bidiagonalizing L by Q in A
-* (CWorkspace: need 2*M+N, prefer 2*M+N*NB)
-* (RWorkspace: 0)
-*
- CALL ZUNMBR( 'P', 'L', 'C', M, N, M, U, LDU,
- $ WORK( ITAUP ), A, LDA, WORK( IWORK ),
- $ LWORK-IWORK+1, IERR )
-*
-* Generate left vectors bidiagonalizing L in U
-* (CWorkspace: need 3*M, prefer 2*M+M*NB)
-* (RWorkspace: 0)
-*
- CALL ZUNGBR( 'Q', M, M, M, U, LDU, WORK( ITAUQ ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
- IRWORK = IE + M
-*
-* Perform bidiagonal QR iteration, computing left
-* singular vectors of A in U and computing right
-* singular vectors of A in A
-* (CWorkspace: 0)
-* (RWorkspace: need BDSPAC)
-*
- CALL ZBDSQR( 'U', M, N, M, 0, S, RWORK( IE ), A, LDA,
- $ U, LDU, CDUM, 1, RWORK( IRWORK ), INFO )
-*
- END IF
-*
- ELSE IF( WNTVS ) THEN
-*
- IF( WNTUN ) THEN
-*
-* Path 4t(N much larger than M, JOBU='N', JOBVT='S')
-* M right singular vectors to be computed in VT and
-* no left singular vectors to be computed
-*
- IF( LWORK.GE.M*M+3*M ) THEN
-*
-* Sufficient workspace for a fast algorithm
-*
- IR = 1
- IF( LWORK.GE.WRKBL+LDA*M ) THEN
-*
-* WORK(IR) is LDA by M
-*
- LDWRKR = LDA
- ELSE
-*
-* WORK(IR) is M by M
-*
- LDWRKR = M
- END IF
- ITAU = IR + LDWRKR*M
- IWORK = ITAU + M
-*
-* Compute A=L*Q
-* (CWorkspace: need M*M+2*M, prefer M*M+M+M*NB)
-* (RWorkspace: 0)
-*
- CALL ZGELQF( M, N, A, LDA, WORK( ITAU ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
-*
-* Copy L to WORK(IR), zeroing out above it
-*
- CALL ZLACPY( 'L', M, M, A, LDA, WORK( IR ),
- $ LDWRKR )
- CALL ZLASET( 'U', M-1, M-1, CZERO, CZERO,
- $ WORK( IR+LDWRKR ), LDWRKR )
-*
-* Generate Q in A
-* (CWorkspace: need M*M+2*M, prefer M*M+M+M*NB)
-* (RWorkspace: 0)
-*
- CALL ZUNGLQ( M, N, M, A, LDA, WORK( ITAU ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
- IE = 1
- ITAUQ = ITAU
- ITAUP = ITAUQ + M
- IWORK = ITAUP + M
-*
-* Bidiagonalize L in WORK(IR)
-* (CWorkspace: need M*M+3*M, prefer M*M+2*M+2*M*NB)
-* (RWorkspace: need M)
-*
- CALL ZGEBRD( M, M, WORK( IR ), LDWRKR, S,
- $ RWORK( IE ), WORK( ITAUQ ),
- $ WORK( ITAUP ), WORK( IWORK ),
- $ LWORK-IWORK+1, IERR )
-*
-* Generate right vectors bidiagonalizing L in
-* WORK(IR)
-* (CWorkspace: need M*M+3*M, prefer M*M+2*M+(M-1)*NB)
-* (RWorkspace: 0)
-*
- CALL ZUNGBR( 'P', M, M, M, WORK( IR ), LDWRKR,
- $ WORK( ITAUP ), WORK( IWORK ),
- $ LWORK-IWORK+1, IERR )
- IRWORK = IE + M
-*
-* Perform bidiagonal QR iteration, computing right
-* singular vectors of L in WORK(IR)
-* (CWorkspace: need M*M)
-* (RWorkspace: need BDSPAC)
-*
- CALL ZBDSQR( 'U', M, M, 0, 0, S, RWORK( IE ),
- $ WORK( IR ), LDWRKR, CDUM, 1, CDUM, 1,
- $ RWORK( IRWORK ), INFO )
-*
-* Multiply right singular vectors of L in WORK(IR) by
-* Q in A, storing result in VT
-* (CWorkspace: need M*M)
-* (RWorkspace: 0)
-*
- CALL ZGEMM( 'N', 'N', M, N, M, CONE, WORK( IR ),
- $ LDWRKR, A, LDA, CZERO, VT, LDVT )
-*
- ELSE
-*
-* Insufficient workspace for a fast algorithm
-*
- ITAU = 1
- IWORK = ITAU + M
-*
-* Compute A=L*Q
-* (CWorkspace: need 2*M, prefer M+M*NB)
-* (RWorkspace: 0)
-*
- CALL ZGELQF( M, N, A, LDA, WORK( ITAU ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
-*
-* Copy result to VT
-*
- CALL ZLACPY( 'U', M, N, A, LDA, VT, LDVT )
-*
-* Generate Q in VT
-* (CWorkspace: need 2*M, prefer M+M*NB)
-* (RWorkspace: 0)
-*
- CALL ZUNGLQ( M, N, M, VT, LDVT, WORK( ITAU ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
- IE = 1
- ITAUQ = ITAU
- ITAUP = ITAUQ + M
- IWORK = ITAUP + M
-*
-* Zero out above L in A
-*
- CALL ZLASET( 'U', M-1, M-1, CZERO, CZERO,
- $ A( 1, 2 ), LDA )
-*
-* Bidiagonalize L in A
-* (CWorkspace: need 3*M, prefer 2*M+2*M*NB)
-* (RWorkspace: need M)
-*
- CALL ZGEBRD( M, M, A, LDA, S, RWORK( IE ),
- $ WORK( ITAUQ ), WORK( ITAUP ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
-*
-* Multiply right vectors bidiagonalizing L by Q in VT
-* (CWorkspace: need 2*M+N, prefer 2*M+N*NB)
-* (RWorkspace: 0)
-*
- CALL ZUNMBR( 'P', 'L', 'C', M, N, M, A, LDA,
- $ WORK( ITAUP ), VT, LDVT,
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
- IRWORK = IE + M
-*
-* Perform bidiagonal QR iteration, computing right
-* singular vectors of A in VT
-* (CWorkspace: 0)
-* (RWorkspace: need BDSPAC)
-*
- CALL ZBDSQR( 'U', M, N, 0, 0, S, RWORK( IE ), VT,
- $ LDVT, CDUM, 1, CDUM, 1,
- $ RWORK( IRWORK ), INFO )
-*
- END IF
-*
- ELSE IF( WNTUO ) THEN
-*
-* Path 5t(N much larger than M, JOBU='O', JOBVT='S')
-* M right singular vectors to be computed in VT and
-* M left singular vectors to be overwritten on A
-*
- IF( LWORK.GE.2*M*M+3*M ) THEN
-*
-* Sufficient workspace for a fast algorithm
-*
- IU = 1
- IF( LWORK.GE.WRKBL+2*LDA*M ) THEN
-*
-* WORK(IU) is LDA by M and WORK(IR) is LDA by M
-*
- LDWRKU = LDA
- IR = IU + LDWRKU*M
- LDWRKR = LDA
- ELSE IF( LWORK.GE.WRKBL+( LDA+M )*M ) THEN
-*
-* WORK(IU) is LDA by M and WORK(IR) is M by M
-*
- LDWRKU = LDA
- IR = IU + LDWRKU*M
- LDWRKR = M
- ELSE
-*
-* WORK(IU) is M by M and WORK(IR) is M by M
-*
- LDWRKU = M
- IR = IU + LDWRKU*M
- LDWRKR = M
- END IF
- ITAU = IR + LDWRKR*M
- IWORK = ITAU + M
-*
-* Compute A=L*Q
-* (CWorkspace: need 2*M*M+2*M, prefer 2*M*M+M+M*NB)
-* (RWorkspace: 0)
-*
- CALL ZGELQF( M, N, A, LDA, WORK( ITAU ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
-*
-* Copy L to WORK(IU), zeroing out below it
-*
- CALL ZLACPY( 'L', M, M, A, LDA, WORK( IU ),
- $ LDWRKU )
- CALL ZLASET( 'U', M-1, M-1, CZERO, CZERO,
- $ WORK( IU+LDWRKU ), LDWRKU )
-*
-* Generate Q in A
-* (CWorkspace: need 2*M*M+2*M, prefer 2*M*M+M+M*NB)
-* (RWorkspace: 0)
-*
- CALL ZUNGLQ( M, N, M, A, LDA, WORK( ITAU ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
- IE = 1
- ITAUQ = ITAU
- ITAUP = ITAUQ + M
- IWORK = ITAUP + M
-*
-* Bidiagonalize L in WORK(IU), copying result to
-* WORK(IR)
-* (CWorkspace: need 2*M*M+3*M,
-* prefer 2*M*M+2*M+2*M*NB)
-* (RWorkspace: need M)
-*
- CALL ZGEBRD( M, M, WORK( IU ), LDWRKU, S,
- $ RWORK( IE ), WORK( ITAUQ ),
- $ WORK( ITAUP ), WORK( IWORK ),
- $ LWORK-IWORK+1, IERR )
- CALL ZLACPY( 'L', M, M, WORK( IU ), LDWRKU,
- $ WORK( IR ), LDWRKR )
-*
-* Generate right bidiagonalizing vectors in WORK(IU)
-* (CWorkspace: need 2*M*M+3*M-1,
-* prefer 2*M*M+2*M+(M-1)*NB)
-* (RWorkspace: 0)
-*
- CALL ZUNGBR( 'P', M, M, M, WORK( IU ), LDWRKU,
- $ WORK( ITAUP ), WORK( IWORK ),
- $ LWORK-IWORK+1, IERR )
-*
-* Generate left bidiagonalizing vectors in WORK(IR)
-* (CWorkspace: need 2*M*M+3*M, prefer 2*M*M+2*M+M*NB)
-* (RWorkspace: 0)
-*
- CALL ZUNGBR( 'Q', M, M, M, WORK( IR ), LDWRKR,
- $ WORK( ITAUQ ), WORK( IWORK ),
- $ LWORK-IWORK+1, IERR )
- IRWORK = IE + M
-*
-* Perform bidiagonal QR iteration, computing left
-* singular vectors of L in WORK(IR) and computing
-* right singular vectors of L in WORK(IU)
-* (CWorkspace: need 2*M*M)
-* (RWorkspace: need BDSPAC)
-*
- CALL ZBDSQR( 'U', M, M, M, 0, S, RWORK( IE ),
- $ WORK( IU ), LDWRKU, WORK( IR ),
- $ LDWRKR, CDUM, 1, RWORK( IRWORK ),
- $ INFO )
-*
-* Multiply right singular vectors of L in WORK(IU) by
-* Q in A, storing result in VT
-* (CWorkspace: need M*M)
-* (RWorkspace: 0)
-*
- CALL ZGEMM( 'N', 'N', M, N, M, CONE, WORK( IU ),
- $ LDWRKU, A, LDA, CZERO, VT, LDVT )
-*
-* Copy left singular vectors of L to A
-* (CWorkspace: need M*M)
-* (RWorkspace: 0)
-*
- CALL ZLACPY( 'F', M, M, WORK( IR ), LDWRKR, A,
- $ LDA )
-*
- ELSE
-*
-* Insufficient workspace for a fast algorithm
-*
- ITAU = 1
- IWORK = ITAU + M
-*
-* Compute A=L*Q, copying result to VT
-* (CWorkspace: need 2*M, prefer M+M*NB)
-* (RWorkspace: 0)
-*
- CALL ZGELQF( M, N, A, LDA, WORK( ITAU ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
- CALL ZLACPY( 'U', M, N, A, LDA, VT, LDVT )
-*
-* Generate Q in VT
-* (CWorkspace: need 2*M, prefer M+M*NB)
-* (RWorkspace: 0)
-*
- CALL ZUNGLQ( M, N, M, VT, LDVT, WORK( ITAU ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
- IE = 1
- ITAUQ = ITAU
- ITAUP = ITAUQ + M
- IWORK = ITAUP + M
-*
-* Zero out above L in A
-*
- CALL ZLASET( 'U', M-1, M-1, CZERO, CZERO,
- $ A( 1, 2 ), LDA )
-*
-* Bidiagonalize L in A
-* (CWorkspace: need 3*M, prefer 2*M+2*M*NB)
-* (RWorkspace: need M)
-*
- CALL ZGEBRD( M, M, A, LDA, S, RWORK( IE ),
- $ WORK( ITAUQ ), WORK( ITAUP ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
-*
-* Multiply right vectors bidiagonalizing L by Q in VT
-* (CWorkspace: need 2*M+N, prefer 2*M+N*NB)
-* (RWorkspace: 0)
-*
- CALL ZUNMBR( 'P', 'L', 'C', M, N, M, A, LDA,
- $ WORK( ITAUP ), VT, LDVT,
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
-*
-* Generate left bidiagonalizing vectors of L in A
-* (CWorkspace: need 3*M, prefer 2*M+M*NB)
-* (RWorkspace: 0)
-*
- CALL ZUNGBR( 'Q', M, M, M, A, LDA, WORK( ITAUQ ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
- IRWORK = IE + M
-*
-* Perform bidiagonal QR iteration, computing left
-* singular vectors of A in A and computing right
-* singular vectors of A in VT
-* (CWorkspace: 0)
-* (RWorkspace: need BDSPAC)
-*
- CALL ZBDSQR( 'U', M, N, M, 0, S, RWORK( IE ), VT,
- $ LDVT, A, LDA, CDUM, 1,
- $ RWORK( IRWORK ), INFO )
-*
- END IF
-*
- ELSE IF( WNTUAS ) THEN
-*
-* Path 6t(N much larger than M, JOBU='S' or 'A',
-* JOBVT='S')
-* M right singular vectors to be computed in VT and
-* M left singular vectors to be computed in U
-*
- IF( LWORK.GE.M*M+3*M ) THEN
-*
-* Sufficient workspace for a fast algorithm
-*
- IU = 1
- IF( LWORK.GE.WRKBL+LDA*M ) THEN
-*
-* WORK(IU) is LDA by N
-*
- LDWRKU = LDA
- ELSE
-*
-* WORK(IU) is LDA by M
-*
- LDWRKU = M
- END IF
- ITAU = IU + LDWRKU*M
- IWORK = ITAU + M
-*
-* Compute A=L*Q
-* (CWorkspace: need M*M+2*M, prefer M*M+M+M*NB)
-* (RWorkspace: 0)
-*
- CALL ZGELQF( M, N, A, LDA, WORK( ITAU ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
-*
-* Copy L to WORK(IU), zeroing out above it
-*
- CALL ZLACPY( 'L', M, M, A, LDA, WORK( IU ),
- $ LDWRKU )
- CALL ZLASET( 'U', M-1, M-1, CZERO, CZERO,
- $ WORK( IU+LDWRKU ), LDWRKU )
-*
-* Generate Q in A
-* (CWorkspace: need M*M+2*M, prefer M*M+M+M*NB)
-* (RWorkspace: 0)
-*
- CALL ZUNGLQ( M, N, M, A, LDA, WORK( ITAU ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
- IE = 1
- ITAUQ = ITAU
- ITAUP = ITAUQ + M
- IWORK = ITAUP + M
-*
-* Bidiagonalize L in WORK(IU), copying result to U
-* (CWorkspace: need M*M+3*M, prefer M*M+2*M+2*M*NB)
-* (RWorkspace: need M)
-*
- CALL ZGEBRD( M, M, WORK( IU ), LDWRKU, S,
- $ RWORK( IE ), WORK( ITAUQ ),
- $ WORK( ITAUP ), WORK( IWORK ),
- $ LWORK-IWORK+1, IERR )
- CALL ZLACPY( 'L', M, M, WORK( IU ), LDWRKU, U,
- $ LDU )
-*
-* Generate right bidiagonalizing vectors in WORK(IU)
-* (CWorkspace: need M*M+3*M-1,
-* prefer M*M+2*M+(M-1)*NB)
-* (RWorkspace: 0)
-*
- CALL ZUNGBR( 'P', M, M, M, WORK( IU ), LDWRKU,
- $ WORK( ITAUP ), WORK( IWORK ),
- $ LWORK-IWORK+1, IERR )
-*
-* Generate left bidiagonalizing vectors in U
-* (CWorkspace: need M*M+3*M, prefer M*M+2*M+M*NB)
-* (RWorkspace: 0)
-*
- CALL ZUNGBR( 'Q', M, M, M, U, LDU, WORK( ITAUQ ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
- IRWORK = IE + M
-*
-* Perform bidiagonal QR iteration, computing left
-* singular vectors of L in U and computing right
-* singular vectors of L in WORK(IU)
-* (CWorkspace: need M*M)
-* (RWorkspace: need BDSPAC)
-*
- CALL ZBDSQR( 'U', M, M, M, 0, S, RWORK( IE ),
- $ WORK( IU ), LDWRKU, U, LDU, CDUM, 1,
- $ RWORK( IRWORK ), INFO )
-*
-* Multiply right singular vectors of L in WORK(IU) by
-* Q in A, storing result in VT
-* (CWorkspace: need M*M)
-* (RWorkspace: 0)
-*
- CALL ZGEMM( 'N', 'N', M, N, M, CONE, WORK( IU ),
- $ LDWRKU, A, LDA, CZERO, VT, LDVT )
-*
- ELSE
-*
-* Insufficient workspace for a fast algorithm
-*
- ITAU = 1
- IWORK = ITAU + M
-*
-* Compute A=L*Q, copying result to VT
-* (CWorkspace: need 2*M, prefer M+M*NB)
-* (RWorkspace: 0)
-*
- CALL ZGELQF( M, N, A, LDA, WORK( ITAU ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
- CALL ZLACPY( 'U', M, N, A, LDA, VT, LDVT )
-*
-* Generate Q in VT
-* (CWorkspace: need 2*M, prefer M+M*NB)
-* (RWorkspace: 0)
-*
- CALL ZUNGLQ( M, N, M, VT, LDVT, WORK( ITAU ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
-*
-* Copy L to U, zeroing out above it
-*
- CALL ZLACPY( 'L', M, M, A, LDA, U, LDU )
- CALL ZLASET( 'U', M-1, M-1, CZERO, CZERO,
- $ U( 1, 2 ), LDU )
- IE = 1
- ITAUQ = ITAU
- ITAUP = ITAUQ + M
- IWORK = ITAUP + M
-*
-* Bidiagonalize L in U
-* (CWorkspace: need 3*M, prefer 2*M+2*M*NB)
-* (RWorkspace: need M)
-*
- CALL ZGEBRD( M, M, U, LDU, S, RWORK( IE ),
- $ WORK( ITAUQ ), WORK( ITAUP ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
-*
-* Multiply right bidiagonalizing vectors in U by Q
-* in VT
-* (CWorkspace: need 2*M+N, prefer 2*M+N*NB)
-* (RWorkspace: 0)
-*
- CALL ZUNMBR( 'P', 'L', 'C', M, N, M, U, LDU,
- $ WORK( ITAUP ), VT, LDVT,
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
-*
-* Generate left bidiagonalizing vectors in U
-* (CWorkspace: need 3*M, prefer 2*M+M*NB)
-* (RWorkspace: 0)
-*
- CALL ZUNGBR( 'Q', M, M, M, U, LDU, WORK( ITAUQ ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
- IRWORK = IE + M
-*
-* Perform bidiagonal QR iteration, computing left
-* singular vectors of A in U and computing right
-* singular vectors of A in VT
-* (CWorkspace: 0)
-* (RWorkspace: need BDSPAC)
-*
- CALL ZBDSQR( 'U', M, N, M, 0, S, RWORK( IE ), VT,
- $ LDVT, U, LDU, CDUM, 1,
- $ RWORK( IRWORK ), INFO )
-*
- END IF
-*
- END IF
-*
- ELSE IF( WNTVA ) THEN
-*
- IF( WNTUN ) THEN
-*
-* Path 7t(N much larger than M, JOBU='N', JOBVT='A')
-* N right singular vectors to be computed in VT and
-* no left singular vectors to be computed
-*
- IF( LWORK.GE.M*M+MAX( N+M, 3*M ) ) THEN
-*
-* Sufficient workspace for a fast algorithm
-*
- IR = 1
- IF( LWORK.GE.WRKBL+LDA*M ) THEN
-*
-* WORK(IR) is LDA by M
-*
- LDWRKR = LDA
- ELSE
-*
-* WORK(IR) is M by M
-*
- LDWRKR = M
- END IF
- ITAU = IR + LDWRKR*M
- IWORK = ITAU + M
-*
-* Compute A=L*Q, copying result to VT
-* (CWorkspace: need M*M+2*M, prefer M*M+M+M*NB)
-* (RWorkspace: 0)
-*
- CALL ZGELQF( M, N, A, LDA, WORK( ITAU ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
- CALL ZLACPY( 'U', M, N, A, LDA, VT, LDVT )
-*
-* Copy L to WORK(IR), zeroing out above it
-*
- CALL ZLACPY( 'L', M, M, A, LDA, WORK( IR ),
- $ LDWRKR )
- CALL ZLASET( 'U', M-1, M-1, CZERO, CZERO,
- $ WORK( IR+LDWRKR ), LDWRKR )
-*
-* Generate Q in VT
-* (CWorkspace: need M*M+M+N, prefer M*M+M+N*NB)
-* (RWorkspace: 0)
-*
- CALL ZUNGLQ( N, N, M, VT, LDVT, WORK( ITAU ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
- IE = 1
- ITAUQ = ITAU
- ITAUP = ITAUQ + M
- IWORK = ITAUP + M
-*
-* Bidiagonalize L in WORK(IR)
-* (CWorkspace: need M*M+3*M, prefer M*M+2*M+2*M*NB)
-* (RWorkspace: need M)
-*
- CALL ZGEBRD( M, M, WORK( IR ), LDWRKR, S,
- $ RWORK( IE ), WORK( ITAUQ ),
- $ WORK( ITAUP ), WORK( IWORK ),
- $ LWORK-IWORK+1, IERR )
-*
-* Generate right bidiagonalizing vectors in WORK(IR)
-* (CWorkspace: need M*M+3*M-1,
-* prefer M*M+2*M+(M-1)*NB)
-* (RWorkspace: 0)
-*
- CALL ZUNGBR( 'P', M, M, M, WORK( IR ), LDWRKR,
- $ WORK( ITAUP ), WORK( IWORK ),
- $ LWORK-IWORK+1, IERR )
- IRWORK = IE + M
-*
-* Perform bidiagonal QR iteration, computing right
-* singular vectors of L in WORK(IR)
-* (CWorkspace: need M*M)
-* (RWorkspace: need BDSPAC)
-*
- CALL ZBDSQR( 'U', M, M, 0, 0, S, RWORK( IE ),
- $ WORK( IR ), LDWRKR, CDUM, 1, CDUM, 1,
- $ RWORK( IRWORK ), INFO )
-*
-* Multiply right singular vectors of L in WORK(IR) by
-* Q in VT, storing result in A
-* (CWorkspace: need M*M)
-* (RWorkspace: 0)
-*
- CALL ZGEMM( 'N', 'N', M, N, M, CONE, WORK( IR ),
- $ LDWRKR, VT, LDVT, CZERO, A, LDA )
-*
-* Copy right singular vectors of A from A to VT
-*
- CALL ZLACPY( 'F', M, N, A, LDA, VT, LDVT )
-*
- ELSE
-*
-* Insufficient workspace for a fast algorithm
-*
- ITAU = 1
- IWORK = ITAU + M
-*
-* Compute A=L*Q, copying result to VT
-* (CWorkspace: need 2*M, prefer M+M*NB)
-* (RWorkspace: 0)
-*
- CALL ZGELQF( M, N, A, LDA, WORK( ITAU ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
- CALL ZLACPY( 'U', M, N, A, LDA, VT, LDVT )
-*
-* Generate Q in VT
-* (CWorkspace: need M+N, prefer M+N*NB)
-* (RWorkspace: 0)
-*
- CALL ZUNGLQ( N, N, M, VT, LDVT, WORK( ITAU ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
- IE = 1
- ITAUQ = ITAU
- ITAUP = ITAUQ + M
- IWORK = ITAUP + M
-*
-* Zero out above L in A
-*
- CALL ZLASET( 'U', M-1, M-1, CZERO, CZERO,
- $ A( 1, 2 ), LDA )
-*
-* Bidiagonalize L in A
-* (CWorkspace: need 3*M, prefer 2*M+2*M*NB)
-* (RWorkspace: need M)
-*
- CALL ZGEBRD( M, M, A, LDA, S, RWORK( IE ),
- $ WORK( ITAUQ ), WORK( ITAUP ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
-*
-* Multiply right bidiagonalizing vectors in A by Q
-* in VT
-* (CWorkspace: need 2*M+N, prefer 2*M+N*NB)
-* (RWorkspace: 0)
-*
- CALL ZUNMBR( 'P', 'L', 'C', M, N, M, A, LDA,
- $ WORK( ITAUP ), VT, LDVT,
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
- IRWORK = IE + M
-*
-* Perform bidiagonal QR iteration, computing right
-* singular vectors of A in VT
-* (CWorkspace: 0)
-* (RWorkspace: need BDSPAC)
-*
- CALL ZBDSQR( 'U', M, N, 0, 0, S, RWORK( IE ), VT,
- $ LDVT, CDUM, 1, CDUM, 1,
- $ RWORK( IRWORK ), INFO )
-*
- END IF
-*
- ELSE IF( WNTUO ) THEN
-*
-* Path 8t(N much larger than M, JOBU='O', JOBVT='A')
-* N right singular vectors to be computed in VT and
-* M left singular vectors to be overwritten on A
-*
- IF( LWORK.GE.2*M*M+MAX( N+M, 3*M ) ) THEN
-*
-* Sufficient workspace for a fast algorithm
-*
- IU = 1
- IF( LWORK.GE.WRKBL+2*LDA*M ) THEN
-*
-* WORK(IU) is LDA by M and WORK(IR) is LDA by M
-*
- LDWRKU = LDA
- IR = IU + LDWRKU*M
- LDWRKR = LDA
- ELSE IF( LWORK.GE.WRKBL+( LDA+M )*M ) THEN
-*
-* WORK(IU) is LDA by M and WORK(IR) is M by M
-*
- LDWRKU = LDA
- IR = IU + LDWRKU*M
- LDWRKR = M
- ELSE
-*
-* WORK(IU) is M by M and WORK(IR) is M by M
-*
- LDWRKU = M
- IR = IU + LDWRKU*M
- LDWRKR = M
- END IF
- ITAU = IR + LDWRKR*M
- IWORK = ITAU + M
-*
-* Compute A=L*Q, copying result to VT
-* (CWorkspace: need 2*M*M+2*M, prefer 2*M*M+M+M*NB)
-* (RWorkspace: 0)
-*
- CALL ZGELQF( M, N, A, LDA, WORK( ITAU ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
- CALL ZLACPY( 'U', M, N, A, LDA, VT, LDVT )
-*
-* Generate Q in VT
-* (CWorkspace: need 2*M*M+M+N, prefer 2*M*M+M+N*NB)
-* (RWorkspace: 0)
-*
- CALL ZUNGLQ( N, N, M, VT, LDVT, WORK( ITAU ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
-*
-* Copy L to WORK(IU), zeroing out above it
-*
- CALL ZLACPY( 'L', M, M, A, LDA, WORK( IU ),
- $ LDWRKU )
- CALL ZLASET( 'U', M-1, M-1, CZERO, CZERO,
- $ WORK( IU+LDWRKU ), LDWRKU )
- IE = 1
- ITAUQ = ITAU
- ITAUP = ITAUQ + M
- IWORK = ITAUP + M
-*
-* Bidiagonalize L in WORK(IU), copying result to
-* WORK(IR)
-* (CWorkspace: need 2*M*M+3*M,
-* prefer 2*M*M+2*M+2*M*NB)
-* (RWorkspace: need M)
-*
- CALL ZGEBRD( M, M, WORK( IU ), LDWRKU, S,
- $ RWORK( IE ), WORK( ITAUQ ),
- $ WORK( ITAUP ), WORK( IWORK ),
- $ LWORK-IWORK+1, IERR )
- CALL ZLACPY( 'L', M, M, WORK( IU ), LDWRKU,
- $ WORK( IR ), LDWRKR )
-*
-* Generate right bidiagonalizing vectors in WORK(IU)
-* (CWorkspace: need 2*M*M+3*M-1,
-* prefer 2*M*M+2*M+(M-1)*NB)
-* (RWorkspace: 0)
-*
- CALL ZUNGBR( 'P', M, M, M, WORK( IU ), LDWRKU,
- $ WORK( ITAUP ), WORK( IWORK ),
- $ LWORK-IWORK+1, IERR )
-*
-* Generate left bidiagonalizing vectors in WORK(IR)
-* (CWorkspace: need 2*M*M+3*M, prefer 2*M*M+2*M+M*NB)
-* (RWorkspace: 0)
-*
- CALL ZUNGBR( 'Q', M, M, M, WORK( IR ), LDWRKR,
- $ WORK( ITAUQ ), WORK( IWORK ),
- $ LWORK-IWORK+1, IERR )
- IRWORK = IE + M
-*
-* Perform bidiagonal QR iteration, computing left
-* singular vectors of L in WORK(IR) and computing
-* right singular vectors of L in WORK(IU)
-* (CWorkspace: need 2*M*M)
-* (RWorkspace: need BDSPAC)
-*
- CALL ZBDSQR( 'U', M, M, M, 0, S, RWORK( IE ),
- $ WORK( IU ), LDWRKU, WORK( IR ),
- $ LDWRKR, CDUM, 1, RWORK( IRWORK ),
- $ INFO )
-*
-* Multiply right singular vectors of L in WORK(IU) by
-* Q in VT, storing result in A
-* (CWorkspace: need M*M)
-* (RWorkspace: 0)
-*
- CALL ZGEMM( 'N', 'N', M, N, M, CONE, WORK( IU ),
- $ LDWRKU, VT, LDVT, CZERO, A, LDA )
-*
-* Copy right singular vectors of A from A to VT
-*
- CALL ZLACPY( 'F', M, N, A, LDA, VT, LDVT )
-*
-* Copy left singular vectors of A from WORK(IR) to A
-*
- CALL ZLACPY( 'F', M, M, WORK( IR ), LDWRKR, A,
- $ LDA )
-*
- ELSE
-*
-* Insufficient workspace for a fast algorithm
-*
- ITAU = 1
- IWORK = ITAU + M
-*
-* Compute A=L*Q, copying result to VT
-* (CWorkspace: need 2*M, prefer M+M*NB)
-* (RWorkspace: 0)
-*
- CALL ZGELQF( M, N, A, LDA, WORK( ITAU ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
- CALL ZLACPY( 'U', M, N, A, LDA, VT, LDVT )
-*
-* Generate Q in VT
-* (CWorkspace: need M+N, prefer M+N*NB)
-* (RWorkspace: 0)
-*
- CALL ZUNGLQ( N, N, M, VT, LDVT, WORK( ITAU ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
- IE = 1
- ITAUQ = ITAU
- ITAUP = ITAUQ + M
- IWORK = ITAUP + M
-*
-* Zero out above L in A
-*
- CALL ZLASET( 'U', M-1, M-1, CZERO, CZERO,
- $ A( 1, 2 ), LDA )
-*
-* Bidiagonalize L in A
-* (CWorkspace: need 3*M, prefer 2*M+2*M*NB)
-* (RWorkspace: need M)
-*
- CALL ZGEBRD( M, M, A, LDA, S, RWORK( IE ),
- $ WORK( ITAUQ ), WORK( ITAUP ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
-*
-* Multiply right bidiagonalizing vectors in A by Q
-* in VT
-* (CWorkspace: need 2*M+N, prefer 2*M+N*NB)
-* (RWorkspace: 0)
-*
- CALL ZUNMBR( 'P', 'L', 'C', M, N, M, A, LDA,
- $ WORK( ITAUP ), VT, LDVT,
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
-*
-* Generate left bidiagonalizing vectors in A
-* (CWorkspace: need 3*M, prefer 2*M+M*NB)
-* (RWorkspace: 0)
-*
- CALL ZUNGBR( 'Q', M, M, M, A, LDA, WORK( ITAUQ ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
- IRWORK = IE + M
-*
-* Perform bidiagonal QR iteration, computing left
-* singular vectors of A in A and computing right
-* singular vectors of A in VT
-* (CWorkspace: 0)
-* (RWorkspace: need BDSPAC)
-*
- CALL ZBDSQR( 'U', M, N, M, 0, S, RWORK( IE ), VT,
- $ LDVT, A, LDA, CDUM, 1,
- $ RWORK( IRWORK ), INFO )
-*
- END IF
-*
- ELSE IF( WNTUAS ) THEN
-*
-* Path 9t(N much larger than M, JOBU='S' or 'A',
-* JOBVT='A')
-* N right singular vectors to be computed in VT and
-* M left singular vectors to be computed in U
-*
- IF( LWORK.GE.M*M+MAX( N+M, 3*M ) ) THEN
-*
-* Sufficient workspace for a fast algorithm
-*
- IU = 1
- IF( LWORK.GE.WRKBL+LDA*M ) THEN
-*
-* WORK(IU) is LDA by M
-*
- LDWRKU = LDA
- ELSE
-*
-* WORK(IU) is M by M
-*
- LDWRKU = M
- END IF
- ITAU = IU + LDWRKU*M
- IWORK = ITAU + M
-*
-* Compute A=L*Q, copying result to VT
-* (CWorkspace: need M*M+2*M, prefer M*M+M+M*NB)
-* (RWorkspace: 0)
-*
- CALL ZGELQF( M, N, A, LDA, WORK( ITAU ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
- CALL ZLACPY( 'U', M, N, A, LDA, VT, LDVT )
-*
-* Generate Q in VT
-* (CWorkspace: need M*M+M+N, prefer M*M+M+N*NB)
-* (RWorkspace: 0)
-*
- CALL ZUNGLQ( N, N, M, VT, LDVT, WORK( ITAU ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
-*
-* Copy L to WORK(IU), zeroing out above it
-*
- CALL ZLACPY( 'L', M, M, A, LDA, WORK( IU ),
- $ LDWRKU )
- CALL ZLASET( 'U', M-1, M-1, CZERO, CZERO,
- $ WORK( IU+LDWRKU ), LDWRKU )
- IE = 1
- ITAUQ = ITAU
- ITAUP = ITAUQ + M
- IWORK = ITAUP + M
-*
-* Bidiagonalize L in WORK(IU), copying result to U
-* (CWorkspace: need M*M+3*M, prefer M*M+2*M+2*M*NB)
-* (RWorkspace: need M)
-*
- CALL ZGEBRD( M, M, WORK( IU ), LDWRKU, S,
- $ RWORK( IE ), WORK( ITAUQ ),
- $ WORK( ITAUP ), WORK( IWORK ),
- $ LWORK-IWORK+1, IERR )
- CALL ZLACPY( 'L', M, M, WORK( IU ), LDWRKU, U,
- $ LDU )
-*
-* Generate right bidiagonalizing vectors in WORK(IU)
-* (CWorkspace: need M*M+3*M, prefer M*M+2*M+(M-1)*NB)
-* (RWorkspace: 0)
-*
- CALL ZUNGBR( 'P', M, M, M, WORK( IU ), LDWRKU,
- $ WORK( ITAUP ), WORK( IWORK ),
- $ LWORK-IWORK+1, IERR )
-*
-* Generate left bidiagonalizing vectors in U
-* (CWorkspace: need M*M+3*M, prefer M*M+2*M+M*NB)
-* (RWorkspace: 0)
-*
- CALL ZUNGBR( 'Q', M, M, M, U, LDU, WORK( ITAUQ ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
- IRWORK = IE + M
-*
-* Perform bidiagonal QR iteration, computing left
-* singular vectors of L in U and computing right
-* singular vectors of L in WORK(IU)
-* (CWorkspace: need M*M)
-* (RWorkspace: need BDSPAC)
-*
- CALL ZBDSQR( 'U', M, M, M, 0, S, RWORK( IE ),
- $ WORK( IU ), LDWRKU, U, LDU, CDUM, 1,
- $ RWORK( IRWORK ), INFO )
-*
-* Multiply right singular vectors of L in WORK(IU) by
-* Q in VT, storing result in A
-* (CWorkspace: need M*M)
-* (RWorkspace: 0)
-*
- CALL ZGEMM( 'N', 'N', M, N, M, CONE, WORK( IU ),
- $ LDWRKU, VT, LDVT, CZERO, A, LDA )
-*
-* Copy right singular vectors of A from A to VT
-*
- CALL ZLACPY( 'F', M, N, A, LDA, VT, LDVT )
-*
- ELSE
-*
-* Insufficient workspace for a fast algorithm
-*
- ITAU = 1
- IWORK = ITAU + M
-*
-* Compute A=L*Q, copying result to VT
-* (CWorkspace: need 2*M, prefer M+M*NB)
-* (RWorkspace: 0)
-*
- CALL ZGELQF( M, N, A, LDA, WORK( ITAU ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
- CALL ZLACPY( 'U', M, N, A, LDA, VT, LDVT )
-*
-* Generate Q in VT
-* (CWorkspace: need M+N, prefer M+N*NB)
-* (RWorkspace: 0)
-*
- CALL ZUNGLQ( N, N, M, VT, LDVT, WORK( ITAU ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
-*
-* Copy L to U, zeroing out above it
-*
- CALL ZLACPY( 'L', M, M, A, LDA, U, LDU )
- CALL ZLASET( 'U', M-1, M-1, CZERO, CZERO,
- $ U( 1, 2 ), LDU )
- IE = 1
- ITAUQ = ITAU
- ITAUP = ITAUQ + M
- IWORK = ITAUP + M
-*
-* Bidiagonalize L in U
-* (CWorkspace: need 3*M, prefer 2*M+2*M*NB)
-* (RWorkspace: need M)
-*
- CALL ZGEBRD( M, M, U, LDU, S, RWORK( IE ),
- $ WORK( ITAUQ ), WORK( ITAUP ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
-*
-* Multiply right bidiagonalizing vectors in U by Q
-* in VT
-* (CWorkspace: need 2*M+N, prefer 2*M+N*NB)
-* (RWorkspace: 0)
-*
- CALL ZUNMBR( 'P', 'L', 'C', M, N, M, U, LDU,
- $ WORK( ITAUP ), VT, LDVT,
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
-*
-* Generate left bidiagonalizing vectors in U
-* (CWorkspace: need 3*M, prefer 2*M+M*NB)
-* (RWorkspace: 0)
-*
- CALL ZUNGBR( 'Q', M, M, M, U, LDU, WORK( ITAUQ ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
- IRWORK = IE + M
-*
-* Perform bidiagonal QR iteration, computing left
-* singular vectors of A in U and computing right
-* singular vectors of A in VT
-* (CWorkspace: 0)
-* (RWorkspace: need BDSPAC)
-*
- CALL ZBDSQR( 'U', M, N, M, 0, S, RWORK( IE ), VT,
- $ LDVT, U, LDU, CDUM, 1,
- $ RWORK( IRWORK ), INFO )
-*
- END IF
-*
- END IF
-*
- END IF
-*
- ELSE
-*
-* N .LT. MNTHR
-*
-* Path 10t(N greater than M, but not much larger)
-* Reduce to bidiagonal form without LQ decomposition
-*
- IE = 1
- ITAUQ = 1
- ITAUP = ITAUQ + M
- IWORK = ITAUP + M
-*
-* Bidiagonalize A
-* (CWorkspace: need 2*M+N, prefer 2*M+(M+N)*NB)
-* (RWorkspace: M)
-*
- CALL ZGEBRD( M, N, A, LDA, S, RWORK( IE ), WORK( ITAUQ ),
- $ WORK( ITAUP ), WORK( IWORK ), LWORK-IWORK+1,
- $ IERR )
- IF( WNTUAS ) THEN
-*
-* If left singular vectors desired in U, copy result to U
-* and generate left bidiagonalizing vectors in U
-* (CWorkspace: need 3*M-1, prefer 2*M+(M-1)*NB)
-* (RWorkspace: 0)
-*
- CALL ZLACPY( 'L', M, M, A, LDA, U, LDU )
- CALL ZUNGBR( 'Q', M, M, N, U, LDU, WORK( ITAUQ ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
- END IF
- IF( WNTVAS ) THEN
-*
-* If right singular vectors desired in VT, copy result to
-* VT and generate right bidiagonalizing vectors in VT
-* (CWorkspace: need 2*M+NRVT, prefer 2*M+NRVT*NB)
-* (RWorkspace: 0)
-*
- CALL ZLACPY( 'U', M, N, A, LDA, VT, LDVT )
- IF( WNTVA )
- $ NRVT = N
- IF( WNTVS )
- $ NRVT = M
- CALL ZUNGBR( 'P', NRVT, N, M, VT, LDVT, WORK( ITAUP ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
- END IF
- IF( WNTUO ) THEN
-*
-* If left singular vectors desired in A, generate left
-* bidiagonalizing vectors in A
-* (CWorkspace: need 3*M-1, prefer 2*M+(M-1)*NB)
-* (RWorkspace: 0)
-*
- CALL ZUNGBR( 'Q', M, M, N, A, LDA, WORK( ITAUQ ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
- END IF
- IF( WNTVO ) THEN
-*
-* If right singular vectors desired in A, generate right
-* bidiagonalizing vectors in A
-* (CWorkspace: need 3*M, prefer 2*M+M*NB)
-* (RWorkspace: 0)
-*
- CALL ZUNGBR( 'P', M, N, M, A, LDA, WORK( ITAUP ),
- $ WORK( IWORK ), LWORK-IWORK+1, IERR )
- END IF
- IRWORK = IE + M
- IF( WNTUAS .OR. WNTUO )
- $ NRU = M
- IF( WNTUN )
- $ NRU = 0
- IF( WNTVAS .OR. WNTVO )
- $ NCVT = N
- IF( WNTVN )
- $ NCVT = 0
- IF( ( .NOT.WNTUO ) .AND. ( .NOT.WNTVO ) ) THEN
-*
-* Perform bidiagonal QR iteration, if desired, computing
-* left singular vectors in U and computing right singular
-* vectors in VT
-* (CWorkspace: 0)
-* (RWorkspace: need BDSPAC)
-*
- CALL ZBDSQR( 'L', M, NCVT, NRU, 0, S, RWORK( IE ), VT,
- $ LDVT, U, LDU, CDUM, 1, RWORK( IRWORK ),
- $ INFO )
- ELSE IF( ( .NOT.WNTUO ) .AND. WNTVO ) THEN
-*
-* Perform bidiagonal QR iteration, if desired, computing
-* left singular vectors in U and computing right singular
-* vectors in A
-* (CWorkspace: 0)
-* (RWorkspace: need BDSPAC)
-*
- CALL ZBDSQR( 'L', M, NCVT, NRU, 0, S, RWORK( IE ), A,
- $ LDA, U, LDU, CDUM, 1, RWORK( IRWORK ),
- $ INFO )
- ELSE
-*
-* Perform bidiagonal QR iteration, if desired, computing
-* left singular vectors in A and computing right singular
-* vectors in VT
-* (CWorkspace: 0)
-* (RWorkspace: need BDSPAC)
-*
- CALL ZBDSQR( 'L', M, NCVT, NRU, 0, S, RWORK( IE ), VT,
- $ LDVT, A, LDA, CDUM, 1, RWORK( IRWORK ),
- $ INFO )
- END IF
-*
- END IF
-*
- END IF
-*
-* Undo scaling if necessary
-*
- IF( ISCL.EQ.1 ) THEN
- IF( ANRM.GT.BIGNUM )
- $ CALL DLASCL( 'G', 0, 0, BIGNUM, ANRM, MINMN, 1, S, MINMN,
- $ IERR )
- IF( INFO.NE.0 .AND. ANRM.GT.BIGNUM )
- $ CALL DLASCL( 'G', 0, 0, BIGNUM, ANRM, MINMN-1, 1,
- $ RWORK( IE ), MINMN, IERR )
- IF( ANRM.LT.SMLNUM )
- $ CALL DLASCL( 'G', 0, 0, SMLNUM, ANRM, MINMN, 1, S, MINMN,
- $ IERR )
- IF( INFO.NE.0 .AND. ANRM.LT.SMLNUM )
- $ CALL DLASCL( 'G', 0, 0, SMLNUM, ANRM, MINMN-1, 1,
- $ RWORK( IE ), MINMN, IERR )
- END IF
-*
-* Return optimal workspace in WORK(1)
-*
- WORK( 1 ) = MAXWRK
-*
- RETURN
-*
-* End of ZGESVD
-*
- END
diff --git a/src/lib/lapack/zgetc2.f b/src/lib/lapack/zgetc2.f
deleted file mode 100644
index 35ac376c..00000000
--- a/src/lib/lapack/zgetc2.f
+++ /dev/null
@@ -1,145 +0,0 @@
- SUBROUTINE ZGETC2( N, A, LDA, IPIV, JPIV, INFO )
-*
-* -- LAPACK auxiliary routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- INTEGER INFO, LDA, N
-* ..
-* .. Array Arguments ..
- INTEGER IPIV( * ), JPIV( * )
- COMPLEX*16 A( LDA, * )
-* ..
-*
-* Purpose
-* =======
-*
-* ZGETC2 computes an LU factorization, using complete pivoting, of the
-* n-by-n matrix A. The factorization has the form A = P * L * U * Q,
-* where P and Q are permutation matrices, L is lower triangular with
-* unit diagonal elements and U is upper triangular.
-*
-* This is a level 1 BLAS version of the algorithm.
-*
-* Arguments
-* =========
-*
-* N (input) INTEGER
-* The order of the matrix A. N >= 0.
-*
-* A (input/output) COMPLEX*16 array, dimension (LDA, N)
-* On entry, the n-by-n matrix to be factored.
-* On exit, the factors L and U from the factorization
-* A = P*L*U*Q; the unit diagonal elements of L are not stored.
-* If U(k, k) appears to be less than SMIN, U(k, k) is given the
-* value of SMIN, giving a nonsingular perturbed system.
-*
-* LDA (input) INTEGER
-* The leading dimension of the array A. LDA >= max(1, N).
-*
-* IPIV (output) INTEGER array, dimension (N).
-* The pivot indices; for 1 <= i <= N, row i of the
-* matrix has been interchanged with row IPIV(i).
-*
-* JPIV (output) INTEGER array, dimension (N).
-* The pivot indices; for 1 <= j <= N, column j of the
-* matrix has been interchanged with column JPIV(j).
-*
-* INFO (output) INTEGER
-* = 0: successful exit
-* > 0: if INFO = k, U(k, k) is likely to produce overflow if
-* one tries to solve for x in Ax = b. So U is perturbed
-* to avoid the overflow.
-*
-* Further Details
-* ===============
-*
-* Based on contributions by
-* Bo Kagstrom and Peter Poromaa, Department of Computing Science,
-* Umea University, S-901 87 Umea, Sweden.
-*
-* =====================================================================
-*
-* .. Parameters ..
- DOUBLE PRECISION ZERO, ONE
- PARAMETER ( ZERO = 0.0D+0, ONE = 1.0D+0 )
-* ..
-* .. Local Scalars ..
- INTEGER I, IP, IPV, J, JP, JPV
- DOUBLE PRECISION BIGNUM, EPS, SMIN, SMLNUM, XMAX
-* ..
-* .. External Subroutines ..
- EXTERNAL ZGERU, ZSWAP
-* ..
-* .. External Functions ..
- DOUBLE PRECISION DLAMCH
- EXTERNAL DLAMCH
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC ABS, DCMPLX, MAX
-* ..
-* .. Executable Statements ..
-*
-* Set constants to control overflow
-*
- INFO = 0
- EPS = DLAMCH( 'P' )
- SMLNUM = DLAMCH( 'S' ) / EPS
- BIGNUM = ONE / SMLNUM
- CALL DLABAD( SMLNUM, BIGNUM )
-*
-* Factorize A using complete pivoting.
-* Set pivots less than SMIN to SMIN
-*
- DO 40 I = 1, N - 1
-*
-* Find max element in matrix A
-*
- XMAX = ZERO
- DO 20 IP = I, N
- DO 10 JP = I, N
- IF( ABS( A( IP, JP ) ).GE.XMAX ) THEN
- XMAX = ABS( A( IP, JP ) )
- IPV = IP
- JPV = JP
- END IF
- 10 CONTINUE
- 20 CONTINUE
- IF( I.EQ.1 )
- $ SMIN = MAX( EPS*XMAX, SMLNUM )
-*
-* Swap rows
-*
- IF( IPV.NE.I )
- $ CALL ZSWAP( N, A( IPV, 1 ), LDA, A( I, 1 ), LDA )
- IPIV( I ) = IPV
-*
-* Swap columns
-*
- IF( JPV.NE.I )
- $ CALL ZSWAP( N, A( 1, JPV ), 1, A( 1, I ), 1 )
- JPIV( I ) = JPV
-*
-* Check for singularity
-*
- IF( ABS( A( I, I ) ).LT.SMIN ) THEN
- INFO = I
- A( I, I ) = DCMPLX( SMIN, ZERO )
- END IF
- DO 30 J = I + 1, N
- A( J, I ) = A( J, I ) / A( I, I )
- 30 CONTINUE
- CALL ZGERU( N-I, N-I, -DCMPLX( ONE ), A( I+1, I ), 1,
- $ A( I, I+1 ), LDA, A( I+1, I+1 ), LDA )
- 40 CONTINUE
-*
- IF( ABS( A( N, N ) ).LT.SMIN ) THEN
- INFO = N
- A( N, N ) = DCMPLX( SMIN, ZERO )
- END IF
- RETURN
-*
-* End of ZGETC2
-*
- END
diff --git a/src/lib/lapack/zgetf2.f b/src/lib/lapack/zgetf2.f
deleted file mode 100644
index a2dc1834..00000000
--- a/src/lib/lapack/zgetf2.f
+++ /dev/null
@@ -1,148 +0,0 @@
- SUBROUTINE ZGETF2( M, N, A, LDA, IPIV, INFO )
-*
-* -- LAPACK routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- INTEGER INFO, LDA, M, N
-* ..
-* .. Array Arguments ..
- INTEGER IPIV( * )
- COMPLEX*16 A( LDA, * )
-* ..
-*
-* Purpose
-* =======
-*
-* ZGETF2 computes an LU factorization of a general m-by-n matrix A
-* using partial pivoting with row interchanges.
-*
-* The factorization has the form
-* A = P * L * U
-* where P is a permutation matrix, L is lower triangular with unit
-* diagonal elements (lower trapezoidal if m > n), and U is upper
-* triangular (upper trapezoidal if m < n).
-*
-* This is the right-looking Level 2 BLAS version of the algorithm.
-*
-* Arguments
-* =========
-*
-* M (input) INTEGER
-* The number of rows of the matrix A. M >= 0.
-*
-* N (input) INTEGER
-* The number of columns of the matrix A. N >= 0.
-*
-* A (input/output) COMPLEX*16 array, dimension (LDA,N)
-* On entry, the m by n matrix to be factored.
-* On exit, the factors L and U from the factorization
-* A = P*L*U; the unit diagonal elements of L are not stored.
-*
-* LDA (input) INTEGER
-* The leading dimension of the array A. LDA >= max(1,M).
-*
-* IPIV (output) INTEGER array, dimension (min(M,N))
-* The pivot indices; for 1 <= i <= min(M,N), row i of the
-* matrix was interchanged with row IPIV(i).
-*
-* INFO (output) INTEGER
-* = 0: successful exit
-* < 0: if INFO = -k, the k-th argument had an illegal value
-* > 0: if INFO = k, U(k,k) is exactly zero. The factorization
-* has been completed, but the factor U is exactly
-* singular, and division by zero will occur if it is used
-* to solve a system of equations.
-*
-* =====================================================================
-*
-* .. Parameters ..
- COMPLEX*16 ONE, ZERO
- PARAMETER ( ONE = ( 1.0D+0, 0.0D+0 ),
- $ ZERO = ( 0.0D+0, 0.0D+0 ) )
-* ..
-* .. Local Scalars ..
- DOUBLE PRECISION SFMIN
- INTEGER I, J, JP
-* ..
-* .. External Functions ..
- DOUBLE PRECISION DLAMCH
- INTEGER IZAMAX
- EXTERNAL DLAMCH, IZAMAX
-* ..
-* .. External Subroutines ..
- EXTERNAL XERBLA, ZGERU, ZSCAL, ZSWAP
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC MAX, MIN
-* ..
-* .. Executable Statements ..
-*
-* Test the input parameters.
-*
- INFO = 0
- IF( M.LT.0 ) THEN
- INFO = -1
- ELSE IF( N.LT.0 ) THEN
- INFO = -2
- ELSE IF( LDA.LT.MAX( 1, M ) ) THEN
- INFO = -4
- END IF
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'ZGETF2', -INFO )
- RETURN
- END IF
-*
-* Quick return if possible
-*
- IF( M.EQ.0 .OR. N.EQ.0 )
- $ RETURN
-*
-* Compute machine safe minimum
-*
- SFMIN = DLAMCH('S')
-*
- DO 10 J = 1, MIN( M, N )
-*
-* Find pivot and test for singularity.
-*
- JP = J - 1 + IZAMAX( M-J+1, A( J, J ), 1 )
- IPIV( J ) = JP
- IF( A( JP, J ).NE.ZERO ) THEN
-*
-* Apply the interchange to columns 1:N.
-*
- IF( JP.NE.J )
- $ CALL ZSWAP( N, A( J, 1 ), LDA, A( JP, 1 ), LDA )
-*
-* Compute elements J+1:M of J-th column.
-*
- IF( J.LT.M ) THEN
- IF( ABS(A( J, J )) .GE. SFMIN ) THEN
- CALL ZSCAL( M-J, ONE / A( J, J ), A( J+1, J ), 1 )
- ELSE
- DO 20 I = 1, M-J
- A( J+I, J ) = A( J+I, J ) / A( J, J )
- 20 CONTINUE
- END IF
- END IF
-*
- ELSE IF( INFO.EQ.0 ) THEN
-*
- INFO = J
- END IF
-*
- IF( J.LT.MIN( M, N ) ) THEN
-*
-* Update trailing submatrix.
-*
- CALL ZGERU( M-J, N-J, -ONE, A( J+1, J ), 1, A( J, J+1 ),
- $ LDA, A( J+1, J+1 ), LDA )
- END IF
- 10 CONTINUE
- RETURN
-*
-* End of ZGETF2
-*
- END
diff --git a/src/lib/lapack/zgetrf.f b/src/lib/lapack/zgetrf.f
deleted file mode 100644
index 9c7bfbbf..00000000
--- a/src/lib/lapack/zgetrf.f
+++ /dev/null
@@ -1,159 +0,0 @@
- SUBROUTINE ZGETRF( M, N, A, LDA, IPIV, INFO )
-*
-* -- LAPACK routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- INTEGER INFO, LDA, M, N
-* ..
-* .. Array Arguments ..
- INTEGER IPIV( * )
- COMPLEX*16 A( LDA, * )
-* ..
-*
-* Purpose
-* =======
-*
-* ZGETRF computes an LU factorization of a general M-by-N matrix A
-* using partial pivoting with row interchanges.
-*
-* The factorization has the form
-* A = P * L * U
-* where P is a permutation matrix, L is lower triangular with unit
-* diagonal elements (lower trapezoidal if m > n), and U is upper
-* triangular (upper trapezoidal if m < n).
-*
-* This is the right-looking Level 3 BLAS version of the algorithm.
-*
-* Arguments
-* =========
-*
-* M (input) INTEGER
-* The number of rows of the matrix A. M >= 0.
-*
-* N (input) INTEGER
-* The number of columns of the matrix A. N >= 0.
-*
-* A (input/output) COMPLEX*16 array, dimension (LDA,N)
-* On entry, the M-by-N matrix to be factored.
-* On exit, the factors L and U from the factorization
-* A = P*L*U; the unit diagonal elements of L are not stored.
-*
-* LDA (input) INTEGER
-* The leading dimension of the array A. LDA >= max(1,M).
-*
-* IPIV (output) INTEGER array, dimension (min(M,N))
-* The pivot indices; for 1 <= i <= min(M,N), row i of the
-* matrix was interchanged with row IPIV(i).
-*
-* INFO (output) INTEGER
-* = 0: successful exit
-* < 0: if INFO = -i, the i-th argument had an illegal value
-* > 0: if INFO = i, U(i,i) is exactly zero. The factorization
-* has been completed, but the factor U is exactly
-* singular, and division by zero will occur if it is used
-* to solve a system of equations.
-*
-* =====================================================================
-*
-* .. Parameters ..
- COMPLEX*16 ONE
- PARAMETER ( ONE = ( 1.0D+0, 0.0D+0 ) )
-* ..
-* .. Local Scalars ..
- INTEGER I, IINFO, J, JB, NB
-* ..
-* .. External Subroutines ..
- EXTERNAL XERBLA, ZGEMM, ZGETF2, ZLASWP, ZTRSM
-* ..
-* .. External Functions ..
- INTEGER ILAENV
- EXTERNAL ILAENV
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC MAX, MIN
-* ..
-* .. Executable Statements ..
-*
-* Test the input parameters.
-*
- INFO = 0
- IF( M.LT.0 ) THEN
- INFO = -1
- ELSE IF( N.LT.0 ) THEN
- INFO = -2
- ELSE IF( LDA.LT.MAX( 1, M ) ) THEN
- INFO = -4
- END IF
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'ZGETRF', -INFO )
- RETURN
- END IF
-*
-* Quick return if possible
-*
- IF( M.EQ.0 .OR. N.EQ.0 )
- $ RETURN
-*
-* Determine the block size for this environment.
-*
- NB = ILAENV( 1, 'ZGETRF', ' ', M, N, -1, -1 )
- IF( NB.LE.1 .OR. NB.GE.MIN( M, N ) ) THEN
-*
-* Use unblocked code.
-*
- CALL ZGETF2( M, N, A, LDA, IPIV, INFO )
- ELSE
-*
-* Use blocked code.
-*
- DO 20 J = 1, MIN( M, N ), NB
- JB = MIN( MIN( M, N )-J+1, NB )
-*
-* Factor diagonal and subdiagonal blocks and test for exact
-* singularity.
-*
- CALL ZGETF2( M-J+1, JB, A( J, J ), LDA, IPIV( J ), IINFO )
-*
-* Adjust INFO and the pivot indices.
-*
- IF( INFO.EQ.0 .AND. IINFO.GT.0 )
- $ INFO = IINFO + J - 1
- DO 10 I = J, MIN( M, J+JB-1 )
- IPIV( I ) = J - 1 + IPIV( I )
- 10 CONTINUE
-*
-* Apply interchanges to columns 1:J-1.
-*
- CALL ZLASWP( J-1, A, LDA, J, J+JB-1, IPIV, 1 )
-*
- IF( J+JB.LE.N ) THEN
-*
-* Apply interchanges to columns J+JB:N.
-*
- CALL ZLASWP( N-J-JB+1, A( 1, J+JB ), LDA, J, J+JB-1,
- $ IPIV, 1 )
-*
-* Compute block row of U.
-*
- CALL ZTRSM( 'Left', 'Lower', 'No transpose', 'Unit', JB,
- $ N-J-JB+1, ONE, A( J, J ), LDA, A( J, J+JB ),
- $ LDA )
- IF( J+JB.LE.M ) THEN
-*
-* Update trailing submatrix.
-*
- CALL ZGEMM( 'No transpose', 'No transpose', M-J-JB+1,
- $ N-J-JB+1, JB, -ONE, A( J+JB, J ), LDA,
- $ A( J, J+JB ), LDA, ONE, A( J+JB, J+JB ),
- $ LDA )
- END IF
- END IF
- 20 CONTINUE
- END IF
- RETURN
-*
-* End of ZGETRF
-*
- END
diff --git a/src/lib/lapack/zgetri.f b/src/lib/lapack/zgetri.f
deleted file mode 100644
index 685518e6..00000000
--- a/src/lib/lapack/zgetri.f
+++ /dev/null
@@ -1,193 +0,0 @@
- SUBROUTINE ZGETRI( N, A, LDA, IPIV, WORK, LWORK, INFO )
-*
-* -- LAPACK routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- INTEGER INFO, LDA, LWORK, N
-* ..
-* .. Array Arguments ..
- INTEGER IPIV( * )
- COMPLEX*16 A( LDA, * ), WORK( * )
-* ..
-*
-* Purpose
-* =======
-*
-* ZGETRI computes the inverse of a matrix using the LU factorization
-* computed by ZGETRF.
-*
-* This method inverts U and then computes inv(A) by solving the system
-* inv(A)*L = inv(U) for inv(A).
-*
-* Arguments
-* =========
-*
-* N (input) INTEGER
-* The order of the matrix A. N >= 0.
-*
-* A (input/output) COMPLEX*16 array, dimension (LDA,N)
-* On entry, the factors L and U from the factorization
-* A = P*L*U as computed by ZGETRF.
-* On exit, if INFO = 0, the inverse of the original matrix A.
-*
-* LDA (input) INTEGER
-* The leading dimension of the array A. LDA >= max(1,N).
-*
-* IPIV (input) INTEGER array, dimension (N)
-* The pivot indices from ZGETRF; for 1<=i<=N, row i of the
-* matrix was interchanged with row IPIV(i).
-*
-* WORK (workspace/output) COMPLEX*16 array, dimension (MAX(1,LWORK))
-* On exit, if INFO=0, then WORK(1) returns the optimal LWORK.
-*
-* LWORK (input) INTEGER
-* The dimension of the array WORK. LWORK >= max(1,N).
-* For optimal performance LWORK >= N*NB, where NB is
-* the optimal blocksize returned by ILAENV.
-*
-* If LWORK = -1, then a workspace query is assumed; the routine
-* only calculates the optimal size of the WORK array, returns
-* this value as the first entry of the WORK array, and no error
-* message related to LWORK is issued by XERBLA.
-*
-* INFO (output) INTEGER
-* = 0: successful exit
-* < 0: if INFO = -i, the i-th argument had an illegal value
-* > 0: if INFO = i, U(i,i) is exactly zero; the matrix is
-* singular and its inverse could not be computed.
-*
-* =====================================================================
-*
-* .. Parameters ..
- COMPLEX*16 ZERO, ONE
- PARAMETER ( ZERO = ( 0.0D+0, 0.0D+0 ),
- $ ONE = ( 1.0D+0, 0.0D+0 ) )
-* ..
-* .. Local Scalars ..
- LOGICAL LQUERY
- INTEGER I, IWS, J, JB, JJ, JP, LDWORK, LWKOPT, NB,
- $ NBMIN, NN
-* ..
-* .. External Functions ..
- INTEGER ILAENV
- EXTERNAL ILAENV
-* ..
-* .. External Subroutines ..
- EXTERNAL XERBLA, ZGEMM, ZGEMV, ZSWAP, ZTRSM, ZTRTRI
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC MAX, MIN
-* ..
-* .. Executable Statements ..
-*
-* Test the input parameters.
-*
- INFO = 0
- NB = ILAENV( 1, 'ZGETRI', ' ', N, -1, -1, -1 )
- LWKOPT = N*NB
- WORK( 1 ) = LWKOPT
- LQUERY = ( LWORK.EQ.-1 )
- IF( N.LT.0 ) THEN
- INFO = -1
- ELSE IF( LDA.LT.MAX( 1, N ) ) THEN
- INFO = -3
- ELSE IF( LWORK.LT.MAX( 1, N ) .AND. .NOT.LQUERY ) THEN
- INFO = -6
- END IF
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'ZGETRI', -INFO )
- RETURN
- ELSE IF( LQUERY ) THEN
- RETURN
- END IF
-*
-* Quick return if possible
-*
- IF( N.EQ.0 )
- $ RETURN
-*
-* Form inv(U). If INFO > 0 from ZTRTRI, then U is singular,
-* and the inverse is not computed.
-*
- CALL ZTRTRI( 'Upper', 'Non-unit', N, A, LDA, INFO )
- IF( INFO.GT.0 )
- $ RETURN
-*
- NBMIN = 2
- LDWORK = N
- IF( NB.GT.1 .AND. NB.LT.N ) THEN
- IWS = MAX( LDWORK*NB, 1 )
- IF( LWORK.LT.IWS ) THEN
- NB = LWORK / LDWORK
- NBMIN = MAX( 2, ILAENV( 2, 'ZGETRI', ' ', N, -1, -1, -1 ) )
- END IF
- ELSE
- IWS = N
- END IF
-*
-* Solve the equation inv(A)*L = inv(U) for inv(A).
-*
- IF( NB.LT.NBMIN .OR. NB.GE.N ) THEN
-*
-* Use unblocked code.
-*
- DO 20 J = N, 1, -1
-*
-* Copy current column of L to WORK and replace with zeros.
-*
- DO 10 I = J + 1, N
- WORK( I ) = A( I, J )
- A( I, J ) = ZERO
- 10 CONTINUE
-*
-* Compute current column of inv(A).
-*
- IF( J.LT.N )
- $ CALL ZGEMV( 'No transpose', N, N-J, -ONE, A( 1, J+1 ),
- $ LDA, WORK( J+1 ), 1, ONE, A( 1, J ), 1 )
- 20 CONTINUE
- ELSE
-*
-* Use blocked code.
-*
- NN = ( ( N-1 ) / NB )*NB + 1
- DO 50 J = NN, 1, -NB
- JB = MIN( NB, N-J+1 )
-*
-* Copy current block column of L to WORK and replace with
-* zeros.
-*
- DO 40 JJ = J, J + JB - 1
- DO 30 I = JJ + 1, N
- WORK( I+( JJ-J )*LDWORK ) = A( I, JJ )
- A( I, JJ ) = ZERO
- 30 CONTINUE
- 40 CONTINUE
-*
-* Compute current block column of inv(A).
-*
- IF( J+JB.LE.N )
- $ CALL ZGEMM( 'No transpose', 'No transpose', N, JB,
- $ N-J-JB+1, -ONE, A( 1, J+JB ), LDA,
- $ WORK( J+JB ), LDWORK, ONE, A( 1, J ), LDA )
- CALL ZTRSM( 'Right', 'Lower', 'No transpose', 'Unit', N, JB,
- $ ONE, WORK( J ), LDWORK, A( 1, J ), LDA )
- 50 CONTINUE
- END IF
-*
-* Apply column interchanges.
-*
- DO 60 J = N - 1, 1, -1
- JP = IPIV( J )
- IF( JP.NE.J )
- $ CALL ZSWAP( N, A( 1, J ), 1, A( 1, JP ), 1 )
- 60 CONTINUE
-*
- WORK( 1 ) = IWS
- RETURN
-*
-* End of ZGETRI
-*
- END
diff --git a/src/lib/lapack/zgetrs.f b/src/lib/lapack/zgetrs.f
deleted file mode 100644
index e32549cd..00000000
--- a/src/lib/lapack/zgetrs.f
+++ /dev/null
@@ -1,149 +0,0 @@
- SUBROUTINE ZGETRS( TRANS, N, NRHS, A, LDA, IPIV, B, LDB, INFO )
-*
-* -- LAPACK routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- CHARACTER TRANS
- INTEGER INFO, LDA, LDB, N, NRHS
-* ..
-* .. Array Arguments ..
- INTEGER IPIV( * )
- COMPLEX*16 A( LDA, * ), B( LDB, * )
-* ..
-*
-* Purpose
-* =======
-*
-* ZGETRS solves a system of linear equations
-* A * X = B, A**T * X = B, or A**H * X = B
-* with a general N-by-N matrix A using the LU factorization computed
-* by ZGETRF.
-*
-* Arguments
-* =========
-*
-* TRANS (input) CHARACTER*1
-* Specifies the form of the system of equations:
-* = 'N': A * X = B (No transpose)
-* = 'T': A**T * X = B (Transpose)
-* = 'C': A**H * X = B (Conjugate transpose)
-*
-* N (input) INTEGER
-* The order of the matrix A. N >= 0.
-*
-* NRHS (input) INTEGER
-* The number of right hand sides, i.e., the number of columns
-* of the matrix B. NRHS >= 0.
-*
-* A (input) COMPLEX*16 array, dimension (LDA,N)
-* The factors L and U from the factorization A = P*L*U
-* as computed by ZGETRF.
-*
-* LDA (input) INTEGER
-* The leading dimension of the array A. LDA >= max(1,N).
-*
-* IPIV (input) INTEGER array, dimension (N)
-* The pivot indices from ZGETRF; for 1<=i<=N, row i of the
-* matrix was interchanged with row IPIV(i).
-*
-* B (input/output) COMPLEX*16 array, dimension (LDB,NRHS)
-* On entry, the right hand side matrix B.
-* On exit, the solution matrix X.
-*
-* LDB (input) INTEGER
-* The leading dimension of the array B. LDB >= max(1,N).
-*
-* INFO (output) INTEGER
-* = 0: successful exit
-* < 0: if INFO = -i, the i-th argument had an illegal value
-*
-* =====================================================================
-*
-* .. Parameters ..
- COMPLEX*16 ONE
- PARAMETER ( ONE = ( 1.0D+0, 0.0D+0 ) )
-* ..
-* .. Local Scalars ..
- LOGICAL NOTRAN
-* ..
-* .. External Functions ..
- LOGICAL LSAME
- EXTERNAL LSAME
-* ..
-* .. External Subroutines ..
- EXTERNAL XERBLA, ZLASWP, ZTRSM
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC MAX
-* ..
-* .. Executable Statements ..
-*
-* Test the input parameters.
-*
- INFO = 0
- NOTRAN = LSAME( TRANS, 'N' )
- IF( .NOT.NOTRAN .AND. .NOT.LSAME( TRANS, 'T' ) .AND. .NOT.
- $ LSAME( TRANS, 'C' ) ) THEN
- INFO = -1
- ELSE IF( N.LT.0 ) THEN
- INFO = -2
- ELSE IF( NRHS.LT.0 ) THEN
- INFO = -3
- ELSE IF( LDA.LT.MAX( 1, N ) ) THEN
- INFO = -5
- ELSE IF( LDB.LT.MAX( 1, N ) ) THEN
- INFO = -8
- END IF
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'ZGETRS', -INFO )
- RETURN
- END IF
-*
-* Quick return if possible
-*
- IF( N.EQ.0 .OR. NRHS.EQ.0 )
- $ RETURN
-*
- IF( NOTRAN ) THEN
-*
-* Solve A * X = B.
-*
-* Apply row interchanges to the right hand sides.
-*
- CALL ZLASWP( NRHS, B, LDB, 1, N, IPIV, 1 )
-*
-* Solve L*X = B, overwriting B with X.
-*
- CALL ZTRSM( 'Left', 'Lower', 'No transpose', 'Unit', N, NRHS,
- $ ONE, A, LDA, B, LDB )
-*
-* Solve U*X = B, overwriting B with X.
-*
- CALL ZTRSM( 'Left', 'Upper', 'No transpose', 'Non-unit', N,
- $ NRHS, ONE, A, LDA, B, LDB )
- ELSE
-*
-* Solve A**T * X = B or A**H * X = B.
-*
-* Solve U'*X = B, overwriting B with X.
-*
- CALL ZTRSM( 'Left', 'Upper', TRANS, 'Non-unit', N, NRHS, ONE,
- $ A, LDA, B, LDB )
-*
-* Solve L'*X = B, overwriting B with X.
-*
- CALL ZTRSM( 'Left', 'Lower', TRANS, 'Unit', N, NRHS, ONE, A,
- $ LDA, B, LDB )
-*
-* Apply row interchanges to the solution vectors.
-*
- CALL ZLASWP( NRHS, B, LDB, 1, N, IPIV, -1 )
- END IF
-*
- RETURN
-*
-* End of ZGETRS
-*
- END
diff --git a/src/lib/lapack/zggbak.f b/src/lib/lapack/zggbak.f
deleted file mode 100644
index ad6dd032..00000000
--- a/src/lib/lapack/zggbak.f
+++ /dev/null
@@ -1,220 +0,0 @@
- SUBROUTINE ZGGBAK( JOB, SIDE, N, ILO, IHI, LSCALE, RSCALE, M, V,
- $ LDV, INFO )
-*
-* -- LAPACK routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- CHARACTER JOB, SIDE
- INTEGER IHI, ILO, INFO, LDV, M, N
-* ..
-* .. Array Arguments ..
- DOUBLE PRECISION LSCALE( * ), RSCALE( * )
- COMPLEX*16 V( LDV, * )
-* ..
-*
-* Purpose
-* =======
-*
-* ZGGBAK forms the right or left eigenvectors of a complex generalized
-* eigenvalue problem A*x = lambda*B*x, by backward transformation on
-* the computed eigenvectors of the balanced pair of matrices output by
-* ZGGBAL.
-*
-* Arguments
-* =========
-*
-* JOB (input) CHARACTER*1
-* Specifies the type of backward transformation required:
-* = 'N': do nothing, return immediately;
-* = 'P': do backward transformation for permutation only;
-* = 'S': do backward transformation for scaling only;
-* = 'B': do backward transformations for both permutation and
-* scaling.
-* JOB must be the same as the argument JOB supplied to ZGGBAL.
-*
-* SIDE (input) CHARACTER*1
-* = 'R': V contains right eigenvectors;
-* = 'L': V contains left eigenvectors.
-*
-* N (input) INTEGER
-* The number of rows of the matrix V. N >= 0.
-*
-* ILO (input) INTEGER
-* IHI (input) INTEGER
-* The integers ILO and IHI determined by ZGGBAL.
-* 1 <= ILO <= IHI <= N, if N > 0; ILO=1 and IHI=0, if N=0.
-*
-* LSCALE (input) DOUBLE PRECISION array, dimension (N)
-* Details of the permutations and/or scaling factors applied
-* to the left side of A and B, as returned by ZGGBAL.
-*
-* RSCALE (input) DOUBLE PRECISION array, dimension (N)
-* Details of the permutations and/or scaling factors applied
-* to the right side of A and B, as returned by ZGGBAL.
-*
-* M (input) INTEGER
-* The number of columns of the matrix V. M >= 0.
-*
-* V (input/output) COMPLEX*16 array, dimension (LDV,M)
-* On entry, the matrix of right or left eigenvectors to be
-* transformed, as returned by ZTGEVC.
-* On exit, V is overwritten by the transformed eigenvectors.
-*
-* LDV (input) INTEGER
-* The leading dimension of the matrix V. LDV >= max(1,N).
-*
-* INFO (output) INTEGER
-* = 0: successful exit.
-* < 0: if INFO = -i, the i-th argument had an illegal value.
-*
-* Further Details
-* ===============
-*
-* See R.C. Ward, Balancing the generalized eigenvalue problem,
-* SIAM J. Sci. Stat. Comp. 2 (1981), 141-152.
-*
-* =====================================================================
-*
-* .. Local Scalars ..
- LOGICAL LEFTV, RIGHTV
- INTEGER I, K
-* ..
-* .. External Functions ..
- LOGICAL LSAME
- EXTERNAL LSAME
-* ..
-* .. External Subroutines ..
- EXTERNAL XERBLA, ZDSCAL, ZSWAP
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC MAX
-* ..
-* .. Executable Statements ..
-*
-* Test the input parameters
-*
- RIGHTV = LSAME( SIDE, 'R' )
- LEFTV = LSAME( SIDE, 'L' )
-*
- INFO = 0
- IF( .NOT.LSAME( JOB, 'N' ) .AND. .NOT.LSAME( JOB, 'P' ) .AND.
- $ .NOT.LSAME( JOB, 'S' ) .AND. .NOT.LSAME( JOB, 'B' ) ) THEN
- INFO = -1
- ELSE IF( .NOT.RIGHTV .AND. .NOT.LEFTV ) THEN
- INFO = -2
- ELSE IF( N.LT.0 ) THEN
- INFO = -3
- ELSE IF( ILO.LT.1 ) THEN
- INFO = -4
- ELSE IF( N.EQ.0 .AND. IHI.EQ.0 .AND. ILO.NE.1 ) THEN
- INFO = -4
- ELSE IF( N.GT.0 .AND. ( IHI.LT.ILO .OR. IHI.GT.MAX( 1, N ) ) )
- $ THEN
- INFO = -5
- ELSE IF( N.EQ.0 .AND. ILO.EQ.1 .AND. IHI.NE.0 ) THEN
- INFO = -5
- ELSE IF( M.LT.0 ) THEN
- INFO = -8
- ELSE IF( LDV.LT.MAX( 1, N ) ) THEN
- INFO = -10
- END IF
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'ZGGBAK', -INFO )
- RETURN
- END IF
-*
-* Quick return if possible
-*
- IF( N.EQ.0 )
- $ RETURN
- IF( M.EQ.0 )
- $ RETURN
- IF( LSAME( JOB, 'N' ) )
- $ RETURN
-*
- IF( ILO.EQ.IHI )
- $ GO TO 30
-*
-* Backward balance
-*
- IF( LSAME( JOB, 'S' ) .OR. LSAME( JOB, 'B' ) ) THEN
-*
-* Backward transformation on right eigenvectors
-*
- IF( RIGHTV ) THEN
- DO 10 I = ILO, IHI
- CALL ZDSCAL( M, RSCALE( I ), V( I, 1 ), LDV )
- 10 CONTINUE
- END IF
-*
-* Backward transformation on left eigenvectors
-*
- IF( LEFTV ) THEN
- DO 20 I = ILO, IHI
- CALL ZDSCAL( M, LSCALE( I ), V( I, 1 ), LDV )
- 20 CONTINUE
- END IF
- END IF
-*
-* Backward permutation
-*
- 30 CONTINUE
- IF( LSAME( JOB, 'P' ) .OR. LSAME( JOB, 'B' ) ) THEN
-*
-* Backward permutation on right eigenvectors
-*
- IF( RIGHTV ) THEN
- IF( ILO.EQ.1 )
- $ GO TO 50
- DO 40 I = ILO - 1, 1, -1
- K = RSCALE( I )
- IF( K.EQ.I )
- $ GO TO 40
- CALL ZSWAP( M, V( I, 1 ), LDV, V( K, 1 ), LDV )
- 40 CONTINUE
-*
- 50 CONTINUE
- IF( IHI.EQ.N )
- $ GO TO 70
- DO 60 I = IHI + 1, N
- K = RSCALE( I )
- IF( K.EQ.I )
- $ GO TO 60
- CALL ZSWAP( M, V( I, 1 ), LDV, V( K, 1 ), LDV )
- 60 CONTINUE
- END IF
-*
-* Backward permutation on left eigenvectors
-*
- 70 CONTINUE
- IF( LEFTV ) THEN
- IF( ILO.EQ.1 )
- $ GO TO 90
- DO 80 I = ILO - 1, 1, -1
- K = LSCALE( I )
- IF( K.EQ.I )
- $ GO TO 80
- CALL ZSWAP( M, V( I, 1 ), LDV, V( K, 1 ), LDV )
- 80 CONTINUE
-*
- 90 CONTINUE
- IF( IHI.EQ.N )
- $ GO TO 110
- DO 100 I = IHI + 1, N
- K = LSCALE( I )
- IF( K.EQ.I )
- $ GO TO 100
- CALL ZSWAP( M, V( I, 1 ), LDV, V( K, 1 ), LDV )
- 100 CONTINUE
- END IF
- END IF
-*
- 110 CONTINUE
-*
- RETURN
-*
-* End of ZGGBAK
-*
- END
diff --git a/src/lib/lapack/zggbal.f b/src/lib/lapack/zggbal.f
deleted file mode 100644
index b75ae456..00000000
--- a/src/lib/lapack/zggbal.f
+++ /dev/null
@@ -1,482 +0,0 @@
- SUBROUTINE ZGGBAL( JOB, N, A, LDA, B, LDB, ILO, IHI, LSCALE,
- $ RSCALE, WORK, INFO )
-*
-* -- LAPACK routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- CHARACTER JOB
- INTEGER IHI, ILO, INFO, LDA, LDB, N
-* ..
-* .. Array Arguments ..
- DOUBLE PRECISION LSCALE( * ), RSCALE( * ), WORK( * )
- COMPLEX*16 A( LDA, * ), B( LDB, * )
-* ..
-*
-* Purpose
-* =======
-*
-* ZGGBAL balances a pair of general complex matrices (A,B). This
-* involves, first, permuting A and B by similarity transformations to
-* isolate eigenvalues in the first 1 to ILO$-$1 and last IHI+1 to N
-* elements on the diagonal; and second, applying a diagonal similarity
-* transformation to rows and columns ILO to IHI to make the rows
-* and columns as close in norm as possible. Both steps are optional.
-*
-* Balancing may reduce the 1-norm of the matrices, and improve the
-* accuracy of the computed eigenvalues and/or eigenvectors in the
-* generalized eigenvalue problem A*x = lambda*B*x.
-*
-* Arguments
-* =========
-*
-* JOB (input) CHARACTER*1
-* Specifies the operations to be performed on A and B:
-* = 'N': none: simply set ILO = 1, IHI = N, LSCALE(I) = 1.0
-* and RSCALE(I) = 1.0 for i=1,...,N;
-* = 'P': permute only;
-* = 'S': scale only;
-* = 'B': both permute and scale.
-*
-* N (input) INTEGER
-* The order of the matrices A and B. N >= 0.
-*
-* A (input/output) COMPLEX*16 array, dimension (LDA,N)
-* On entry, the input matrix A.
-* On exit, A is overwritten by the balanced matrix.
-* If JOB = 'N', A is not referenced.
-*
-* LDA (input) INTEGER
-* The leading dimension of the array A. LDA >= max(1,N).
-*
-* B (input/output) COMPLEX*16 array, dimension (LDB,N)
-* On entry, the input matrix B.
-* On exit, B is overwritten by the balanced matrix.
-* If JOB = 'N', B is not referenced.
-*
-* LDB (input) INTEGER
-* The leading dimension of the array B. LDB >= max(1,N).
-*
-* ILO (output) INTEGER
-* IHI (output) INTEGER
-* ILO and IHI are set to integers such that on exit
-* A(i,j) = 0 and B(i,j) = 0 if i > j and
-* j = 1,...,ILO-1 or i = IHI+1,...,N.
-* If JOB = 'N' or 'S', ILO = 1 and IHI = N.
-*
-* LSCALE (output) DOUBLE PRECISION array, dimension (N)
-* Details of the permutations and scaling factors applied
-* to the left side of A and B. If P(j) is the index of the
-* row interchanged with row j, and D(j) is the scaling factor
-* applied to row j, then
-* LSCALE(j) = P(j) for J = 1,...,ILO-1
-* = D(j) for J = ILO,...,IHI
-* = P(j) for J = IHI+1,...,N.
-* The order in which the interchanges are made is N to IHI+1,
-* then 1 to ILO-1.
-*
-* RSCALE (output) DOUBLE PRECISION array, dimension (N)
-* Details of the permutations and scaling factors applied
-* to the right side of A and B. If P(j) is the index of the
-* column interchanged with column j, and D(j) is the scaling
-* factor applied to column j, then
-* RSCALE(j) = P(j) for J = 1,...,ILO-1
-* = D(j) for J = ILO,...,IHI
-* = P(j) for J = IHI+1,...,N.
-* The order in which the interchanges are made is N to IHI+1,
-* then 1 to ILO-1.
-*
-* WORK (workspace) REAL array, dimension (lwork)
-* lwork must be at least max(1,6*N) when JOB = 'S' or 'B', and
-* at least 1 when JOB = 'N' or 'P'.
-*
-* INFO (output) INTEGER
-* = 0: successful exit
-* < 0: if INFO = -i, the i-th argument had an illegal value.
-*
-* Further Details
-* ===============
-*
-* See R.C. WARD, Balancing the generalized eigenvalue problem,
-* SIAM J. Sci. Stat. Comp. 2 (1981), 141-152.
-*
-* =====================================================================
-*
-* .. Parameters ..
- DOUBLE PRECISION ZERO, HALF, ONE
- PARAMETER ( ZERO = 0.0D+0, HALF = 0.5D+0, ONE = 1.0D+0 )
- DOUBLE PRECISION THREE, SCLFAC
- PARAMETER ( THREE = 3.0D+0, SCLFAC = 1.0D+1 )
- COMPLEX*16 CZERO
- PARAMETER ( CZERO = ( 0.0D+0, 0.0D+0 ) )
-* ..
-* .. Local Scalars ..
- INTEGER I, ICAB, IFLOW, IP1, IR, IRAB, IT, J, JC, JP1,
- $ K, KOUNT, L, LCAB, LM1, LRAB, LSFMAX, LSFMIN,
- $ M, NR, NRP2
- DOUBLE PRECISION ALPHA, BASL, BETA, CAB, CMAX, COEF, COEF2,
- $ COEF5, COR, EW, EWC, GAMMA, PGAMMA, RAB, SFMAX,
- $ SFMIN, SUM, T, TA, TB, TC
- COMPLEX*16 CDUM
-* ..
-* .. External Functions ..
- LOGICAL LSAME
- INTEGER IZAMAX
- DOUBLE PRECISION DDOT, DLAMCH
- EXTERNAL LSAME, IZAMAX, DDOT, DLAMCH
-* ..
-* .. External Subroutines ..
- EXTERNAL DAXPY, DSCAL, XERBLA, ZDSCAL, ZSWAP
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC ABS, DBLE, DIMAG, INT, LOG10, MAX, MIN, SIGN
-* ..
-* .. Statement Functions ..
- DOUBLE PRECISION CABS1
-* ..
-* .. Statement Function definitions ..
- CABS1( CDUM ) = ABS( DBLE( CDUM ) ) + ABS( DIMAG( CDUM ) )
-* ..
-* .. Executable Statements ..
-*
-* Test the input parameters
-*
- INFO = 0
- IF( .NOT.LSAME( JOB, 'N' ) .AND. .NOT.LSAME( JOB, 'P' ) .AND.
- $ .NOT.LSAME( JOB, 'S' ) .AND. .NOT.LSAME( JOB, 'B' ) ) THEN
- INFO = -1
- ELSE IF( N.LT.0 ) THEN
- INFO = -2
- ELSE IF( LDA.LT.MAX( 1, N ) ) THEN
- INFO = -4
- ELSE IF( LDB.LT.MAX( 1, N ) ) THEN
- INFO = -6
- END IF
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'ZGGBAL', -INFO )
- RETURN
- END IF
-*
-* Quick return if possible
-*
- IF( N.EQ.0 ) THEN
- ILO = 1
- IHI = N
- RETURN
- END IF
-*
- IF( N.EQ.1 ) THEN
- ILO = 1
- IHI = N
- LSCALE( 1 ) = ONE
- RSCALE( 1 ) = ONE
- RETURN
- END IF
-*
- IF( LSAME( JOB, 'N' ) ) THEN
- ILO = 1
- IHI = N
- DO 10 I = 1, N
- LSCALE( I ) = ONE
- RSCALE( I ) = ONE
- 10 CONTINUE
- RETURN
- END IF
-*
- K = 1
- L = N
- IF( LSAME( JOB, 'S' ) )
- $ GO TO 190
-*
- GO TO 30
-*
-* Permute the matrices A and B to isolate the eigenvalues.
-*
-* Find row with one nonzero in columns 1 through L
-*
- 20 CONTINUE
- L = LM1
- IF( L.NE.1 )
- $ GO TO 30
-*
- RSCALE( 1 ) = 1
- LSCALE( 1 ) = 1
- GO TO 190
-*
- 30 CONTINUE
- LM1 = L - 1
- DO 80 I = L, 1, -1
- DO 40 J = 1, LM1
- JP1 = J + 1
- IF( A( I, J ).NE.CZERO .OR. B( I, J ).NE.CZERO )
- $ GO TO 50
- 40 CONTINUE
- J = L
- GO TO 70
-*
- 50 CONTINUE
- DO 60 J = JP1, L
- IF( A( I, J ).NE.CZERO .OR. B( I, J ).NE.CZERO )
- $ GO TO 80
- 60 CONTINUE
- J = JP1 - 1
-*
- 70 CONTINUE
- M = L
- IFLOW = 1
- GO TO 160
- 80 CONTINUE
- GO TO 100
-*
-* Find column with one nonzero in rows K through N
-*
- 90 CONTINUE
- K = K + 1
-*
- 100 CONTINUE
- DO 150 J = K, L
- DO 110 I = K, LM1
- IP1 = I + 1
- IF( A( I, J ).NE.CZERO .OR. B( I, J ).NE.CZERO )
- $ GO TO 120
- 110 CONTINUE
- I = L
- GO TO 140
- 120 CONTINUE
- DO 130 I = IP1, L
- IF( A( I, J ).NE.CZERO .OR. B( I, J ).NE.CZERO )
- $ GO TO 150
- 130 CONTINUE
- I = IP1 - 1
- 140 CONTINUE
- M = K
- IFLOW = 2
- GO TO 160
- 150 CONTINUE
- GO TO 190
-*
-* Permute rows M and I
-*
- 160 CONTINUE
- LSCALE( M ) = I
- IF( I.EQ.M )
- $ GO TO 170
- CALL ZSWAP( N-K+1, A( I, K ), LDA, A( M, K ), LDA )
- CALL ZSWAP( N-K+1, B( I, K ), LDB, B( M, K ), LDB )
-*
-* Permute columns M and J
-*
- 170 CONTINUE
- RSCALE( M ) = J
- IF( J.EQ.M )
- $ GO TO 180
- CALL ZSWAP( L, A( 1, J ), 1, A( 1, M ), 1 )
- CALL ZSWAP( L, B( 1, J ), 1, B( 1, M ), 1 )
-*
- 180 CONTINUE
- GO TO ( 20, 90 )IFLOW
-*
- 190 CONTINUE
- ILO = K
- IHI = L
-*
- IF( LSAME( JOB, 'P' ) ) THEN
- DO 195 I = ILO, IHI
- LSCALE( I ) = ONE
- RSCALE( I ) = ONE
- 195 CONTINUE
- RETURN
- END IF
-*
- IF( ILO.EQ.IHI )
- $ RETURN
-*
-* Balance the submatrix in rows ILO to IHI.
-*
- NR = IHI - ILO + 1
- DO 200 I = ILO, IHI
- RSCALE( I ) = ZERO
- LSCALE( I ) = ZERO
-*
- WORK( I ) = ZERO
- WORK( I+N ) = ZERO
- WORK( I+2*N ) = ZERO
- WORK( I+3*N ) = ZERO
- WORK( I+4*N ) = ZERO
- WORK( I+5*N ) = ZERO
- 200 CONTINUE
-*
-* Compute right side vector in resulting linear equations
-*
- BASL = LOG10( SCLFAC )
- DO 240 I = ILO, IHI
- DO 230 J = ILO, IHI
- IF( A( I, J ).EQ.CZERO ) THEN
- TA = ZERO
- GO TO 210
- END IF
- TA = LOG10( CABS1( A( I, J ) ) ) / BASL
-*
- 210 CONTINUE
- IF( B( I, J ).EQ.CZERO ) THEN
- TB = ZERO
- GO TO 220
- END IF
- TB = LOG10( CABS1( B( I, J ) ) ) / BASL
-*
- 220 CONTINUE
- WORK( I+4*N ) = WORK( I+4*N ) - TA - TB
- WORK( J+5*N ) = WORK( J+5*N ) - TA - TB
- 230 CONTINUE
- 240 CONTINUE
-*
- COEF = ONE / DBLE( 2*NR )
- COEF2 = COEF*COEF
- COEF5 = HALF*COEF2
- NRP2 = NR + 2
- BETA = ZERO
- IT = 1
-*
-* Start generalized conjugate gradient iteration
-*
- 250 CONTINUE
-*
- GAMMA = DDOT( NR, WORK( ILO+4*N ), 1, WORK( ILO+4*N ), 1 ) +
- $ DDOT( NR, WORK( ILO+5*N ), 1, WORK( ILO+5*N ), 1 )
-*
- EW = ZERO
- EWC = ZERO
- DO 260 I = ILO, IHI
- EW = EW + WORK( I+4*N )
- EWC = EWC + WORK( I+5*N )
- 260 CONTINUE
-*
- GAMMA = COEF*GAMMA - COEF2*( EW**2+EWC**2 ) - COEF5*( EW-EWC )**2
- IF( GAMMA.EQ.ZERO )
- $ GO TO 350
- IF( IT.NE.1 )
- $ BETA = GAMMA / PGAMMA
- T = COEF5*( EWC-THREE*EW )
- TC = COEF5*( EW-THREE*EWC )
-*
- CALL DSCAL( NR, BETA, WORK( ILO ), 1 )
- CALL DSCAL( NR, BETA, WORK( ILO+N ), 1 )
-*
- CALL DAXPY( NR, COEF, WORK( ILO+4*N ), 1, WORK( ILO+N ), 1 )
- CALL DAXPY( NR, COEF, WORK( ILO+5*N ), 1, WORK( ILO ), 1 )
-*
- DO 270 I = ILO, IHI
- WORK( I ) = WORK( I ) + TC
- WORK( I+N ) = WORK( I+N ) + T
- 270 CONTINUE
-*
-* Apply matrix to vector
-*
- DO 300 I = ILO, IHI
- KOUNT = 0
- SUM = ZERO
- DO 290 J = ILO, IHI
- IF( A( I, J ).EQ.CZERO )
- $ GO TO 280
- KOUNT = KOUNT + 1
- SUM = SUM + WORK( J )
- 280 CONTINUE
- IF( B( I, J ).EQ.CZERO )
- $ GO TO 290
- KOUNT = KOUNT + 1
- SUM = SUM + WORK( J )
- 290 CONTINUE
- WORK( I+2*N ) = DBLE( KOUNT )*WORK( I+N ) + SUM
- 300 CONTINUE
-*
- DO 330 J = ILO, IHI
- KOUNT = 0
- SUM = ZERO
- DO 320 I = ILO, IHI
- IF( A( I, J ).EQ.CZERO )
- $ GO TO 310
- KOUNT = KOUNT + 1
- SUM = SUM + WORK( I+N )
- 310 CONTINUE
- IF( B( I, J ).EQ.CZERO )
- $ GO TO 320
- KOUNT = KOUNT + 1
- SUM = SUM + WORK( I+N )
- 320 CONTINUE
- WORK( J+3*N ) = DBLE( KOUNT )*WORK( J ) + SUM
- 330 CONTINUE
-*
- SUM = DDOT( NR, WORK( ILO+N ), 1, WORK( ILO+2*N ), 1 ) +
- $ DDOT( NR, WORK( ILO ), 1, WORK( ILO+3*N ), 1 )
- ALPHA = GAMMA / SUM
-*
-* Determine correction to current iteration
-*
- CMAX = ZERO
- DO 340 I = ILO, IHI
- COR = ALPHA*WORK( I+N )
- IF( ABS( COR ).GT.CMAX )
- $ CMAX = ABS( COR )
- LSCALE( I ) = LSCALE( I ) + COR
- COR = ALPHA*WORK( I )
- IF( ABS( COR ).GT.CMAX )
- $ CMAX = ABS( COR )
- RSCALE( I ) = RSCALE( I ) + COR
- 340 CONTINUE
- IF( CMAX.LT.HALF )
- $ GO TO 350
-*
- CALL DAXPY( NR, -ALPHA, WORK( ILO+2*N ), 1, WORK( ILO+4*N ), 1 )
- CALL DAXPY( NR, -ALPHA, WORK( ILO+3*N ), 1, WORK( ILO+5*N ), 1 )
-*
- PGAMMA = GAMMA
- IT = IT + 1
- IF( IT.LE.NRP2 )
- $ GO TO 250
-*
-* End generalized conjugate gradient iteration
-*
- 350 CONTINUE
- SFMIN = DLAMCH( 'S' )
- SFMAX = ONE / SFMIN
- LSFMIN = INT( LOG10( SFMIN ) / BASL+ONE )
- LSFMAX = INT( LOG10( SFMAX ) / BASL )
- DO 360 I = ILO, IHI
- IRAB = IZAMAX( N-ILO+1, A( I, ILO ), LDA )
- RAB = ABS( A( I, IRAB+ILO-1 ) )
- IRAB = IZAMAX( N-ILO+1, B( I, ILO ), LDB )
- RAB = MAX( RAB, ABS( B( I, IRAB+ILO-1 ) ) )
- LRAB = INT( LOG10( RAB+SFMIN ) / BASL+ONE )
- IR = LSCALE( I ) + SIGN( HALF, LSCALE( I ) )
- IR = MIN( MAX( IR, LSFMIN ), LSFMAX, LSFMAX-LRAB )
- LSCALE( I ) = SCLFAC**IR
- ICAB = IZAMAX( IHI, A( 1, I ), 1 )
- CAB = ABS( A( ICAB, I ) )
- ICAB = IZAMAX( IHI, B( 1, I ), 1 )
- CAB = MAX( CAB, ABS( B( ICAB, I ) ) )
- LCAB = INT( LOG10( CAB+SFMIN ) / BASL+ONE )
- JC = RSCALE( I ) + SIGN( HALF, RSCALE( I ) )
- JC = MIN( MAX( JC, LSFMIN ), LSFMAX, LSFMAX-LCAB )
- RSCALE( I ) = SCLFAC**JC
- 360 CONTINUE
-*
-* Row scaling of matrices A and B
-*
- DO 370 I = ILO, IHI
- CALL ZDSCAL( N-ILO+1, LSCALE( I ), A( I, ILO ), LDA )
- CALL ZDSCAL( N-ILO+1, LSCALE( I ), B( I, ILO ), LDB )
- 370 CONTINUE
-*
-* Column scaling of matrices A and B
-*
- DO 380 J = ILO, IHI
- CALL ZDSCAL( IHI, RSCALE( J ), A( 1, J ), 1 )
- CALL ZDSCAL( IHI, RSCALE( J ), B( 1, J ), 1 )
- 380 CONTINUE
-*
- RETURN
-*
-* End of ZGGBAL
-*
- END
diff --git a/src/lib/lapack/zgges.f b/src/lib/lapack/zgges.f
deleted file mode 100644
index c1499003..00000000
--- a/src/lib/lapack/zgges.f
+++ /dev/null
@@ -1,477 +0,0 @@
- SUBROUTINE ZGGES( JOBVSL, JOBVSR, SORT, SELCTG, N, A, LDA, B, LDB,
- $ SDIM, ALPHA, BETA, VSL, LDVSL, VSR, LDVSR, WORK,
- $ LWORK, RWORK, BWORK, INFO )
-*
-* -- LAPACK driver routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- CHARACTER JOBVSL, JOBVSR, SORT
- INTEGER INFO, LDA, LDB, LDVSL, LDVSR, LWORK, N, SDIM
-* ..
-* .. Array Arguments ..
- LOGICAL BWORK( * )
- DOUBLE PRECISION RWORK( * )
- COMPLEX*16 A( LDA, * ), ALPHA( * ), B( LDB, * ),
- $ BETA( * ), VSL( LDVSL, * ), VSR( LDVSR, * ),
- $ WORK( * )
-* ..
-* .. Function Arguments ..
- LOGICAL SELCTG
- EXTERNAL SELCTG
-* ..
-*
-* Purpose
-* =======
-*
-* ZGGES computes for a pair of N-by-N complex nonsymmetric matrices
-* (A,B), the generalized eigenvalues, the generalized complex Schur
-* form (S, T), and optionally left and/or right Schur vectors (VSL
-* and VSR). This gives the generalized Schur factorization
-*
-* (A,B) = ( (VSL)*S*(VSR)**H, (VSL)*T*(VSR)**H )
-*
-* where (VSR)**H is the conjugate-transpose of VSR.
-*
-* Optionally, it also orders the eigenvalues so that a selected cluster
-* of eigenvalues appears in the leading diagonal blocks of the upper
-* triangular matrix S and the upper triangular matrix T. The leading
-* columns of VSL and VSR then form an unitary basis for the
-* corresponding left and right eigenspaces (deflating subspaces).
-*
-* (If only the generalized eigenvalues are needed, use the driver
-* ZGGEV instead, which is faster.)
-*
-* A generalized eigenvalue for a pair of matrices (A,B) is a scalar w
-* or a ratio alpha/beta = w, such that A - w*B is singular. It is
-* usually represented as the pair (alpha,beta), as there is a
-* reasonable interpretation for beta=0, and even for both being zero.
-*
-* A pair of matrices (S,T) is in generalized complex Schur form if S
-* and T are upper triangular and, in addition, the diagonal elements
-* of T are non-negative real numbers.
-*
-* Arguments
-* =========
-*
-* JOBVSL (input) CHARACTER*1
-* = 'N': do not compute the left Schur vectors;
-* = 'V': compute the left Schur vectors.
-*
-* JOBVSR (input) CHARACTER*1
-* = 'N': do not compute the right Schur vectors;
-* = 'V': compute the right Schur vectors.
-*
-* SORT (input) CHARACTER*1
-* Specifies whether or not to order the eigenvalues on the
-* diagonal of the generalized Schur form.
-* = 'N': Eigenvalues are not ordered;
-* = 'S': Eigenvalues are ordered (see SELCTG).
-*
-* SELCTG (external procedure) LOGICAL FUNCTION of two COMPLEX*16 arguments
-* SELCTG must be declared EXTERNAL in the calling subroutine.
-* If SORT = 'N', SELCTG is not referenced.
-* If SORT = 'S', SELCTG is used to select eigenvalues to sort
-* to the top left of the Schur form.
-* An eigenvalue ALPHA(j)/BETA(j) is selected if
-* SELCTG(ALPHA(j),BETA(j)) is true.
-*
-* Note that a selected complex eigenvalue may no longer satisfy
-* SELCTG(ALPHA(j),BETA(j)) = .TRUE. after ordering, since
-* ordering may change the value of complex eigenvalues
-* (especially if the eigenvalue is ill-conditioned), in this
-* case INFO is set to N+2 (See INFO below).
-*
-* N (input) INTEGER
-* The order of the matrices A, B, VSL, and VSR. N >= 0.
-*
-* A (input/output) COMPLEX*16 array, dimension (LDA, N)
-* On entry, the first of the pair of matrices.
-* On exit, A has been overwritten by its generalized Schur
-* form S.
-*
-* LDA (input) INTEGER
-* The leading dimension of A. LDA >= max(1,N).
-*
-* B (input/output) COMPLEX*16 array, dimension (LDB, N)
-* On entry, the second of the pair of matrices.
-* On exit, B has been overwritten by its generalized Schur
-* form T.
-*
-* LDB (input) INTEGER
-* The leading dimension of B. LDB >= max(1,N).
-*
-* SDIM (output) INTEGER
-* If SORT = 'N', SDIM = 0.
-* If SORT = 'S', SDIM = number of eigenvalues (after sorting)
-* for which SELCTG is true.
-*
-* ALPHA (output) COMPLEX*16 array, dimension (N)
-* BETA (output) COMPLEX*16 array, dimension (N)
-* On exit, ALPHA(j)/BETA(j), j=1,...,N, will be the
-* generalized eigenvalues. ALPHA(j), j=1,...,N and BETA(j),
-* j=1,...,N are the diagonals of the complex Schur form (A,B)
-* output by ZGGES. The BETA(j) will be non-negative real.
-*
-* Note: the quotients ALPHA(j)/BETA(j) may easily over- or
-* underflow, and BETA(j) may even be zero. Thus, the user
-* should avoid naively computing the ratio alpha/beta.
-* However, ALPHA will be always less than and usually
-* comparable with norm(A) in magnitude, and BETA always less
-* than and usually comparable with norm(B).
-*
-* VSL (output) COMPLEX*16 array, dimension (LDVSL,N)
-* If JOBVSL = 'V', VSL will contain the left Schur vectors.
-* Not referenced if JOBVSL = 'N'.
-*
-* LDVSL (input) INTEGER
-* The leading dimension of the matrix VSL. LDVSL >= 1, and
-* if JOBVSL = 'V', LDVSL >= N.
-*
-* VSR (output) COMPLEX*16 array, dimension (LDVSR,N)
-* If JOBVSR = 'V', VSR will contain the right Schur vectors.
-* Not referenced if JOBVSR = 'N'.
-*
-* LDVSR (input) INTEGER
-* The leading dimension of the matrix VSR. LDVSR >= 1, and
-* if JOBVSR = 'V', LDVSR >= N.
-*
-* WORK (workspace/output) COMPLEX*16 array, dimension (MAX(1,LWORK))
-* On exit, if INFO = 0, WORK(1) returns the optimal LWORK.
-*
-* LWORK (input) INTEGER
-* The dimension of the array WORK. LWORK >= max(1,2*N).
-* For good performance, LWORK must generally be larger.
-*
-* If LWORK = -1, then a workspace query is assumed; the routine
-* only calculates the optimal size of the WORK array, returns
-* this value as the first entry of the WORK array, and no error
-* message related to LWORK is issued by XERBLA.
-*
-* RWORK (workspace) DOUBLE PRECISION array, dimension (8*N)
-*
-* BWORK (workspace) LOGICAL array, dimension (N)
-* Not referenced if SORT = 'N'.
-*
-* INFO (output) INTEGER
-* = 0: successful exit
-* < 0: if INFO = -i, the i-th argument had an illegal value.
-* =1,...,N:
-* The QZ iteration failed. (A,B) are not in Schur
-* form, but ALPHA(j) and BETA(j) should be correct for
-* j=INFO+1,...,N.
-* > N: =N+1: other than QZ iteration failed in ZHGEQZ
-* =N+2: after reordering, roundoff changed values of
-* some complex eigenvalues so that leading
-* eigenvalues in the Generalized Schur form no
-* longer satisfy SELCTG=.TRUE. This could also
-* be caused due to scaling.
-* =N+3: reordering falied in ZTGSEN.
-*
-* =====================================================================
-*
-* .. Parameters ..
- DOUBLE PRECISION ZERO, ONE
- PARAMETER ( ZERO = 0.0D0, ONE = 1.0D0 )
- COMPLEX*16 CZERO, CONE
- PARAMETER ( CZERO = ( 0.0D0, 0.0D0 ),
- $ CONE = ( 1.0D0, 0.0D0 ) )
-* ..
-* .. Local Scalars ..
- LOGICAL CURSL, ILASCL, ILBSCL, ILVSL, ILVSR, LASTSL,
- $ LQUERY, WANTST
- INTEGER I, ICOLS, IERR, IHI, IJOBVL, IJOBVR, ILEFT,
- $ ILO, IRIGHT, IROWS, IRWRK, ITAU, IWRK, LWKMIN,
- $ LWKOPT
- DOUBLE PRECISION ANRM, ANRMTO, BIGNUM, BNRM, BNRMTO, EPS, PVSL,
- $ PVSR, SMLNUM
-* ..
-* .. Local Arrays ..
- INTEGER IDUM( 1 )
- DOUBLE PRECISION DIF( 2 )
-* ..
-* .. External Subroutines ..
- EXTERNAL DLABAD, XERBLA, ZGEQRF, ZGGBAK, ZGGBAL, ZGGHRD,
- $ ZHGEQZ, ZLACPY, ZLASCL, ZLASET, ZTGSEN, ZUNGQR,
- $ ZUNMQR
-* ..
-* .. External Functions ..
- LOGICAL LSAME
- INTEGER ILAENV
- DOUBLE PRECISION DLAMCH, ZLANGE
- EXTERNAL LSAME, ILAENV, DLAMCH, ZLANGE
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC MAX, SQRT
-* ..
-* .. Executable Statements ..
-*
-* Decode the input arguments
-*
- IF( LSAME( JOBVSL, 'N' ) ) THEN
- IJOBVL = 1
- ILVSL = .FALSE.
- ELSE IF( LSAME( JOBVSL, 'V' ) ) THEN
- IJOBVL = 2
- ILVSL = .TRUE.
- ELSE
- IJOBVL = -1
- ILVSL = .FALSE.
- END IF
-*
- IF( LSAME( JOBVSR, 'N' ) ) THEN
- IJOBVR = 1
- ILVSR = .FALSE.
- ELSE IF( LSAME( JOBVSR, 'V' ) ) THEN
- IJOBVR = 2
- ILVSR = .TRUE.
- ELSE
- IJOBVR = -1
- ILVSR = .FALSE.
- END IF
-*
- WANTST = LSAME( SORT, 'S' )
-*
-* Test the input arguments
-*
- INFO = 0
- LQUERY = ( LWORK.EQ.-1 )
- IF( IJOBVL.LE.0 ) THEN
- INFO = -1
- ELSE IF( IJOBVR.LE.0 ) THEN
- INFO = -2
- ELSE IF( ( .NOT.WANTST ) .AND. ( .NOT.LSAME( SORT, 'N' ) ) ) THEN
- INFO = -3
- ELSE IF( N.LT.0 ) THEN
- INFO = -5
- ELSE IF( LDA.LT.MAX( 1, N ) ) THEN
- INFO = -7
- ELSE IF( LDB.LT.MAX( 1, N ) ) THEN
- INFO = -9
- ELSE IF( LDVSL.LT.1 .OR. ( ILVSL .AND. LDVSL.LT.N ) ) THEN
- INFO = -14
- ELSE IF( LDVSR.LT.1 .OR. ( ILVSR .AND. LDVSR.LT.N ) ) THEN
- INFO = -16
- END IF
-*
-* Compute workspace
-* (Note: Comments in the code beginning "Workspace:" describe the
-* minimal amount of workspace needed at that point in the code,
-* as well as the preferred amount for good performance.
-* NB refers to the optimal block size for the immediately
-* following subroutine, as returned by ILAENV.)
-*
- IF( INFO.EQ.0 ) THEN
- LWKMIN = MAX( 1, 2*N )
- LWKOPT = MAX( 1, N + N*ILAENV( 1, 'ZGEQRF', ' ', N, 1, N, 0 ) )
- LWKOPT = MAX( LWKOPT, N +
- $ N*ILAENV( 1, 'ZUNMQR', ' ', N, 1, N, -1 ) )
- IF( ILVSL ) THEN
- LWKOPT = MAX( LWKOPT, N +
- $ N*ILAENV( 1, 'ZUNGQR', ' ', N, 1, N, -1 ) )
- END IF
- WORK( 1 ) = LWKOPT
-*
- IF( LWORK.LT.LWKMIN .AND. .NOT.LQUERY )
- $ INFO = -18
- END IF
-*
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'ZGGES ', -INFO )
- RETURN
- ELSE IF( LQUERY ) THEN
- RETURN
- END IF
-*
-* Quick return if possible
-*
- IF( N.EQ.0 ) THEN
- SDIM = 0
- RETURN
- END IF
-*
-* Get machine constants
-*
- EPS = DLAMCH( 'P' )
- SMLNUM = DLAMCH( 'S' )
- BIGNUM = ONE / SMLNUM
- CALL DLABAD( SMLNUM, BIGNUM )
- SMLNUM = SQRT( SMLNUM ) / EPS
- BIGNUM = ONE / SMLNUM
-*
-* Scale A if max element outside range [SMLNUM,BIGNUM]
-*
- ANRM = ZLANGE( 'M', N, N, A, LDA, RWORK )
- ILASCL = .FALSE.
- IF( ANRM.GT.ZERO .AND. ANRM.LT.SMLNUM ) THEN
- ANRMTO = SMLNUM
- ILASCL = .TRUE.
- ELSE IF( ANRM.GT.BIGNUM ) THEN
- ANRMTO = BIGNUM
- ILASCL = .TRUE.
- END IF
-*
- IF( ILASCL )
- $ CALL ZLASCL( 'G', 0, 0, ANRM, ANRMTO, N, N, A, LDA, IERR )
-*
-* Scale B if max element outside range [SMLNUM,BIGNUM]
-*
- BNRM = ZLANGE( 'M', N, N, B, LDB, RWORK )
- ILBSCL = .FALSE.
- IF( BNRM.GT.ZERO .AND. BNRM.LT.SMLNUM ) THEN
- BNRMTO = SMLNUM
- ILBSCL = .TRUE.
- ELSE IF( BNRM.GT.BIGNUM ) THEN
- BNRMTO = BIGNUM
- ILBSCL = .TRUE.
- END IF
-*
- IF( ILBSCL )
- $ CALL ZLASCL( 'G', 0, 0, BNRM, BNRMTO, N, N, B, LDB, IERR )
-*
-* Permute the matrix to make it more nearly triangular
-* (Real Workspace: need 6*N)
-*
- ILEFT = 1
- IRIGHT = N + 1
- IRWRK = IRIGHT + N
- CALL ZGGBAL( 'P', N, A, LDA, B, LDB, ILO, IHI, RWORK( ILEFT ),
- $ RWORK( IRIGHT ), RWORK( IRWRK ), IERR )
-*
-* Reduce B to triangular form (QR decomposition of B)
-* (Complex Workspace: need N, prefer N*NB)
-*
- IROWS = IHI + 1 - ILO
- ICOLS = N + 1 - ILO
- ITAU = 1
- IWRK = ITAU + IROWS
- CALL ZGEQRF( IROWS, ICOLS, B( ILO, ILO ), LDB, WORK( ITAU ),
- $ WORK( IWRK ), LWORK+1-IWRK, IERR )
-*
-* Apply the orthogonal transformation to matrix A
-* (Complex Workspace: need N, prefer N*NB)
-*
- CALL ZUNMQR( 'L', 'C', IROWS, ICOLS, IROWS, B( ILO, ILO ), LDB,
- $ WORK( ITAU ), A( ILO, ILO ), LDA, WORK( IWRK ),
- $ LWORK+1-IWRK, IERR )
-*
-* Initialize VSL
-* (Complex Workspace: need N, prefer N*NB)
-*
- IF( ILVSL ) THEN
- CALL ZLASET( 'Full', N, N, CZERO, CONE, VSL, LDVSL )
- IF( IROWS.GT.1 ) THEN
- CALL ZLACPY( 'L', IROWS-1, IROWS-1, B( ILO+1, ILO ), LDB,
- $ VSL( ILO+1, ILO ), LDVSL )
- END IF
- CALL ZUNGQR( IROWS, IROWS, IROWS, VSL( ILO, ILO ), LDVSL,
- $ WORK( ITAU ), WORK( IWRK ), LWORK+1-IWRK, IERR )
- END IF
-*
-* Initialize VSR
-*
- IF( ILVSR )
- $ CALL ZLASET( 'Full', N, N, CZERO, CONE, VSR, LDVSR )
-*
-* Reduce to generalized Hessenberg form
-* (Workspace: none needed)
-*
- CALL ZGGHRD( JOBVSL, JOBVSR, N, ILO, IHI, A, LDA, B, LDB, VSL,
- $ LDVSL, VSR, LDVSR, IERR )
-*
- SDIM = 0
-*
-* Perform QZ algorithm, computing Schur vectors if desired
-* (Complex Workspace: need N)
-* (Real Workspace: need N)
-*
- IWRK = ITAU
- CALL ZHGEQZ( 'S', JOBVSL, JOBVSR, N, ILO, IHI, A, LDA, B, LDB,
- $ ALPHA, BETA, VSL, LDVSL, VSR, LDVSR, WORK( IWRK ),
- $ LWORK+1-IWRK, RWORK( IRWRK ), IERR )
- IF( IERR.NE.0 ) THEN
- IF( IERR.GT.0 .AND. IERR.LE.N ) THEN
- INFO = IERR
- ELSE IF( IERR.GT.N .AND. IERR.LE.2*N ) THEN
- INFO = IERR - N
- ELSE
- INFO = N + 1
- END IF
- GO TO 30
- END IF
-*
-* Sort eigenvalues ALPHA/BETA if desired
-* (Workspace: none needed)
-*
- IF( WANTST ) THEN
-*
-* Undo scaling on eigenvalues before selecting
-*
- IF( ILASCL )
- $ CALL ZLASCL( 'G', 0, 0, ANRM, ANRMTO, N, 1, ALPHA, N, IERR )
- IF( ILBSCL )
- $ CALL ZLASCL( 'G', 0, 0, BNRM, BNRMTO, N, 1, BETA, N, IERR )
-*
-* Select eigenvalues
-*
- DO 10 I = 1, N
- BWORK( I ) = SELCTG( ALPHA( I ), BETA( I ) )
- 10 CONTINUE
-*
- CALL ZTGSEN( 0, ILVSL, ILVSR, BWORK, N, A, LDA, B, LDB, ALPHA,
- $ BETA, VSL, LDVSL, VSR, LDVSR, SDIM, PVSL, PVSR,
- $ DIF, WORK( IWRK ), LWORK-IWRK+1, IDUM, 1, IERR )
- IF( IERR.EQ.1 )
- $ INFO = N + 3
-*
- END IF
-*
-* Apply back-permutation to VSL and VSR
-* (Workspace: none needed)
-*
- IF( ILVSL )
- $ CALL ZGGBAK( 'P', 'L', N, ILO, IHI, RWORK( ILEFT ),
- $ RWORK( IRIGHT ), N, VSL, LDVSL, IERR )
- IF( ILVSR )
- $ CALL ZGGBAK( 'P', 'R', N, ILO, IHI, RWORK( ILEFT ),
- $ RWORK( IRIGHT ), N, VSR, LDVSR, IERR )
-*
-* Undo scaling
-*
- IF( ILASCL ) THEN
- CALL ZLASCL( 'U', 0, 0, ANRMTO, ANRM, N, N, A, LDA, IERR )
- CALL ZLASCL( 'G', 0, 0, ANRMTO, ANRM, N, 1, ALPHA, N, IERR )
- END IF
-*
- IF( ILBSCL ) THEN
- CALL ZLASCL( 'U', 0, 0, BNRMTO, BNRM, N, N, B, LDB, IERR )
- CALL ZLASCL( 'G', 0, 0, BNRMTO, BNRM, N, 1, BETA, N, IERR )
- END IF
-*
- IF( WANTST ) THEN
-*
-* Check if reordering is correct
-*
- LASTSL = .TRUE.
- SDIM = 0
- DO 20 I = 1, N
- CURSL = SELCTG( ALPHA( I ), BETA( I ) )
- IF( CURSL )
- $ SDIM = SDIM + 1
- IF( CURSL .AND. .NOT.LASTSL )
- $ INFO = N + 2
- LASTSL = CURSL
- 20 CONTINUE
-*
- END IF
-*
- 30 CONTINUE
-*
- WORK( 1 ) = LWKOPT
-*
- RETURN
-*
-* End of ZGGES
-*
- END
diff --git a/src/lib/lapack/zggev.f b/src/lib/lapack/zggev.f
deleted file mode 100644
index 94fb3dc2..00000000
--- a/src/lib/lapack/zggev.f
+++ /dev/null
@@ -1,454 +0,0 @@
- SUBROUTINE ZGGEV( JOBVL, JOBVR, N, A, LDA, B, LDB, ALPHA, BETA,
- $ VL, LDVL, VR, LDVR, WORK, LWORK, RWORK, INFO )
-*
-* -- LAPACK driver routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- CHARACTER JOBVL, JOBVR
- INTEGER INFO, LDA, LDB, LDVL, LDVR, LWORK, N
-* ..
-* .. Array Arguments ..
- DOUBLE PRECISION RWORK( * )
- COMPLEX*16 A( LDA, * ), ALPHA( * ), B( LDB, * ),
- $ BETA( * ), VL( LDVL, * ), VR( LDVR, * ),
- $ WORK( * )
-* ..
-*
-* Purpose
-* =======
-*
-* ZGGEV computes for a pair of N-by-N complex nonsymmetric matrices
-* (A,B), the generalized eigenvalues, and optionally, the left and/or
-* right generalized eigenvectors.
-*
-* A generalized eigenvalue for a pair of matrices (A,B) is a scalar
-* lambda or a ratio alpha/beta = lambda, such that A - lambda*B is
-* singular. It is usually represented as the pair (alpha,beta), as
-* there is a reasonable interpretation for beta=0, and even for both
-* being zero.
-*
-* The right generalized eigenvector v(j) corresponding to the
-* generalized eigenvalue lambda(j) of (A,B) satisfies
-*
-* A * v(j) = lambda(j) * B * v(j).
-*
-* The left generalized eigenvector u(j) corresponding to the
-* generalized eigenvalues lambda(j) of (A,B) satisfies
-*
-* u(j)**H * A = lambda(j) * u(j)**H * B
-*
-* where u(j)**H is the conjugate-transpose of u(j).
-*
-* Arguments
-* =========
-*
-* JOBVL (input) CHARACTER*1
-* = 'N': do not compute the left generalized eigenvectors;
-* = 'V': compute the left generalized eigenvectors.
-*
-* JOBVR (input) CHARACTER*1
-* = 'N': do not compute the right generalized eigenvectors;
-* = 'V': compute the right generalized eigenvectors.
-*
-* N (input) INTEGER
-* The order of the matrices A, B, VL, and VR. N >= 0.
-*
-* A (input/output) COMPLEX*16 array, dimension (LDA, N)
-* On entry, the matrix A in the pair (A,B).
-* On exit, A has been overwritten.
-*
-* LDA (input) INTEGER
-* The leading dimension of A. LDA >= max(1,N).
-*
-* B (input/output) COMPLEX*16 array, dimension (LDB, N)
-* On entry, the matrix B in the pair (A,B).
-* On exit, B has been overwritten.
-*
-* LDB (input) INTEGER
-* The leading dimension of B. LDB >= max(1,N).
-*
-* ALPHA (output) COMPLEX*16 array, dimension (N)
-* BETA (output) COMPLEX*16 array, dimension (N)
-* On exit, ALPHA(j)/BETA(j), j=1,...,N, will be the
-* generalized eigenvalues.
-*
-* Note: the quotients ALPHA(j)/BETA(j) may easily over- or
-* underflow, and BETA(j) may even be zero. Thus, the user
-* should avoid naively computing the ratio alpha/beta.
-* However, ALPHA will be always less than and usually
-* comparable with norm(A) in magnitude, and BETA always less
-* than and usually comparable with norm(B).
-*
-* VL (output) COMPLEX*16 array, dimension (LDVL,N)
-* If JOBVL = 'V', the left generalized eigenvectors u(j) are
-* stored one after another in the columns of VL, in the same
-* order as their eigenvalues.
-* Each eigenvector is scaled so the largest component has
-* abs(real part) + abs(imag. part) = 1.
-* Not referenced if JOBVL = 'N'.
-*
-* LDVL (input) INTEGER
-* The leading dimension of the matrix VL. LDVL >= 1, and
-* if JOBVL = 'V', LDVL >= N.
-*
-* VR (output) COMPLEX*16 array, dimension (LDVR,N)
-* If JOBVR = 'V', the right generalized eigenvectors v(j) are
-* stored one after another in the columns of VR, in the same
-* order as their eigenvalues.
-* Each eigenvector is scaled so the largest component has
-* abs(real part) + abs(imag. part) = 1.
-* Not referenced if JOBVR = 'N'.
-*
-* LDVR (input) INTEGER
-* The leading dimension of the matrix VR. LDVR >= 1, and
-* if JOBVR = 'V', LDVR >= N.
-*
-* WORK (workspace/output) COMPLEX*16 array, dimension (MAX(1,LWORK))
-* On exit, if INFO = 0, WORK(1) returns the optimal LWORK.
-*
-* LWORK (input) INTEGER
-* The dimension of the array WORK. LWORK >= max(1,2*N).
-* For good performance, LWORK must generally be larger.
-*
-* If LWORK = -1, then a workspace query is assumed; the routine
-* only calculates the optimal size of the WORK array, returns
-* this value as the first entry of the WORK array, and no error
-* message related to LWORK is issued by XERBLA.
-*
-* RWORK (workspace/output) DOUBLE PRECISION array, dimension (8*N)
-*
-* INFO (output) INTEGER
-* = 0: successful exit
-* < 0: if INFO = -i, the i-th argument had an illegal value.
-* =1,...,N:
-* The QZ iteration failed. No eigenvectors have been
-* calculated, but ALPHA(j) and BETA(j) should be
-* correct for j=INFO+1,...,N.
-* > N: =N+1: other then QZ iteration failed in DHGEQZ,
-* =N+2: error return from DTGEVC.
-*
-* =====================================================================
-*
-* .. Parameters ..
- DOUBLE PRECISION ZERO, ONE
- PARAMETER ( ZERO = 0.0D0, ONE = 1.0D0 )
- COMPLEX*16 CZERO, CONE
- PARAMETER ( CZERO = ( 0.0D0, 0.0D0 ),
- $ CONE = ( 1.0D0, 0.0D0 ) )
-* ..
-* .. Local Scalars ..
- LOGICAL ILASCL, ILBSCL, ILV, ILVL, ILVR, LQUERY
- CHARACTER CHTEMP
- INTEGER ICOLS, IERR, IHI, IJOBVL, IJOBVR, ILEFT, ILO,
- $ IN, IRIGHT, IROWS, IRWRK, ITAU, IWRK, JC, JR,
- $ LWKMIN, LWKOPT
- DOUBLE PRECISION ANRM, ANRMTO, BIGNUM, BNRM, BNRMTO, EPS,
- $ SMLNUM, TEMP
- COMPLEX*16 X
-* ..
-* .. Local Arrays ..
- LOGICAL LDUMMA( 1 )
-* ..
-* .. External Subroutines ..
- EXTERNAL DLABAD, XERBLA, ZGEQRF, ZGGBAK, ZGGBAL, ZGGHRD,
- $ ZHGEQZ, ZLACPY, ZLASCL, ZLASET, ZTGEVC, ZUNGQR,
- $ ZUNMQR
-* ..
-* .. External Functions ..
- LOGICAL LSAME
- INTEGER ILAENV
- DOUBLE PRECISION DLAMCH, ZLANGE
- EXTERNAL LSAME, ILAENV, DLAMCH, ZLANGE
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC ABS, DBLE, DIMAG, MAX, SQRT
-* ..
-* .. Statement Functions ..
- DOUBLE PRECISION ABS1
-* ..
-* .. Statement Function definitions ..
- ABS1( X ) = ABS( DBLE( X ) ) + ABS( DIMAG( X ) )
-* ..
-* .. Executable Statements ..
-*
-* Decode the input arguments
-*
- IF( LSAME( JOBVL, 'N' ) ) THEN
- IJOBVL = 1
- ILVL = .FALSE.
- ELSE IF( LSAME( JOBVL, 'V' ) ) THEN
- IJOBVL = 2
- ILVL = .TRUE.
- ELSE
- IJOBVL = -1
- ILVL = .FALSE.
- END IF
-*
- IF( LSAME( JOBVR, 'N' ) ) THEN
- IJOBVR = 1
- ILVR = .FALSE.
- ELSE IF( LSAME( JOBVR, 'V' ) ) THEN
- IJOBVR = 2
- ILVR = .TRUE.
- ELSE
- IJOBVR = -1
- ILVR = .FALSE.
- END IF
- ILV = ILVL .OR. ILVR
-*
-* Test the input arguments
-*
- INFO = 0
- LQUERY = ( LWORK.EQ.-1 )
- IF( IJOBVL.LE.0 ) THEN
- INFO = -1
- ELSE IF( IJOBVR.LE.0 ) THEN
- INFO = -2
- ELSE IF( N.LT.0 ) THEN
- INFO = -3
- ELSE IF( LDA.LT.MAX( 1, N ) ) THEN
- INFO = -5
- ELSE IF( LDB.LT.MAX( 1, N ) ) THEN
- INFO = -7
- ELSE IF( LDVL.LT.1 .OR. ( ILVL .AND. LDVL.LT.N ) ) THEN
- INFO = -11
- ELSE IF( LDVR.LT.1 .OR. ( ILVR .AND. LDVR.LT.N ) ) THEN
- INFO = -13
- END IF
-*
-* Compute workspace
-* (Note: Comments in the code beginning "Workspace:" describe the
-* minimal amount of workspace needed at that point in the code,
-* as well as the preferred amount for good performance.
-* NB refers to the optimal block size for the immediately
-* following subroutine, as returned by ILAENV. The workspace is
-* computed assuming ILO = 1 and IHI = N, the worst case.)
-*
- IF( INFO.EQ.0 ) THEN
- LWKMIN = MAX( 1, 2*N )
- LWKOPT = MAX( 1, N + N*ILAENV( 1, 'ZGEQRF', ' ', N, 1, N, 0 ) )
- LWKOPT = MAX( LWKOPT, N +
- $ N*ILAENV( 1, 'ZUNMQR', ' ', N, 1, N, 0 ) )
- IF( ILVL ) THEN
- LWKOPT = MAX( LWKOPT, N +
- $ N*ILAENV( 1, 'ZUNGQR', ' ', N, 1, N, -1 ) )
- END IF
- WORK( 1 ) = LWKOPT
-*
- IF( LWORK.LT.LWKMIN .AND. .NOT.LQUERY )
- $ INFO = -15
- END IF
-*
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'ZGGEV ', -INFO )
- RETURN
- ELSE IF( LQUERY ) THEN
- RETURN
- END IF
-*
-* Quick return if possible
-*
- IF( N.EQ.0 )
- $ RETURN
-*
-* Get machine constants
-*
- EPS = DLAMCH( 'E' )*DLAMCH( 'B' )
- SMLNUM = DLAMCH( 'S' )
- BIGNUM = ONE / SMLNUM
- CALL DLABAD( SMLNUM, BIGNUM )
- SMLNUM = SQRT( SMLNUM ) / EPS
- BIGNUM = ONE / SMLNUM
-*
-* Scale A if max element outside range [SMLNUM,BIGNUM]
-*
- ANRM = ZLANGE( 'M', N, N, A, LDA, RWORK )
- ILASCL = .FALSE.
- IF( ANRM.GT.ZERO .AND. ANRM.LT.SMLNUM ) THEN
- ANRMTO = SMLNUM
- ILASCL = .TRUE.
- ELSE IF( ANRM.GT.BIGNUM ) THEN
- ANRMTO = BIGNUM
- ILASCL = .TRUE.
- END IF
- IF( ILASCL )
- $ CALL ZLASCL( 'G', 0, 0, ANRM, ANRMTO, N, N, A, LDA, IERR )
-*
-* Scale B if max element outside range [SMLNUM,BIGNUM]
-*
- BNRM = ZLANGE( 'M', N, N, B, LDB, RWORK )
- ILBSCL = .FALSE.
- IF( BNRM.GT.ZERO .AND. BNRM.LT.SMLNUM ) THEN
- BNRMTO = SMLNUM
- ILBSCL = .TRUE.
- ELSE IF( BNRM.GT.BIGNUM ) THEN
- BNRMTO = BIGNUM
- ILBSCL = .TRUE.
- END IF
- IF( ILBSCL )
- $ CALL ZLASCL( 'G', 0, 0, BNRM, BNRMTO, N, N, B, LDB, IERR )
-*
-* Permute the matrices A, B to isolate eigenvalues if possible
-* (Real Workspace: need 6*N)
-*
- ILEFT = 1
- IRIGHT = N + 1
- IRWRK = IRIGHT + N
- CALL ZGGBAL( 'P', N, A, LDA, B, LDB, ILO, IHI, RWORK( ILEFT ),
- $ RWORK( IRIGHT ), RWORK( IRWRK ), IERR )
-*
-* Reduce B to triangular form (QR decomposition of B)
-* (Complex Workspace: need N, prefer N*NB)
-*
- IROWS = IHI + 1 - ILO
- IF( ILV ) THEN
- ICOLS = N + 1 - ILO
- ELSE
- ICOLS = IROWS
- END IF
- ITAU = 1
- IWRK = ITAU + IROWS
- CALL ZGEQRF( IROWS, ICOLS, B( ILO, ILO ), LDB, WORK( ITAU ),
- $ WORK( IWRK ), LWORK+1-IWRK, IERR )
-*
-* Apply the orthogonal transformation to matrix A
-* (Complex Workspace: need N, prefer N*NB)
-*
- CALL ZUNMQR( 'L', 'C', IROWS, ICOLS, IROWS, B( ILO, ILO ), LDB,
- $ WORK( ITAU ), A( ILO, ILO ), LDA, WORK( IWRK ),
- $ LWORK+1-IWRK, IERR )
-*
-* Initialize VL
-* (Complex Workspace: need N, prefer N*NB)
-*
- IF( ILVL ) THEN
- CALL ZLASET( 'Full', N, N, CZERO, CONE, VL, LDVL )
- IF( IROWS.GT.1 ) THEN
- CALL ZLACPY( 'L', IROWS-1, IROWS-1, B( ILO+1, ILO ), LDB,
- $ VL( ILO+1, ILO ), LDVL )
- END IF
- CALL ZUNGQR( IROWS, IROWS, IROWS, VL( ILO, ILO ), LDVL,
- $ WORK( ITAU ), WORK( IWRK ), LWORK+1-IWRK, IERR )
- END IF
-*
-* Initialize VR
-*
- IF( ILVR )
- $ CALL ZLASET( 'Full', N, N, CZERO, CONE, VR, LDVR )
-*
-* Reduce to generalized Hessenberg form
-*
- IF( ILV ) THEN
-*
-* Eigenvectors requested -- work on whole matrix.
-*
- CALL ZGGHRD( JOBVL, JOBVR, N, ILO, IHI, A, LDA, B, LDB, VL,
- $ LDVL, VR, LDVR, IERR )
- ELSE
- CALL ZGGHRD( 'N', 'N', IROWS, 1, IROWS, A( ILO, ILO ), LDA,
- $ B( ILO, ILO ), LDB, VL, LDVL, VR, LDVR, IERR )
- END IF
-*
-* Perform QZ algorithm (Compute eigenvalues, and optionally, the
-* Schur form and Schur vectors)
-* (Complex Workspace: need N)
-* (Real Workspace: need N)
-*
- IWRK = ITAU
- IF( ILV ) THEN
- CHTEMP = 'S'
- ELSE
- CHTEMP = 'E'
- END IF
- CALL ZHGEQZ( CHTEMP, JOBVL, JOBVR, N, ILO, IHI, A, LDA, B, LDB,
- $ ALPHA, BETA, VL, LDVL, VR, LDVR, WORK( IWRK ),
- $ LWORK+1-IWRK, RWORK( IRWRK ), IERR )
- IF( IERR.NE.0 ) THEN
- IF( IERR.GT.0 .AND. IERR.LE.N ) THEN
- INFO = IERR
- ELSE IF( IERR.GT.N .AND. IERR.LE.2*N ) THEN
- INFO = IERR - N
- ELSE
- INFO = N + 1
- END IF
- GO TO 70
- END IF
-*
-* Compute Eigenvectors
-* (Real Workspace: need 2*N)
-* (Complex Workspace: need 2*N)
-*
- IF( ILV ) THEN
- IF( ILVL ) THEN
- IF( ILVR ) THEN
- CHTEMP = 'B'
- ELSE
- CHTEMP = 'L'
- END IF
- ELSE
- CHTEMP = 'R'
- END IF
-*
- CALL ZTGEVC( CHTEMP, 'B', LDUMMA, N, A, LDA, B, LDB, VL, LDVL,
- $ VR, LDVR, N, IN, WORK( IWRK ), RWORK( IRWRK ),
- $ IERR )
- IF( IERR.NE.0 ) THEN
- INFO = N + 2
- GO TO 70
- END IF
-*
-* Undo balancing on VL and VR and normalization
-* (Workspace: none needed)
-*
- IF( ILVL ) THEN
- CALL ZGGBAK( 'P', 'L', N, ILO, IHI, RWORK( ILEFT ),
- $ RWORK( IRIGHT ), N, VL, LDVL, IERR )
- DO 30 JC = 1, N
- TEMP = ZERO
- DO 10 JR = 1, N
- TEMP = MAX( TEMP, ABS1( VL( JR, JC ) ) )
- 10 CONTINUE
- IF( TEMP.LT.SMLNUM )
- $ GO TO 30
- TEMP = ONE / TEMP
- DO 20 JR = 1, N
- VL( JR, JC ) = VL( JR, JC )*TEMP
- 20 CONTINUE
- 30 CONTINUE
- END IF
- IF( ILVR ) THEN
- CALL ZGGBAK( 'P', 'R', N, ILO, IHI, RWORK( ILEFT ),
- $ RWORK( IRIGHT ), N, VR, LDVR, IERR )
- DO 60 JC = 1, N
- TEMP = ZERO
- DO 40 JR = 1, N
- TEMP = MAX( TEMP, ABS1( VR( JR, JC ) ) )
- 40 CONTINUE
- IF( TEMP.LT.SMLNUM )
- $ GO TO 60
- TEMP = ONE / TEMP
- DO 50 JR = 1, N
- VR( JR, JC ) = VR( JR, JC )*TEMP
- 50 CONTINUE
- 60 CONTINUE
- END IF
- END IF
-*
-* Undo scaling if necessary
-*
- IF( ILASCL )
- $ CALL ZLASCL( 'G', 0, 0, ANRMTO, ANRM, N, 1, ALPHA, N, IERR )
-*
- IF( ILBSCL )
- $ CALL ZLASCL( 'G', 0, 0, BNRMTO, BNRM, N, 1, BETA, N, IERR )
-*
- 70 CONTINUE
- WORK( 1 ) = LWKOPT
-*
- RETURN
-*
-* End of ZGGEV
-*
- END
diff --git a/src/lib/lapack/zgghrd.f b/src/lib/lapack/zgghrd.f
deleted file mode 100644
index 652c09d7..00000000
--- a/src/lib/lapack/zgghrd.f
+++ /dev/null
@@ -1,264 +0,0 @@
- SUBROUTINE ZGGHRD( COMPQ, COMPZ, N, ILO, IHI, A, LDA, B, LDB, Q,
- $ LDQ, Z, LDZ, INFO )
-*
-* -- LAPACK routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- CHARACTER COMPQ, COMPZ
- INTEGER IHI, ILO, INFO, LDA, LDB, LDQ, LDZ, N
-* ..
-* .. Array Arguments ..
- COMPLEX*16 A( LDA, * ), B( LDB, * ), Q( LDQ, * ),
- $ Z( LDZ, * )
-* ..
-*
-* Purpose
-* =======
-*
-* ZGGHRD reduces a pair of complex matrices (A,B) to generalized upper
-* Hessenberg form using unitary transformations, where A is a
-* general matrix and B is upper triangular. The form of the
-* generalized eigenvalue problem is
-* A*x = lambda*B*x,
-* and B is typically made upper triangular by computing its QR
-* factorization and moving the unitary matrix Q to the left side
-* of the equation.
-*
-* This subroutine simultaneously reduces A to a Hessenberg matrix H:
-* Q**H*A*Z = H
-* and transforms B to another upper triangular matrix T:
-* Q**H*B*Z = T
-* in order to reduce the problem to its standard form
-* H*y = lambda*T*y
-* where y = Z**H*x.
-*
-* The unitary matrices Q and Z are determined as products of Givens
-* rotations. They may either be formed explicitly, or they may be
-* postmultiplied into input matrices Q1 and Z1, so that
-* Q1 * A * Z1**H = (Q1*Q) * H * (Z1*Z)**H
-* Q1 * B * Z1**H = (Q1*Q) * T * (Z1*Z)**H
-* If Q1 is the unitary matrix from the QR factorization of B in the
-* original equation A*x = lambda*B*x, then ZGGHRD reduces the original
-* problem to generalized Hessenberg form.
-*
-* Arguments
-* =========
-*
-* COMPQ (input) CHARACTER*1
-* = 'N': do not compute Q;
-* = 'I': Q is initialized to the unit matrix, and the
-* unitary matrix Q is returned;
-* = 'V': Q must contain a unitary matrix Q1 on entry,
-* and the product Q1*Q is returned.
-*
-* COMPZ (input) CHARACTER*1
-* = 'N': do not compute Q;
-* = 'I': Q is initialized to the unit matrix, and the
-* unitary matrix Q is returned;
-* = 'V': Q must contain a unitary matrix Q1 on entry,
-* and the product Q1*Q is returned.
-*
-* N (input) INTEGER
-* The order of the matrices A and B. N >= 0.
-*
-* ILO (input) INTEGER
-* IHI (input) INTEGER
-* ILO and IHI mark the rows and columns of A which are to be
-* reduced. It is assumed that A is already upper triangular
-* in rows and columns 1:ILO-1 and IHI+1:N. ILO and IHI are
-* normally set by a previous call to ZGGBAL; otherwise they
-* should be set to 1 and N respectively.
-* 1 <= ILO <= IHI <= N, if N > 0; ILO=1 and IHI=0, if N=0.
-*
-* A (input/output) COMPLEX*16 array, dimension (LDA, N)
-* On entry, the N-by-N general matrix to be reduced.
-* On exit, the upper triangle and the first subdiagonal of A
-* are overwritten with the upper Hessenberg matrix H, and the
-* rest is set to zero.
-*
-* LDA (input) INTEGER
-* The leading dimension of the array A. LDA >= max(1,N).
-*
-* B (input/output) COMPLEX*16 array, dimension (LDB, N)
-* On entry, the N-by-N upper triangular matrix B.
-* On exit, the upper triangular matrix T = Q**H B Z. The
-* elements below the diagonal are set to zero.
-*
-* LDB (input) INTEGER
-* The leading dimension of the array B. LDB >= max(1,N).
-*
-* Q (input/output) COMPLEX*16 array, dimension (LDQ, N)
-* On entry, if COMPQ = 'V', the unitary matrix Q1, typically
-* from the QR factorization of B.
-* On exit, if COMPQ='I', the unitary matrix Q, and if
-* COMPQ = 'V', the product Q1*Q.
-* Not referenced if COMPQ='N'.
-*
-* LDQ (input) INTEGER
-* The leading dimension of the array Q.
-* LDQ >= N if COMPQ='V' or 'I'; LDQ >= 1 otherwise.
-*
-* Z (input/output) COMPLEX*16 array, dimension (LDZ, N)
-* On entry, if COMPZ = 'V', the unitary matrix Z1.
-* On exit, if COMPZ='I', the unitary matrix Z, and if
-* COMPZ = 'V', the product Z1*Z.
-* Not referenced if COMPZ='N'.
-*
-* LDZ (input) INTEGER
-* The leading dimension of the array Z.
-* LDZ >= N if COMPZ='V' or 'I'; LDZ >= 1 otherwise.
-*
-* INFO (output) INTEGER
-* = 0: successful exit.
-* < 0: if INFO = -i, the i-th argument had an illegal value.
-*
-* Further Details
-* ===============
-*
-* This routine reduces A to Hessenberg and B to triangular form by
-* an unblocked reduction, as described in _Matrix_Computations_,
-* by Golub and van Loan (Johns Hopkins Press).
-*
-* =====================================================================
-*
-* .. Parameters ..
- COMPLEX*16 CONE, CZERO
- PARAMETER ( CONE = ( 1.0D+0, 0.0D+0 ),
- $ CZERO = ( 0.0D+0, 0.0D+0 ) )
-* ..
-* .. Local Scalars ..
- LOGICAL ILQ, ILZ
- INTEGER ICOMPQ, ICOMPZ, JCOL, JROW
- DOUBLE PRECISION C
- COMPLEX*16 CTEMP, S
-* ..
-* .. External Functions ..
- LOGICAL LSAME
- EXTERNAL LSAME
-* ..
-* .. External Subroutines ..
- EXTERNAL XERBLA, ZLARTG, ZLASET, ZROT
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC DCONJG, MAX
-* ..
-* .. Executable Statements ..
-*
-* Decode COMPQ
-*
- IF( LSAME( COMPQ, 'N' ) ) THEN
- ILQ = .FALSE.
- ICOMPQ = 1
- ELSE IF( LSAME( COMPQ, 'V' ) ) THEN
- ILQ = .TRUE.
- ICOMPQ = 2
- ELSE IF( LSAME( COMPQ, 'I' ) ) THEN
- ILQ = .TRUE.
- ICOMPQ = 3
- ELSE
- ICOMPQ = 0
- END IF
-*
-* Decode COMPZ
-*
- IF( LSAME( COMPZ, 'N' ) ) THEN
- ILZ = .FALSE.
- ICOMPZ = 1
- ELSE IF( LSAME( COMPZ, 'V' ) ) THEN
- ILZ = .TRUE.
- ICOMPZ = 2
- ELSE IF( LSAME( COMPZ, 'I' ) ) THEN
- ILZ = .TRUE.
- ICOMPZ = 3
- ELSE
- ICOMPZ = 0
- END IF
-*
-* Test the input parameters.
-*
- INFO = 0
- IF( ICOMPQ.LE.0 ) THEN
- INFO = -1
- ELSE IF( ICOMPZ.LE.0 ) THEN
- INFO = -2
- ELSE IF( N.LT.0 ) THEN
- INFO = -3
- ELSE IF( ILO.LT.1 ) THEN
- INFO = -4
- ELSE IF( IHI.GT.N .OR. IHI.LT.ILO-1 ) THEN
- INFO = -5
- ELSE IF( LDA.LT.MAX( 1, N ) ) THEN
- INFO = -7
- ELSE IF( LDB.LT.MAX( 1, N ) ) THEN
- INFO = -9
- ELSE IF( ( ILQ .AND. LDQ.LT.N ) .OR. LDQ.LT.1 ) THEN
- INFO = -11
- ELSE IF( ( ILZ .AND. LDZ.LT.N ) .OR. LDZ.LT.1 ) THEN
- INFO = -13
- END IF
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'ZGGHRD', -INFO )
- RETURN
- END IF
-*
-* Initialize Q and Z if desired.
-*
- IF( ICOMPQ.EQ.3 )
- $ CALL ZLASET( 'Full', N, N, CZERO, CONE, Q, LDQ )
- IF( ICOMPZ.EQ.3 )
- $ CALL ZLASET( 'Full', N, N, CZERO, CONE, Z, LDZ )
-*
-* Quick return if possible
-*
- IF( N.LE.1 )
- $ RETURN
-*
-* Zero out lower triangle of B
-*
- DO 20 JCOL = 1, N - 1
- DO 10 JROW = JCOL + 1, N
- B( JROW, JCOL ) = CZERO
- 10 CONTINUE
- 20 CONTINUE
-*
-* Reduce A and B
-*
- DO 40 JCOL = ILO, IHI - 2
-*
- DO 30 JROW = IHI, JCOL + 2, -1
-*
-* Step 1: rotate rows JROW-1, JROW to kill A(JROW,JCOL)
-*
- CTEMP = A( JROW-1, JCOL )
- CALL ZLARTG( CTEMP, A( JROW, JCOL ), C, S,
- $ A( JROW-1, JCOL ) )
- A( JROW, JCOL ) = CZERO
- CALL ZROT( N-JCOL, A( JROW-1, JCOL+1 ), LDA,
- $ A( JROW, JCOL+1 ), LDA, C, S )
- CALL ZROT( N+2-JROW, B( JROW-1, JROW-1 ), LDB,
- $ B( JROW, JROW-1 ), LDB, C, S )
- IF( ILQ )
- $ CALL ZROT( N, Q( 1, JROW-1 ), 1, Q( 1, JROW ), 1, C,
- $ DCONJG( S ) )
-*
-* Step 2: rotate columns JROW, JROW-1 to kill B(JROW,JROW-1)
-*
- CTEMP = B( JROW, JROW )
- CALL ZLARTG( CTEMP, B( JROW, JROW-1 ), C, S,
- $ B( JROW, JROW ) )
- B( JROW, JROW-1 ) = CZERO
- CALL ZROT( IHI, A( 1, JROW ), 1, A( 1, JROW-1 ), 1, C, S )
- CALL ZROT( JROW-1, B( 1, JROW ), 1, B( 1, JROW-1 ), 1, C,
- $ S )
- IF( ILZ )
- $ CALL ZROT( N, Z( 1, JROW ), 1, Z( 1, JROW-1 ), 1, C, S )
- 30 CONTINUE
- 40 CONTINUE
-*
- RETURN
-*
-* End of ZGGHRD
-*
- END
diff --git a/src/lib/lapack/zheev.f b/src/lib/lapack/zheev.f
deleted file mode 100644
index 324d1612..00000000
--- a/src/lib/lapack/zheev.f
+++ /dev/null
@@ -1,218 +0,0 @@
- SUBROUTINE ZHEEV( JOBZ, UPLO, N, A, LDA, W, WORK, LWORK, RWORK,
- $ INFO )
-*
-* -- LAPACK driver routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- CHARACTER JOBZ, UPLO
- INTEGER INFO, LDA, LWORK, N
-* ..
-* .. Array Arguments ..
- DOUBLE PRECISION RWORK( * ), W( * )
- COMPLEX*16 A( LDA, * ), WORK( * )
-* ..
-*
-* Purpose
-* =======
-*
-* ZHEEV computes all eigenvalues and, optionally, eigenvectors of a
-* complex Hermitian matrix A.
-*
-* Arguments
-* =========
-*
-* JOBZ (input) CHARACTER*1
-* = 'N': Compute eigenvalues only;
-* = 'V': Compute eigenvalues and eigenvectors.
-*
-* UPLO (input) CHARACTER*1
-* = 'U': Upper triangle of A is stored;
-* = 'L': Lower triangle of A is stored.
-*
-* N (input) INTEGER
-* The order of the matrix A. N >= 0.
-*
-* A (input/output) COMPLEX*16 array, dimension (LDA, N)
-* On entry, the Hermitian matrix A. If UPLO = 'U', the
-* leading N-by-N upper triangular part of A contains the
-* upper triangular part of the matrix A. If UPLO = 'L',
-* the leading N-by-N lower triangular part of A contains
-* the lower triangular part of the matrix A.
-* On exit, if JOBZ = 'V', then if INFO = 0, A contains the
-* orthonormal eigenvectors of the matrix A.
-* If JOBZ = 'N', then on exit the lower triangle (if UPLO='L')
-* or the upper triangle (if UPLO='U') of A, including the
-* diagonal, is destroyed.
-*
-* LDA (input) INTEGER
-* The leading dimension of the array A. LDA >= max(1,N).
-*
-* W (output) DOUBLE PRECISION array, dimension (N)
-* If INFO = 0, the eigenvalues in ascending order.
-*
-* WORK (workspace/output) COMPLEX*16 array, dimension (MAX(1,LWORK))
-* On exit, if INFO = 0, WORK(1) returns the optimal LWORK.
-*
-* LWORK (input) INTEGER
-* The length of the array WORK. LWORK >= max(1,2*N-1).
-* For optimal efficiency, LWORK >= (NB+1)*N,
-* where NB is the blocksize for ZHETRD returned by ILAENV.
-*
-* If LWORK = -1, then a workspace query is assumed; the routine
-* only calculates the optimal size of the WORK array, returns
-* this value as the first entry of the WORK array, and no error
-* message related to LWORK is issued by XERBLA.
-*
-* RWORK (workspace) DOUBLE PRECISION array, dimension (max(1, 3*N-2))
-*
-* INFO (output) INTEGER
-* = 0: successful exit
-* < 0: if INFO = -i, the i-th argument had an illegal value
-* > 0: if INFO = i, the algorithm failed to converge; i
-* off-diagonal elements of an intermediate tridiagonal
-* form did not converge to zero.
-*
-* =====================================================================
-*
-* .. Parameters ..
- DOUBLE PRECISION ZERO, ONE
- PARAMETER ( ZERO = 0.0D0, ONE = 1.0D0 )
- COMPLEX*16 CONE
- PARAMETER ( CONE = ( 1.0D0, 0.0D0 ) )
-* ..
-* .. Local Scalars ..
- LOGICAL LOWER, LQUERY, WANTZ
- INTEGER IINFO, IMAX, INDE, INDTAU, INDWRK, ISCALE,
- $ LLWORK, LWKOPT, NB
- DOUBLE PRECISION ANRM, BIGNUM, EPS, RMAX, RMIN, SAFMIN, SIGMA,
- $ SMLNUM
-* ..
-* .. External Functions ..
- LOGICAL LSAME
- INTEGER ILAENV
- DOUBLE PRECISION DLAMCH, ZLANHE
- EXTERNAL LSAME, ILAENV, DLAMCH, ZLANHE
-* ..
-* .. External Subroutines ..
- EXTERNAL DSCAL, DSTERF, XERBLA, ZHETRD, ZLASCL, ZSTEQR,
- $ ZUNGTR
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC MAX, SQRT
-* ..
-* .. Executable Statements ..
-*
-* Test the input parameters.
-*
- WANTZ = LSAME( JOBZ, 'V' )
- LOWER = LSAME( UPLO, 'L' )
- LQUERY = ( LWORK.EQ.-1 )
-*
- INFO = 0
- IF( .NOT.( WANTZ .OR. LSAME( JOBZ, 'N' ) ) ) THEN
- INFO = -1
- ELSE IF( .NOT.( LOWER .OR. LSAME( UPLO, 'U' ) ) ) THEN
- INFO = -2
- ELSE IF( N.LT.0 ) THEN
- INFO = -3
- ELSE IF( LDA.LT.MAX( 1, N ) ) THEN
- INFO = -5
- END IF
-*
- IF( INFO.EQ.0 ) THEN
- NB = ILAENV( 1, 'ZHETRD', UPLO, N, -1, -1, -1 )
- LWKOPT = MAX( 1, ( NB+1 )*N )
- WORK( 1 ) = LWKOPT
-*
- IF( LWORK.LT.MAX( 1, 2*N-1 ) .AND. .NOT.LQUERY )
- $ INFO = -8
- END IF
-*
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'ZHEEV ', -INFO )
- RETURN
- ELSE IF( LQUERY ) THEN
- RETURN
- END IF
-*
-* Quick return if possible
-*
- IF( N.EQ.0 ) THEN
- RETURN
- END IF
-*
- IF( N.EQ.1 ) THEN
- W( 1 ) = A( 1, 1 )
- WORK( 1 ) = 1
- IF( WANTZ )
- $ A( 1, 1 ) = CONE
- RETURN
- END IF
-*
-* Get machine constants.
-*
- SAFMIN = DLAMCH( 'Safe minimum' )
- EPS = DLAMCH( 'Precision' )
- SMLNUM = SAFMIN / EPS
- BIGNUM = ONE / SMLNUM
- RMIN = SQRT( SMLNUM )
- RMAX = SQRT( BIGNUM )
-*
-* Scale matrix to allowable range, if necessary.
-*
- ANRM = ZLANHE( 'M', UPLO, N, A, LDA, RWORK )
- ISCALE = 0
- IF( ANRM.GT.ZERO .AND. ANRM.LT.RMIN ) THEN
- ISCALE = 1
- SIGMA = RMIN / ANRM
- ELSE IF( ANRM.GT.RMAX ) THEN
- ISCALE = 1
- SIGMA = RMAX / ANRM
- END IF
- IF( ISCALE.EQ.1 )
- $ CALL ZLASCL( UPLO, 0, 0, ONE, SIGMA, N, N, A, LDA, INFO )
-*
-* Call ZHETRD to reduce Hermitian matrix to tridiagonal form.
-*
- INDE = 1
- INDTAU = 1
- INDWRK = INDTAU + N
- LLWORK = LWORK - INDWRK + 1
- CALL ZHETRD( UPLO, N, A, LDA, W, RWORK( INDE ), WORK( INDTAU ),
- $ WORK( INDWRK ), LLWORK, IINFO )
-*
-* For eigenvalues only, call DSTERF. For eigenvectors, first call
-* ZUNGTR to generate the unitary matrix, then call ZSTEQR.
-*
- IF( .NOT.WANTZ ) THEN
- CALL DSTERF( N, W, RWORK( INDE ), INFO )
- ELSE
- CALL ZUNGTR( UPLO, N, A, LDA, WORK( INDTAU ), WORK( INDWRK ),
- $ LLWORK, IINFO )
- INDWRK = INDE + N
- CALL ZSTEQR( JOBZ, N, W, RWORK( INDE ), A, LDA,
- $ RWORK( INDWRK ), INFO )
- END IF
-*
-* If matrix was scaled, then rescale eigenvalues appropriately.
-*
- IF( ISCALE.EQ.1 ) THEN
- IF( INFO.EQ.0 ) THEN
- IMAX = N
- ELSE
- IMAX = INFO - 1
- END IF
- CALL DSCAL( IMAX, ONE / SIGMA, W, 1 )
- END IF
-*
-* Set WORK(1) to optimal complex workspace size.
-*
- WORK( 1 ) = LWKOPT
-*
- RETURN
-*
-* End of ZHEEV
-*
- END
diff --git a/src/lib/lapack/zhetd2.f b/src/lib/lapack/zhetd2.f
deleted file mode 100644
index 24b0a1df..00000000
--- a/src/lib/lapack/zhetd2.f
+++ /dev/null
@@ -1,258 +0,0 @@
- SUBROUTINE ZHETD2( UPLO, N, A, LDA, D, E, TAU, INFO )
-*
-* -- LAPACK routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- CHARACTER UPLO
- INTEGER INFO, LDA, N
-* ..
-* .. Array Arguments ..
- DOUBLE PRECISION D( * ), E( * )
- COMPLEX*16 A( LDA, * ), TAU( * )
-* ..
-*
-* Purpose
-* =======
-*
-* ZHETD2 reduces a complex Hermitian matrix A to real symmetric
-* tridiagonal form T by a unitary similarity transformation:
-* Q' * A * Q = T.
-*
-* Arguments
-* =========
-*
-* UPLO (input) CHARACTER*1
-* Specifies whether the upper or lower triangular part of the
-* Hermitian matrix A is stored:
-* = 'U': Upper triangular
-* = 'L': Lower triangular
-*
-* N (input) INTEGER
-* The order of the matrix A. N >= 0.
-*
-* A (input/output) COMPLEX*16 array, dimension (LDA,N)
-* On entry, the Hermitian matrix A. If UPLO = 'U', the leading
-* n-by-n upper triangular part of A contains the upper
-* triangular part of the matrix A, and the strictly lower
-* triangular part of A is not referenced. If UPLO = 'L', the
-* leading n-by-n lower triangular part of A contains the lower
-* triangular part of the matrix A, and the strictly upper
-* triangular part of A is not referenced.
-* On exit, if UPLO = 'U', the diagonal and first superdiagonal
-* of A are overwritten by the corresponding elements of the
-* tridiagonal matrix T, and the elements above the first
-* superdiagonal, with the array TAU, represent the unitary
-* matrix Q as a product of elementary reflectors; if UPLO
-* = 'L', the diagonal and first subdiagonal of A are over-
-* written by the corresponding elements of the tridiagonal
-* matrix T, and the elements below the first subdiagonal, with
-* the array TAU, represent the unitary matrix Q as a product
-* of elementary reflectors. See Further Details.
-*
-* LDA (input) INTEGER
-* The leading dimension of the array A. LDA >= max(1,N).
-*
-* D (output) DOUBLE PRECISION array, dimension (N)
-* The diagonal elements of the tridiagonal matrix T:
-* D(i) = A(i,i).
-*
-* E (output) DOUBLE PRECISION array, dimension (N-1)
-* The off-diagonal elements of the tridiagonal matrix T:
-* E(i) = A(i,i+1) if UPLO = 'U', E(i) = A(i+1,i) if UPLO = 'L'.
-*
-* TAU (output) COMPLEX*16 array, dimension (N-1)
-* The scalar factors of the elementary reflectors (see Further
-* Details).
-*
-* INFO (output) INTEGER
-* = 0: successful exit
-* < 0: if INFO = -i, the i-th argument had an illegal value.
-*
-* Further Details
-* ===============
-*
-* If UPLO = 'U', the matrix Q is represented as a product of elementary
-* reflectors
-*
-* Q = H(n-1) . . . H(2) H(1).
-*
-* Each H(i) has the form
-*
-* H(i) = I - tau * v * v'
-*
-* where tau is a complex scalar, and v is a complex vector with
-* v(i+1:n) = 0 and v(i) = 1; v(1:i-1) is stored on exit in
-* A(1:i-1,i+1), and tau in TAU(i).
-*
-* If UPLO = 'L', the matrix Q is represented as a product of elementary
-* reflectors
-*
-* Q = H(1) H(2) . . . H(n-1).
-*
-* Each H(i) has the form
-*
-* H(i) = I - tau * v * v'
-*
-* where tau is a complex scalar, and v is a complex vector with
-* v(1:i) = 0 and v(i+1) = 1; v(i+2:n) is stored on exit in A(i+2:n,i),
-* and tau in TAU(i).
-*
-* The contents of A on exit are illustrated by the following examples
-* with n = 5:
-*
-* if UPLO = 'U': if UPLO = 'L':
-*
-* ( d e v2 v3 v4 ) ( d )
-* ( d e v3 v4 ) ( e d )
-* ( d e v4 ) ( v1 e d )
-* ( d e ) ( v1 v2 e d )
-* ( d ) ( v1 v2 v3 e d )
-*
-* where d and e denote diagonal and off-diagonal elements of T, and vi
-* denotes an element of the vector defining H(i).
-*
-* =====================================================================
-*
-* .. Parameters ..
- COMPLEX*16 ONE, ZERO, HALF
- PARAMETER ( ONE = ( 1.0D+0, 0.0D+0 ),
- $ ZERO = ( 0.0D+0, 0.0D+0 ),
- $ HALF = ( 0.5D+0, 0.0D+0 ) )
-* ..
-* .. Local Scalars ..
- LOGICAL UPPER
- INTEGER I
- COMPLEX*16 ALPHA, TAUI
-* ..
-* .. External Subroutines ..
- EXTERNAL XERBLA, ZAXPY, ZHEMV, ZHER2, ZLARFG
-* ..
-* .. External Functions ..
- LOGICAL LSAME
- COMPLEX*16 ZDOTC
- EXTERNAL LSAME, ZDOTC
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC DBLE, MAX, MIN
-* ..
-* .. Executable Statements ..
-*
-* Test the input parameters
-*
- INFO = 0
- UPPER = LSAME( UPLO, 'U' )
- IF( .NOT.UPPER .AND. .NOT.LSAME( UPLO, 'L' ) ) THEN
- INFO = -1
- ELSE IF( N.LT.0 ) THEN
- INFO = -2
- ELSE IF( LDA.LT.MAX( 1, N ) ) THEN
- INFO = -4
- END IF
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'ZHETD2', -INFO )
- RETURN
- END IF
-*
-* Quick return if possible
-*
- IF( N.LE.0 )
- $ RETURN
-*
- IF( UPPER ) THEN
-*
-* Reduce the upper triangle of A
-*
- A( N, N ) = DBLE( A( N, N ) )
- DO 10 I = N - 1, 1, -1
-*
-* Generate elementary reflector H(i) = I - tau * v * v'
-* to annihilate A(1:i-1,i+1)
-*
- ALPHA = A( I, I+1 )
- CALL ZLARFG( I, ALPHA, A( 1, I+1 ), 1, TAUI )
- E( I ) = ALPHA
-*
- IF( TAUI.NE.ZERO ) THEN
-*
-* Apply H(i) from both sides to A(1:i,1:i)
-*
- A( I, I+1 ) = ONE
-*
-* Compute x := tau * A * v storing x in TAU(1:i)
-*
- CALL ZHEMV( UPLO, I, TAUI, A, LDA, A( 1, I+1 ), 1, ZERO,
- $ TAU, 1 )
-*
-* Compute w := x - 1/2 * tau * (x'*v) * v
-*
- ALPHA = -HALF*TAUI*ZDOTC( I, TAU, 1, A( 1, I+1 ), 1 )
- CALL ZAXPY( I, ALPHA, A( 1, I+1 ), 1, TAU, 1 )
-*
-* Apply the transformation as a rank-2 update:
-* A := A - v * w' - w * v'
-*
- CALL ZHER2( UPLO, I, -ONE, A( 1, I+1 ), 1, TAU, 1, A,
- $ LDA )
-*
- ELSE
- A( I, I ) = DBLE( A( I, I ) )
- END IF
- A( I, I+1 ) = E( I )
- D( I+1 ) = A( I+1, I+1 )
- TAU( I ) = TAUI
- 10 CONTINUE
- D( 1 ) = A( 1, 1 )
- ELSE
-*
-* Reduce the lower triangle of A
-*
- A( 1, 1 ) = DBLE( A( 1, 1 ) )
- DO 20 I = 1, N - 1
-*
-* Generate elementary reflector H(i) = I - tau * v * v'
-* to annihilate A(i+2:n,i)
-*
- ALPHA = A( I+1, I )
- CALL ZLARFG( N-I, ALPHA, A( MIN( I+2, N ), I ), 1, TAUI )
- E( I ) = ALPHA
-*
- IF( TAUI.NE.ZERO ) THEN
-*
-* Apply H(i) from both sides to A(i+1:n,i+1:n)
-*
- A( I+1, I ) = ONE
-*
-* Compute x := tau * A * v storing y in TAU(i:n-1)
-*
- CALL ZHEMV( UPLO, N-I, TAUI, A( I+1, I+1 ), LDA,
- $ A( I+1, I ), 1, ZERO, TAU( I ), 1 )
-*
-* Compute w := x - 1/2 * tau * (x'*v) * v
-*
- ALPHA = -HALF*TAUI*ZDOTC( N-I, TAU( I ), 1, A( I+1, I ),
- $ 1 )
- CALL ZAXPY( N-I, ALPHA, A( I+1, I ), 1, TAU( I ), 1 )
-*
-* Apply the transformation as a rank-2 update:
-* A := A - v * w' - w * v'
-*
- CALL ZHER2( UPLO, N-I, -ONE, A( I+1, I ), 1, TAU( I ), 1,
- $ A( I+1, I+1 ), LDA )
-*
- ELSE
- A( I+1, I+1 ) = DBLE( A( I+1, I+1 ) )
- END IF
- A( I+1, I ) = E( I )
- D( I ) = A( I, I )
- TAU( I ) = TAUI
- 20 CONTINUE
- D( N ) = A( N, N )
- END IF
-*
- RETURN
-*
-* End of ZHETD2
-*
- END
diff --git a/src/lib/lapack/zhetrd.f b/src/lib/lapack/zhetrd.f
deleted file mode 100644
index fb0cd0b2..00000000
--- a/src/lib/lapack/zhetrd.f
+++ /dev/null
@@ -1,296 +0,0 @@
- SUBROUTINE ZHETRD( UPLO, N, A, LDA, D, E, TAU, WORK, LWORK, INFO )
-*
-* -- LAPACK routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- CHARACTER UPLO
- INTEGER INFO, LDA, LWORK, N
-* ..
-* .. Array Arguments ..
- DOUBLE PRECISION D( * ), E( * )
- COMPLEX*16 A( LDA, * ), TAU( * ), WORK( * )
-* ..
-*
-* Purpose
-* =======
-*
-* ZHETRD reduces a complex Hermitian matrix A to real symmetric
-* tridiagonal form T by a unitary similarity transformation:
-* Q**H * A * Q = T.
-*
-* Arguments
-* =========
-*
-* UPLO (input) CHARACTER*1
-* = 'U': Upper triangle of A is stored;
-* = 'L': Lower triangle of A is stored.
-*
-* N (input) INTEGER
-* The order of the matrix A. N >= 0.
-*
-* A (input/output) COMPLEX*16 array, dimension (LDA,N)
-* On entry, the Hermitian matrix A. If UPLO = 'U', the leading
-* N-by-N upper triangular part of A contains the upper
-* triangular part of the matrix A, and the strictly lower
-* triangular part of A is not referenced. If UPLO = 'L', the
-* leading N-by-N lower triangular part of A contains the lower
-* triangular part of the matrix A, and the strictly upper
-* triangular part of A is not referenced.
-* On exit, if UPLO = 'U', the diagonal and first superdiagonal
-* of A are overwritten by the corresponding elements of the
-* tridiagonal matrix T, and the elements above the first
-* superdiagonal, with the array TAU, represent the unitary
-* matrix Q as a product of elementary reflectors; if UPLO
-* = 'L', the diagonal and first subdiagonal of A are over-
-* written by the corresponding elements of the tridiagonal
-* matrix T, and the elements below the first subdiagonal, with
-* the array TAU, represent the unitary matrix Q as a product
-* of elementary reflectors. See Further Details.
-*
-* LDA (input) INTEGER
-* The leading dimension of the array A. LDA >= max(1,N).
-*
-* D (output) DOUBLE PRECISION array, dimension (N)
-* The diagonal elements of the tridiagonal matrix T:
-* D(i) = A(i,i).
-*
-* E (output) DOUBLE PRECISION array, dimension (N-1)
-* The off-diagonal elements of the tridiagonal matrix T:
-* E(i) = A(i,i+1) if UPLO = 'U', E(i) = A(i+1,i) if UPLO = 'L'.
-*
-* TAU (output) COMPLEX*16 array, dimension (N-1)
-* The scalar factors of the elementary reflectors (see Further
-* Details).
-*
-* WORK (workspace/output) COMPLEX*16 array, dimension (MAX(1,LWORK))
-* On exit, if INFO = 0, WORK(1) returns the optimal LWORK.
-*
-* LWORK (input) INTEGER
-* The dimension of the array WORK. LWORK >= 1.
-* For optimum performance LWORK >= N*NB, where NB is the
-* optimal blocksize.
-*
-* If LWORK = -1, then a workspace query is assumed; the routine
-* only calculates the optimal size of the WORK array, returns
-* this value as the first entry of the WORK array, and no error
-* message related to LWORK is issued by XERBLA.
-*
-* INFO (output) INTEGER
-* = 0: successful exit
-* < 0: if INFO = -i, the i-th argument had an illegal value
-*
-* Further Details
-* ===============
-*
-* If UPLO = 'U', the matrix Q is represented as a product of elementary
-* reflectors
-*
-* Q = H(n-1) . . . H(2) H(1).
-*
-* Each H(i) has the form
-*
-* H(i) = I - tau * v * v'
-*
-* where tau is a complex scalar, and v is a complex vector with
-* v(i+1:n) = 0 and v(i) = 1; v(1:i-1) is stored on exit in
-* A(1:i-1,i+1), and tau in TAU(i).
-*
-* If UPLO = 'L', the matrix Q is represented as a product of elementary
-* reflectors
-*
-* Q = H(1) H(2) . . . H(n-1).
-*
-* Each H(i) has the form
-*
-* H(i) = I - tau * v * v'
-*
-* where tau is a complex scalar, and v is a complex vector with
-* v(1:i) = 0 and v(i+1) = 1; v(i+2:n) is stored on exit in A(i+2:n,i),
-* and tau in TAU(i).
-*
-* The contents of A on exit are illustrated by the following examples
-* with n = 5:
-*
-* if UPLO = 'U': if UPLO = 'L':
-*
-* ( d e v2 v3 v4 ) ( d )
-* ( d e v3 v4 ) ( e d )
-* ( d e v4 ) ( v1 e d )
-* ( d e ) ( v1 v2 e d )
-* ( d ) ( v1 v2 v3 e d )
-*
-* where d and e denote diagonal and off-diagonal elements of T, and vi
-* denotes an element of the vector defining H(i).
-*
-* =====================================================================
-*
-* .. Parameters ..
- DOUBLE PRECISION ONE
- PARAMETER ( ONE = 1.0D+0 )
- COMPLEX*16 CONE
- PARAMETER ( CONE = ( 1.0D+0, 0.0D+0 ) )
-* ..
-* .. Local Scalars ..
- LOGICAL LQUERY, UPPER
- INTEGER I, IINFO, IWS, J, KK, LDWORK, LWKOPT, NB,
- $ NBMIN, NX
-* ..
-* .. External Subroutines ..
- EXTERNAL XERBLA, ZHER2K, ZHETD2, ZLATRD
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC MAX
-* ..
-* .. External Functions ..
- LOGICAL LSAME
- INTEGER ILAENV
- EXTERNAL LSAME, ILAENV
-* ..
-* .. Executable Statements ..
-*
-* Test the input parameters
-*
- INFO = 0
- UPPER = LSAME( UPLO, 'U' )
- LQUERY = ( LWORK.EQ.-1 )
- IF( .NOT.UPPER .AND. .NOT.LSAME( UPLO, 'L' ) ) THEN
- INFO = -1
- ELSE IF( N.LT.0 ) THEN
- INFO = -2
- ELSE IF( LDA.LT.MAX( 1, N ) ) THEN
- INFO = -4
- ELSE IF( LWORK.LT.1 .AND. .NOT.LQUERY ) THEN
- INFO = -9
- END IF
-*
- IF( INFO.EQ.0 ) THEN
-*
-* Determine the block size.
-*
- NB = ILAENV( 1, 'ZHETRD', UPLO, N, -1, -1, -1 )
- LWKOPT = N*NB
- WORK( 1 ) = LWKOPT
- END IF
-*
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'ZHETRD', -INFO )
- RETURN
- ELSE IF( LQUERY ) THEN
- RETURN
- END IF
-*
-* Quick return if possible
-*
- IF( N.EQ.0 ) THEN
- WORK( 1 ) = 1
- RETURN
- END IF
-*
- NX = N
- IWS = 1
- IF( NB.GT.1 .AND. NB.LT.N ) THEN
-*
-* Determine when to cross over from blocked to unblocked code
-* (last block is always handled by unblocked code).
-*
- NX = MAX( NB, ILAENV( 3, 'ZHETRD', UPLO, N, -1, -1, -1 ) )
- IF( NX.LT.N ) THEN
-*
-* Determine if workspace is large enough for blocked code.
-*
- LDWORK = N
- IWS = LDWORK*NB
- IF( LWORK.LT.IWS ) THEN
-*
-* Not enough workspace to use optimal NB: determine the
-* minimum value of NB, and reduce NB or force use of
-* unblocked code by setting NX = N.
-*
- NB = MAX( LWORK / LDWORK, 1 )
- NBMIN = ILAENV( 2, 'ZHETRD', UPLO, N, -1, -1, -1 )
- IF( NB.LT.NBMIN )
- $ NX = N
- END IF
- ELSE
- NX = N
- END IF
- ELSE
- NB = 1
- END IF
-*
- IF( UPPER ) THEN
-*
-* Reduce the upper triangle of A.
-* Columns 1:kk are handled by the unblocked method.
-*
- KK = N - ( ( N-NX+NB-1 ) / NB )*NB
- DO 20 I = N - NB + 1, KK + 1, -NB
-*
-* Reduce columns i:i+nb-1 to tridiagonal form and form the
-* matrix W which is needed to update the unreduced part of
-* the matrix
-*
- CALL ZLATRD( UPLO, I+NB-1, NB, A, LDA, E, TAU, WORK,
- $ LDWORK )
-*
-* Update the unreduced submatrix A(1:i-1,1:i-1), using an
-* update of the form: A := A - V*W' - W*V'
-*
- CALL ZHER2K( UPLO, 'No transpose', I-1, NB, -CONE,
- $ A( 1, I ), LDA, WORK, LDWORK, ONE, A, LDA )
-*
-* Copy superdiagonal elements back into A, and diagonal
-* elements into D
-*
- DO 10 J = I, I + NB - 1
- A( J-1, J ) = E( J-1 )
- D( J ) = A( J, J )
- 10 CONTINUE
- 20 CONTINUE
-*
-* Use unblocked code to reduce the last or only block
-*
- CALL ZHETD2( UPLO, KK, A, LDA, D, E, TAU, IINFO )
- ELSE
-*
-* Reduce the lower triangle of A
-*
- DO 40 I = 1, N - NX, NB
-*
-* Reduce columns i:i+nb-1 to tridiagonal form and form the
-* matrix W which is needed to update the unreduced part of
-* the matrix
-*
- CALL ZLATRD( UPLO, N-I+1, NB, A( I, I ), LDA, E( I ),
- $ TAU( I ), WORK, LDWORK )
-*
-* Update the unreduced submatrix A(i+nb:n,i+nb:n), using
-* an update of the form: A := A - V*W' - W*V'
-*
- CALL ZHER2K( UPLO, 'No transpose', N-I-NB+1, NB, -CONE,
- $ A( I+NB, I ), LDA, WORK( NB+1 ), LDWORK, ONE,
- $ A( I+NB, I+NB ), LDA )
-*
-* Copy subdiagonal elements back into A, and diagonal
-* elements into D
-*
- DO 30 J = I, I + NB - 1
- A( J+1, J ) = E( J )
- D( J ) = A( J, J )
- 30 CONTINUE
- 40 CONTINUE
-*
-* Use unblocked code to reduce the last or only block
-*
- CALL ZHETD2( UPLO, N-I+1, A( I, I ), LDA, D( I ), E( I ),
- $ TAU( I ), IINFO )
- END IF
-*
- WORK( 1 ) = LWKOPT
- RETURN
-*
-* End of ZHETRD
-*
- END
diff --git a/src/lib/lapack/zhgeqz.f b/src/lib/lapack/zhgeqz.f
deleted file mode 100644
index 6a9403bd..00000000
--- a/src/lib/lapack/zhgeqz.f
+++ /dev/null
@@ -1,759 +0,0 @@
- SUBROUTINE ZHGEQZ( JOB, COMPQ, COMPZ, N, ILO, IHI, H, LDH, T, LDT,
- $ ALPHA, BETA, Q, LDQ, Z, LDZ, WORK, LWORK,
- $ RWORK, INFO )
-*
-* -- LAPACK routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- CHARACTER COMPQ, COMPZ, JOB
- INTEGER IHI, ILO, INFO, LDH, LDQ, LDT, LDZ, LWORK, N
-* ..
-* .. Array Arguments ..
- DOUBLE PRECISION RWORK( * )
- COMPLEX*16 ALPHA( * ), BETA( * ), H( LDH, * ),
- $ Q( LDQ, * ), T( LDT, * ), WORK( * ),
- $ Z( LDZ, * )
-* ..
-*
-* Purpose
-* =======
-*
-* ZHGEQZ computes the eigenvalues of a complex matrix pair (H,T),
-* where H is an upper Hessenberg matrix and T is upper triangular,
-* using the single-shift QZ method.
-* Matrix pairs of this type are produced by the reduction to
-* generalized upper Hessenberg form of a complex matrix pair (A,B):
-*
-* A = Q1*H*Z1**H, B = Q1*T*Z1**H,
-*
-* as computed by ZGGHRD.
-*
-* If JOB='S', then the Hessenberg-triangular pair (H,T) is
-* also reduced to generalized Schur form,
-*
-* H = Q*S*Z**H, T = Q*P*Z**H,
-*
-* where Q and Z are unitary matrices and S and P are upper triangular.
-*
-* Optionally, the unitary matrix Q from the generalized Schur
-* factorization may be postmultiplied into an input matrix Q1, and the
-* unitary matrix Z may be postmultiplied into an input matrix Z1.
-* If Q1 and Z1 are the unitary matrices from ZGGHRD that reduced
-* the matrix pair (A,B) to generalized Hessenberg form, then the output
-* matrices Q1*Q and Z1*Z are the unitary factors from the generalized
-* Schur factorization of (A,B):
-*
-* A = (Q1*Q)*S*(Z1*Z)**H, B = (Q1*Q)*P*(Z1*Z)**H.
-*
-* To avoid overflow, eigenvalues of the matrix pair (H,T)
-* (equivalently, of (A,B)) are computed as a pair of complex values
-* (alpha,beta). If beta is nonzero, lambda = alpha / beta is an
-* eigenvalue of the generalized nonsymmetric eigenvalue problem (GNEP)
-* A*x = lambda*B*x
-* and if alpha is nonzero, mu = beta / alpha is an eigenvalue of the
-* alternate form of the GNEP
-* mu*A*y = B*y.
-* The values of alpha and beta for the i-th eigenvalue can be read
-* directly from the generalized Schur form: alpha = S(i,i),
-* beta = P(i,i).
-*
-* Ref: C.B. Moler & G.W. Stewart, "An Algorithm for Generalized Matrix
-* Eigenvalue Problems", SIAM J. Numer. Anal., 10(1973),
-* pp. 241--256.
-*
-* Arguments
-* =========
-*
-* JOB (input) CHARACTER*1
-* = 'E': Compute eigenvalues only;
-* = 'S': Computer eigenvalues and the Schur form.
-*
-* COMPQ (input) CHARACTER*1
-* = 'N': Left Schur vectors (Q) are not computed;
-* = 'I': Q is initialized to the unit matrix and the matrix Q
-* of left Schur vectors of (H,T) is returned;
-* = 'V': Q must contain a unitary matrix Q1 on entry and
-* the product Q1*Q is returned.
-*
-* COMPZ (input) CHARACTER*1
-* = 'N': Right Schur vectors (Z) are not computed;
-* = 'I': Q is initialized to the unit matrix and the matrix Z
-* of right Schur vectors of (H,T) is returned;
-* = 'V': Z must contain a unitary matrix Z1 on entry and
-* the product Z1*Z is returned.
-*
-* N (input) INTEGER
-* The order of the matrices H, T, Q, and Z. N >= 0.
-*
-* ILO (input) INTEGER
-* IHI (input) INTEGER
-* ILO and IHI mark the rows and columns of H which are in
-* Hessenberg form. It is assumed that A is already upper
-* triangular in rows and columns 1:ILO-1 and IHI+1:N.
-* If N > 0, 1 <= ILO <= IHI <= N; if N = 0, ILO=1 and IHI=0.
-*
-* H (input/output) COMPLEX*16 array, dimension (LDH, N)
-* On entry, the N-by-N upper Hessenberg matrix H.
-* On exit, if JOB = 'S', H contains the upper triangular
-* matrix S from the generalized Schur factorization.
-* If JOB = 'E', the diagonal of H matches that of S, but
-* the rest of H is unspecified.
-*
-* LDH (input) INTEGER
-* The leading dimension of the array H. LDH >= max( 1, N ).
-*
-* T (input/output) COMPLEX*16 array, dimension (LDT, N)
-* On entry, the N-by-N upper triangular matrix T.
-* On exit, if JOB = 'S', T contains the upper triangular
-* matrix P from the generalized Schur factorization.
-* If JOB = 'E', the diagonal of T matches that of P, but
-* the rest of T is unspecified.
-*
-* LDT (input) INTEGER
-* The leading dimension of the array T. LDT >= max( 1, N ).
-*
-* ALPHA (output) COMPLEX*16 array, dimension (N)
-* The complex scalars alpha that define the eigenvalues of
-* GNEP. ALPHA(i) = S(i,i) in the generalized Schur
-* factorization.
-*
-* BETA (output) COMPLEX*16 array, dimension (N)
-* The real non-negative scalars beta that define the
-* eigenvalues of GNEP. BETA(i) = P(i,i) in the generalized
-* Schur factorization.
-*
-* Together, the quantities alpha = ALPHA(j) and beta = BETA(j)
-* represent the j-th eigenvalue of the matrix pair (A,B), in
-* one of the forms lambda = alpha/beta or mu = beta/alpha.
-* Since either lambda or mu may overflow, they should not,
-* in general, be computed.
-*
-* Q (input/output) COMPLEX*16 array, dimension (LDQ, N)
-* On entry, if COMPZ = 'V', the unitary matrix Q1 used in the
-* reduction of (A,B) to generalized Hessenberg form.
-* On exit, if COMPZ = 'I', the unitary matrix of left Schur
-* vectors of (H,T), and if COMPZ = 'V', the unitary matrix of
-* left Schur vectors of (A,B).
-* Not referenced if COMPZ = 'N'.
-*
-* LDQ (input) INTEGER
-* The leading dimension of the array Q. LDQ >= 1.
-* If COMPQ='V' or 'I', then LDQ >= N.
-*
-* Z (input/output) COMPLEX*16 array, dimension (LDZ, N)
-* On entry, if COMPZ = 'V', the unitary matrix Z1 used in the
-* reduction of (A,B) to generalized Hessenberg form.
-* On exit, if COMPZ = 'I', the unitary matrix of right Schur
-* vectors of (H,T), and if COMPZ = 'V', the unitary matrix of
-* right Schur vectors of (A,B).
-* Not referenced if COMPZ = 'N'.
-*
-* LDZ (input) INTEGER
-* The leading dimension of the array Z. LDZ >= 1.
-* If COMPZ='V' or 'I', then LDZ >= N.
-*
-* WORK (workspace/output) COMPLEX*16 array, dimension (MAX(1,LWORK))
-* On exit, if INFO >= 0, WORK(1) returns the optimal LWORK.
-*
-* LWORK (input) INTEGER
-* The dimension of the array WORK. LWORK >= max(1,N).
-*
-* If LWORK = -1, then a workspace query is assumed; the routine
-* only calculates the optimal size of the WORK array, returns
-* this value as the first entry of the WORK array, and no error
-* message related to LWORK is issued by XERBLA.
-*
-* RWORK (workspace) DOUBLE PRECISION array, dimension (N)
-*
-* INFO (output) INTEGER
-* = 0: successful exit
-* < 0: if INFO = -i, the i-th argument had an illegal value
-* = 1,...,N: the QZ iteration did not converge. (H,T) is not
-* in Schur form, but ALPHA(i) and BETA(i),
-* i=INFO+1,...,N should be correct.
-* = N+1,...,2*N: the shift calculation failed. (H,T) is not
-* in Schur form, but ALPHA(i) and BETA(i),
-* i=INFO-N+1,...,N should be correct.
-*
-* Further Details
-* ===============
-*
-* We assume that complex ABS works as long as its value is less than
-* overflow.
-*
-* =====================================================================
-*
-* .. Parameters ..
- COMPLEX*16 CZERO, CONE
- PARAMETER ( CZERO = ( 0.0D+0, 0.0D+0 ),
- $ CONE = ( 1.0D+0, 0.0D+0 ) )
- DOUBLE PRECISION ZERO, ONE
- PARAMETER ( ZERO = 0.0D+0, ONE = 1.0D+0 )
- DOUBLE PRECISION HALF
- PARAMETER ( HALF = 0.5D+0 )
-* ..
-* .. Local Scalars ..
- LOGICAL ILAZR2, ILAZRO, ILQ, ILSCHR, ILZ, LQUERY
- INTEGER ICOMPQ, ICOMPZ, IFIRST, IFRSTM, IITER, ILAST,
- $ ILASTM, IN, ISCHUR, ISTART, J, JC, JCH, JITER,
- $ JR, MAXIT
- DOUBLE PRECISION ABSB, ANORM, ASCALE, ATOL, BNORM, BSCALE, BTOL,
- $ C, SAFMIN, TEMP, TEMP2, TEMPR, ULP
- COMPLEX*16 ABI22, AD11, AD12, AD21, AD22, CTEMP, CTEMP2,
- $ CTEMP3, ESHIFT, RTDISC, S, SHIFT, SIGNBC, T1,
- $ U12, X
-* ..
-* .. External Functions ..
- LOGICAL LSAME
- DOUBLE PRECISION DLAMCH, ZLANHS
- EXTERNAL LSAME, DLAMCH, ZLANHS
-* ..
-* .. External Subroutines ..
- EXTERNAL XERBLA, ZLARTG, ZLASET, ZROT, ZSCAL
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC ABS, DBLE, DCMPLX, DCONJG, DIMAG, MAX, MIN,
- $ SQRT
-* ..
-* .. Statement Functions ..
- DOUBLE PRECISION ABS1
-* ..
-* .. Statement Function definitions ..
- ABS1( X ) = ABS( DBLE( X ) ) + ABS( DIMAG( X ) )
-* ..
-* .. Executable Statements ..
-*
-* Decode JOB, COMPQ, COMPZ
-*
- IF( LSAME( JOB, 'E' ) ) THEN
- ILSCHR = .FALSE.
- ISCHUR = 1
- ELSE IF( LSAME( JOB, 'S' ) ) THEN
- ILSCHR = .TRUE.
- ISCHUR = 2
- ELSE
- ISCHUR = 0
- END IF
-*
- IF( LSAME( COMPQ, 'N' ) ) THEN
- ILQ = .FALSE.
- ICOMPQ = 1
- ELSE IF( LSAME( COMPQ, 'V' ) ) THEN
- ILQ = .TRUE.
- ICOMPQ = 2
- ELSE IF( LSAME( COMPQ, 'I' ) ) THEN
- ILQ = .TRUE.
- ICOMPQ = 3
- ELSE
- ICOMPQ = 0
- END IF
-*
- IF( LSAME( COMPZ, 'N' ) ) THEN
- ILZ = .FALSE.
- ICOMPZ = 1
- ELSE IF( LSAME( COMPZ, 'V' ) ) THEN
- ILZ = .TRUE.
- ICOMPZ = 2
- ELSE IF( LSAME( COMPZ, 'I' ) ) THEN
- ILZ = .TRUE.
- ICOMPZ = 3
- ELSE
- ICOMPZ = 0
- END IF
-*
-* Check Argument Values
-*
- INFO = 0
- WORK( 1 ) = MAX( 1, N )
- LQUERY = ( LWORK.EQ.-1 )
- IF( ISCHUR.EQ.0 ) THEN
- INFO = -1
- ELSE IF( ICOMPQ.EQ.0 ) THEN
- INFO = -2
- ELSE IF( ICOMPZ.EQ.0 ) THEN
- INFO = -3
- ELSE IF( N.LT.0 ) THEN
- INFO = -4
- ELSE IF( ILO.LT.1 ) THEN
- INFO = -5
- ELSE IF( IHI.GT.N .OR. IHI.LT.ILO-1 ) THEN
- INFO = -6
- ELSE IF( LDH.LT.N ) THEN
- INFO = -8
- ELSE IF( LDT.LT.N ) THEN
- INFO = -10
- ELSE IF( LDQ.LT.1 .OR. ( ILQ .AND. LDQ.LT.N ) ) THEN
- INFO = -14
- ELSE IF( LDZ.LT.1 .OR. ( ILZ .AND. LDZ.LT.N ) ) THEN
- INFO = -16
- ELSE IF( LWORK.LT.MAX( 1, N ) .AND. .NOT.LQUERY ) THEN
- INFO = -18
- END IF
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'ZHGEQZ', -INFO )
- RETURN
- ELSE IF( LQUERY ) THEN
- RETURN
- END IF
-*
-* Quick return if possible
-*
-* WORK( 1 ) = CMPLX( 1 )
- IF( N.LE.0 ) THEN
- WORK( 1 ) = DCMPLX( 1 )
- RETURN
- END IF
-*
-* Initialize Q and Z
-*
- IF( ICOMPQ.EQ.3 )
- $ CALL ZLASET( 'Full', N, N, CZERO, CONE, Q, LDQ )
- IF( ICOMPZ.EQ.3 )
- $ CALL ZLASET( 'Full', N, N, CZERO, CONE, Z, LDZ )
-*
-* Machine Constants
-*
- IN = IHI + 1 - ILO
- SAFMIN = DLAMCH( 'S' )
- ULP = DLAMCH( 'E' )*DLAMCH( 'B' )
- ANORM = ZLANHS( 'F', IN, H( ILO, ILO ), LDH, RWORK )
- BNORM = ZLANHS( 'F', IN, T( ILO, ILO ), LDT, RWORK )
- ATOL = MAX( SAFMIN, ULP*ANORM )
- BTOL = MAX( SAFMIN, ULP*BNORM )
- ASCALE = ONE / MAX( SAFMIN, ANORM )
- BSCALE = ONE / MAX( SAFMIN, BNORM )
-*
-*
-* Set Eigenvalues IHI+1:N
-*
- DO 10 J = IHI + 1, N
- ABSB = ABS( T( J, J ) )
- IF( ABSB.GT.SAFMIN ) THEN
- SIGNBC = DCONJG( T( J, J ) / ABSB )
- T( J, J ) = ABSB
- IF( ILSCHR ) THEN
- CALL ZSCAL( J-1, SIGNBC, T( 1, J ), 1 )
- CALL ZSCAL( J, SIGNBC, H( 1, J ), 1 )
- ELSE
- H( J, J ) = H( J, J )*SIGNBC
- END IF
- IF( ILZ )
- $ CALL ZSCAL( N, SIGNBC, Z( 1, J ), 1 )
- ELSE
- T( J, J ) = CZERO
- END IF
- ALPHA( J ) = H( J, J )
- BETA( J ) = T( J, J )
- 10 CONTINUE
-*
-* If IHI < ILO, skip QZ steps
-*
- IF( IHI.LT.ILO )
- $ GO TO 190
-*
-* MAIN QZ ITERATION LOOP
-*
-* Initialize dynamic indices
-*
-* Eigenvalues ILAST+1:N have been found.
-* Column operations modify rows IFRSTM:whatever
-* Row operations modify columns whatever:ILASTM
-*
-* If only eigenvalues are being computed, then
-* IFRSTM is the row of the last splitting row above row ILAST;
-* this is always at least ILO.
-* IITER counts iterations since the last eigenvalue was found,
-* to tell when to use an extraordinary shift.
-* MAXIT is the maximum number of QZ sweeps allowed.
-*
- ILAST = IHI
- IF( ILSCHR ) THEN
- IFRSTM = 1
- ILASTM = N
- ELSE
- IFRSTM = ILO
- ILASTM = IHI
- END IF
- IITER = 0
- ESHIFT = CZERO
- MAXIT = 30*( IHI-ILO+1 )
-*
- DO 170 JITER = 1, MAXIT
-*
-* Check for too many iterations.
-*
- IF( JITER.GT.MAXIT )
- $ GO TO 180
-*
-* Split the matrix if possible.
-*
-* Two tests:
-* 1: H(j,j-1)=0 or j=ILO
-* 2: T(j,j)=0
-*
-* Special case: j=ILAST
-*
- IF( ILAST.EQ.ILO ) THEN
- GO TO 60
- ELSE
- IF( ABS1( H( ILAST, ILAST-1 ) ).LE.ATOL ) THEN
- H( ILAST, ILAST-1 ) = CZERO
- GO TO 60
- END IF
- END IF
-*
- IF( ABS( T( ILAST, ILAST ) ).LE.BTOL ) THEN
- T( ILAST, ILAST ) = CZERO
- GO TO 50
- END IF
-*
-* General case: j<ILAST
-*
- DO 40 J = ILAST - 1, ILO, -1
-*
-* Test 1: for H(j,j-1)=0 or j=ILO
-*
- IF( J.EQ.ILO ) THEN
- ILAZRO = .TRUE.
- ELSE
- IF( ABS1( H( J, J-1 ) ).LE.ATOL ) THEN
- H( J, J-1 ) = CZERO
- ILAZRO = .TRUE.
- ELSE
- ILAZRO = .FALSE.
- END IF
- END IF
-*
-* Test 2: for T(j,j)=0
-*
- IF( ABS( T( J, J ) ).LT.BTOL ) THEN
- T( J, J ) = CZERO
-*
-* Test 1a: Check for 2 consecutive small subdiagonals in A
-*
- ILAZR2 = .FALSE.
- IF( .NOT.ILAZRO ) THEN
- IF( ABS1( H( J, J-1 ) )*( ASCALE*ABS1( H( J+1,
- $ J ) ) ).LE.ABS1( H( J, J ) )*( ASCALE*ATOL ) )
- $ ILAZR2 = .TRUE.
- END IF
-*
-* If both tests pass (1 & 2), i.e., the leading diagonal
-* element of B in the block is zero, split a 1x1 block off
-* at the top. (I.e., at the J-th row/column) The leading
-* diagonal element of the remainder can also be zero, so
-* this may have to be done repeatedly.
-*
- IF( ILAZRO .OR. ILAZR2 ) THEN
- DO 20 JCH = J, ILAST - 1
- CTEMP = H( JCH, JCH )
- CALL ZLARTG( CTEMP, H( JCH+1, JCH ), C, S,
- $ H( JCH, JCH ) )
- H( JCH+1, JCH ) = CZERO
- CALL ZROT( ILASTM-JCH, H( JCH, JCH+1 ), LDH,
- $ H( JCH+1, JCH+1 ), LDH, C, S )
- CALL ZROT( ILASTM-JCH, T( JCH, JCH+1 ), LDT,
- $ T( JCH+1, JCH+1 ), LDT, C, S )
- IF( ILQ )
- $ CALL ZROT( N, Q( 1, JCH ), 1, Q( 1, JCH+1 ), 1,
- $ C, DCONJG( S ) )
- IF( ILAZR2 )
- $ H( JCH, JCH-1 ) = H( JCH, JCH-1 )*C
- ILAZR2 = .FALSE.
- IF( ABS1( T( JCH+1, JCH+1 ) ).GE.BTOL ) THEN
- IF( JCH+1.GE.ILAST ) THEN
- GO TO 60
- ELSE
- IFIRST = JCH + 1
- GO TO 70
- END IF
- END IF
- T( JCH+1, JCH+1 ) = CZERO
- 20 CONTINUE
- GO TO 50
- ELSE
-*
-* Only test 2 passed -- chase the zero to T(ILAST,ILAST)
-* Then process as in the case T(ILAST,ILAST)=0
-*
- DO 30 JCH = J, ILAST - 1
- CTEMP = T( JCH, JCH+1 )
- CALL ZLARTG( CTEMP, T( JCH+1, JCH+1 ), C, S,
- $ T( JCH, JCH+1 ) )
- T( JCH+1, JCH+1 ) = CZERO
- IF( JCH.LT.ILASTM-1 )
- $ CALL ZROT( ILASTM-JCH-1, T( JCH, JCH+2 ), LDT,
- $ T( JCH+1, JCH+2 ), LDT, C, S )
- CALL ZROT( ILASTM-JCH+2, H( JCH, JCH-1 ), LDH,
- $ H( JCH+1, JCH-1 ), LDH, C, S )
- IF( ILQ )
- $ CALL ZROT( N, Q( 1, JCH ), 1, Q( 1, JCH+1 ), 1,
- $ C, DCONJG( S ) )
- CTEMP = H( JCH+1, JCH )
- CALL ZLARTG( CTEMP, H( JCH+1, JCH-1 ), C, S,
- $ H( JCH+1, JCH ) )
- H( JCH+1, JCH-1 ) = CZERO
- CALL ZROT( JCH+1-IFRSTM, H( IFRSTM, JCH ), 1,
- $ H( IFRSTM, JCH-1 ), 1, C, S )
- CALL ZROT( JCH-IFRSTM, T( IFRSTM, JCH ), 1,
- $ T( IFRSTM, JCH-1 ), 1, C, S )
- IF( ILZ )
- $ CALL ZROT( N, Z( 1, JCH ), 1, Z( 1, JCH-1 ), 1,
- $ C, S )
- 30 CONTINUE
- GO TO 50
- END IF
- ELSE IF( ILAZRO ) THEN
-*
-* Only test 1 passed -- work on J:ILAST
-*
- IFIRST = J
- GO TO 70
- END IF
-*
-* Neither test passed -- try next J
-*
- 40 CONTINUE
-*
-* (Drop-through is "impossible")
-*
- INFO = 2*N + 1
- GO TO 210
-*
-* T(ILAST,ILAST)=0 -- clear H(ILAST,ILAST-1) to split off a
-* 1x1 block.
-*
- 50 CONTINUE
- CTEMP = H( ILAST, ILAST )
- CALL ZLARTG( CTEMP, H( ILAST, ILAST-1 ), C, S,
- $ H( ILAST, ILAST ) )
- H( ILAST, ILAST-1 ) = CZERO
- CALL ZROT( ILAST-IFRSTM, H( IFRSTM, ILAST ), 1,
- $ H( IFRSTM, ILAST-1 ), 1, C, S )
- CALL ZROT( ILAST-IFRSTM, T( IFRSTM, ILAST ), 1,
- $ T( IFRSTM, ILAST-1 ), 1, C, S )
- IF( ILZ )
- $ CALL ZROT( N, Z( 1, ILAST ), 1, Z( 1, ILAST-1 ), 1, C, S )
-*
-* H(ILAST,ILAST-1)=0 -- Standardize B, set ALPHA and BETA
-*
- 60 CONTINUE
- ABSB = ABS( T( ILAST, ILAST ) )
- IF( ABSB.GT.SAFMIN ) THEN
- SIGNBC = DCONJG( T( ILAST, ILAST ) / ABSB )
- T( ILAST, ILAST ) = ABSB
- IF( ILSCHR ) THEN
- CALL ZSCAL( ILAST-IFRSTM, SIGNBC, T( IFRSTM, ILAST ), 1 )
- CALL ZSCAL( ILAST+1-IFRSTM, SIGNBC, H( IFRSTM, ILAST ),
- $ 1 )
- ELSE
- H( ILAST, ILAST ) = H( ILAST, ILAST )*SIGNBC
- END IF
- IF( ILZ )
- $ CALL ZSCAL( N, SIGNBC, Z( 1, ILAST ), 1 )
- ELSE
- T( ILAST, ILAST ) = CZERO
- END IF
- ALPHA( ILAST ) = H( ILAST, ILAST )
- BETA( ILAST ) = T( ILAST, ILAST )
-*
-* Go to next block -- exit if finished.
-*
- ILAST = ILAST - 1
- IF( ILAST.LT.ILO )
- $ GO TO 190
-*
-* Reset counters
-*
- IITER = 0
- ESHIFT = CZERO
- IF( .NOT.ILSCHR ) THEN
- ILASTM = ILAST
- IF( IFRSTM.GT.ILAST )
- $ IFRSTM = ILO
- END IF
- GO TO 160
-*
-* QZ step
-*
-* This iteration only involves rows/columns IFIRST:ILAST. We
-* assume IFIRST < ILAST, and that the diagonal of B is non-zero.
-*
- 70 CONTINUE
- IITER = IITER + 1
- IF( .NOT.ILSCHR ) THEN
- IFRSTM = IFIRST
- END IF
-*
-* Compute the Shift.
-*
-* At this point, IFIRST < ILAST, and the diagonal elements of
-* T(IFIRST:ILAST,IFIRST,ILAST) are larger than BTOL (in
-* magnitude)
-*
- IF( ( IITER / 10 )*10.NE.IITER ) THEN
-*
-* The Wilkinson shift (AEP p.512), i.e., the eigenvalue of
-* the bottom-right 2x2 block of A inv(B) which is nearest to
-* the bottom-right element.
-*
-* We factor B as U*D, where U has unit diagonals, and
-* compute (A*inv(D))*inv(U).
-*
- U12 = ( BSCALE*T( ILAST-1, ILAST ) ) /
- $ ( BSCALE*T( ILAST, ILAST ) )
- AD11 = ( ASCALE*H( ILAST-1, ILAST-1 ) ) /
- $ ( BSCALE*T( ILAST-1, ILAST-1 ) )
- AD21 = ( ASCALE*H( ILAST, ILAST-1 ) ) /
- $ ( BSCALE*T( ILAST-1, ILAST-1 ) )
- AD12 = ( ASCALE*H( ILAST-1, ILAST ) ) /
- $ ( BSCALE*T( ILAST, ILAST ) )
- AD22 = ( ASCALE*H( ILAST, ILAST ) ) /
- $ ( BSCALE*T( ILAST, ILAST ) )
- ABI22 = AD22 - U12*AD21
-*
- T1 = HALF*( AD11+ABI22 )
- RTDISC = SQRT( T1**2+AD12*AD21-AD11*AD22 )
- TEMP = DBLE( T1-ABI22 )*DBLE( RTDISC ) +
- $ DIMAG( T1-ABI22 )*DIMAG( RTDISC )
- IF( TEMP.LE.ZERO ) THEN
- SHIFT = T1 + RTDISC
- ELSE
- SHIFT = T1 - RTDISC
- END IF
- ELSE
-*
-* Exceptional shift. Chosen for no particularly good reason.
-*
- ESHIFT = ESHIFT + DCONJG( ( ASCALE*H( ILAST-1, ILAST ) ) /
- $ ( BSCALE*T( ILAST-1, ILAST-1 ) ) )
- SHIFT = ESHIFT
- END IF
-*
-* Now check for two consecutive small subdiagonals.
-*
- DO 80 J = ILAST - 1, IFIRST + 1, -1
- ISTART = J
- CTEMP = ASCALE*H( J, J ) - SHIFT*( BSCALE*T( J, J ) )
- TEMP = ABS1( CTEMP )
- TEMP2 = ASCALE*ABS1( H( J+1, J ) )
- TEMPR = MAX( TEMP, TEMP2 )
- IF( TEMPR.LT.ONE .AND. TEMPR.NE.ZERO ) THEN
- TEMP = TEMP / TEMPR
- TEMP2 = TEMP2 / TEMPR
- END IF
- IF( ABS1( H( J, J-1 ) )*TEMP2.LE.TEMP*ATOL )
- $ GO TO 90
- 80 CONTINUE
-*
- ISTART = IFIRST
- CTEMP = ASCALE*H( IFIRST, IFIRST ) -
- $ SHIFT*( BSCALE*T( IFIRST, IFIRST ) )
- 90 CONTINUE
-*
-* Do an implicit-shift QZ sweep.
-*
-* Initial Q
-*
- CTEMP2 = ASCALE*H( ISTART+1, ISTART )
- CALL ZLARTG( CTEMP, CTEMP2, C, S, CTEMP3 )
-*
-* Sweep
-*
- DO 150 J = ISTART, ILAST - 1
- IF( J.GT.ISTART ) THEN
- CTEMP = H( J, J-1 )
- CALL ZLARTG( CTEMP, H( J+1, J-1 ), C, S, H( J, J-1 ) )
- H( J+1, J-1 ) = CZERO
- END IF
-*
- DO 100 JC = J, ILASTM
- CTEMP = C*H( J, JC ) + S*H( J+1, JC )
- H( J+1, JC ) = -DCONJG( S )*H( J, JC ) + C*H( J+1, JC )
- H( J, JC ) = CTEMP
- CTEMP2 = C*T( J, JC ) + S*T( J+1, JC )
- T( J+1, JC ) = -DCONJG( S )*T( J, JC ) + C*T( J+1, JC )
- T( J, JC ) = CTEMP2
- 100 CONTINUE
- IF( ILQ ) THEN
- DO 110 JR = 1, N
- CTEMP = C*Q( JR, J ) + DCONJG( S )*Q( JR, J+1 )
- Q( JR, J+1 ) = -S*Q( JR, J ) + C*Q( JR, J+1 )
- Q( JR, J ) = CTEMP
- 110 CONTINUE
- END IF
-*
- CTEMP = T( J+1, J+1 )
- CALL ZLARTG( CTEMP, T( J+1, J ), C, S, T( J+1, J+1 ) )
- T( J+1, J ) = CZERO
-*
- DO 120 JR = IFRSTM, MIN( J+2, ILAST )
- CTEMP = C*H( JR, J+1 ) + S*H( JR, J )
- H( JR, J ) = -DCONJG( S )*H( JR, J+1 ) + C*H( JR, J )
- H( JR, J+1 ) = CTEMP
- 120 CONTINUE
- DO 130 JR = IFRSTM, J
- CTEMP = C*T( JR, J+1 ) + S*T( JR, J )
- T( JR, J ) = -DCONJG( S )*T( JR, J+1 ) + C*T( JR, J )
- T( JR, J+1 ) = CTEMP
- 130 CONTINUE
- IF( ILZ ) THEN
- DO 140 JR = 1, N
- CTEMP = C*Z( JR, J+1 ) + S*Z( JR, J )
- Z( JR, J ) = -DCONJG( S )*Z( JR, J+1 ) + C*Z( JR, J )
- Z( JR, J+1 ) = CTEMP
- 140 CONTINUE
- END IF
- 150 CONTINUE
-*
- 160 CONTINUE
-*
- 170 CONTINUE
-*
-* Drop-through = non-convergence
-*
- 180 CONTINUE
- INFO = ILAST
- GO TO 210
-*
-* Successful completion of all QZ steps
-*
- 190 CONTINUE
-*
-* Set Eigenvalues 1:ILO-1
-*
- DO 200 J = 1, ILO - 1
- ABSB = ABS( T( J, J ) )
- IF( ABSB.GT.SAFMIN ) THEN
- SIGNBC = DCONJG( T( J, J ) / ABSB )
- T( J, J ) = ABSB
- IF( ILSCHR ) THEN
- CALL ZSCAL( J-1, SIGNBC, T( 1, J ), 1 )
- CALL ZSCAL( J, SIGNBC, H( 1, J ), 1 )
- ELSE
- H( J, J ) = H( J, J )*SIGNBC
- END IF
- IF( ILZ )
- $ CALL ZSCAL( N, SIGNBC, Z( 1, J ), 1 )
- ELSE
- T( J, J ) = CZERO
- END IF
- ALPHA( J ) = H( J, J )
- BETA( J ) = T( J, J )
- 200 CONTINUE
-*
-* Normal Termination
-*
- INFO = 0
-*
-* Exit (other than argument error) -- return optimal workspace size
-*
- 210 CONTINUE
- WORK( 1 ) = DCMPLX( N )
- RETURN
-*
-* End of ZHGEQZ
-*
- END
diff --git a/src/lib/lapack/zhseqr.f b/src/lib/lapack/zhseqr.f
deleted file mode 100644
index fb721dad..00000000
--- a/src/lib/lapack/zhseqr.f
+++ /dev/null
@@ -1,395 +0,0 @@
- SUBROUTINE ZHSEQR( JOB, COMPZ, N, ILO, IHI, H, LDH, W, Z, LDZ,
- $ WORK, LWORK, INFO )
-*
-* -- LAPACK driver routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- INTEGER IHI, ILO, INFO, LDH, LDZ, LWORK, N
- CHARACTER COMPZ, JOB
-* ..
-* .. Array Arguments ..
- COMPLEX*16 H( LDH, * ), W( * ), WORK( * ), Z( LDZ, * )
-* ..
-* Purpose
-* =======
-*
-* ZHSEQR computes the eigenvalues of a Hessenberg matrix H
-* and, optionally, the matrices T and Z from the Schur decomposition
-* H = Z T Z**H, where T is an upper triangular matrix (the
-* Schur form), and Z is the unitary matrix of Schur vectors.
-*
-* Optionally Z may be postmultiplied into an input unitary
-* matrix Q so that this routine can give the Schur factorization
-* of a matrix A which has been reduced to the Hessenberg form H
-* by the unitary matrix Q: A = Q*H*Q**H = (QZ)*H*(QZ)**H.
-*
-* Arguments
-* =========
-*
-* JOB (input) CHARACTER*1
-* = 'E': compute eigenvalues only;
-* = 'S': compute eigenvalues and the Schur form T.
-*
-* COMPZ (input) CHARACTER*1
-* = 'N': no Schur vectors are computed;
-* = 'I': Z is initialized to the unit matrix and the matrix Z
-* of Schur vectors of H is returned;
-* = 'V': Z must contain an unitary matrix Q on entry, and
-* the product Q*Z is returned.
-*
-* N (input) INTEGER
-* The order of the matrix H. N .GE. 0.
-*
-* ILO (input) INTEGER
-* IHI (input) INTEGER
-* It is assumed that H is already upper triangular in rows
-* and columns 1:ILO-1 and IHI+1:N. ILO and IHI are normally
-* set by a previous call to ZGEBAL, and then passed to ZGEHRD
-* when the matrix output by ZGEBAL is reduced to Hessenberg
-* form. Otherwise ILO and IHI should be set to 1 and N
-* respectively. If N.GT.0, then 1.LE.ILO.LE.IHI.LE.N.
-* If N = 0, then ILO = 1 and IHI = 0.
-*
-* H (input/output) COMPLEX*16 array, dimension (LDH,N)
-* On entry, the upper Hessenberg matrix H.
-* On exit, if INFO = 0 and JOB = 'S', H contains the upper
-* triangular matrix T from the Schur decomposition (the
-* Schur form). If INFO = 0 and JOB = 'E', the contents of
-* H are unspecified on exit. (The output value of H when
-* INFO.GT.0 is given under the description of INFO below.)
-*
-* Unlike earlier versions of ZHSEQR, this subroutine may
-* explicitly H(i,j) = 0 for i.GT.j and j = 1, 2, ... ILO-1
-* or j = IHI+1, IHI+2, ... N.
-*
-* LDH (input) INTEGER
-* The leading dimension of the array H. LDH .GE. max(1,N).
-*
-* W (output) COMPLEX*16 array, dimension (N)
-* The computed eigenvalues. If JOB = 'S', the eigenvalues are
-* stored in the same order as on the diagonal of the Schur
-* form returned in H, with W(i) = H(i,i).
-*
-* Z (input/output) COMPLEX*16 array, dimension (LDZ,N)
-* If COMPZ = 'N', Z is not referenced.
-* If COMPZ = 'I', on entry Z need not be set and on exit,
-* if INFO = 0, Z contains the unitary matrix Z of the Schur
-* vectors of H. If COMPZ = 'V', on entry Z must contain an
-* N-by-N matrix Q, which is assumed to be equal to the unit
-* matrix except for the submatrix Z(ILO:IHI,ILO:IHI). On exit,
-* if INFO = 0, Z contains Q*Z.
-* Normally Q is the unitary matrix generated by ZUNGHR
-* after the call to ZGEHRD which formed the Hessenberg matrix
-* H. (The output value of Z when INFO.GT.0 is given under
-* the description of INFO below.)
-*
-* LDZ (input) INTEGER
-* The leading dimension of the array Z. if COMPZ = 'I' or
-* COMPZ = 'V', then LDZ.GE.MAX(1,N). Otherwize, LDZ.GE.1.
-*
-* WORK (workspace/output) COMPLEX*16 array, dimension (LWORK)
-* On exit, if INFO = 0, WORK(1) returns an estimate of
-* the optimal value for LWORK.
-*
-* LWORK (input) INTEGER
-* The dimension of the array WORK. LWORK .GE. max(1,N)
-* is sufficient, but LWORK typically as large as 6*N may
-* be required for optimal performance. A workspace query
-* to determine the optimal workspace size is recommended.
-*
-* If LWORK = -1, then ZHSEQR does a workspace query.
-* In this case, ZHSEQR checks the input parameters and
-* estimates the optimal workspace size for the given
-* values of N, ILO and IHI. The estimate is returned
-* in WORK(1). No error message related to LWORK is
-* issued by XERBLA. Neither H nor Z are accessed.
-*
-*
-* INFO (output) INTEGER
-* = 0: successful exit
-* .LT. 0: if INFO = -i, the i-th argument had an illegal
-* value
-* .GT. 0: if INFO = i, ZHSEQR failed to compute all of
-* the eigenvalues. Elements 1:ilo-1 and i+1:n of WR
-* and WI contain those eigenvalues which have been
-* successfully computed. (Failures are rare.)
-*
-* If INFO .GT. 0 and JOB = 'E', then on exit, the
-* remaining unconverged eigenvalues are the eigen-
-* values of the upper Hessenberg matrix rows and
-* columns ILO through INFO of the final, output
-* value of H.
-*
-* If INFO .GT. 0 and JOB = 'S', then on exit
-*
-* (*) (initial value of H)*U = U*(final value of H)
-*
-* where U is a unitary matrix. The final
-* value of H is upper Hessenberg and triangular in
-* rows and columns INFO+1 through IHI.
-*
-* If INFO .GT. 0 and COMPZ = 'V', then on exit
-*
-* (final value of Z) = (initial value of Z)*U
-*
-* where U is the unitary matrix in (*) (regard-
-* less of the value of JOB.)
-*
-* If INFO .GT. 0 and COMPZ = 'I', then on exit
-* (final value of Z) = U
-* where U is the unitary matrix in (*) (regard-
-* less of the value of JOB.)
-*
-* If INFO .GT. 0 and COMPZ = 'N', then Z is not
-* accessed.
-*
-* ================================================================
-* Default values supplied by
-* ILAENV(ISPEC,'ZHSEQR',JOB(:1)//COMPZ(:1),N,ILO,IHI,LWORK).
-* It is suggested that these defaults be adjusted in order
-* to attain best performance in each particular
-* computational environment.
-*
-* ISPEC=1: The ZLAHQR vs ZLAQR0 crossover point.
-* Default: 75. (Must be at least 11.)
-*
-* ISPEC=2: Recommended deflation window size.
-* This depends on ILO, IHI and NS. NS is the
-* number of simultaneous shifts returned
-* by ILAENV(ISPEC=4). (See ISPEC=4 below.)
-* The default for (IHI-ILO+1).LE.500 is NS.
-* The default for (IHI-ILO+1).GT.500 is 3*NS/2.
-*
-* ISPEC=3: Nibble crossover point. (See ILAENV for
-* details.) Default: 14% of deflation window
-* size.
-*
-* ISPEC=4: Number of simultaneous shifts, NS, in
-* a multi-shift QR iteration.
-*
-* If IHI-ILO+1 is ...
-*
-* greater than ...but less ... the
-* or equal to ... than default is
-*
-* 1 30 NS - 2(+)
-* 30 60 NS - 4(+)
-* 60 150 NS = 10(+)
-* 150 590 NS = **
-* 590 3000 NS = 64
-* 3000 6000 NS = 128
-* 6000 infinity NS = 256
-*
-* (+) By default some or all matrices of this order
-* are passed to the implicit double shift routine
-* ZLAHQR and NS is ignored. See ISPEC=1 above
-* and comments in IPARM for details.
-*
-* The asterisks (**) indicate an ad-hoc
-* function of N increasing from 10 to 64.
-*
-* ISPEC=5: Select structured matrix multiply.
-* (See ILAENV for details.) Default: 3.
-*
-* ================================================================
-* Based on contributions by
-* Karen Braman and Ralph Byers, Department of Mathematics,
-* University of Kansas, USA
-*
-* ================================================================
-* References:
-* K. Braman, R. Byers and R. Mathias, The Multi-Shift QR
-* Algorithm Part I: Maintaining Well Focused Shifts, and Level 3
-* Performance, SIAM Journal of Matrix Analysis, volume 23, pages
-* 929--947, 2002.
-*
-* K. Braman, R. Byers and R. Mathias, The Multi-Shift QR
-* Algorithm Part II: Aggressive Early Deflation, SIAM Journal
-* of Matrix Analysis, volume 23, pages 948--973, 2002.
-*
-* ================================================================
-* .. Parameters ..
-*
-* ==== Matrices of order NTINY or smaller must be processed by
-* . ZLAHQR because of insufficient subdiagonal scratch space.
-* . (This is a hard limit.) ====
-*
-* ==== NL allocates some local workspace to help small matrices
-* . through a rare ZLAHQR failure. NL .GT. NTINY = 11 is
-* . required and NL .LE. NMIN = ILAENV(ISPEC=1,...) is recom-
-* . mended. (The default value of NMIN is 75.) Using NL = 49
-* . allows up to six simultaneous shifts and a 16-by-16
-* . deflation window. ====
-*
- INTEGER NTINY
- PARAMETER ( NTINY = 11 )
- INTEGER NL
- PARAMETER ( NL = 49 )
- COMPLEX*16 ZERO, ONE
- PARAMETER ( ZERO = ( 0.0d0, 0.0d0 ),
- $ ONE = ( 1.0d0, 0.0d0 ) )
- DOUBLE PRECISION RZERO
- PARAMETER ( RZERO = 0.0d0 )
-* ..
-* .. Local Arrays ..
- COMPLEX*16 HL( NL, NL ), WORKL( NL )
-* ..
-* .. Local Scalars ..
- INTEGER KBOT, NMIN
- LOGICAL INITZ, LQUERY, WANTT, WANTZ
-* ..
-* .. External Functions ..
- INTEGER ILAENV
- LOGICAL LSAME
- EXTERNAL ILAENV, LSAME
-* ..
-* .. External Subroutines ..
- EXTERNAL XERBLA, ZCOPY, ZLACPY, ZLAHQR, ZLAQR0, ZLASET
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC DBLE, DCMPLX, MAX, MIN
-* ..
-* .. Executable Statements ..
-*
-* ==== Decode and check the input parameters. ====
-*
- WANTT = LSAME( JOB, 'S' )
- INITZ = LSAME( COMPZ, 'I' )
- WANTZ = INITZ .OR. LSAME( COMPZ, 'V' )
- WORK( 1 ) = DCMPLX( DBLE( MAX( 1, N ) ), RZERO )
- LQUERY = LWORK.EQ.-1
-*
- INFO = 0
- IF( .NOT.LSAME( JOB, 'E' ) .AND. .NOT.WANTT ) THEN
- INFO = -1
- ELSE IF( .NOT.LSAME( COMPZ, 'N' ) .AND. .NOT.WANTZ ) THEN
- INFO = -2
- ELSE IF( N.LT.0 ) THEN
- INFO = -3
- ELSE IF( ILO.LT.1 .OR. ILO.GT.MAX( 1, N ) ) THEN
- INFO = -4
- ELSE IF( IHI.LT.MIN( ILO, N ) .OR. IHI.GT.N ) THEN
- INFO = -5
- ELSE IF( LDH.LT.MAX( 1, N ) ) THEN
- INFO = -7
- ELSE IF( LDZ.LT.1 .OR. ( WANTZ .AND. LDZ.LT.MAX( 1, N ) ) ) THEN
- INFO = -10
- ELSE IF( LWORK.LT.MAX( 1, N ) .AND. .NOT.LQUERY ) THEN
- INFO = -12
- END IF
-*
- IF( INFO.NE.0 ) THEN
-*
-* ==== Quick return in case of invalid argument. ====
-*
- CALL XERBLA( 'ZHSEQR', -INFO )
- RETURN
-*
- ELSE IF( N.EQ.0 ) THEN
-*
-* ==== Quick return in case N = 0; nothing to do. ====
-*
- RETURN
-*
- ELSE IF( LQUERY ) THEN
-*
-* ==== Quick return in case of a workspace query ====
-*
- CALL ZLAQR0( WANTT, WANTZ, N, ILO, IHI, H, LDH, W, ILO, IHI, Z,
- $ LDZ, WORK, LWORK, INFO )
-* ==== Ensure reported workspace size is backward-compatible with
-* . previous LAPACK versions. ====
- WORK( 1 ) = DCMPLX( MAX( DBLE( WORK( 1 ) ), DBLE( MAX( 1,
- $ N ) ) ), RZERO )
- RETURN
-*
- ELSE
-*
-* ==== copy eigenvalues isolated by ZGEBAL ====
-*
- IF( ILO.GT.1 )
- $ CALL ZCOPY( ILO-1, H, LDH+1, W, 1 )
- IF( IHI.LT.N )
- $ CALL ZCOPY( N-IHI, H( IHI+1, IHI+1 ), LDH+1, W( IHI+1 ), 1 )
-*
-* ==== Initialize Z, if requested ====
-*
- IF( INITZ )
- $ CALL ZLASET( 'A', N, N, ZERO, ONE, Z, LDZ )
-*
-* ==== Quick return if possible ====
-*
- IF( ILO.EQ.IHI ) THEN
- W( ILO ) = H( ILO, ILO )
- RETURN
- END IF
-*
-* ==== ZLAHQR/ZLAQR0 crossover point ====
-*
- NMIN = ILAENV( 1, 'ZHSEQR', JOB( : 1 ) // COMPZ( : 1 ), N, ILO,
- $ IHI, LWORK )
- NMIN = MAX( NTINY, NMIN )
-*
-* ==== ZLAQR0 for big matrices; ZLAHQR for small ones ====
-*
- IF( N.GT.NMIN ) THEN
- CALL ZLAQR0( WANTT, WANTZ, N, ILO, IHI, H, LDH, W, ILO, IHI,
- $ Z, LDZ, WORK, LWORK, INFO )
- ELSE
-*
-* ==== Small matrix ====
-*
- CALL ZLAHQR( WANTT, WANTZ, N, ILO, IHI, H, LDH, W, ILO, IHI,
- $ Z, LDZ, INFO )
-*
- IF( INFO.GT.0 ) THEN
-*
-* ==== A rare ZLAHQR failure! ZLAQR0 sometimes succeeds
-* . when ZLAHQR fails. ====
-*
- KBOT = INFO
-*
- IF( N.GE.NL ) THEN
-*
-* ==== Larger matrices have enough subdiagonal scratch
-* . space to call ZLAQR0 directly. ====
-*
- CALL ZLAQR0( WANTT, WANTZ, N, ILO, KBOT, H, LDH, W,
- $ ILO, IHI, Z, LDZ, WORK, LWORK, INFO )
-*
- ELSE
-*
-* ==== Tiny matrices don't have enough subdiagonal
-* . scratch space to benefit from ZLAQR0. Hence,
-* . tiny matrices must be copied into a larger
-* . array before calling ZLAQR0. ====
-*
- CALL ZLACPY( 'A', N, N, H, LDH, HL, NL )
- HL( N+1, N ) = ZERO
- CALL ZLASET( 'A', NL, NL-N, ZERO, ZERO, HL( 1, N+1 ),
- $ NL )
- CALL ZLAQR0( WANTT, WANTZ, NL, ILO, KBOT, HL, NL, W,
- $ ILO, IHI, Z, LDZ, WORKL, NL, INFO )
- IF( WANTT .OR. INFO.NE.0 )
- $ CALL ZLACPY( 'A', N, N, HL, NL, H, LDH )
- END IF
- END IF
- END IF
-*
-* ==== Clear out the trash, if necessary. ====
-*
- IF( ( WANTT .OR. INFO.NE.0 ) .AND. N.GT.2 )
- $ CALL ZLASET( 'L', N-2, N-2, ZERO, ZERO, H( 3, 1 ), LDH )
-*
-* ==== Ensure reported workspace size is backward-compatible with
-* . previous LAPACK versions. ====
-*
- WORK( 1 ) = DCMPLX( MAX( DBLE( MAX( 1, N ) ),
- $ DBLE( WORK( 1 ) ) ), RZERO )
- END IF
-*
-* ==== End of ZHSEQR ====
-*
- END
diff --git a/src/lib/lapack/zlabrd.f b/src/lib/lapack/zlabrd.f
deleted file mode 100644
index fb482c84..00000000
--- a/src/lib/lapack/zlabrd.f
+++ /dev/null
@@ -1,328 +0,0 @@
- SUBROUTINE ZLABRD( M, N, NB, A, LDA, D, E, TAUQ, TAUP, X, LDX, Y,
- $ LDY )
-*
-* -- LAPACK auxiliary routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- INTEGER LDA, LDX, LDY, M, N, NB
-* ..
-* .. Array Arguments ..
- DOUBLE PRECISION D( * ), E( * )
- COMPLEX*16 A( LDA, * ), TAUP( * ), TAUQ( * ), X( LDX, * ),
- $ Y( LDY, * )
-* ..
-*
-* Purpose
-* =======
-*
-* ZLABRD reduces the first NB rows and columns of a complex general
-* m by n matrix A to upper or lower real bidiagonal form by a unitary
-* transformation Q' * A * P, and returns the matrices X and Y which
-* are needed to apply the transformation to the unreduced part of A.
-*
-* If m >= n, A is reduced to upper bidiagonal form; if m < n, to lower
-* bidiagonal form.
-*
-* This is an auxiliary routine called by ZGEBRD
-*
-* Arguments
-* =========
-*
-* M (input) INTEGER
-* The number of rows in the matrix A.
-*
-* N (input) INTEGER
-* The number of columns in the matrix A.
-*
-* NB (input) INTEGER
-* The number of leading rows and columns of A to be reduced.
-*
-* A (input/output) COMPLEX*16 array, dimension (LDA,N)
-* On entry, the m by n general matrix to be reduced.
-* On exit, the first NB rows and columns of the matrix are
-* overwritten; the rest of the array is unchanged.
-* If m >= n, elements on and below the diagonal in the first NB
-* columns, with the array TAUQ, represent the unitary
-* matrix Q as a product of elementary reflectors; and
-* elements above the diagonal in the first NB rows, with the
-* array TAUP, represent the unitary matrix P as a product
-* of elementary reflectors.
-* If m < n, elements below the diagonal in the first NB
-* columns, with the array TAUQ, represent the unitary
-* matrix Q as a product of elementary reflectors, and
-* elements on and above the diagonal in the first NB rows,
-* with the array TAUP, represent the unitary matrix P as
-* a product of elementary reflectors.
-* See Further Details.
-*
-* LDA (input) INTEGER
-* The leading dimension of the array A. LDA >= max(1,M).
-*
-* D (output) DOUBLE PRECISION array, dimension (NB)
-* The diagonal elements of the first NB rows and columns of
-* the reduced matrix. D(i) = A(i,i).
-*
-* E (output) DOUBLE PRECISION array, dimension (NB)
-* The off-diagonal elements of the first NB rows and columns of
-* the reduced matrix.
-*
-* TAUQ (output) COMPLEX*16 array dimension (NB)
-* The scalar factors of the elementary reflectors which
-* represent the unitary matrix Q. See Further Details.
-*
-* TAUP (output) COMPLEX*16 array, dimension (NB)
-* The scalar factors of the elementary reflectors which
-* represent the unitary matrix P. See Further Details.
-*
-* X (output) COMPLEX*16 array, dimension (LDX,NB)
-* The m-by-nb matrix X required to update the unreduced part
-* of A.
-*
-* LDX (input) INTEGER
-* The leading dimension of the array X. LDX >= max(1,M).
-*
-* Y (output) COMPLEX*16 array, dimension (LDY,NB)
-* The n-by-nb matrix Y required to update the unreduced part
-* of A.
-*
-* LDY (input) INTEGER
-* The leading dimension of the array Y. LDY >= max(1,N).
-*
-* Further Details
-* ===============
-*
-* The matrices Q and P are represented as products of elementary
-* reflectors:
-*
-* Q = H(1) H(2) . . . H(nb) and P = G(1) G(2) . . . G(nb)
-*
-* Each H(i) and G(i) has the form:
-*
-* H(i) = I - tauq * v * v' and G(i) = I - taup * u * u'
-*
-* where tauq and taup are complex scalars, and v and u are complex
-* vectors.
-*
-* If m >= n, v(1:i-1) = 0, v(i) = 1, and v(i:m) is stored on exit in
-* A(i:m,i); u(1:i) = 0, u(i+1) = 1, and u(i+1:n) is stored on exit in
-* A(i,i+1:n); tauq is stored in TAUQ(i) and taup in TAUP(i).
-*
-* If m < n, v(1:i) = 0, v(i+1) = 1, and v(i+1:m) is stored on exit in
-* A(i+2:m,i); u(1:i-1) = 0, u(i) = 1, and u(i:n) is stored on exit in
-* A(i,i+1:n); tauq is stored in TAUQ(i) and taup in TAUP(i).
-*
-* The elements of the vectors v and u together form the m-by-nb matrix
-* V and the nb-by-n matrix U' which are needed, with X and Y, to apply
-* the transformation to the unreduced part of the matrix, using a block
-* update of the form: A := A - V*Y' - X*U'.
-*
-* The contents of A on exit are illustrated by the following examples
-* with nb = 2:
-*
-* m = 6 and n = 5 (m > n): m = 5 and n = 6 (m < n):
-*
-* ( 1 1 u1 u1 u1 ) ( 1 u1 u1 u1 u1 u1 )
-* ( v1 1 1 u2 u2 ) ( 1 1 u2 u2 u2 u2 )
-* ( v1 v2 a a a ) ( v1 1 a a a a )
-* ( v1 v2 a a a ) ( v1 v2 a a a a )
-* ( v1 v2 a a a ) ( v1 v2 a a a a )
-* ( v1 v2 a a a )
-*
-* where a denotes an element of the original matrix which is unchanged,
-* vi denotes an element of the vector defining H(i), and ui an element
-* of the vector defining G(i).
-*
-* =====================================================================
-*
-* .. Parameters ..
- COMPLEX*16 ZERO, ONE
- PARAMETER ( ZERO = ( 0.0D+0, 0.0D+0 ),
- $ ONE = ( 1.0D+0, 0.0D+0 ) )
-* ..
-* .. Local Scalars ..
- INTEGER I
- COMPLEX*16 ALPHA
-* ..
-* .. External Subroutines ..
- EXTERNAL ZGEMV, ZLACGV, ZLARFG, ZSCAL
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC MIN
-* ..
-* .. Executable Statements ..
-*
-* Quick return if possible
-*
- IF( M.LE.0 .OR. N.LE.0 )
- $ RETURN
-*
- IF( M.GE.N ) THEN
-*
-* Reduce to upper bidiagonal form
-*
- DO 10 I = 1, NB
-*
-* Update A(i:m,i)
-*
- CALL ZLACGV( I-1, Y( I, 1 ), LDY )
- CALL ZGEMV( 'No transpose', M-I+1, I-1, -ONE, A( I, 1 ),
- $ LDA, Y( I, 1 ), LDY, ONE, A( I, I ), 1 )
- CALL ZLACGV( I-1, Y( I, 1 ), LDY )
- CALL ZGEMV( 'No transpose', M-I+1, I-1, -ONE, X( I, 1 ),
- $ LDX, A( 1, I ), 1, ONE, A( I, I ), 1 )
-*
-* Generate reflection Q(i) to annihilate A(i+1:m,i)
-*
- ALPHA = A( I, I )
- CALL ZLARFG( M-I+1, ALPHA, A( MIN( I+1, M ), I ), 1,
- $ TAUQ( I ) )
- D( I ) = ALPHA
- IF( I.LT.N ) THEN
- A( I, I ) = ONE
-*
-* Compute Y(i+1:n,i)
-*
- CALL ZGEMV( 'Conjugate transpose', M-I+1, N-I, ONE,
- $ A( I, I+1 ), LDA, A( I, I ), 1, ZERO,
- $ Y( I+1, I ), 1 )
- CALL ZGEMV( 'Conjugate transpose', M-I+1, I-1, ONE,
- $ A( I, 1 ), LDA, A( I, I ), 1, ZERO,
- $ Y( 1, I ), 1 )
- CALL ZGEMV( 'No transpose', N-I, I-1, -ONE, Y( I+1, 1 ),
- $ LDY, Y( 1, I ), 1, ONE, Y( I+1, I ), 1 )
- CALL ZGEMV( 'Conjugate transpose', M-I+1, I-1, ONE,
- $ X( I, 1 ), LDX, A( I, I ), 1, ZERO,
- $ Y( 1, I ), 1 )
- CALL ZGEMV( 'Conjugate transpose', I-1, N-I, -ONE,
- $ A( 1, I+1 ), LDA, Y( 1, I ), 1, ONE,
- $ Y( I+1, I ), 1 )
- CALL ZSCAL( N-I, TAUQ( I ), Y( I+1, I ), 1 )
-*
-* Update A(i,i+1:n)
-*
- CALL ZLACGV( N-I, A( I, I+1 ), LDA )
- CALL ZLACGV( I, A( I, 1 ), LDA )
- CALL ZGEMV( 'No transpose', N-I, I, -ONE, Y( I+1, 1 ),
- $ LDY, A( I, 1 ), LDA, ONE, A( I, I+1 ), LDA )
- CALL ZLACGV( I, A( I, 1 ), LDA )
- CALL ZLACGV( I-1, X( I, 1 ), LDX )
- CALL ZGEMV( 'Conjugate transpose', I-1, N-I, -ONE,
- $ A( 1, I+1 ), LDA, X( I, 1 ), LDX, ONE,
- $ A( I, I+1 ), LDA )
- CALL ZLACGV( I-1, X( I, 1 ), LDX )
-*
-* Generate reflection P(i) to annihilate A(i,i+2:n)
-*
- ALPHA = A( I, I+1 )
- CALL ZLARFG( N-I, ALPHA, A( I, MIN( I+2, N ) ), LDA,
- $ TAUP( I ) )
- E( I ) = ALPHA
- A( I, I+1 ) = ONE
-*
-* Compute X(i+1:m,i)
-*
- CALL ZGEMV( 'No transpose', M-I, N-I, ONE, A( I+1, I+1 ),
- $ LDA, A( I, I+1 ), LDA, ZERO, X( I+1, I ), 1 )
- CALL ZGEMV( 'Conjugate transpose', N-I, I, ONE,
- $ Y( I+1, 1 ), LDY, A( I, I+1 ), LDA, ZERO,
- $ X( 1, I ), 1 )
- CALL ZGEMV( 'No transpose', M-I, I, -ONE, A( I+1, 1 ),
- $ LDA, X( 1, I ), 1, ONE, X( I+1, I ), 1 )
- CALL ZGEMV( 'No transpose', I-1, N-I, ONE, A( 1, I+1 ),
- $ LDA, A( I, I+1 ), LDA, ZERO, X( 1, I ), 1 )
- CALL ZGEMV( 'No transpose', M-I, I-1, -ONE, X( I+1, 1 ),
- $ LDX, X( 1, I ), 1, ONE, X( I+1, I ), 1 )
- CALL ZSCAL( M-I, TAUP( I ), X( I+1, I ), 1 )
- CALL ZLACGV( N-I, A( I, I+1 ), LDA )
- END IF
- 10 CONTINUE
- ELSE
-*
-* Reduce to lower bidiagonal form
-*
- DO 20 I = 1, NB
-*
-* Update A(i,i:n)
-*
- CALL ZLACGV( N-I+1, A( I, I ), LDA )
- CALL ZLACGV( I-1, A( I, 1 ), LDA )
- CALL ZGEMV( 'No transpose', N-I+1, I-1, -ONE, Y( I, 1 ),
- $ LDY, A( I, 1 ), LDA, ONE, A( I, I ), LDA )
- CALL ZLACGV( I-1, A( I, 1 ), LDA )
- CALL ZLACGV( I-1, X( I, 1 ), LDX )
- CALL ZGEMV( 'Conjugate transpose', I-1, N-I+1, -ONE,
- $ A( 1, I ), LDA, X( I, 1 ), LDX, ONE, A( I, I ),
- $ LDA )
- CALL ZLACGV( I-1, X( I, 1 ), LDX )
-*
-* Generate reflection P(i) to annihilate A(i,i+1:n)
-*
- ALPHA = A( I, I )
- CALL ZLARFG( N-I+1, ALPHA, A( I, MIN( I+1, N ) ), LDA,
- $ TAUP( I ) )
- D( I ) = ALPHA
- IF( I.LT.M ) THEN
- A( I, I ) = ONE
-*
-* Compute X(i+1:m,i)
-*
- CALL ZGEMV( 'No transpose', M-I, N-I+1, ONE, A( I+1, I ),
- $ LDA, A( I, I ), LDA, ZERO, X( I+1, I ), 1 )
- CALL ZGEMV( 'Conjugate transpose', N-I+1, I-1, ONE,
- $ Y( I, 1 ), LDY, A( I, I ), LDA, ZERO,
- $ X( 1, I ), 1 )
- CALL ZGEMV( 'No transpose', M-I, I-1, -ONE, A( I+1, 1 ),
- $ LDA, X( 1, I ), 1, ONE, X( I+1, I ), 1 )
- CALL ZGEMV( 'No transpose', I-1, N-I+1, ONE, A( 1, I ),
- $ LDA, A( I, I ), LDA, ZERO, X( 1, I ), 1 )
- CALL ZGEMV( 'No transpose', M-I, I-1, -ONE, X( I+1, 1 ),
- $ LDX, X( 1, I ), 1, ONE, X( I+1, I ), 1 )
- CALL ZSCAL( M-I, TAUP( I ), X( I+1, I ), 1 )
- CALL ZLACGV( N-I+1, A( I, I ), LDA )
-*
-* Update A(i+1:m,i)
-*
- CALL ZLACGV( I-1, Y( I, 1 ), LDY )
- CALL ZGEMV( 'No transpose', M-I, I-1, -ONE, A( I+1, 1 ),
- $ LDA, Y( I, 1 ), LDY, ONE, A( I+1, I ), 1 )
- CALL ZLACGV( I-1, Y( I, 1 ), LDY )
- CALL ZGEMV( 'No transpose', M-I, I, -ONE, X( I+1, 1 ),
- $ LDX, A( 1, I ), 1, ONE, A( I+1, I ), 1 )
-*
-* Generate reflection Q(i) to annihilate A(i+2:m,i)
-*
- ALPHA = A( I+1, I )
- CALL ZLARFG( M-I, ALPHA, A( MIN( I+2, M ), I ), 1,
- $ TAUQ( I ) )
- E( I ) = ALPHA
- A( I+1, I ) = ONE
-*
-* Compute Y(i+1:n,i)
-*
- CALL ZGEMV( 'Conjugate transpose', M-I, N-I, ONE,
- $ A( I+1, I+1 ), LDA, A( I+1, I ), 1, ZERO,
- $ Y( I+1, I ), 1 )
- CALL ZGEMV( 'Conjugate transpose', M-I, I-1, ONE,
- $ A( I+1, 1 ), LDA, A( I+1, I ), 1, ZERO,
- $ Y( 1, I ), 1 )
- CALL ZGEMV( 'No transpose', N-I, I-1, -ONE, Y( I+1, 1 ),
- $ LDY, Y( 1, I ), 1, ONE, Y( I+1, I ), 1 )
- CALL ZGEMV( 'Conjugate transpose', M-I, I, ONE,
- $ X( I+1, 1 ), LDX, A( I+1, I ), 1, ZERO,
- $ Y( 1, I ), 1 )
- CALL ZGEMV( 'Conjugate transpose', I, N-I, -ONE,
- $ A( 1, I+1 ), LDA, Y( 1, I ), 1, ONE,
- $ Y( I+1, I ), 1 )
- CALL ZSCAL( N-I, TAUQ( I ), Y( I+1, I ), 1 )
- ELSE
- CALL ZLACGV( N-I+1, A( I, I ), LDA )
- END IF
- 20 CONTINUE
- END IF
- RETURN
-*
-* End of ZLABRD
-*
- END
diff --git a/src/lib/lapack/zlacgv.f b/src/lib/lapack/zlacgv.f
deleted file mode 100644
index 0033e306..00000000
--- a/src/lib/lapack/zlacgv.f
+++ /dev/null
@@ -1,60 +0,0 @@
- SUBROUTINE ZLACGV( N, X, INCX )
-*
-* -- LAPACK auxiliary routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- INTEGER INCX, N
-* ..
-* .. Array Arguments ..
- COMPLEX*16 X( * )
-* ..
-*
-* Purpose
-* =======
-*
-* ZLACGV conjugates a complex vector of length N.
-*
-* Arguments
-* =========
-*
-* N (input) INTEGER
-* The length of the vector X. N >= 0.
-*
-* X (input/output) COMPLEX*16 array, dimension
-* (1+(N-1)*abs(INCX))
-* On entry, the vector of length N to be conjugated.
-* On exit, X is overwritten with conjg(X).
-*
-* INCX (input) INTEGER
-* The spacing between successive elements of X.
-*
-* =====================================================================
-*
-* .. Local Scalars ..
- INTEGER I, IOFF
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC DCONJG
-* ..
-* .. Executable Statements ..
-*
- IF( INCX.EQ.1 ) THEN
- DO 10 I = 1, N
- X( I ) = DCONJG( X( I ) )
- 10 CONTINUE
- ELSE
- IOFF = 1
- IF( INCX.LT.0 )
- $ IOFF = 1 - ( N-1 )*INCX
- DO 20 I = 1, N
- X( IOFF ) = DCONJG( X( IOFF ) )
- IOFF = IOFF + INCX
- 20 CONTINUE
- END IF
- RETURN
-*
-* End of ZLACGV
-*
- END
diff --git a/src/lib/lapack/zlacn2.f b/src/lib/lapack/zlacn2.f
deleted file mode 100644
index 99f7ae35..00000000
--- a/src/lib/lapack/zlacn2.f
+++ /dev/null
@@ -1,221 +0,0 @@
- SUBROUTINE ZLACN2( N, V, X, EST, KASE, ISAVE )
-*
-* -- LAPACK auxiliary routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- INTEGER KASE, N
- DOUBLE PRECISION EST
-* ..
-* .. Array Arguments ..
- INTEGER ISAVE( 3 )
- COMPLEX*16 V( * ), X( * )
-* ..
-*
-* Purpose
-* =======
-*
-* ZLACN2 estimates the 1-norm of a square, complex matrix A.
-* Reverse communication is used for evaluating matrix-vector products.
-*
-* Arguments
-* =========
-*
-* N (input) INTEGER
-* The order of the matrix. N >= 1.
-*
-* V (workspace) COMPLEX*16 array, dimension (N)
-* On the final return, V = A*W, where EST = norm(V)/norm(W)
-* (W is not returned).
-*
-* X (input/output) COMPLEX*16 array, dimension (N)
-* On an intermediate return, X should be overwritten by
-* A * X, if KASE=1,
-* A' * X, if KASE=2,
-* where A' is the conjugate transpose of A, and ZLACN2 must be
-* re-called with all the other parameters unchanged.
-*
-* EST (input/output) DOUBLE PRECISION
-* On entry with KASE = 1 or 2 and ISAVE(1) = 3, EST should be
-* unchanged from the previous call to ZLACN2.
-* On exit, EST is an estimate (a lower bound) for norm(A).
-*
-* KASE (input/output) INTEGER
-* On the initial call to ZLACN2, KASE should be 0.
-* On an intermediate return, KASE will be 1 or 2, indicating
-* whether X should be overwritten by A * X or A' * X.
-* On the final return from ZLACN2, KASE will again be 0.
-*
-* ISAVE (input/output) INTEGER array, dimension (3)
-* ISAVE is used to save variables between calls to ZLACN2
-*
-* Further Details
-* ======= =======
-*
-* Contributed by Nick Higham, University of Manchester.
-* Originally named CONEST, dated March 16, 1988.
-*
-* Reference: N.J. Higham, "FORTRAN codes for estimating the one-norm of
-* a real or complex matrix, with applications to condition estimation",
-* ACM Trans. Math. Soft., vol. 14, no. 4, pp. 381-396, December 1988.
-*
-* Last modified: April, 1999
-*
-* This is a thread safe version of ZLACON, which uses the array ISAVE
-* in place of a SAVE statement, as follows:
-*
-* ZLACON ZLACN2
-* JUMP ISAVE(1)
-* J ISAVE(2)
-* ITER ISAVE(3)
-*
-* =====================================================================
-*
-* .. Parameters ..
- INTEGER ITMAX
- PARAMETER ( ITMAX = 5 )
- DOUBLE PRECISION ONE, TWO
- PARAMETER ( ONE = 1.0D0, TWO = 2.0D0 )
- COMPLEX*16 CZERO, CONE
- PARAMETER ( CZERO = ( 0.0D0, 0.0D0 ),
- $ CONE = ( 1.0D0, 0.0D0 ) )
-* ..
-* .. Local Scalars ..
- INTEGER I, JLAST
- DOUBLE PRECISION ABSXI, ALTSGN, ESTOLD, SAFMIN, TEMP
-* ..
-* .. External Functions ..
- INTEGER IZMAX1
- DOUBLE PRECISION DLAMCH, DZSUM1
- EXTERNAL IZMAX1, DLAMCH, DZSUM1
-* ..
-* .. External Subroutines ..
- EXTERNAL ZCOPY
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC ABS, DBLE, DCMPLX, DIMAG
-* ..
-* .. Executable Statements ..
-*
- SAFMIN = DLAMCH( 'Safe minimum' )
- IF( KASE.EQ.0 ) THEN
- DO 10 I = 1, N
- X( I ) = DCMPLX( ONE / DBLE( N ) )
- 10 CONTINUE
- KASE = 1
- ISAVE( 1 ) = 1
- RETURN
- END IF
-*
- GO TO ( 20, 40, 70, 90, 120 )ISAVE( 1 )
-*
-* ................ ENTRY (ISAVE( 1 ) = 1)
-* FIRST ITERATION. X HAS BEEN OVERWRITTEN BY A*X.
-*
- 20 CONTINUE
- IF( N.EQ.1 ) THEN
- V( 1 ) = X( 1 )
- EST = ABS( V( 1 ) )
-* ... QUIT
- GO TO 130
- END IF
- EST = DZSUM1( N, X, 1 )
-*
- DO 30 I = 1, N
- ABSXI = ABS( X( I ) )
- IF( ABSXI.GT.SAFMIN ) THEN
- X( I ) = DCMPLX( DBLE( X( I ) ) / ABSXI,
- $ DIMAG( X( I ) ) / ABSXI )
- ELSE
- X( I ) = CONE
- END IF
- 30 CONTINUE
- KASE = 2
- ISAVE( 1 ) = 2
- RETURN
-*
-* ................ ENTRY (ISAVE( 1 ) = 2)
-* FIRST ITERATION. X HAS BEEN OVERWRITTEN BY CTRANS(A)*X.
-*
- 40 CONTINUE
- ISAVE( 2 ) = IZMAX1( N, X, 1 )
- ISAVE( 3 ) = 2
-*
-* MAIN LOOP - ITERATIONS 2,3,...,ITMAX.
-*
- 50 CONTINUE
- DO 60 I = 1, N
- X( I ) = CZERO
- 60 CONTINUE
- X( ISAVE( 2 ) ) = CONE
- KASE = 1
- ISAVE( 1 ) = 3
- RETURN
-*
-* ................ ENTRY (ISAVE( 1 ) = 3)
-* X HAS BEEN OVERWRITTEN BY A*X.
-*
- 70 CONTINUE
- CALL ZCOPY( N, X, 1, V, 1 )
- ESTOLD = EST
- EST = DZSUM1( N, V, 1 )
-*
-* TEST FOR CYCLING.
- IF( EST.LE.ESTOLD )
- $ GO TO 100
-*
- DO 80 I = 1, N
- ABSXI = ABS( X( I ) )
- IF( ABSXI.GT.SAFMIN ) THEN
- X( I ) = DCMPLX( DBLE( X( I ) ) / ABSXI,
- $ DIMAG( X( I ) ) / ABSXI )
- ELSE
- X( I ) = CONE
- END IF
- 80 CONTINUE
- KASE = 2
- ISAVE( 1 ) = 4
- RETURN
-*
-* ................ ENTRY (ISAVE( 1 ) = 4)
-* X HAS BEEN OVERWRITTEN BY CTRANS(A)*X.
-*
- 90 CONTINUE
- JLAST = ISAVE( 2 )
- ISAVE( 2 ) = IZMAX1( N, X, 1 )
- IF( ( ABS( X( JLAST ) ).NE.ABS( X( ISAVE( 2 ) ) ) ) .AND.
- $ ( ISAVE( 3 ).LT.ITMAX ) ) THEN
- ISAVE( 3 ) = ISAVE( 3 ) + 1
- GO TO 50
- END IF
-*
-* ITERATION COMPLETE. FINAL STAGE.
-*
- 100 CONTINUE
- ALTSGN = ONE
- DO 110 I = 1, N
- X( I ) = DCMPLX( ALTSGN*( ONE+DBLE( I-1 ) / DBLE( N-1 ) ) )
- ALTSGN = -ALTSGN
- 110 CONTINUE
- KASE = 1
- ISAVE( 1 ) = 5
- RETURN
-*
-* ................ ENTRY (ISAVE( 1 ) = 5)
-* X HAS BEEN OVERWRITTEN BY A*X.
-*
- 120 CONTINUE
- TEMP = TWO*( DZSUM1( N, X, 1 ) / DBLE( 3*N ) )
- IF( TEMP.GT.EST ) THEN
- CALL ZCOPY( N, X, 1, V, 1 )
- EST = TEMP
- END IF
-*
- 130 CONTINUE
- KASE = 0
- RETURN
-*
-* End of ZLACN2
-*
- END
diff --git a/src/lib/lapack/zlacon.f b/src/lib/lapack/zlacon.f
deleted file mode 100644
index 5773ef92..00000000
--- a/src/lib/lapack/zlacon.f
+++ /dev/null
@@ -1,212 +0,0 @@
- SUBROUTINE ZLACON( N, V, X, EST, KASE )
-*
-* -- LAPACK auxiliary routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- INTEGER KASE, N
- DOUBLE PRECISION EST
-* ..
-* .. Array Arguments ..
- COMPLEX*16 V( N ), X( N )
-* ..
-*
-* Purpose
-* =======
-*
-* ZLACON estimates the 1-norm of a square, complex matrix A.
-* Reverse communication is used for evaluating matrix-vector products.
-*
-* Arguments
-* =========
-*
-* N (input) INTEGER
-* The order of the matrix. N >= 1.
-*
-* V (workspace) COMPLEX*16 array, dimension (N)
-* On the final return, V = A*W, where EST = norm(V)/norm(W)
-* (W is not returned).
-*
-* X (input/output) COMPLEX*16 array, dimension (N)
-* On an intermediate return, X should be overwritten by
-* A * X, if KASE=1,
-* A' * X, if KASE=2,
-* where A' is the conjugate transpose of A, and ZLACON must be
-* re-called with all the other parameters unchanged.
-*
-* EST (input/output) DOUBLE PRECISION
-* On entry with KASE = 1 or 2 and JUMP = 3, EST should be
-* unchanged from the previous call to ZLACON.
-* On exit, EST is an estimate (a lower bound) for norm(A).
-*
-* KASE (input/output) INTEGER
-* On the initial call to ZLACON, KASE should be 0.
-* On an intermediate return, KASE will be 1 or 2, indicating
-* whether X should be overwritten by A * X or A' * X.
-* On the final return from ZLACON, KASE will again be 0.
-*
-* Further Details
-* ======= =======
-*
-* Contributed by Nick Higham, University of Manchester.
-* Originally named CONEST, dated March 16, 1988.
-*
-* Reference: N.J. Higham, "FORTRAN codes for estimating the one-norm of
-* a real or complex matrix, with applications to condition estimation",
-* ACM Trans. Math. Soft., vol. 14, no. 4, pp. 381-396, December 1988.
-*
-* Last modified: April, 1999
-*
-* =====================================================================
-*
-* .. Parameters ..
- INTEGER ITMAX
- PARAMETER ( ITMAX = 5 )
- DOUBLE PRECISION ONE, TWO
- PARAMETER ( ONE = 1.0D0, TWO = 2.0D0 )
- COMPLEX*16 CZERO, CONE
- PARAMETER ( CZERO = ( 0.0D0, 0.0D0 ),
- $ CONE = ( 1.0D0, 0.0D0 ) )
-* ..
-* .. Local Scalars ..
- INTEGER I, ITER, J, JLAST, JUMP
- DOUBLE PRECISION ABSXI, ALTSGN, ESTOLD, SAFMIN, TEMP
-* ..
-* .. External Functions ..
- INTEGER IZMAX1
- DOUBLE PRECISION DLAMCH, DZSUM1
- EXTERNAL IZMAX1, DLAMCH, DZSUM1
-* ..
-* .. External Subroutines ..
- EXTERNAL ZCOPY
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC ABS, DBLE, DCMPLX, DIMAG
-* ..
-* .. Save statement ..
- SAVE
-* ..
-* .. Executable Statements ..
-*
- SAFMIN = DLAMCH( 'Safe minimum' )
- IF( KASE.EQ.0 ) THEN
- DO 10 I = 1, N
- X( I ) = DCMPLX( ONE / DBLE( N ) )
- 10 CONTINUE
- KASE = 1
- JUMP = 1
- RETURN
- END IF
-*
- GO TO ( 20, 40, 70, 90, 120 )JUMP
-*
-* ................ ENTRY (JUMP = 1)
-* FIRST ITERATION. X HAS BEEN OVERWRITTEN BY A*X.
-*
- 20 CONTINUE
- IF( N.EQ.1 ) THEN
- V( 1 ) = X( 1 )
- EST = ABS( V( 1 ) )
-* ... QUIT
- GO TO 130
- END IF
- EST = DZSUM1( N, X, 1 )
-*
- DO 30 I = 1, N
- ABSXI = ABS( X( I ) )
- IF( ABSXI.GT.SAFMIN ) THEN
- X( I ) = DCMPLX( DBLE( X( I ) ) / ABSXI,
- $ DIMAG( X( I ) ) / ABSXI )
- ELSE
- X( I ) = CONE
- END IF
- 30 CONTINUE
- KASE = 2
- JUMP = 2
- RETURN
-*
-* ................ ENTRY (JUMP = 2)
-* FIRST ITERATION. X HAS BEEN OVERWRITTEN BY CTRANS(A)*X.
-*
- 40 CONTINUE
- J = IZMAX1( N, X, 1 )
- ITER = 2
-*
-* MAIN LOOP - ITERATIONS 2,3,...,ITMAX.
-*
- 50 CONTINUE
- DO 60 I = 1, N
- X( I ) = CZERO
- 60 CONTINUE
- X( J ) = CONE
- KASE = 1
- JUMP = 3
- RETURN
-*
-* ................ ENTRY (JUMP = 3)
-* X HAS BEEN OVERWRITTEN BY A*X.
-*
- 70 CONTINUE
- CALL ZCOPY( N, X, 1, V, 1 )
- ESTOLD = EST
- EST = DZSUM1( N, V, 1 )
-*
-* TEST FOR CYCLING.
- IF( EST.LE.ESTOLD )
- $ GO TO 100
-*
- DO 80 I = 1, N
- ABSXI = ABS( X( I ) )
- IF( ABSXI.GT.SAFMIN ) THEN
- X( I ) = DCMPLX( DBLE( X( I ) ) / ABSXI,
- $ DIMAG( X( I ) ) / ABSXI )
- ELSE
- X( I ) = CONE
- END IF
- 80 CONTINUE
- KASE = 2
- JUMP = 4
- RETURN
-*
-* ................ ENTRY (JUMP = 4)
-* X HAS BEEN OVERWRITTEN BY CTRANS(A)*X.
-*
- 90 CONTINUE
- JLAST = J
- J = IZMAX1( N, X, 1 )
- IF( ( ABS( X( JLAST ) ).NE.ABS( X( J ) ) ) .AND.
- $ ( ITER.LT.ITMAX ) ) THEN
- ITER = ITER + 1
- GO TO 50
- END IF
-*
-* ITERATION COMPLETE. FINAL STAGE.
-*
- 100 CONTINUE
- ALTSGN = ONE
- DO 110 I = 1, N
- X( I ) = DCMPLX( ALTSGN*( ONE+DBLE( I-1 ) / DBLE( N-1 ) ) )
- ALTSGN = -ALTSGN
- 110 CONTINUE
- KASE = 1
- JUMP = 5
- RETURN
-*
-* ................ ENTRY (JUMP = 5)
-* X HAS BEEN OVERWRITTEN BY A*X.
-*
- 120 CONTINUE
- TEMP = TWO*( DZSUM1( N, X, 1 ) / DBLE( 3*N ) )
- IF( TEMP.GT.EST ) THEN
- CALL ZCOPY( N, X, 1, V, 1 )
- EST = TEMP
- END IF
-*
- 130 CONTINUE
- KASE = 0
- RETURN
-*
-* End of ZLACON
-*
- END
diff --git a/src/lib/lapack/zlacpy.f b/src/lib/lapack/zlacpy.f
deleted file mode 100644
index 8878311a..00000000
--- a/src/lib/lapack/zlacpy.f
+++ /dev/null
@@ -1,90 +0,0 @@
- SUBROUTINE ZLACPY( UPLO, M, N, A, LDA, B, LDB )
-*
-* -- LAPACK auxiliary routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- CHARACTER UPLO
- INTEGER LDA, LDB, M, N
-* ..
-* .. Array Arguments ..
- COMPLEX*16 A( LDA, * ), B( LDB, * )
-* ..
-*
-* Purpose
-* =======
-*
-* ZLACPY copies all or part of a two-dimensional matrix A to another
-* matrix B.
-*
-* Arguments
-* =========
-*
-* UPLO (input) CHARACTER*1
-* Specifies the part of the matrix A to be copied to B.
-* = 'U': Upper triangular part
-* = 'L': Lower triangular part
-* Otherwise: All of the matrix A
-*
-* M (input) INTEGER
-* The number of rows of the matrix A. M >= 0.
-*
-* N (input) INTEGER
-* The number of columns of the matrix A. N >= 0.
-*
-* A (input) COMPLEX*16 array, dimension (LDA,N)
-* The m by n matrix A. If UPLO = 'U', only the upper trapezium
-* is accessed; if UPLO = 'L', only the lower trapezium is
-* accessed.
-*
-* LDA (input) INTEGER
-* The leading dimension of the array A. LDA >= max(1,M).
-*
-* B (output) COMPLEX*16 array, dimension (LDB,N)
-* On exit, B = A in the locations specified by UPLO.
-*
-* LDB (input) INTEGER
-* The leading dimension of the array B. LDB >= max(1,M).
-*
-* =====================================================================
-*
-* .. Local Scalars ..
- INTEGER I, J
-* ..
-* .. External Functions ..
- LOGICAL LSAME
- EXTERNAL LSAME
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC MIN
-* ..
-* .. Executable Statements ..
-*
- IF( LSAME( UPLO, 'U' ) ) THEN
- DO 20 J = 1, N
- DO 10 I = 1, MIN( J, M )
- B( I, J ) = A( I, J )
- 10 CONTINUE
- 20 CONTINUE
-*
- ELSE IF( LSAME( UPLO, 'L' ) ) THEN
- DO 40 J = 1, N
- DO 30 I = J, M
- B( I, J ) = A( I, J )
- 30 CONTINUE
- 40 CONTINUE
-*
- ELSE
- DO 60 J = 1, N
- DO 50 I = 1, M
- B( I, J ) = A( I, J )
- 50 CONTINUE
- 60 CONTINUE
- END IF
-*
- RETURN
-*
-* End of ZLACPY
-*
- END
diff --git a/src/lib/lapack/zladiv.f b/src/lib/lapack/zladiv.f
deleted file mode 100644
index 4a12055e..00000000
--- a/src/lib/lapack/zladiv.f
+++ /dev/null
@@ -1,46 +0,0 @@
- COMPLEX*16 FUNCTION ZLADIV( X, Y )
-*
-* -- LAPACK auxiliary routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- COMPLEX*16 X, Y
-* ..
-*
-* Purpose
-* =======
-*
-* ZLADIV := X / Y, where X and Y are complex. The computation of X / Y
-* will not overflow on an intermediary step unless the results
-* overflows.
-*
-* Arguments
-* =========
-*
-* X (input) COMPLEX*16
-* Y (input) COMPLEX*16
-* The complex scalars X and Y.
-*
-* =====================================================================
-*
-* .. Local Scalars ..
- DOUBLE PRECISION ZI, ZR
-* ..
-* .. External Subroutines ..
- EXTERNAL DLADIV
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC DBLE, DCMPLX, DIMAG
-* ..
-* .. Executable Statements ..
-*
- CALL DLADIV( DBLE( X ), DIMAG( X ), DBLE( Y ), DIMAG( Y ), ZR,
- $ ZI )
- ZLADIV = DCMPLX( ZR, ZI )
-*
- RETURN
-*
-* End of ZLADIV
-*
- END
diff --git a/src/lib/lapack/zlahqr.f b/src/lib/lapack/zlahqr.f
deleted file mode 100644
index 9ce9be19..00000000
--- a/src/lib/lapack/zlahqr.f
+++ /dev/null
@@ -1,470 +0,0 @@
- SUBROUTINE ZLAHQR( WANTT, WANTZ, N, ILO, IHI, H, LDH, W, ILOZ,
- $ IHIZ, Z, LDZ, INFO )
-*
-* -- LAPACK auxiliary routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- INTEGER IHI, IHIZ, ILO, ILOZ, INFO, LDH, LDZ, N
- LOGICAL WANTT, WANTZ
-* ..
-* .. Array Arguments ..
- COMPLEX*16 H( LDH, * ), W( * ), Z( LDZ, * )
-* ..
-*
-* Purpose
-* =======
-*
-* ZLAHQR is an auxiliary routine called by CHSEQR to update the
-* eigenvalues and Schur decomposition already computed by CHSEQR, by
-* dealing with the Hessenberg submatrix in rows and columns ILO to
-* IHI.
-*
-* Arguments
-* =========
-*
-* WANTT (input) LOGICAL
-* = .TRUE. : the full Schur form T is required;
-* = .FALSE.: only eigenvalues are required.
-*
-* WANTZ (input) LOGICAL
-* = .TRUE. : the matrix of Schur vectors Z is required;
-* = .FALSE.: Schur vectors are not required.
-*
-* N (input) INTEGER
-* The order of the matrix H. N >= 0.
-*
-* ILO (input) INTEGER
-* IHI (input) INTEGER
-* It is assumed that H is already upper triangular in rows and
-* columns IHI+1:N, and that H(ILO,ILO-1) = 0 (unless ILO = 1).
-* ZLAHQR works primarily with the Hessenberg submatrix in rows
-* and columns ILO to IHI, but applies transformations to all of
-* H if WANTT is .TRUE..
-* 1 <= ILO <= max(1,IHI); IHI <= N.
-*
-* H (input/output) COMPLEX*16 array, dimension (LDH,N)
-* On entry, the upper Hessenberg matrix H.
-* On exit, if INFO is zero and if WANTT is .TRUE., then H
-* is upper triangular in rows and columns ILO:IHI. If INFO
-* is zero and if WANTT is .FALSE., then the contents of H
-* are unspecified on exit. The output state of H in case
-* INF is positive is below under the description of INFO.
-*
-* LDH (input) INTEGER
-* The leading dimension of the array H. LDH >= max(1,N).
-*
-* W (output) COMPLEX*16 array, dimension (N)
-* The computed eigenvalues ILO to IHI are stored in the
-* corresponding elements of W. If WANTT is .TRUE., the
-* eigenvalues are stored in the same order as on the diagonal
-* of the Schur form returned in H, with W(i) = H(i,i).
-*
-* ILOZ (input) INTEGER
-* IHIZ (input) INTEGER
-* Specify the rows of Z to which transformations must be
-* applied if WANTZ is .TRUE..
-* 1 <= ILOZ <= ILO; IHI <= IHIZ <= N.
-*
-* Z (input/output) COMPLEX*16 array, dimension (LDZ,N)
-* If WANTZ is .TRUE., on entry Z must contain the current
-* matrix Z of transformations accumulated by CHSEQR, and on
-* exit Z has been updated; transformations are applied only to
-* the submatrix Z(ILOZ:IHIZ,ILO:IHI).
-* If WANTZ is .FALSE., Z is not referenced.
-*
-* LDZ (input) INTEGER
-* The leading dimension of the array Z. LDZ >= max(1,N).
-*
-* INFO (output) INTEGER
-* = 0: successful exit
-* .GT. 0: if INFO = i, ZLAHQR failed to compute all the
-* eigenvalues ILO to IHI in a total of 30 iterations
-* per eigenvalue; elements i+1:ihi of W contain
-* those eigenvalues which have been successfully
-* computed.
-*
-* If INFO .GT. 0 and WANTT is .FALSE., then on exit,
-* the remaining unconverged eigenvalues are the
-* eigenvalues of the upper Hessenberg matrix
-* rows and columns ILO thorugh INFO of the final,
-* output value of H.
-*
-* If INFO .GT. 0 and WANTT is .TRUE., then on exit
-* (*) (initial value of H)*U = U*(final value of H)
-* where U is an orthognal matrix. The final
-* value of H is upper Hessenberg and triangular in
-* rows and columns INFO+1 through IHI.
-*
-* If INFO .GT. 0 and WANTZ is .TRUE., then on exit
-* (final value of Z) = (initial value of Z)*U
-* where U is the orthogonal matrix in (*)
-* (regardless of the value of WANTT.)
-*
-* Further Details
-* ===============
-*
-* 02-96 Based on modifications by
-* David Day, Sandia National Laboratory, USA
-*
-* 12-04 Further modifications by
-* Ralph Byers, University of Kansas, USA
-*
-* This is a modified version of ZLAHQR from LAPACK version 3.0.
-* It is (1) more robust against overflow and underflow and
-* (2) adopts the more conservative Ahues & Tisseur stopping
-* criterion (LAWN 122, 1997).
-*
-* =========================================================
-*
-* .. Parameters ..
- INTEGER ITMAX
- PARAMETER ( ITMAX = 30 )
- COMPLEX*16 ZERO, ONE
- PARAMETER ( ZERO = ( 0.0d0, 0.0d0 ),
- $ ONE = ( 1.0d0, 0.0d0 ) )
- DOUBLE PRECISION RZERO, RONE, HALF
- PARAMETER ( RZERO = 0.0d0, RONE = 1.0d0, HALF = 0.5d0 )
- DOUBLE PRECISION DAT1
- PARAMETER ( DAT1 = 3.0d0 / 4.0d0 )
-* ..
-* .. Local Scalars ..
- COMPLEX*16 CDUM, H11, H11S, H22, SC, SUM, T, T1, TEMP, U,
- $ V2, X, Y
- DOUBLE PRECISION AA, AB, BA, BB, H10, H21, RTEMP, S, SAFMAX,
- $ SAFMIN, SMLNUM, SX, T2, TST, ULP
- INTEGER I, I1, I2, ITS, J, JHI, JLO, K, L, M, NH, NZ
-* ..
-* .. Local Arrays ..
- COMPLEX*16 V( 2 )
-* ..
-* .. External Functions ..
- COMPLEX*16 ZLADIV
- DOUBLE PRECISION DLAMCH
- EXTERNAL ZLADIV, DLAMCH
-* ..
-* .. External Subroutines ..
- EXTERNAL DLABAD, ZCOPY, ZLARFG, ZSCAL
-* ..
-* .. Statement Functions ..
- DOUBLE PRECISION CABS1
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC ABS, DBLE, DCONJG, DIMAG, MAX, MIN, SQRT
-* ..
-* .. Statement Function definitions ..
- CABS1( CDUM ) = ABS( DBLE( CDUM ) ) + ABS( DIMAG( CDUM ) )
-* ..
-* .. Executable Statements ..
-*
- INFO = 0
-*
-* Quick return if possible
-*
- IF( N.EQ.0 )
- $ RETURN
- IF( ILO.EQ.IHI ) THEN
- W( ILO ) = H( ILO, ILO )
- RETURN
- END IF
-*
-* ==== clear out the trash ====
- DO 10 J = ILO, IHI - 3
- H( J+2, J ) = ZERO
- H( J+3, J ) = ZERO
- 10 CONTINUE
- IF( ILO.LE.IHI-2 )
- $ H( IHI, IHI-2 ) = ZERO
-* ==== ensure that subdiagonal entries are real ====
- DO 20 I = ILO + 1, IHI
- IF( DIMAG( H( I, I-1 ) ).NE.RZERO ) THEN
-* ==== The following redundant normalization
-* . avoids problems with both gradual and
-* . sudden underflow in ABS(H(I,I-1)) ====
- SC = H( I, I-1 ) / CABS1( H( I, I-1 ) )
- SC = DCONJG( SC ) / ABS( SC )
- H( I, I-1 ) = ABS( H( I, I-1 ) )
- IF( WANTT ) THEN
- JLO = 1
- JHI = N
- ELSE
- JLO = ILO
- JHI = IHI
- END IF
- CALL ZSCAL( JHI-I+1, SC, H( I, I ), LDH )
- CALL ZSCAL( MIN( JHI, I+1 )-JLO+1, DCONJG( SC ),
- $ H( JLO, I ), 1 )
- IF( WANTZ )
- $ CALL ZSCAL( IHIZ-ILOZ+1, DCONJG( SC ), Z( ILOZ, I ), 1 )
- END IF
- 20 CONTINUE
-*
- NH = IHI - ILO + 1
- NZ = IHIZ - ILOZ + 1
-*
-* Set machine-dependent constants for the stopping criterion.
-*
- SAFMIN = DLAMCH( 'SAFE MINIMUM' )
- SAFMAX = RONE / SAFMIN
- CALL DLABAD( SAFMIN, SAFMAX )
- ULP = DLAMCH( 'PRECISION' )
- SMLNUM = SAFMIN*( DBLE( NH ) / ULP )
-*
-* I1 and I2 are the indices of the first row and last column of H
-* to which transformations must be applied. If eigenvalues only are
-* being computed, I1 and I2 are set inside the main loop.
-*
- IF( WANTT ) THEN
- I1 = 1
- I2 = N
- END IF
-*
-* The main loop begins here. I is the loop index and decreases from
-* IHI to ILO in steps of 1. Each iteration of the loop works
-* with the active submatrix in rows and columns L to I.
-* Eigenvalues I+1 to IHI have already converged. Either L = ILO, or
-* H(L,L-1) is negligible so that the matrix splits.
-*
- I = IHI
- 30 CONTINUE
- IF( I.LT.ILO )
- $ GO TO 150
-*
-* Perform QR iterations on rows and columns ILO to I until a
-* submatrix of order 1 splits off at the bottom because a
-* subdiagonal element has become negligible.
-*
- L = ILO
- DO 130 ITS = 0, ITMAX
-*
-* Look for a single small subdiagonal element.
-*
- DO 40 K = I, L + 1, -1
- IF( CABS1( H( K, K-1 ) ).LE.SMLNUM )
- $ GO TO 50
- TST = CABS1( H( K-1, K-1 ) ) + CABS1( H( K, K ) )
- IF( TST.EQ.ZERO ) THEN
- IF( K-2.GE.ILO )
- $ TST = TST + ABS( DBLE( H( K-1, K-2 ) ) )
- IF( K+1.LE.IHI )
- $ TST = TST + ABS( DBLE( H( K+1, K ) ) )
- END IF
-* ==== The following is a conservative small subdiagonal
-* . deflation criterion due to Ahues & Tisseur (LAWN 122,
-* . 1997). It has better mathematical foundation and
-* . improves accuracy in some examples. ====
- IF( ABS( DBLE( H( K, K-1 ) ) ).LE.ULP*TST ) THEN
- AB = MAX( CABS1( H( K, K-1 ) ), CABS1( H( K-1, K ) ) )
- BA = MIN( CABS1( H( K, K-1 ) ), CABS1( H( K-1, K ) ) )
- AA = MAX( CABS1( H( K, K ) ),
- $ CABS1( H( K-1, K-1 )-H( K, K ) ) )
- BB = MIN( CABS1( H( K, K ) ),
- $ CABS1( H( K-1, K-1 )-H( K, K ) ) )
- S = AA + AB
- IF( BA*( AB / S ).LE.MAX( SMLNUM,
- $ ULP*( BB*( AA / S ) ) ) )GO TO 50
- END IF
- 40 CONTINUE
- 50 CONTINUE
- L = K
- IF( L.GT.ILO ) THEN
-*
-* H(L,L-1) is negligible
-*
- H( L, L-1 ) = ZERO
- END IF
-*
-* Exit from loop if a submatrix of order 1 has split off.
-*
- IF( L.GE.I )
- $ GO TO 140
-*
-* Now the active submatrix is in rows and columns L to I. If
-* eigenvalues only are being computed, only the active submatrix
-* need be transformed.
-*
- IF( .NOT.WANTT ) THEN
- I1 = L
- I2 = I
- END IF
-*
- IF( ITS.EQ.10 .OR. ITS.EQ.20 ) THEN
-*
-* Exceptional shift.
-*
- S = DAT1*ABS( DBLE( H( I, I-1 ) ) )
- T = S + H( I, I )
- ELSE
-*
-* Wilkinson's shift.
-*
- T = H( I, I )
- U = SQRT( H( I-1, I ) )*SQRT( H( I, I-1 ) )
- S = CABS1( U )
- IF( S.NE.RZERO ) THEN
- X = HALF*( H( I-1, I-1 )-T )
- SX = CABS1( X )
- S = MAX( S, CABS1( X ) )
- Y = S*SQRT( ( X / S )**2+( U / S )**2 )
- IF( SX.GT.RZERO ) THEN
- IF( DBLE( X / SX )*DBLE( Y )+DIMAG( X / SX )*
- $ DIMAG( Y ).LT.RZERO )Y = -Y
- END IF
- T = T - U*ZLADIV( U, ( X+Y ) )
- END IF
- END IF
-*
-* Look for two consecutive small subdiagonal elements.
-*
- DO 60 M = I - 1, L + 1, -1
-*
-* Determine the effect of starting the single-shift QR
-* iteration at row M, and see if this would make H(M,M-1)
-* negligible.
-*
- H11 = H( M, M )
- H22 = H( M+1, M+1 )
- H11S = H11 - T
- H21 = H( M+1, M )
- S = CABS1( H11S ) + ABS( H21 )
- H11S = H11S / S
- H21 = H21 / S
- V( 1 ) = H11S
- V( 2 ) = H21
- H10 = H( M, M-1 )
- IF( ABS( H10 )*ABS( H21 ).LE.ULP*
- $ ( CABS1( H11S )*( CABS1( H11 )+CABS1( H22 ) ) ) )
- $ GO TO 70
- 60 CONTINUE
- H11 = H( L, L )
- H22 = H( L+1, L+1 )
- H11S = H11 - T
- H21 = H( L+1, L )
- S = CABS1( H11S ) + ABS( H21 )
- H11S = H11S / S
- H21 = H21 / S
- V( 1 ) = H11S
- V( 2 ) = H21
- 70 CONTINUE
-*
-* Single-shift QR step
-*
- DO 120 K = M, I - 1
-*
-* The first iteration of this loop determines a reflection G
-* from the vector V and applies it from left and right to H,
-* thus creating a nonzero bulge below the subdiagonal.
-*
-* Each subsequent iteration determines a reflection G to
-* restore the Hessenberg form in the (K-1)th column, and thus
-* chases the bulge one step toward the bottom of the active
-* submatrix.
-*
-* V(2) is always real before the call to ZLARFG, and hence
-* after the call T2 ( = T1*V(2) ) is also real.
-*
- IF( K.GT.M )
- $ CALL ZCOPY( 2, H( K, K-1 ), 1, V, 1 )
- CALL ZLARFG( 2, V( 1 ), V( 2 ), 1, T1 )
- IF( K.GT.M ) THEN
- H( K, K-1 ) = V( 1 )
- H( K+1, K-1 ) = ZERO
- END IF
- V2 = V( 2 )
- T2 = DBLE( T1*V2 )
-*
-* Apply G from the left to transform the rows of the matrix
-* in columns K to I2.
-*
- DO 80 J = K, I2
- SUM = DCONJG( T1 )*H( K, J ) + T2*H( K+1, J )
- H( K, J ) = H( K, J ) - SUM
- H( K+1, J ) = H( K+1, J ) - SUM*V2
- 80 CONTINUE
-*
-* Apply G from the right to transform the columns of the
-* matrix in rows I1 to min(K+2,I).
-*
- DO 90 J = I1, MIN( K+2, I )
- SUM = T1*H( J, K ) + T2*H( J, K+1 )
- H( J, K ) = H( J, K ) - SUM
- H( J, K+1 ) = H( J, K+1 ) - SUM*DCONJG( V2 )
- 90 CONTINUE
-*
- IF( WANTZ ) THEN
-*
-* Accumulate transformations in the matrix Z
-*
- DO 100 J = ILOZ, IHIZ
- SUM = T1*Z( J, K ) + T2*Z( J, K+1 )
- Z( J, K ) = Z( J, K ) - SUM
- Z( J, K+1 ) = Z( J, K+1 ) - SUM*DCONJG( V2 )
- 100 CONTINUE
- END IF
-*
- IF( K.EQ.M .AND. M.GT.L ) THEN
-*
-* If the QR step was started at row M > L because two
-* consecutive small subdiagonals were found, then extra
-* scaling must be performed to ensure that H(M,M-1) remains
-* real.
-*
- TEMP = ONE - T1
- TEMP = TEMP / ABS( TEMP )
- H( M+1, M ) = H( M+1, M )*DCONJG( TEMP )
- IF( M+2.LE.I )
- $ H( M+2, M+1 ) = H( M+2, M+1 )*TEMP
- DO 110 J = M, I
- IF( J.NE.M+1 ) THEN
- IF( I2.GT.J )
- $ CALL ZSCAL( I2-J, TEMP, H( J, J+1 ), LDH )
- CALL ZSCAL( J-I1, DCONJG( TEMP ), H( I1, J ), 1 )
- IF( WANTZ ) THEN
- CALL ZSCAL( NZ, DCONJG( TEMP ), Z( ILOZ, J ),
- $ 1 )
- END IF
- END IF
- 110 CONTINUE
- END IF
- 120 CONTINUE
-*
-* Ensure that H(I,I-1) is real.
-*
- TEMP = H( I, I-1 )
- IF( DIMAG( TEMP ).NE.RZERO ) THEN
- RTEMP = ABS( TEMP )
- H( I, I-1 ) = RTEMP
- TEMP = TEMP / RTEMP
- IF( I2.GT.I )
- $ CALL ZSCAL( I2-I, DCONJG( TEMP ), H( I, I+1 ), LDH )
- CALL ZSCAL( I-I1, TEMP, H( I1, I ), 1 )
- IF( WANTZ ) THEN
- CALL ZSCAL( NZ, TEMP, Z( ILOZ, I ), 1 )
- END IF
- END IF
-*
- 130 CONTINUE
-*
-* Failure to converge in remaining number of iterations
-*
- INFO = I
- RETURN
-*
- 140 CONTINUE
-*
-* H(I,I-1) is negligible: one eigenvalue has converged.
-*
- W( I ) = H( I, I )
-*
-* return to start of the main loop with new value of I.
-*
- I = L - 1
- GO TO 30
-*
- 150 CONTINUE
- RETURN
-*
-* End of ZLAHQR
-*
- END
diff --git a/src/lib/lapack/zlahr2.f b/src/lib/lapack/zlahr2.f
deleted file mode 100644
index f3cb5515..00000000
--- a/src/lib/lapack/zlahr2.f
+++ /dev/null
@@ -1,240 +0,0 @@
- SUBROUTINE ZLAHR2( N, K, NB, A, LDA, TAU, T, LDT, Y, LDY )
-*
-* -- LAPACK auxiliary routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- INTEGER K, LDA, LDT, LDY, N, NB
-* ..
-* .. Array Arguments ..
- COMPLEX*16 A( LDA, * ), T( LDT, NB ), TAU( NB ),
- $ Y( LDY, NB )
-* ..
-*
-* Purpose
-* =======
-*
-* ZLAHR2 reduces the first NB columns of A complex general n-BY-(n-k+1)
-* matrix A so that elements below the k-th subdiagonal are zero. The
-* reduction is performed by an unitary similarity transformation
-* Q' * A * Q. The routine returns the matrices V and T which determine
-* Q as a block reflector I - V*T*V', and also the matrix Y = A * V * T.
-*
-* This is an auxiliary routine called by ZGEHRD.
-*
-* Arguments
-* =========
-*
-* N (input) INTEGER
-* The order of the matrix A.
-*
-* K (input) INTEGER
-* The offset for the reduction. Elements below the k-th
-* subdiagonal in the first NB columns are reduced to zero.
-* K < N.
-*
-* NB (input) INTEGER
-* The number of columns to be reduced.
-*
-* A (input/output) COMPLEX*16 array, dimension (LDA,N-K+1)
-* On entry, the n-by-(n-k+1) general matrix A.
-* On exit, the elements on and above the k-th subdiagonal in
-* the first NB columns are overwritten with the corresponding
-* elements of the reduced matrix; the elements below the k-th
-* subdiagonal, with the array TAU, represent the matrix Q as a
-* product of elementary reflectors. The other columns of A are
-* unchanged. See Further Details.
-*
-* LDA (input) INTEGER
-* The leading dimension of the array A. LDA >= max(1,N).
-*
-* TAU (output) COMPLEX*16 array, dimension (NB)
-* The scalar factors of the elementary reflectors. See Further
-* Details.
-*
-* T (output) COMPLEX*16 array, dimension (LDT,NB)
-* The upper triangular matrix T.
-*
-* LDT (input) INTEGER
-* The leading dimension of the array T. LDT >= NB.
-*
-* Y (output) COMPLEX*16 array, dimension (LDY,NB)
-* The n-by-nb matrix Y.
-*
-* LDY (input) INTEGER
-* The leading dimension of the array Y. LDY >= N.
-*
-* Further Details
-* ===============
-*
-* The matrix Q is represented as a product of nb elementary reflectors
-*
-* Q = H(1) H(2) . . . H(nb).
-*
-* Each H(i) has the form
-*
-* H(i) = I - tau * v * v'
-*
-* where tau is a complex scalar, and v is a complex vector with
-* v(1:i+k-1) = 0, v(i+k) = 1; v(i+k+1:n) is stored on exit in
-* A(i+k+1:n,i), and tau in TAU(i).
-*
-* The elements of the vectors v together form the (n-k+1)-by-nb matrix
-* V which is needed, with T and Y, to apply the transformation to the
-* unreduced part of the matrix, using an update of the form:
-* A := (I - V*T*V') * (A - Y*V').
-*
-* The contents of A on exit are illustrated by the following example
-* with n = 7, k = 3 and nb = 2:
-*
-* ( a a a a a )
-* ( a a a a a )
-* ( a a a a a )
-* ( h h a a a )
-* ( v1 h a a a )
-* ( v1 v2 a a a )
-* ( v1 v2 a a a )
-*
-* where a denotes an element of the original matrix A, h denotes a
-* modified element of the upper Hessenberg matrix H, and vi denotes an
-* element of the vector defining H(i).
-*
-* This file is a slight modification of LAPACK-3.0's ZLAHRD
-* incorporating improvements proposed by Quintana-Orti and Van de
-* Gejin. Note that the entries of A(1:K,2:NB) differ from those
-* returned by the original LAPACK routine. This function is
-* not backward compatible with LAPACK3.0.
-*
-* =====================================================================
-*
-* .. Parameters ..
- COMPLEX*16 ZERO, ONE
- PARAMETER ( ZERO = ( 0.0D+0, 0.0D+0 ),
- $ ONE = ( 1.0D+0, 0.0D+0 ) )
-* ..
-* .. Local Scalars ..
- INTEGER I
- COMPLEX*16 EI
-* ..
-* .. External Subroutines ..
- EXTERNAL ZAXPY, ZCOPY, ZGEMM, ZGEMV, ZLACPY,
- $ ZLARFG, ZSCAL, ZTRMM, ZTRMV, ZLACGV
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC MIN
-* ..
-* .. Executable Statements ..
-*
-* Quick return if possible
-*
- IF( N.LE.1 )
- $ RETURN
-*
- DO 10 I = 1, NB
- IF( I.GT.1 ) THEN
-*
-* Update A(K+1:N,I)
-*
-* Update I-th column of A - Y * V'
-*
- CALL ZLACGV( I-1, A( K+I-1, 1 ), LDA )
- CALL ZGEMV( 'NO TRANSPOSE', N-K, I-1, -ONE, Y(K+1,1), LDY,
- $ A( K+I-1, 1 ), LDA, ONE, A( K+1, I ), 1 )
- CALL ZLACGV( I-1, A( K+I-1, 1 ), LDA )
-*
-* Apply I - V * T' * V' to this column (call it b) from the
-* left, using the last column of T as workspace
-*
-* Let V = ( V1 ) and b = ( b1 ) (first I-1 rows)
-* ( V2 ) ( b2 )
-*
-* where V1 is unit lower triangular
-*
-* w := V1' * b1
-*
- CALL ZCOPY( I-1, A( K+1, I ), 1, T( 1, NB ), 1 )
- CALL ZTRMV( 'Lower', 'Conjugate transpose', 'UNIT',
- $ I-1, A( K+1, 1 ),
- $ LDA, T( 1, NB ), 1 )
-*
-* w := w + V2'*b2
-*
- CALL ZGEMV( 'Conjugate transpose', N-K-I+1, I-1,
- $ ONE, A( K+I, 1 ),
- $ LDA, A( K+I, I ), 1, ONE, T( 1, NB ), 1 )
-*
-* w := T'*w
-*
- CALL ZTRMV( 'Upper', 'Conjugate transpose', 'NON-UNIT',
- $ I-1, T, LDT,
- $ T( 1, NB ), 1 )
-*
-* b2 := b2 - V2*w
-*
- CALL ZGEMV( 'NO TRANSPOSE', N-K-I+1, I-1, -ONE,
- $ A( K+I, 1 ),
- $ LDA, T( 1, NB ), 1, ONE, A( K+I, I ), 1 )
-*
-* b1 := b1 - V1*w
-*
- CALL ZTRMV( 'Lower', 'NO TRANSPOSE',
- $ 'UNIT', I-1,
- $ A( K+1, 1 ), LDA, T( 1, NB ), 1 )
- CALL ZAXPY( I-1, -ONE, T( 1, NB ), 1, A( K+1, I ), 1 )
-*
- A( K+I-1, I-1 ) = EI
- END IF
-*
-* Generate the elementary reflector H(I) to annihilate
-* A(K+I+1:N,I)
-*
- CALL ZLARFG( N-K-I+1, A( K+I, I ), A( MIN( K+I+1, N ), I ), 1,
- $ TAU( I ) )
- EI = A( K+I, I )
- A( K+I, I ) = ONE
-*
-* Compute Y(K+1:N,I)
-*
- CALL ZGEMV( 'NO TRANSPOSE', N-K, N-K-I+1,
- $ ONE, A( K+1, I+1 ),
- $ LDA, A( K+I, I ), 1, ZERO, Y( K+1, I ), 1 )
- CALL ZGEMV( 'Conjugate transpose', N-K-I+1, I-1,
- $ ONE, A( K+I, 1 ), LDA,
- $ A( K+I, I ), 1, ZERO, T( 1, I ), 1 )
- CALL ZGEMV( 'NO TRANSPOSE', N-K, I-1, -ONE,
- $ Y( K+1, 1 ), LDY,
- $ T( 1, I ), 1, ONE, Y( K+1, I ), 1 )
- CALL ZSCAL( N-K, TAU( I ), Y( K+1, I ), 1 )
-*
-* Compute T(1:I,I)
-*
- CALL ZSCAL( I-1, -TAU( I ), T( 1, I ), 1 )
- CALL ZTRMV( 'Upper', 'No Transpose', 'NON-UNIT',
- $ I-1, T, LDT,
- $ T( 1, I ), 1 )
- T( I, I ) = TAU( I )
-*
- 10 CONTINUE
- A( K+NB, NB ) = EI
-*
-* Compute Y(1:K,1:NB)
-*
- CALL ZLACPY( 'ALL', K, NB, A( 1, 2 ), LDA, Y, LDY )
- CALL ZTRMM( 'RIGHT', 'Lower', 'NO TRANSPOSE',
- $ 'UNIT', K, NB,
- $ ONE, A( K+1, 1 ), LDA, Y, LDY )
- IF( N.GT.K+NB )
- $ CALL ZGEMM( 'NO TRANSPOSE', 'NO TRANSPOSE', K,
- $ NB, N-K-NB, ONE,
- $ A( 1, 2+NB ), LDA, A( K+1+NB, 1 ), LDA, ONE, Y,
- $ LDY )
- CALL ZTRMM( 'RIGHT', 'Upper', 'NO TRANSPOSE',
- $ 'NON-UNIT', K, NB,
- $ ONE, T, LDT, Y, LDY )
-*
- RETURN
-*
-* End of ZLAHR2
-*
- END
diff --git a/src/lib/lapack/zlahrd.f b/src/lib/lapack/zlahrd.f
deleted file mode 100644
index e7eb9de9..00000000
--- a/src/lib/lapack/zlahrd.f
+++ /dev/null
@@ -1,213 +0,0 @@
- SUBROUTINE ZLAHRD( N, K, NB, A, LDA, TAU, T, LDT, Y, LDY )
-*
-* -- LAPACK auxiliary routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- INTEGER K, LDA, LDT, LDY, N, NB
-* ..
-* .. Array Arguments ..
- COMPLEX*16 A( LDA, * ), T( LDT, NB ), TAU( NB ),
- $ Y( LDY, NB )
-* ..
-*
-* Purpose
-* =======
-*
-* ZLAHRD reduces the first NB columns of a complex general n-by-(n-k+1)
-* matrix A so that elements below the k-th subdiagonal are zero. The
-* reduction is performed by a unitary similarity transformation
-* Q' * A * Q. The routine returns the matrices V and T which determine
-* Q as a block reflector I - V*T*V', and also the matrix Y = A * V * T.
-*
-* This is an OBSOLETE auxiliary routine.
-* This routine will be 'deprecated' in a future release.
-* Please use the new routine ZLAHR2 instead.
-*
-* Arguments
-* =========
-*
-* N (input) INTEGER
-* The order of the matrix A.
-*
-* K (input) INTEGER
-* The offset for the reduction. Elements below the k-th
-* subdiagonal in the first NB columns are reduced to zero.
-*
-* NB (input) INTEGER
-* The number of columns to be reduced.
-*
-* A (input/output) COMPLEX*16 array, dimension (LDA,N-K+1)
-* On entry, the n-by-(n-k+1) general matrix A.
-* On exit, the elements on and above the k-th subdiagonal in
-* the first NB columns are overwritten with the corresponding
-* elements of the reduced matrix; the elements below the k-th
-* subdiagonal, with the array TAU, represent the matrix Q as a
-* product of elementary reflectors. The other columns of A are
-* unchanged. See Further Details.
-*
-* LDA (input) INTEGER
-* The leading dimension of the array A. LDA >= max(1,N).
-*
-* TAU (output) COMPLEX*16 array, dimension (NB)
-* The scalar factors of the elementary reflectors. See Further
-* Details.
-*
-* T (output) COMPLEX*16 array, dimension (LDT,NB)
-* The upper triangular matrix T.
-*
-* LDT (input) INTEGER
-* The leading dimension of the array T. LDT >= NB.
-*
-* Y (output) COMPLEX*16 array, dimension (LDY,NB)
-* The n-by-nb matrix Y.
-*
-* LDY (input) INTEGER
-* The leading dimension of the array Y. LDY >= max(1,N).
-*
-* Further Details
-* ===============
-*
-* The matrix Q is represented as a product of nb elementary reflectors
-*
-* Q = H(1) H(2) . . . H(nb).
-*
-* Each H(i) has the form
-*
-* H(i) = I - tau * v * v'
-*
-* where tau is a complex scalar, and v is a complex vector with
-* v(1:i+k-1) = 0, v(i+k) = 1; v(i+k+1:n) is stored on exit in
-* A(i+k+1:n,i), and tau in TAU(i).
-*
-* The elements of the vectors v together form the (n-k+1)-by-nb matrix
-* V which is needed, with T and Y, to apply the transformation to the
-* unreduced part of the matrix, using an update of the form:
-* A := (I - V*T*V') * (A - Y*V').
-*
-* The contents of A on exit are illustrated by the following example
-* with n = 7, k = 3 and nb = 2:
-*
-* ( a h a a a )
-* ( a h a a a )
-* ( a h a a a )
-* ( h h a a a )
-* ( v1 h a a a )
-* ( v1 v2 a a a )
-* ( v1 v2 a a a )
-*
-* where a denotes an element of the original matrix A, h denotes a
-* modified element of the upper Hessenberg matrix H, and vi denotes an
-* element of the vector defining H(i).
-*
-* =====================================================================
-*
-* .. Parameters ..
- COMPLEX*16 ZERO, ONE
- PARAMETER ( ZERO = ( 0.0D+0, 0.0D+0 ),
- $ ONE = ( 1.0D+0, 0.0D+0 ) )
-* ..
-* .. Local Scalars ..
- INTEGER I
- COMPLEX*16 EI
-* ..
-* .. External Subroutines ..
- EXTERNAL ZAXPY, ZCOPY, ZGEMV, ZLACGV, ZLARFG, ZSCAL,
- $ ZTRMV
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC MIN
-* ..
-* .. Executable Statements ..
-*
-* Quick return if possible
-*
- IF( N.LE.1 )
- $ RETURN
-*
- DO 10 I = 1, NB
- IF( I.GT.1 ) THEN
-*
-* Update A(1:n,i)
-*
-* Compute i-th column of A - Y * V'
-*
- CALL ZLACGV( I-1, A( K+I-1, 1 ), LDA )
- CALL ZGEMV( 'No transpose', N, I-1, -ONE, Y, LDY,
- $ A( K+I-1, 1 ), LDA, ONE, A( 1, I ), 1 )
- CALL ZLACGV( I-1, A( K+I-1, 1 ), LDA )
-*
-* Apply I - V * T' * V' to this column (call it b) from the
-* left, using the last column of T as workspace
-*
-* Let V = ( V1 ) and b = ( b1 ) (first I-1 rows)
-* ( V2 ) ( b2 )
-*
-* where V1 is unit lower triangular
-*
-* w := V1' * b1
-*
- CALL ZCOPY( I-1, A( K+1, I ), 1, T( 1, NB ), 1 )
- CALL ZTRMV( 'Lower', 'Conjugate transpose', 'Unit', I-1,
- $ A( K+1, 1 ), LDA, T( 1, NB ), 1 )
-*
-* w := w + V2'*b2
-*
- CALL ZGEMV( 'Conjugate transpose', N-K-I+1, I-1, ONE,
- $ A( K+I, 1 ), LDA, A( K+I, I ), 1, ONE,
- $ T( 1, NB ), 1 )
-*
-* w := T'*w
-*
- CALL ZTRMV( 'Upper', 'Conjugate transpose', 'Non-unit', I-1,
- $ T, LDT, T( 1, NB ), 1 )
-*
-* b2 := b2 - V2*w
-*
- CALL ZGEMV( 'No transpose', N-K-I+1, I-1, -ONE, A( K+I, 1 ),
- $ LDA, T( 1, NB ), 1, ONE, A( K+I, I ), 1 )
-*
-* b1 := b1 - V1*w
-*
- CALL ZTRMV( 'Lower', 'No transpose', 'Unit', I-1,
- $ A( K+1, 1 ), LDA, T( 1, NB ), 1 )
- CALL ZAXPY( I-1, -ONE, T( 1, NB ), 1, A( K+1, I ), 1 )
-*
- A( K+I-1, I-1 ) = EI
- END IF
-*
-* Generate the elementary reflector H(i) to annihilate
-* A(k+i+1:n,i)
-*
- EI = A( K+I, I )
- CALL ZLARFG( N-K-I+1, EI, A( MIN( K+I+1, N ), I ), 1,
- $ TAU( I ) )
- A( K+I, I ) = ONE
-*
-* Compute Y(1:n,i)
-*
- CALL ZGEMV( 'No transpose', N, N-K-I+1, ONE, A( 1, I+1 ), LDA,
- $ A( K+I, I ), 1, ZERO, Y( 1, I ), 1 )
- CALL ZGEMV( 'Conjugate transpose', N-K-I+1, I-1, ONE,
- $ A( K+I, 1 ), LDA, A( K+I, I ), 1, ZERO, T( 1, I ),
- $ 1 )
- CALL ZGEMV( 'No transpose', N, I-1, -ONE, Y, LDY, T( 1, I ), 1,
- $ ONE, Y( 1, I ), 1 )
- CALL ZSCAL( N, TAU( I ), Y( 1, I ), 1 )
-*
-* Compute T(1:i,i)
-*
- CALL ZSCAL( I-1, -TAU( I ), T( 1, I ), 1 )
- CALL ZTRMV( 'Upper', 'No transpose', 'Non-unit', I-1, T, LDT,
- $ T( 1, I ), 1 )
- T( I, I ) = TAU( I )
-*
- 10 CONTINUE
- A( K+NB, NB ) = EI
-*
- RETURN
-*
-* End of ZLAHRD
-*
- END
diff --git a/src/lib/lapack/zlaic1.f b/src/lib/lapack/zlaic1.f
deleted file mode 100644
index 589f0889..00000000
--- a/src/lib/lapack/zlaic1.f
+++ /dev/null
@@ -1,295 +0,0 @@
- SUBROUTINE ZLAIC1( JOB, J, X, SEST, W, GAMMA, SESTPR, S, C )
-*
-* -- LAPACK auxiliary routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- INTEGER J, JOB
- DOUBLE PRECISION SEST, SESTPR
- COMPLEX*16 C, GAMMA, S
-* ..
-* .. Array Arguments ..
- COMPLEX*16 W( J ), X( J )
-* ..
-*
-* Purpose
-* =======
-*
-* ZLAIC1 applies one step of incremental condition estimation in
-* its simplest version:
-*
-* Let x, twonorm(x) = 1, be an approximate singular vector of an j-by-j
-* lower triangular matrix L, such that
-* twonorm(L*x) = sest
-* Then ZLAIC1 computes sestpr, s, c such that
-* the vector
-* [ s*x ]
-* xhat = [ c ]
-* is an approximate singular vector of
-* [ L 0 ]
-* Lhat = [ w' gamma ]
-* in the sense that
-* twonorm(Lhat*xhat) = sestpr.
-*
-* Depending on JOB, an estimate for the largest or smallest singular
-* value is computed.
-*
-* Note that [s c]' and sestpr**2 is an eigenpair of the system
-*
-* diag(sest*sest, 0) + [alpha gamma] * [ conjg(alpha) ]
-* [ conjg(gamma) ]
-*
-* where alpha = conjg(x)'*w.
-*
-* Arguments
-* =========
-*
-* JOB (input) INTEGER
-* = 1: an estimate for the largest singular value is computed.
-* = 2: an estimate for the smallest singular value is computed.
-*
-* J (input) INTEGER
-* Length of X and W
-*
-* X (input) COMPLEX*16 array, dimension (J)
-* The j-vector x.
-*
-* SEST (input) DOUBLE PRECISION
-* Estimated singular value of j by j matrix L
-*
-* W (input) COMPLEX*16 array, dimension (J)
-* The j-vector w.
-*
-* GAMMA (input) COMPLEX*16
-* The diagonal element gamma.
-*
-* SESTPR (output) DOUBLE PRECISION
-* Estimated singular value of (j+1) by (j+1) matrix Lhat.
-*
-* S (output) COMPLEX*16
-* Sine needed in forming xhat.
-*
-* C (output) COMPLEX*16
-* Cosine needed in forming xhat.
-*
-* =====================================================================
-*
-* .. Parameters ..
- DOUBLE PRECISION ZERO, ONE, TWO
- PARAMETER ( ZERO = 0.0D0, ONE = 1.0D0, TWO = 2.0D0 )
- DOUBLE PRECISION HALF, FOUR
- PARAMETER ( HALF = 0.5D0, FOUR = 4.0D0 )
-* ..
-* .. Local Scalars ..
- DOUBLE PRECISION ABSALP, ABSEST, ABSGAM, B, EPS, NORMA, S1, S2,
- $ SCL, T, TEST, TMP, ZETA1, ZETA2
- COMPLEX*16 ALPHA, COSINE, SINE
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC ABS, DCONJG, MAX, SQRT
-* ..
-* .. External Functions ..
- DOUBLE PRECISION DLAMCH
- COMPLEX*16 ZDOTC
- EXTERNAL DLAMCH, ZDOTC
-* ..
-* .. Executable Statements ..
-*
- EPS = DLAMCH( 'Epsilon' )
- ALPHA = ZDOTC( J, X, 1, W, 1 )
-*
- ABSALP = ABS( ALPHA )
- ABSGAM = ABS( GAMMA )
- ABSEST = ABS( SEST )
-*
- IF( JOB.EQ.1 ) THEN
-*
-* Estimating largest singular value
-*
-* special cases
-*
- IF( SEST.EQ.ZERO ) THEN
- S1 = MAX( ABSGAM, ABSALP )
- IF( S1.EQ.ZERO ) THEN
- S = ZERO
- C = ONE
- SESTPR = ZERO
- ELSE
- S = ALPHA / S1
- C = GAMMA / S1
- TMP = SQRT( S*DCONJG( S )+C*DCONJG( C ) )
- S = S / TMP
- C = C / TMP
- SESTPR = S1*TMP
- END IF
- RETURN
- ELSE IF( ABSGAM.LE.EPS*ABSEST ) THEN
- S = ONE
- C = ZERO
- TMP = MAX( ABSEST, ABSALP )
- S1 = ABSEST / TMP
- S2 = ABSALP / TMP
- SESTPR = TMP*SQRT( S1*S1+S2*S2 )
- RETURN
- ELSE IF( ABSALP.LE.EPS*ABSEST ) THEN
- S1 = ABSGAM
- S2 = ABSEST
- IF( S1.LE.S2 ) THEN
- S = ONE
- C = ZERO
- SESTPR = S2
- ELSE
- S = ZERO
- C = ONE
- SESTPR = S1
- END IF
- RETURN
- ELSE IF( ABSEST.LE.EPS*ABSALP .OR. ABSEST.LE.EPS*ABSGAM ) THEN
- S1 = ABSGAM
- S2 = ABSALP
- IF( S1.LE.S2 ) THEN
- TMP = S1 / S2
- SCL = SQRT( ONE+TMP*TMP )
- SESTPR = S2*SCL
- S = ( ALPHA / S2 ) / SCL
- C = ( GAMMA / S2 ) / SCL
- ELSE
- TMP = S2 / S1
- SCL = SQRT( ONE+TMP*TMP )
- SESTPR = S1*SCL
- S = ( ALPHA / S1 ) / SCL
- C = ( GAMMA / S1 ) / SCL
- END IF
- RETURN
- ELSE
-*
-* normal case
-*
- ZETA1 = ABSALP / ABSEST
- ZETA2 = ABSGAM / ABSEST
-*
- B = ( ONE-ZETA1*ZETA1-ZETA2*ZETA2 )*HALF
- C = ZETA1*ZETA1
- IF( B.GT.ZERO ) THEN
- T = C / ( B+SQRT( B*B+C ) )
- ELSE
- T = SQRT( B*B+C ) - B
- END IF
-*
- SINE = -( ALPHA / ABSEST ) / T
- COSINE = -( GAMMA / ABSEST ) / ( ONE+T )
- TMP = SQRT( SINE*DCONJG( SINE )+COSINE*DCONJG( COSINE ) )
- S = SINE / TMP
- C = COSINE / TMP
- SESTPR = SQRT( T+ONE )*ABSEST
- RETURN
- END IF
-*
- ELSE IF( JOB.EQ.2 ) THEN
-*
-* Estimating smallest singular value
-*
-* special cases
-*
- IF( SEST.EQ.ZERO ) THEN
- SESTPR = ZERO
- IF( MAX( ABSGAM, ABSALP ).EQ.ZERO ) THEN
- SINE = ONE
- COSINE = ZERO
- ELSE
- SINE = -DCONJG( GAMMA )
- COSINE = DCONJG( ALPHA )
- END IF
- S1 = MAX( ABS( SINE ), ABS( COSINE ) )
- S = SINE / S1
- C = COSINE / S1
- TMP = SQRT( S*DCONJG( S )+C*DCONJG( C ) )
- S = S / TMP
- C = C / TMP
- RETURN
- ELSE IF( ABSGAM.LE.EPS*ABSEST ) THEN
- S = ZERO
- C = ONE
- SESTPR = ABSGAM
- RETURN
- ELSE IF( ABSALP.LE.EPS*ABSEST ) THEN
- S1 = ABSGAM
- S2 = ABSEST
- IF( S1.LE.S2 ) THEN
- S = ZERO
- C = ONE
- SESTPR = S1
- ELSE
- S = ONE
- C = ZERO
- SESTPR = S2
- END IF
- RETURN
- ELSE IF( ABSEST.LE.EPS*ABSALP .OR. ABSEST.LE.EPS*ABSGAM ) THEN
- S1 = ABSGAM
- S2 = ABSALP
- IF( S1.LE.S2 ) THEN
- TMP = S1 / S2
- SCL = SQRT( ONE+TMP*TMP )
- SESTPR = ABSEST*( TMP / SCL )
- S = -( DCONJG( GAMMA ) / S2 ) / SCL
- C = ( DCONJG( ALPHA ) / S2 ) / SCL
- ELSE
- TMP = S2 / S1
- SCL = SQRT( ONE+TMP*TMP )
- SESTPR = ABSEST / SCL
- S = -( DCONJG( GAMMA ) / S1 ) / SCL
- C = ( DCONJG( ALPHA ) / S1 ) / SCL
- END IF
- RETURN
- ELSE
-*
-* normal case
-*
- ZETA1 = ABSALP / ABSEST
- ZETA2 = ABSGAM / ABSEST
-*
- NORMA = MAX( ONE+ZETA1*ZETA1+ZETA1*ZETA2,
- $ ZETA1*ZETA2+ZETA2*ZETA2 )
-*
-* See if root is closer to zero or to ONE
-*
- TEST = ONE + TWO*( ZETA1-ZETA2 )*( ZETA1+ZETA2 )
- IF( TEST.GE.ZERO ) THEN
-*
-* root is close to zero, compute directly
-*
- B = ( ZETA1*ZETA1+ZETA2*ZETA2+ONE )*HALF
- C = ZETA2*ZETA2
- T = C / ( B+SQRT( ABS( B*B-C ) ) )
- SINE = ( ALPHA / ABSEST ) / ( ONE-T )
- COSINE = -( GAMMA / ABSEST ) / T
- SESTPR = SQRT( T+FOUR*EPS*EPS*NORMA )*ABSEST
- ELSE
-*
-* root is closer to ONE, shift by that amount
-*
- B = ( ZETA2*ZETA2+ZETA1*ZETA1-ONE )*HALF
- C = ZETA1*ZETA1
- IF( B.GE.ZERO ) THEN
- T = -C / ( B+SQRT( B*B+C ) )
- ELSE
- T = B - SQRT( B*B+C )
- END IF
- SINE = -( ALPHA / ABSEST ) / T
- COSINE = -( GAMMA / ABSEST ) / ( ONE+T )
- SESTPR = SQRT( ONE+T+FOUR*EPS*EPS*NORMA )*ABSEST
- END IF
- TMP = SQRT( SINE*DCONJG( SINE )+COSINE*DCONJG( COSINE ) )
- S = SINE / TMP
- C = COSINE / TMP
- RETURN
-*
- END IF
- END IF
- RETURN
-*
-* End of ZLAIC1
-*
- END
diff --git a/src/lib/lapack/zlange.f b/src/lib/lapack/zlange.f
deleted file mode 100644
index 36cecbdc..00000000
--- a/src/lib/lapack/zlange.f
+++ /dev/null
@@ -1,145 +0,0 @@
- DOUBLE PRECISION FUNCTION ZLANGE( NORM, M, N, A, LDA, WORK )
-*
-* -- LAPACK auxiliary routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- CHARACTER NORM
- INTEGER LDA, M, N
-* ..
-* .. Array Arguments ..
- DOUBLE PRECISION WORK( * )
- COMPLEX*16 A( LDA, * )
-* ..
-*
-* Purpose
-* =======
-*
-* ZLANGE returns the value of the one norm, or the Frobenius norm, or
-* the infinity norm, or the element of largest absolute value of a
-* complex matrix A.
-*
-* Description
-* ===========
-*
-* ZLANGE returns the value
-*
-* ZLANGE = ( max(abs(A(i,j))), NORM = 'M' or 'm'
-* (
-* ( norm1(A), NORM = '1', 'O' or 'o'
-* (
-* ( normI(A), NORM = 'I' or 'i'
-* (
-* ( normF(A), NORM = 'F', 'f', 'E' or 'e'
-*
-* where norm1 denotes the one norm of a matrix (maximum column sum),
-* normI denotes the infinity norm of a matrix (maximum row sum) and
-* normF denotes the Frobenius norm of a matrix (square root of sum of
-* squares). Note that max(abs(A(i,j))) is not a consistent matrix norm.
-*
-* Arguments
-* =========
-*
-* NORM (input) CHARACTER*1
-* Specifies the value to be returned in ZLANGE as described
-* above.
-*
-* M (input) INTEGER
-* The number of rows of the matrix A. M >= 0. When M = 0,
-* ZLANGE is set to zero.
-*
-* N (input) INTEGER
-* The number of columns of the matrix A. N >= 0. When N = 0,
-* ZLANGE is set to zero.
-*
-* A (input) COMPLEX*16 array, dimension (LDA,N)
-* The m by n matrix A.
-*
-* LDA (input) INTEGER
-* The leading dimension of the array A. LDA >= max(M,1).
-*
-* WORK (workspace) DOUBLE PRECISION array, dimension (MAX(1,LWORK)),
-* where LWORK >= M when NORM = 'I'; otherwise, WORK is not
-* referenced.
-*
-* =====================================================================
-*
-* .. Parameters ..
- DOUBLE PRECISION ONE, ZERO
- PARAMETER ( ONE = 1.0D+0, ZERO = 0.0D+0 )
-* ..
-* .. Local Scalars ..
- INTEGER I, J
- DOUBLE PRECISION SCALE, SUM, VALUE
-* ..
-* .. External Functions ..
- LOGICAL LSAME
- EXTERNAL LSAME
-* ..
-* .. External Subroutines ..
- EXTERNAL ZLASSQ
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC ABS, MAX, MIN, SQRT
-* ..
-* .. Executable Statements ..
-*
- IF( MIN( M, N ).EQ.0 ) THEN
- VALUE = ZERO
- ELSE IF( LSAME( NORM, 'M' ) ) THEN
-*
-* Find max(abs(A(i,j))).
-*
- VALUE = ZERO
- DO 20 J = 1, N
- DO 10 I = 1, M
- VALUE = MAX( VALUE, ABS( A( I, J ) ) )
- 10 CONTINUE
- 20 CONTINUE
- ELSE IF( ( LSAME( NORM, 'O' ) ) .OR. ( NORM.EQ.'1' ) ) THEN
-*
-* Find norm1(A).
-*
- VALUE = ZERO
- DO 40 J = 1, N
- SUM = ZERO
- DO 30 I = 1, M
- SUM = SUM + ABS( A( I, J ) )
- 30 CONTINUE
- VALUE = MAX( VALUE, SUM )
- 40 CONTINUE
- ELSE IF( LSAME( NORM, 'I' ) ) THEN
-*
-* Find normI(A).
-*
- DO 50 I = 1, M
- WORK( I ) = ZERO
- 50 CONTINUE
- DO 70 J = 1, N
- DO 60 I = 1, M
- WORK( I ) = WORK( I ) + ABS( A( I, J ) )
- 60 CONTINUE
- 70 CONTINUE
- VALUE = ZERO
- DO 80 I = 1, M
- VALUE = MAX( VALUE, WORK( I ) )
- 80 CONTINUE
- ELSE IF( ( LSAME( NORM, 'F' ) ) .OR. ( LSAME( NORM, 'E' ) ) ) THEN
-*
-* Find normF(A).
-*
- SCALE = ZERO
- SUM = ONE
- DO 90 J = 1, N
- CALL ZLASSQ( M, A( 1, J ), 1, SCALE, SUM )
- 90 CONTINUE
- VALUE = SCALE*SQRT( SUM )
- END IF
-*
- ZLANGE = VALUE
- RETURN
-*
-* End of ZLANGE
-*
- END
diff --git a/src/lib/lapack/zlanhe.f b/src/lib/lapack/zlanhe.f
deleted file mode 100644
index 86e57fcd..00000000
--- a/src/lib/lapack/zlanhe.f
+++ /dev/null
@@ -1,187 +0,0 @@
- DOUBLE PRECISION FUNCTION ZLANHE( NORM, UPLO, N, A, LDA, WORK )
-*
-* -- LAPACK auxiliary routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- CHARACTER NORM, UPLO
- INTEGER LDA, N
-* ..
-* .. Array Arguments ..
- DOUBLE PRECISION WORK( * )
- COMPLEX*16 A( LDA, * )
-* ..
-*
-* Purpose
-* =======
-*
-* ZLANHE returns the value of the one norm, or the Frobenius norm, or
-* the infinity norm, or the element of largest absolute value of a
-* complex hermitian matrix A.
-*
-* Description
-* ===========
-*
-* ZLANHE returns the value
-*
-* ZLANHE = ( max(abs(A(i,j))), NORM = 'M' or 'm'
-* (
-* ( norm1(A), NORM = '1', 'O' or 'o'
-* (
-* ( normI(A), NORM = 'I' or 'i'
-* (
-* ( normF(A), NORM = 'F', 'f', 'E' or 'e'
-*
-* where norm1 denotes the one norm of a matrix (maximum column sum),
-* normI denotes the infinity norm of a matrix (maximum row sum) and
-* normF denotes the Frobenius norm of a matrix (square root of sum of
-* squares). Note that max(abs(A(i,j))) is not a consistent matrix norm.
-*
-* Arguments
-* =========
-*
-* NORM (input) CHARACTER*1
-* Specifies the value to be returned in ZLANHE as described
-* above.
-*
-* UPLO (input) CHARACTER*1
-* Specifies whether the upper or lower triangular part of the
-* hermitian matrix A is to be referenced.
-* = 'U': Upper triangular part of A is referenced
-* = 'L': Lower triangular part of A is referenced
-*
-* N (input) INTEGER
-* The order of the matrix A. N >= 0. When N = 0, ZLANHE is
-* set to zero.
-*
-* A (input) COMPLEX*16 array, dimension (LDA,N)
-* The hermitian matrix A. If UPLO = 'U', the leading n by n
-* upper triangular part of A contains the upper triangular part
-* of the matrix A, and the strictly lower triangular part of A
-* is not referenced. If UPLO = 'L', the leading n by n lower
-* triangular part of A contains the lower triangular part of
-* the matrix A, and the strictly upper triangular part of A is
-* not referenced. Note that the imaginary parts of the diagonal
-* elements need not be set and are assumed to be zero.
-*
-* LDA (input) INTEGER
-* The leading dimension of the array A. LDA >= max(N,1).
-*
-* WORK (workspace) DOUBLE PRECISION array, dimension (MAX(1,LWORK)),
-* where LWORK >= N when NORM = 'I' or '1' or 'O'; otherwise,
-* WORK is not referenced.
-*
-* =====================================================================
-*
-* .. Parameters ..
- DOUBLE PRECISION ONE, ZERO
- PARAMETER ( ONE = 1.0D+0, ZERO = 0.0D+0 )
-* ..
-* .. Local Scalars ..
- INTEGER I, J
- DOUBLE PRECISION ABSA, SCALE, SUM, VALUE
-* ..
-* .. External Functions ..
- LOGICAL LSAME
- EXTERNAL LSAME
-* ..
-* .. External Subroutines ..
- EXTERNAL ZLASSQ
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC ABS, DBLE, MAX, SQRT
-* ..
-* .. Executable Statements ..
-*
- IF( N.EQ.0 ) THEN
- VALUE = ZERO
- ELSE IF( LSAME( NORM, 'M' ) ) THEN
-*
-* Find max(abs(A(i,j))).
-*
- VALUE = ZERO
- IF( LSAME( UPLO, 'U' ) ) THEN
- DO 20 J = 1, N
- DO 10 I = 1, J - 1
- VALUE = MAX( VALUE, ABS( A( I, J ) ) )
- 10 CONTINUE
- VALUE = MAX( VALUE, ABS( DBLE( A( J, J ) ) ) )
- 20 CONTINUE
- ELSE
- DO 40 J = 1, N
- VALUE = MAX( VALUE, ABS( DBLE( A( J, J ) ) ) )
- DO 30 I = J + 1, N
- VALUE = MAX( VALUE, ABS( A( I, J ) ) )
- 30 CONTINUE
- 40 CONTINUE
- END IF
- ELSE IF( ( LSAME( NORM, 'I' ) ) .OR. ( LSAME( NORM, 'O' ) ) .OR.
- $ ( NORM.EQ.'1' ) ) THEN
-*
-* Find normI(A) ( = norm1(A), since A is hermitian).
-*
- VALUE = ZERO
- IF( LSAME( UPLO, 'U' ) ) THEN
- DO 60 J = 1, N
- SUM = ZERO
- DO 50 I = 1, J - 1
- ABSA = ABS( A( I, J ) )
- SUM = SUM + ABSA
- WORK( I ) = WORK( I ) + ABSA
- 50 CONTINUE
- WORK( J ) = SUM + ABS( DBLE( A( J, J ) ) )
- 60 CONTINUE
- DO 70 I = 1, N
- VALUE = MAX( VALUE, WORK( I ) )
- 70 CONTINUE
- ELSE
- DO 80 I = 1, N
- WORK( I ) = ZERO
- 80 CONTINUE
- DO 100 J = 1, N
- SUM = WORK( J ) + ABS( DBLE( A( J, J ) ) )
- DO 90 I = J + 1, N
- ABSA = ABS( A( I, J ) )
- SUM = SUM + ABSA
- WORK( I ) = WORK( I ) + ABSA
- 90 CONTINUE
- VALUE = MAX( VALUE, SUM )
- 100 CONTINUE
- END IF
- ELSE IF( ( LSAME( NORM, 'F' ) ) .OR. ( LSAME( NORM, 'E' ) ) ) THEN
-*
-* Find normF(A).
-*
- SCALE = ZERO
- SUM = ONE
- IF( LSAME( UPLO, 'U' ) ) THEN
- DO 110 J = 2, N
- CALL ZLASSQ( J-1, A( 1, J ), 1, SCALE, SUM )
- 110 CONTINUE
- ELSE
- DO 120 J = 1, N - 1
- CALL ZLASSQ( N-J, A( J+1, J ), 1, SCALE, SUM )
- 120 CONTINUE
- END IF
- SUM = 2*SUM
- DO 130 I = 1, N
- IF( DBLE( A( I, I ) ).NE.ZERO ) THEN
- ABSA = ABS( DBLE( A( I, I ) ) )
- IF( SCALE.LT.ABSA ) THEN
- SUM = ONE + SUM*( SCALE / ABSA )**2
- SCALE = ABSA
- ELSE
- SUM = SUM + ( ABSA / SCALE )**2
- END IF
- END IF
- 130 CONTINUE
- VALUE = SCALE*SQRT( SUM )
- END IF
-*
- ZLANHE = VALUE
- RETURN
-*
-* End of ZLANHE
-*
- END
diff --git a/src/lib/lapack/zlanhs.f b/src/lib/lapack/zlanhs.f
deleted file mode 100644
index d7b187a5..00000000
--- a/src/lib/lapack/zlanhs.f
+++ /dev/null
@@ -1,142 +0,0 @@
- DOUBLE PRECISION FUNCTION ZLANHS( NORM, N, A, LDA, WORK )
-*
-* -- LAPACK auxiliary routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- CHARACTER NORM
- INTEGER LDA, N
-* ..
-* .. Array Arguments ..
- DOUBLE PRECISION WORK( * )
- COMPLEX*16 A( LDA, * )
-* ..
-*
-* Purpose
-* =======
-*
-* ZLANHS returns the value of the one norm, or the Frobenius norm, or
-* the infinity norm, or the element of largest absolute value of a
-* Hessenberg matrix A.
-*
-* Description
-* ===========
-*
-* ZLANHS returns the value
-*
-* ZLANHS = ( max(abs(A(i,j))), NORM = 'M' or 'm'
-* (
-* ( norm1(A), NORM = '1', 'O' or 'o'
-* (
-* ( normI(A), NORM = 'I' or 'i'
-* (
-* ( normF(A), NORM = 'F', 'f', 'E' or 'e'
-*
-* where norm1 denotes the one norm of a matrix (maximum column sum),
-* normI denotes the infinity norm of a matrix (maximum row sum) and
-* normF denotes the Frobenius norm of a matrix (square root of sum of
-* squares). Note that max(abs(A(i,j))) is not a consistent matrix norm.
-*
-* Arguments
-* =========
-*
-* NORM (input) CHARACTER*1
-* Specifies the value to be returned in ZLANHS as described
-* above.
-*
-* N (input) INTEGER
-* The order of the matrix A. N >= 0. When N = 0, ZLANHS is
-* set to zero.
-*
-* A (input) COMPLEX*16 array, dimension (LDA,N)
-* The n by n upper Hessenberg matrix A; the part of A below the
-* first sub-diagonal is not referenced.
-*
-* LDA (input) INTEGER
-* The leading dimension of the array A. LDA >= max(N,1).
-*
-* WORK (workspace) DOUBLE PRECISION array, dimension (MAX(1,LWORK)),
-* where LWORK >= N when NORM = 'I'; otherwise, WORK is not
-* referenced.
-*
-* =====================================================================
-*
-* .. Parameters ..
- DOUBLE PRECISION ONE, ZERO
- PARAMETER ( ONE = 1.0D+0, ZERO = 0.0D+0 )
-* ..
-* .. Local Scalars ..
- INTEGER I, J
- DOUBLE PRECISION SCALE, SUM, VALUE
-* ..
-* .. External Functions ..
- LOGICAL LSAME
- EXTERNAL LSAME
-* ..
-* .. External Subroutines ..
- EXTERNAL ZLASSQ
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC ABS, MAX, MIN, SQRT
-* ..
-* .. Executable Statements ..
-*
- IF( N.EQ.0 ) THEN
- VALUE = ZERO
- ELSE IF( LSAME( NORM, 'M' ) ) THEN
-*
-* Find max(abs(A(i,j))).
-*
- VALUE = ZERO
- DO 20 J = 1, N
- DO 10 I = 1, MIN( N, J+1 )
- VALUE = MAX( VALUE, ABS( A( I, J ) ) )
- 10 CONTINUE
- 20 CONTINUE
- ELSE IF( ( LSAME( NORM, 'O' ) ) .OR. ( NORM.EQ.'1' ) ) THEN
-*
-* Find norm1(A).
-*
- VALUE = ZERO
- DO 40 J = 1, N
- SUM = ZERO
- DO 30 I = 1, MIN( N, J+1 )
- SUM = SUM + ABS( A( I, J ) )
- 30 CONTINUE
- VALUE = MAX( VALUE, SUM )
- 40 CONTINUE
- ELSE IF( LSAME( NORM, 'I' ) ) THEN
-*
-* Find normI(A).
-*
- DO 50 I = 1, N
- WORK( I ) = ZERO
- 50 CONTINUE
- DO 70 J = 1, N
- DO 60 I = 1, MIN( N, J+1 )
- WORK( I ) = WORK( I ) + ABS( A( I, J ) )
- 60 CONTINUE
- 70 CONTINUE
- VALUE = ZERO
- DO 80 I = 1, N
- VALUE = MAX( VALUE, WORK( I ) )
- 80 CONTINUE
- ELSE IF( ( LSAME( NORM, 'F' ) ) .OR. ( LSAME( NORM, 'E' ) ) ) THEN
-*
-* Find normF(A).
-*
- SCALE = ZERO
- SUM = ONE
- DO 90 J = 1, N
- CALL ZLASSQ( MIN( N, J+1 ), A( 1, J ), 1, SCALE, SUM )
- 90 CONTINUE
- VALUE = SCALE*SQRT( SUM )
- END IF
-*
- ZLANHS = VALUE
- RETURN
-*
-* End of ZLANHS
-*
- END
diff --git a/src/lib/lapack/zlaqp2.f b/src/lib/lapack/zlaqp2.f
deleted file mode 100644
index 46f6d95c..00000000
--- a/src/lib/lapack/zlaqp2.f
+++ /dev/null
@@ -1,179 +0,0 @@
- SUBROUTINE ZLAQP2( M, N, OFFSET, A, LDA, JPVT, TAU, VN1, VN2,
- $ WORK )
-*
-* -- LAPACK auxiliary routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- INTEGER LDA, M, N, OFFSET
-* ..
-* .. Array Arguments ..
- INTEGER JPVT( * )
- DOUBLE PRECISION VN1( * ), VN2( * )
- COMPLEX*16 A( LDA, * ), TAU( * ), WORK( * )
-* ..
-*
-* Purpose
-* =======
-*
-* ZLAQP2 computes a QR factorization with column pivoting of
-* the block A(OFFSET+1:M,1:N).
-* The block A(1:OFFSET,1:N) is accordingly pivoted, but not factorized.
-*
-* Arguments
-* =========
-*
-* M (input) INTEGER
-* The number of rows of the matrix A. M >= 0.
-*
-* N (input) INTEGER
-* The number of columns of the matrix A. N >= 0.
-*
-* OFFSET (input) INTEGER
-* The number of rows of the matrix A that must be pivoted
-* but no factorized. OFFSET >= 0.
-*
-* A (input/output) COMPLEX*16 array, dimension (LDA,N)
-* On entry, the M-by-N matrix A.
-* On exit, the upper triangle of block A(OFFSET+1:M,1:N) is
-* the triangular factor obtained; the elements in block
-* A(OFFSET+1:M,1:N) below the diagonal, together with the
-* array TAU, represent the orthogonal matrix Q as a product of
-* elementary reflectors. Block A(1:OFFSET,1:N) has been
-* accordingly pivoted, but no factorized.
-*
-* LDA (input) INTEGER
-* The leading dimension of the array A. LDA >= max(1,M).
-*
-* JPVT (input/output) INTEGER array, dimension (N)
-* On entry, if JPVT(i) .ne. 0, the i-th column of A is permuted
-* to the front of A*P (a leading column); if JPVT(i) = 0,
-* the i-th column of A is a free column.
-* On exit, if JPVT(i) = k, then the i-th column of A*P
-* was the k-th column of A.
-*
-* TAU (output) COMPLEX*16 array, dimension (min(M,N))
-* The scalar factors of the elementary reflectors.
-*
-* VN1 (input/output) DOUBLE PRECISION array, dimension (N)
-* The vector with the partial column norms.
-*
-* VN2 (input/output) DOUBLE PRECISION array, dimension (N)
-* The vector with the exact column norms.
-*
-* WORK (workspace) COMPLEX*16 array, dimension (N)
-*
-* Further Details
-* ===============
-*
-* Based on contributions by
-* G. Quintana-Orti, Depto. de Informatica, Universidad Jaime I, Spain
-* X. Sun, Computer Science Dept., Duke University, USA
-*
-* Partial column norm updating strategy modified by
-* Z. Drmac and Z. Bujanovic, Dept. of Mathematics,
-* University of Zagreb, Croatia.
-* June 2006.
-* For more details see LAPACK Working Note 176.
-* =====================================================================
-*
-* .. Parameters ..
- DOUBLE PRECISION ZERO, ONE
- COMPLEX*16 CONE
- PARAMETER ( ZERO = 0.0D+0, ONE = 1.0D+0,
- $ CONE = ( 1.0D+0, 0.0D+0 ) )
-* ..
-* .. Local Scalars ..
- INTEGER I, ITEMP, J, MN, OFFPI, PVT
- DOUBLE PRECISION TEMP, TEMP2, TOL3Z
- COMPLEX*16 AII
-* ..
-* .. External Subroutines ..
- EXTERNAL ZLARF, ZLARFG, ZSWAP
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC ABS, DCONJG, MAX, MIN, SQRT
-* ..
-* .. External Functions ..
- INTEGER IDAMAX
- DOUBLE PRECISION DLAMCH, DZNRM2
- EXTERNAL IDAMAX, DLAMCH, DZNRM2
-* ..
-* .. Executable Statements ..
-*
- MN = MIN( M-OFFSET, N )
- TOL3Z = SQRT(DLAMCH('Epsilon'))
-*
-* Compute factorization.
-*
- DO 20 I = 1, MN
-*
- OFFPI = OFFSET + I
-*
-* Determine ith pivot column and swap if necessary.
-*
- PVT = ( I-1 ) + IDAMAX( N-I+1, VN1( I ), 1 )
-*
- IF( PVT.NE.I ) THEN
- CALL ZSWAP( M, A( 1, PVT ), 1, A( 1, I ), 1 )
- ITEMP = JPVT( PVT )
- JPVT( PVT ) = JPVT( I )
- JPVT( I ) = ITEMP
- VN1( PVT ) = VN1( I )
- VN2( PVT ) = VN2( I )
- END IF
-*
-* Generate elementary reflector H(i).
-*
- IF( OFFPI.LT.M ) THEN
- CALL ZLARFG( M-OFFPI+1, A( OFFPI, I ), A( OFFPI+1, I ), 1,
- $ TAU( I ) )
- ELSE
- CALL ZLARFG( 1, A( M, I ), A( M, I ), 1, TAU( I ) )
- END IF
-*
- IF( I.LT.N ) THEN
-*
-* Apply H(i)' to A(offset+i:m,i+1:n) from the left.
-*
- AII = A( OFFPI, I )
- A( OFFPI, I ) = CONE
- CALL ZLARF( 'Left', M-OFFPI+1, N-I, A( OFFPI, I ), 1,
- $ DCONJG( TAU( I ) ), A( OFFPI, I+1 ), LDA,
- $ WORK( 1 ) )
- A( OFFPI, I ) = AII
- END IF
-*
-* Update partial column norms.
-*
- DO 10 J = I + 1, N
- IF( VN1( J ).NE.ZERO ) THEN
-*
-* NOTE: The following 4 lines follow from the analysis in
-* Lapack Working Note 176.
-*
- TEMP = ONE - ( ABS( A( OFFPI, J ) ) / VN1( J ) )**2
- TEMP = MAX( TEMP, ZERO )
- TEMP2 = TEMP*( VN1( J ) / VN2( J ) )**2
- IF( TEMP2 .LE. TOL3Z ) THEN
- IF( OFFPI.LT.M ) THEN
- VN1( J ) = DZNRM2( M-OFFPI, A( OFFPI+1, J ), 1 )
- VN2( J ) = VN1( J )
- ELSE
- VN1( J ) = ZERO
- VN2( J ) = ZERO
- END IF
- ELSE
- VN1( J ) = VN1( J )*SQRT( TEMP )
- END IF
- END IF
- 10 CONTINUE
-*
- 20 CONTINUE
-*
- RETURN
-*
-* End of ZLAQP2
-*
- END
diff --git a/src/lib/lapack/zlaqps.f b/src/lib/lapack/zlaqps.f
deleted file mode 100644
index 40414503..00000000
--- a/src/lib/lapack/zlaqps.f
+++ /dev/null
@@ -1,266 +0,0 @@
- SUBROUTINE ZLAQPS( M, N, OFFSET, NB, KB, A, LDA, JPVT, TAU, VN1,
- $ VN2, AUXV, F, LDF )
-*
-* -- LAPACK auxiliary routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- INTEGER KB, LDA, LDF, M, N, NB, OFFSET
-* ..
-* .. Array Arguments ..
- INTEGER JPVT( * )
- DOUBLE PRECISION VN1( * ), VN2( * )
- COMPLEX*16 A( LDA, * ), AUXV( * ), F( LDF, * ), TAU( * )
-* ..
-*
-* Purpose
-* =======
-*
-* ZLAQPS computes a step of QR factorization with column pivoting
-* of a complex M-by-N matrix A by using Blas-3. It tries to factorize
-* NB columns from A starting from the row OFFSET+1, and updates all
-* of the matrix with Blas-3 xGEMM.
-*
-* In some cases, due to catastrophic cancellations, it cannot
-* factorize NB columns. Hence, the actual number of factorized
-* columns is returned in KB.
-*
-* Block A(1:OFFSET,1:N) is accordingly pivoted, but not factorized.
-*
-* Arguments
-* =========
-*
-* M (input) INTEGER
-* The number of rows of the matrix A. M >= 0.
-*
-* N (input) INTEGER
-* The number of columns of the matrix A. N >= 0
-*
-* OFFSET (input) INTEGER
-* The number of rows of A that have been factorized in
-* previous steps.
-*
-* NB (input) INTEGER
-* The number of columns to factorize.
-*
-* KB (output) INTEGER
-* The number of columns actually factorized.
-*
-* A (input/output) COMPLEX*16 array, dimension (LDA,N)
-* On entry, the M-by-N matrix A.
-* On exit, block A(OFFSET+1:M,1:KB) is the triangular
-* factor obtained and block A(1:OFFSET,1:N) has been
-* accordingly pivoted, but no factorized.
-* The rest of the matrix, block A(OFFSET+1:M,KB+1:N) has
-* been updated.
-*
-* LDA (input) INTEGER
-* The leading dimension of the array A. LDA >= max(1,M).
-*
-* JPVT (input/output) INTEGER array, dimension (N)
-* JPVT(I) = K <==> Column K of the full matrix A has been
-* permuted into position I in AP.
-*
-* TAU (output) COMPLEX*16 array, dimension (KB)
-* The scalar factors of the elementary reflectors.
-*
-* VN1 (input/output) DOUBLE PRECISION array, dimension (N)
-* The vector with the partial column norms.
-*
-* VN2 (input/output) DOUBLE PRECISION array, dimension (N)
-* The vector with the exact column norms.
-*
-* AUXV (input/output) COMPLEX*16 array, dimension (NB)
-* Auxiliar vector.
-*
-* F (input/output) COMPLEX*16 array, dimension (LDF,NB)
-* Matrix F' = L*Y'*A.
-*
-* LDF (input) INTEGER
-* The leading dimension of the array F. LDF >= max(1,N).
-*
-* Further Details
-* ===============
-*
-* Based on contributions by
-* G. Quintana-Orti, Depto. de Informatica, Universidad Jaime I, Spain
-* X. Sun, Computer Science Dept., Duke University, USA
-*
-* =====================================================================
-*
-* .. Parameters ..
- DOUBLE PRECISION ZERO, ONE
- COMPLEX*16 CZERO, CONE
- PARAMETER ( ZERO = 0.0D+0, ONE = 1.0D+0,
- $ CZERO = ( 0.0D+0, 0.0D+0 ),
- $ CONE = ( 1.0D+0, 0.0D+0 ) )
-* ..
-* .. Local Scalars ..
- INTEGER ITEMP, J, K, LASTRK, LSTICC, PVT, RK
- DOUBLE PRECISION TEMP, TEMP2, TOL3Z
- COMPLEX*16 AKK
-* ..
-* .. External Subroutines ..
- EXTERNAL ZGEMM, ZGEMV, ZLARFG, ZSWAP
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC ABS, DBLE, DCONJG, MAX, MIN, NINT, SQRT
-* ..
-* .. External Functions ..
- INTEGER IDAMAX
- DOUBLE PRECISION DLAMCH, DZNRM2
- EXTERNAL IDAMAX, DLAMCH, DZNRM2
-* ..
-* .. Executable Statements ..
-*
- LASTRK = MIN( M, N+OFFSET )
- LSTICC = 0
- K = 0
- TOL3Z = SQRT(DLAMCH('Epsilon'))
-*
-* Beginning of while loop.
-*
- 10 CONTINUE
- IF( ( K.LT.NB ) .AND. ( LSTICC.EQ.0 ) ) THEN
- K = K + 1
- RK = OFFSET + K
-*
-* Determine ith pivot column and swap if necessary
-*
- PVT = ( K-1 ) + IDAMAX( N-K+1, VN1( K ), 1 )
- IF( PVT.NE.K ) THEN
- CALL ZSWAP( M, A( 1, PVT ), 1, A( 1, K ), 1 )
- CALL ZSWAP( K-1, F( PVT, 1 ), LDF, F( K, 1 ), LDF )
- ITEMP = JPVT( PVT )
- JPVT( PVT ) = JPVT( K )
- JPVT( K ) = ITEMP
- VN1( PVT ) = VN1( K )
- VN2( PVT ) = VN2( K )
- END IF
-*
-* Apply previous Householder reflectors to column K:
-* A(RK:M,K) := A(RK:M,K) - A(RK:M,1:K-1)*F(K,1:K-1)'.
-*
- IF( K.GT.1 ) THEN
- DO 20 J = 1, K - 1
- F( K, J ) = DCONJG( F( K, J ) )
- 20 CONTINUE
- CALL ZGEMV( 'No transpose', M-RK+1, K-1, -CONE, A( RK, 1 ),
- $ LDA, F( K, 1 ), LDF, CONE, A( RK, K ), 1 )
- DO 30 J = 1, K - 1
- F( K, J ) = DCONJG( F( K, J ) )
- 30 CONTINUE
- END IF
-*
-* Generate elementary reflector H(k).
-*
- IF( RK.LT.M ) THEN
- CALL ZLARFG( M-RK+1, A( RK, K ), A( RK+1, K ), 1, TAU( K ) )
- ELSE
- CALL ZLARFG( 1, A( RK, K ), A( RK, K ), 1, TAU( K ) )
- END IF
-*
- AKK = A( RK, K )
- A( RK, K ) = CONE
-*
-* Compute Kth column of F:
-*
-* Compute F(K+1:N,K) := tau(K)*A(RK:M,K+1:N)'*A(RK:M,K).
-*
- IF( K.LT.N ) THEN
- CALL ZGEMV( 'Conjugate transpose', M-RK+1, N-K, TAU( K ),
- $ A( RK, K+1 ), LDA, A( RK, K ), 1, CZERO,
- $ F( K+1, K ), 1 )
- END IF
-*
-* Padding F(1:K,K) with zeros.
-*
- DO 40 J = 1, K
- F( J, K ) = CZERO
- 40 CONTINUE
-*
-* Incremental updating of F:
-* F(1:N,K) := F(1:N,K) - tau(K)*F(1:N,1:K-1)*A(RK:M,1:K-1)'
-* *A(RK:M,K).
-*
- IF( K.GT.1 ) THEN
- CALL ZGEMV( 'Conjugate transpose', M-RK+1, K-1, -TAU( K ),
- $ A( RK, 1 ), LDA, A( RK, K ), 1, CZERO,
- $ AUXV( 1 ), 1 )
-*
- CALL ZGEMV( 'No transpose', N, K-1, CONE, F( 1, 1 ), LDF,
- $ AUXV( 1 ), 1, CONE, F( 1, K ), 1 )
- END IF
-*
-* Update the current row of A:
-* A(RK,K+1:N) := A(RK,K+1:N) - A(RK,1:K)*F(K+1:N,1:K)'.
-*
- IF( K.LT.N ) THEN
- CALL ZGEMM( 'No transpose', 'Conjugate transpose', 1, N-K,
- $ K, -CONE, A( RK, 1 ), LDA, F( K+1, 1 ), LDF,
- $ CONE, A( RK, K+1 ), LDA )
- END IF
-*
-* Update partial column norms.
-*
- IF( RK.LT.LASTRK ) THEN
- DO 50 J = K + 1, N
- IF( VN1( J ).NE.ZERO ) THEN
-*
-* NOTE: The following 4 lines follow from the analysis in
-* Lapack Working Note 176.
-*
- TEMP = ABS( A( RK, J ) ) / VN1( J )
- TEMP = MAX( ZERO, ( ONE+TEMP )*( ONE-TEMP ) )
- TEMP2 = TEMP*( VN1( J ) / VN2( J ) )**2
- IF( TEMP2 .LE. TOL3Z ) THEN
- VN2( J ) = DBLE( LSTICC )
- LSTICC = J
- ELSE
- VN1( J ) = VN1( J )*SQRT( TEMP )
- END IF
- END IF
- 50 CONTINUE
- END IF
-*
- A( RK, K ) = AKK
-*
-* End of while loop.
-*
- GO TO 10
- END IF
- KB = K
- RK = OFFSET + KB
-*
-* Apply the block reflector to the rest of the matrix:
-* A(OFFSET+KB+1:M,KB+1:N) := A(OFFSET+KB+1:M,KB+1:N) -
-* A(OFFSET+KB+1:M,1:KB)*F(KB+1:N,1:KB)'.
-*
- IF( KB.LT.MIN( N, M-OFFSET ) ) THEN
- CALL ZGEMM( 'No transpose', 'Conjugate transpose', M-RK, N-KB,
- $ KB, -CONE, A( RK+1, 1 ), LDA, F( KB+1, 1 ), LDF,
- $ CONE, A( RK+1, KB+1 ), LDA )
- END IF
-*
-* Recomputation of difficult columns.
-*
- 60 CONTINUE
- IF( LSTICC.GT.0 ) THEN
- ITEMP = NINT( VN2( LSTICC ) )
- VN1( LSTICC ) = DZNRM2( M-RK, A( RK+1, LSTICC ), 1 )
-*
-* NOTE: The computation of VN1( LSTICC ) relies on the fact that
-* SNRM2 does not fail on vectors with norm below the value of
-* SQRT(DLAMCH('S'))
-*
- VN2( LSTICC ) = VN1( LSTICC )
- LSTICC = ITEMP
- GO TO 60
- END IF
-*
- RETURN
-*
-* End of ZLAQPS
-*
- END
diff --git a/src/lib/lapack/zlaqr0.f b/src/lib/lapack/zlaqr0.f
deleted file mode 100644
index 2a35a725..00000000
--- a/src/lib/lapack/zlaqr0.f
+++ /dev/null
@@ -1,601 +0,0 @@
- SUBROUTINE ZLAQR0( WANTT, WANTZ, N, ILO, IHI, H, LDH, W, ILOZ,
- $ IHIZ, Z, LDZ, WORK, LWORK, INFO )
-*
-* -- LAPACK auxiliary routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- INTEGER IHI, IHIZ, ILO, ILOZ, INFO, LDH, LDZ, LWORK, N
- LOGICAL WANTT, WANTZ
-* ..
-* .. Array Arguments ..
- COMPLEX*16 H( LDH, * ), W( * ), WORK( * ), Z( LDZ, * )
-* ..
-*
-* Purpose
-* =======
-*
-* ZLAQR0 computes the eigenvalues of a Hessenberg matrix H
-* and, optionally, the matrices T and Z from the Schur decomposition
-* H = Z T Z**H, where T is an upper triangular matrix (the
-* Schur form), and Z is the unitary matrix of Schur vectors.
-*
-* Optionally Z may be postmultiplied into an input unitary
-* matrix Q so that this routine can give the Schur factorization
-* of a matrix A which has been reduced to the Hessenberg form H
-* by the unitary matrix Q: A = Q*H*Q**H = (QZ)*H*(QZ)**H.
-*
-* Arguments
-* =========
-*
-* WANTT (input) LOGICAL
-* = .TRUE. : the full Schur form T is required;
-* = .FALSE.: only eigenvalues are required.
-*
-* WANTZ (input) LOGICAL
-* = .TRUE. : the matrix of Schur vectors Z is required;
-* = .FALSE.: Schur vectors are not required.
-*
-* N (input) INTEGER
-* The order of the matrix H. N .GE. 0.
-*
-* ILO (input) INTEGER
-* IHI (input) INTEGER
-* It is assumed that H is already upper triangular in rows
-* and columns 1:ILO-1 and IHI+1:N and, if ILO.GT.1,
-* H(ILO,ILO-1) is zero. ILO and IHI are normally set by a
-* previous call to ZGEBAL, and then passed to ZGEHRD when the
-* matrix output by ZGEBAL is reduced to Hessenberg form.
-* Otherwise, ILO and IHI should be set to 1 and N,
-* respectively. If N.GT.0, then 1.LE.ILO.LE.IHI.LE.N.
-* If N = 0, then ILO = 1 and IHI = 0.
-*
-* H (input/output) COMPLEX*16 array, dimension (LDH,N)
-* On entry, the upper Hessenberg matrix H.
-* On exit, if INFO = 0 and WANTT is .TRUE., then H
-* contains the upper triangular matrix T from the Schur
-* decomposition (the Schur form). If INFO = 0 and WANT is
-* .FALSE., then the contents of H are unspecified on exit.
-* (The output value of H when INFO.GT.0 is given under the
-* description of INFO below.)
-*
-* This subroutine may explicitly set H(i,j) = 0 for i.GT.j and
-* j = 1, 2, ... ILO-1 or j = IHI+1, IHI+2, ... N.
-*
-* LDH (input) INTEGER
-* The leading dimension of the array H. LDH .GE. max(1,N).
-*
-* W (output) COMPLEX*16 array, dimension (N)
-* The computed eigenvalues of H(ILO:IHI,ILO:IHI) are stored
-* in W(ILO:IHI). If WANTT is .TRUE., then the eigenvalues are
-* stored in the same order as on the diagonal of the Schur
-* form returned in H, with W(i) = H(i,i).
-*
-* Z (input/output) COMPLEX*16 array, dimension (LDZ,IHI)
-* If WANTZ is .FALSE., then Z is not referenced.
-* If WANTZ is .TRUE., then Z(ILO:IHI,ILOZ:IHIZ) is
-* replaced by Z(ILO:IHI,ILOZ:IHIZ)*U where U is the
-* orthogonal Schur factor of H(ILO:IHI,ILO:IHI).
-* (The output value of Z when INFO.GT.0 is given under
-* the description of INFO below.)
-*
-* LDZ (input) INTEGER
-* The leading dimension of the array Z. if WANTZ is .TRUE.
-* then LDZ.GE.MAX(1,IHIZ). Otherwize, LDZ.GE.1.
-*
-* WORK (workspace/output) COMPLEX*16 array, dimension LWORK
-* On exit, if LWORK = -1, WORK(1) returns an estimate of
-* the optimal value for LWORK.
-*
-* LWORK (input) INTEGER
-* The dimension of the array WORK. LWORK .GE. max(1,N)
-* is sufficient, but LWORK typically as large as 6*N may
-* be required for optimal performance. A workspace query
-* to determine the optimal workspace size is recommended.
-*
-* If LWORK = -1, then ZLAQR0 does a workspace query.
-* In this case, ZLAQR0 checks the input parameters and
-* estimates the optimal workspace size for the given
-* values of N, ILO and IHI. The estimate is returned
-* in WORK(1). No error message related to LWORK is
-* issued by XERBLA. Neither H nor Z are accessed.
-*
-*
-* INFO (output) INTEGER
-* = 0: successful exit
-* .GT. 0: if INFO = i, ZLAQR0 failed to compute all of
-* the eigenvalues. Elements 1:ilo-1 and i+1:n of WR
-* and WI contain those eigenvalues which have been
-* successfully computed. (Failures are rare.)
-*
-* If INFO .GT. 0 and WANT is .FALSE., then on exit,
-* the remaining unconverged eigenvalues are the eigen-
-* values of the upper Hessenberg matrix rows and
-* columns ILO through INFO of the final, output
-* value of H.
-*
-* If INFO .GT. 0 and WANTT is .TRUE., then on exit
-*
-* (*) (initial value of H)*U = U*(final value of H)
-*
-* where U is a unitary matrix. The final
-* value of H is upper Hessenberg and triangular in
-* rows and columns INFO+1 through IHI.
-*
-* If INFO .GT. 0 and WANTZ is .TRUE., then on exit
-*
-* (final value of Z(ILO:IHI,ILOZ:IHIZ)
-* = (initial value of Z(ILO:IHI,ILOZ:IHIZ)*U
-*
-* where U is the unitary matrix in (*) (regard-
-* less of the value of WANTT.)
-*
-* If INFO .GT. 0 and WANTZ is .FALSE., then Z is not
-* accessed.
-*
-* ================================================================
-* Based on contributions by
-* Karen Braman and Ralph Byers, Department of Mathematics,
-* University of Kansas, USA
-*
-* ================================================================
-* References:
-* K. Braman, R. Byers and R. Mathias, The Multi-Shift QR
-* Algorithm Part I: Maintaining Well Focused Shifts, and Level 3
-* Performance, SIAM Journal of Matrix Analysis, volume 23, pages
-* 929--947, 2002.
-*
-* K. Braman, R. Byers and R. Mathias, The Multi-Shift QR
-* Algorithm Part II: Aggressive Early Deflation, SIAM Journal
-* of Matrix Analysis, volume 23, pages 948--973, 2002.
-*
-* ================================================================
-* .. Parameters ..
-*
-* ==== Matrices of order NTINY or smaller must be processed by
-* . ZLAHQR because of insufficient subdiagonal scratch space.
-* . (This is a hard limit.) ====
-*
-* ==== Exceptional deflation windows: try to cure rare
-* . slow convergence by increasing the size of the
-* . deflation window after KEXNW iterations. =====
-*
-* ==== Exceptional shifts: try to cure rare slow convergence
-* . with ad-hoc exceptional shifts every KEXSH iterations.
-* . The constants WILK1 and WILK2 are used to form the
-* . exceptional shifts. ====
-*
- INTEGER NTINY
- PARAMETER ( NTINY = 11 )
- INTEGER KEXNW, KEXSH
- PARAMETER ( KEXNW = 5, KEXSH = 6 )
- DOUBLE PRECISION WILK1
- PARAMETER ( WILK1 = 0.75d0 )
- COMPLEX*16 ZERO, ONE
- PARAMETER ( ZERO = ( 0.0d0, 0.0d0 ),
- $ ONE = ( 1.0d0, 0.0d0 ) )
- DOUBLE PRECISION TWO
- PARAMETER ( TWO = 2.0d0 )
-* ..
-* .. Local Scalars ..
- COMPLEX*16 AA, BB, CC, CDUM, DD, DET, RTDISC, SWAP, TR2
- DOUBLE PRECISION S
- INTEGER I, INF, IT, ITMAX, K, KACC22, KBOT, KDU, KS,
- $ KT, KTOP, KU, KV, KWH, KWTOP, KWV, LD, LS,
- $ LWKOPT, NDFL, NH, NHO, NIBBLE, NMIN, NS, NSMAX,
- $ NSR, NVE, NW, NWMAX, NWR
- LOGICAL NWINC, SORTED
- CHARACTER JBCMPZ*2
-* ..
-* .. External Functions ..
- INTEGER ILAENV
- EXTERNAL ILAENV
-* ..
-* .. Local Arrays ..
- COMPLEX*16 ZDUM( 1, 1 )
-* ..
-* .. External Subroutines ..
- EXTERNAL ZLACPY, ZLAHQR, ZLAQR3, ZLAQR4, ZLAQR5
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC ABS, DBLE, DCMPLX, DIMAG, INT, MAX, MIN, MOD,
- $ SQRT
-* ..
-* .. Statement Functions ..
- DOUBLE PRECISION CABS1
-* ..
-* .. Statement Function definitions ..
- CABS1( CDUM ) = ABS( DBLE( CDUM ) ) + ABS( DIMAG( CDUM ) )
-* ..
-* .. Executable Statements ..
- INFO = 0
-*
-* ==== Quick return for N = 0: nothing to do. ====
-*
- IF( N.EQ.0 ) THEN
- WORK( 1 ) = ONE
- RETURN
- END IF
-*
-* ==== Set up job flags for ILAENV. ====
-*
- IF( WANTT ) THEN
- JBCMPZ( 1: 1 ) = 'S'
- ELSE
- JBCMPZ( 1: 1 ) = 'E'
- END IF
- IF( WANTZ ) THEN
- JBCMPZ( 2: 2 ) = 'V'
- ELSE
- JBCMPZ( 2: 2 ) = 'N'
- END IF
-*
-* ==== Tiny matrices must use ZLAHQR. ====
-*
- IF( N.LE.NTINY ) THEN
-*
-* ==== Estimate optimal workspace. ====
-*
- LWKOPT = 1
- IF( LWORK.NE.-1 )
- $ CALL ZLAHQR( WANTT, WANTZ, N, ILO, IHI, H, LDH, W, ILOZ,
- $ IHIZ, Z, LDZ, INFO )
- ELSE
-*
-* ==== Use small bulge multi-shift QR with aggressive early
-* . deflation on larger-than-tiny matrices. ====
-*
-* ==== Hope for the best. ====
-*
- INFO = 0
-*
-* ==== NWR = recommended deflation window size. At this
-* . point, N .GT. NTINY = 11, so there is enough
-* . subdiagonal workspace for NWR.GE.2 as required.
-* . (In fact, there is enough subdiagonal space for
-* . NWR.GE.3.) ====
-*
- NWR = ILAENV( 13, 'ZLAQR0', JBCMPZ, N, ILO, IHI, LWORK )
- NWR = MAX( 2, NWR )
- NWR = MIN( IHI-ILO+1, ( N-1 ) / 3, NWR )
- NW = NWR
-*
-* ==== NSR = recommended number of simultaneous shifts.
-* . At this point N .GT. NTINY = 11, so there is at
-* . enough subdiagonal workspace for NSR to be even
-* . and greater than or equal to two as required. ====
-*
- NSR = ILAENV( 15, 'ZLAQR0', JBCMPZ, N, ILO, IHI, LWORK )
- NSR = MIN( NSR, ( N+6 ) / 9, IHI-ILO )
- NSR = MAX( 2, NSR-MOD( NSR, 2 ) )
-*
-* ==== Estimate optimal workspace ====
-*
-* ==== Workspace query call to ZLAQR3 ====
-*
- CALL ZLAQR3( WANTT, WANTZ, N, ILO, IHI, NWR+1, H, LDH, ILOZ,
- $ IHIZ, Z, LDZ, LS, LD, W, H, LDH, N, H, LDH, N, H,
- $ LDH, WORK, -1 )
-*
-* ==== Optimal workspace = MAX(ZLAQR5, ZLAQR3) ====
-*
- LWKOPT = MAX( 3*NSR / 2, INT( WORK( 1 ) ) )
-*
-* ==== Quick return in case of workspace query. ====
-*
- IF( LWORK.EQ.-1 ) THEN
- WORK( 1 ) = DCMPLX( LWKOPT, 0 )
- RETURN
- END IF
-*
-* ==== ZLAHQR/ZLAQR0 crossover point ====
-*
- NMIN = ILAENV( 12, 'ZLAQR0', JBCMPZ, N, ILO, IHI, LWORK )
- NMIN = MAX( NTINY, NMIN )
-*
-* ==== Nibble crossover point ====
-*
- NIBBLE = ILAENV( 14, 'ZLAQR0', JBCMPZ, N, ILO, IHI, LWORK )
- NIBBLE = MAX( 0, NIBBLE )
-*
-* ==== Accumulate reflections during ttswp? Use block
-* . 2-by-2 structure during matrix-matrix multiply? ====
-*
- KACC22 = ILAENV( 16, 'ZLAQR0', JBCMPZ, N, ILO, IHI, LWORK )
- KACC22 = MAX( 0, KACC22 )
- KACC22 = MIN( 2, KACC22 )
-*
-* ==== NWMAX = the largest possible deflation window for
-* . which there is sufficient workspace. ====
-*
- NWMAX = MIN( ( N-1 ) / 3, LWORK / 2 )
-*
-* ==== NSMAX = the Largest number of simultaneous shifts
-* . for which there is sufficient workspace. ====
-*
- NSMAX = MIN( ( N+6 ) / 9, 2*LWORK / 3 )
- NSMAX = NSMAX - MOD( NSMAX, 2 )
-*
-* ==== NDFL: an iteration count restarted at deflation. ====
-*
- NDFL = 1
-*
-* ==== ITMAX = iteration limit ====
-*
- ITMAX = MAX( 30, 2*KEXSH )*MAX( 10, ( IHI-ILO+1 ) )
-*
-* ==== Last row and column in the active block ====
-*
- KBOT = IHI
-*
-* ==== Main Loop ====
-*
- DO 70 IT = 1, ITMAX
-*
-* ==== Done when KBOT falls below ILO ====
-*
- IF( KBOT.LT.ILO )
- $ GO TO 80
-*
-* ==== Locate active block ====
-*
- DO 10 K = KBOT, ILO + 1, -1
- IF( H( K, K-1 ).EQ.ZERO )
- $ GO TO 20
- 10 CONTINUE
- K = ILO
- 20 CONTINUE
- KTOP = K
-*
-* ==== Select deflation window size ====
-*
- NH = KBOT - KTOP + 1
- IF( NDFL.LT.KEXNW .OR. NH.LT.NW ) THEN
-*
-* ==== Typical deflation window. If possible and
-* . advisable, nibble the entire active block.
-* . If not, use size NWR or NWR+1 depending upon
-* . which has the smaller corresponding subdiagonal
-* . entry (a heuristic). ====
-*
- NWINC = .TRUE.
- IF( NH.LE.MIN( NMIN, NWMAX ) ) THEN
- NW = NH
- ELSE
- NW = MIN( NWR, NH, NWMAX )
- IF( NW.LT.NWMAX ) THEN
- IF( NW.GE.NH-1 ) THEN
- NW = NH
- ELSE
- KWTOP = KBOT - NW + 1
- IF( CABS1( H( KWTOP, KWTOP-1 ) ).GT.
- $ CABS1( H( KWTOP-1, KWTOP-2 ) ) )NW = NW + 1
- END IF
- END IF
- END IF
- ELSE
-*
-* ==== Exceptional deflation window. If there have
-* . been no deflations in KEXNW or more iterations,
-* . then vary the deflation window size. At first,
-* . because, larger windows are, in general, more
-* . powerful than smaller ones, rapidly increase the
-* . window up to the maximum reasonable and possible.
-* . Then maybe try a slightly smaller window. ====
-*
- IF( NWINC .AND. NW.LT.MIN( NWMAX, NH ) ) THEN
- NW = MIN( NWMAX, NH, 2*NW )
- ELSE
- NWINC = .FALSE.
- IF( NW.EQ.NH .AND. NH.GT.2 )
- $ NW = NH - 1
- END IF
- END IF
-*
-* ==== Aggressive early deflation:
-* . split workspace under the subdiagonal into
-* . - an nw-by-nw work array V in the lower
-* . left-hand-corner,
-* . - an NW-by-at-least-NW-but-more-is-better
-* . (NW-by-NHO) horizontal work array along
-* . the bottom edge,
-* . - an at-least-NW-but-more-is-better (NHV-by-NW)
-* . vertical work array along the left-hand-edge.
-* . ====
-*
- KV = N - NW + 1
- KT = NW + 1
- NHO = ( N-NW-1 ) - KT + 1
- KWV = NW + 2
- NVE = ( N-NW ) - KWV + 1
-*
-* ==== Aggressive early deflation ====
-*
- CALL ZLAQR3( WANTT, WANTZ, N, KTOP, KBOT, NW, H, LDH, ILOZ,
- $ IHIZ, Z, LDZ, LS, LD, W, H( KV, 1 ), LDH, NHO,
- $ H( KV, KT ), LDH, NVE, H( KWV, 1 ), LDH, WORK,
- $ LWORK )
-*
-* ==== Adjust KBOT accounting for new deflations. ====
-*
- KBOT = KBOT - LD
-*
-* ==== KS points to the shifts. ====
-*
- KS = KBOT - LS + 1
-*
-* ==== Skip an expensive QR sweep if there is a (partly
-* . heuristic) reason to expect that many eigenvalues
-* . will deflate without it. Here, the QR sweep is
-* . skipped if many eigenvalues have just been deflated
-* . or if the remaining active block is small.
-*
- IF( ( LD.EQ.0 ) .OR. ( ( 100*LD.LE.NW*NIBBLE ) .AND. ( KBOT-
- $ KTOP+1.GT.MIN( NMIN, NWMAX ) ) ) ) THEN
-*
-* ==== NS = nominal number of simultaneous shifts.
-* . This may be lowered (slightly) if ZLAQR3
-* . did not provide that many shifts. ====
-*
- NS = MIN( NSMAX, NSR, MAX( 2, KBOT-KTOP ) )
- NS = NS - MOD( NS, 2 )
-*
-* ==== If there have been no deflations
-* . in a multiple of KEXSH iterations,
-* . then try exceptional shifts.
-* . Otherwise use shifts provided by
-* . ZLAQR3 above or from the eigenvalues
-* . of a trailing principal submatrix. ====
-*
- IF( MOD( NDFL, KEXSH ).EQ.0 ) THEN
- KS = KBOT - NS + 1
- DO 30 I = KBOT, KS + 1, -2
- W( I ) = H( I, I ) + WILK1*CABS1( H( I, I-1 ) )
- W( I-1 ) = W( I )
- 30 CONTINUE
- ELSE
-*
-* ==== Got NS/2 or fewer shifts? Use ZLAQR4 or
-* . ZLAHQR on a trailing principal submatrix to
-* . get more. (Since NS.LE.NSMAX.LE.(N+6)/9,
-* . there is enough space below the subdiagonal
-* . to fit an NS-by-NS scratch array.) ====
-*
- IF( KBOT-KS+1.LE.NS / 2 ) THEN
- KS = KBOT - NS + 1
- KT = N - NS + 1
- CALL ZLACPY( 'A', NS, NS, H( KS, KS ), LDH,
- $ H( KT, 1 ), LDH )
- IF( NS.GT.NMIN ) THEN
- CALL ZLAQR4( .false., .false., NS, 1, NS,
- $ H( KT, 1 ), LDH, W( KS ), 1, 1,
- $ ZDUM, 1, WORK, LWORK, INF )
- ELSE
- CALL ZLAHQR( .false., .false., NS, 1, NS,
- $ H( KT, 1 ), LDH, W( KS ), 1, 1,
- $ ZDUM, 1, INF )
- END IF
- KS = KS + INF
-*
-* ==== In case of a rare QR failure use
-* . eigenvalues of the trailing 2-by-2
-* . principal submatrix. Scale to avoid
-* . overflows, underflows and subnormals.
-* . (The scale factor S can not be zero,
-* . because H(KBOT,KBOT-1) is nonzero.) ====
-*
- IF( KS.GE.KBOT ) THEN
- S = CABS1( H( KBOT-1, KBOT-1 ) ) +
- $ CABS1( H( KBOT, KBOT-1 ) ) +
- $ CABS1( H( KBOT-1, KBOT ) ) +
- $ CABS1( H( KBOT, KBOT ) )
- AA = H( KBOT-1, KBOT-1 ) / S
- CC = H( KBOT, KBOT-1 ) / S
- BB = H( KBOT-1, KBOT ) / S
- DD = H( KBOT, KBOT ) / S
- TR2 = ( AA+DD ) / TWO
- DET = ( AA-TR2 )*( DD-TR2 ) - BB*CC
- RTDISC = SQRT( -DET )
- W( KBOT-1 ) = ( TR2+RTDISC )*S
- W( KBOT ) = ( TR2-RTDISC )*S
-*
- KS = KBOT - 1
- END IF
- END IF
-*
- IF( KBOT-KS+1.GT.NS ) THEN
-*
-* ==== Sort the shifts (Helps a little) ====
-*
- SORTED = .false.
- DO 50 K = KBOT, KS + 1, -1
- IF( SORTED )
- $ GO TO 60
- SORTED = .true.
- DO 40 I = KS, K - 1
- IF( CABS1( W( I ) ).LT.CABS1( W( I+1 ) ) )
- $ THEN
- SORTED = .false.
- SWAP = W( I )
- W( I ) = W( I+1 )
- W( I+1 ) = SWAP
- END IF
- 40 CONTINUE
- 50 CONTINUE
- 60 CONTINUE
- END IF
- END IF
-*
-* ==== If there are only two shifts, then use
-* . only one. ====
-*
- IF( KBOT-KS+1.EQ.2 ) THEN
- IF( CABS1( W( KBOT )-H( KBOT, KBOT ) ).LT.
- $ CABS1( W( KBOT-1 )-H( KBOT, KBOT ) ) ) THEN
- W( KBOT-1 ) = W( KBOT )
- ELSE
- W( KBOT ) = W( KBOT-1 )
- END IF
- END IF
-*
-* ==== Use up to NS of the the smallest magnatiude
-* . shifts. If there aren't NS shifts available,
-* . then use them all, possibly dropping one to
-* . make the number of shifts even. ====
-*
- NS = MIN( NS, KBOT-KS+1 )
- NS = NS - MOD( NS, 2 )
- KS = KBOT - NS + 1
-*
-* ==== Small-bulge multi-shift QR sweep:
-* . split workspace under the subdiagonal into
-* . - a KDU-by-KDU work array U in the lower
-* . left-hand-corner,
-* . - a KDU-by-at-least-KDU-but-more-is-better
-* . (KDU-by-NHo) horizontal work array WH along
-* . the bottom edge,
-* . - and an at-least-KDU-but-more-is-better-by-KDU
-* . (NVE-by-KDU) vertical work WV arrow along
-* . the left-hand-edge. ====
-*
- KDU = 3*NS - 3
- KU = N - KDU + 1
- KWH = KDU + 1
- NHO = ( N-KDU+1-4 ) - ( KDU+1 ) + 1
- KWV = KDU + 4
- NVE = N - KDU - KWV + 1
-*
-* ==== Small-bulge multi-shift QR sweep ====
-*
- CALL ZLAQR5( WANTT, WANTZ, KACC22, N, KTOP, KBOT, NS,
- $ W( KS ), H, LDH, ILOZ, IHIZ, Z, LDZ, WORK,
- $ 3, H( KU, 1 ), LDH, NVE, H( KWV, 1 ), LDH,
- $ NHO, H( KU, KWH ), LDH )
- END IF
-*
-* ==== Note progress (or the lack of it). ====
-*
- IF( LD.GT.0 ) THEN
- NDFL = 1
- ELSE
- NDFL = NDFL + 1
- END IF
-*
-* ==== End of main loop ====
- 70 CONTINUE
-*
-* ==== Iteration limit exceeded. Set INFO to show where
-* . the problem occurred and exit. ====
-*
- INFO = KBOT
- 80 CONTINUE
- END IF
-*
-* ==== Return the optimal value of LWORK. ====
-*
- WORK( 1 ) = DCMPLX( LWKOPT, 0 )
-*
-* ==== End of ZLAQR0 ====
-*
- END
diff --git a/src/lib/lapack/zlaqr1.f b/src/lib/lapack/zlaqr1.f
deleted file mode 100644
index b8c1c3d4..00000000
--- a/src/lib/lapack/zlaqr1.f
+++ /dev/null
@@ -1,97 +0,0 @@
- SUBROUTINE ZLAQR1( N, H, LDH, S1, S2, V )
-*
-* -- LAPACK auxiliary routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- COMPLEX*16 S1, S2
- INTEGER LDH, N
-* ..
-* .. Array Arguments ..
- COMPLEX*16 H( LDH, * ), V( * )
-* ..
-*
-* Given a 2-by-2 or 3-by-3 matrix H, ZLAQR1 sets v to a
-* scalar multiple of the first column of the product
-*
-* (*) K = (H - s1*I)*(H - s2*I)
-*
-* scaling to avoid overflows and most underflows.
-*
-* This is useful for starting double implicit shift bulges
-* in the QR algorithm.
-*
-*
-* N (input) integer
-* Order of the matrix H. N must be either 2 or 3.
-*
-* H (input) COMPLEX*16 array of dimension (LDH,N)
-* The 2-by-2 or 3-by-3 matrix H in (*).
-*
-* LDH (input) integer
-* The leading dimension of H as declared in
-* the calling procedure. LDH.GE.N
-*
-* S1 (input) COMPLEX*16
-* S2 S1 and S2 are the shifts defining K in (*) above.
-*
-* V (output) COMPLEX*16 array of dimension N
-* A scalar multiple of the first column of the
-* matrix K in (*).
-*
-* ================================================================
-* Based on contributions by
-* Karen Braman and Ralph Byers, Department of Mathematics,
-* University of Kansas, USA
-*
-* ================================================================
-*
-* .. Parameters ..
- COMPLEX*16 ZERO
- PARAMETER ( ZERO = ( 0.0d0, 0.0d0 ) )
- DOUBLE PRECISION RZERO
- PARAMETER ( RZERO = 0.0d0 )
-* ..
-* .. Local Scalars ..
- COMPLEX*16 CDUM
- DOUBLE PRECISION H21S, H31S, S
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC ABS, DBLE, DIMAG
-* ..
-* .. Statement Functions ..
- DOUBLE PRECISION CABS1
-* ..
-* .. Statement Function definitions ..
- CABS1( CDUM ) = ABS( DBLE( CDUM ) ) + ABS( DIMAG( CDUM ) )
-* ..
-* .. Executable Statements ..
- IF( N.EQ.2 ) THEN
- S = CABS1( H( 1, 1 )-S2 ) + CABS1( H( 2, 1 ) )
- IF( S.EQ.RZERO ) THEN
- V( 1 ) = ZERO
- V( 2 ) = ZERO
- ELSE
- H21S = H( 2, 1 ) / S
- V( 1 ) = H21S*H( 1, 2 ) + ( H( 1, 1 )-S1 )*
- $ ( ( H( 1, 1 )-S2 ) / S )
- V( 2 ) = H21S*( H( 1, 1 )+H( 2, 2 )-S1-S2 )
- END IF
- ELSE
- S = CABS1( H( 1, 1 )-S2 ) + CABS1( H( 2, 1 ) ) +
- $ CABS1( H( 3, 1 ) )
- IF( S.EQ.ZERO ) THEN
- V( 1 ) = ZERO
- V( 2 ) = ZERO
- V( 3 ) = ZERO
- ELSE
- H21S = H( 2, 1 ) / S
- H31S = H( 3, 1 ) / S
- V( 1 ) = ( H( 1, 1 )-S1 )*( ( H( 1, 1 )-S2 ) / S ) +
- $ H( 1, 2 )*H21S + H( 1, 3 )*H31S
- V( 2 ) = H21S*( H( 1, 1 )+H( 2, 2 )-S1-S2 ) + H( 2, 3 )*H31S
- V( 3 ) = H31S*( H( 1, 1 )+H( 3, 3 )-S1-S2 ) + H21S*H( 3, 2 )
- END IF
- END IF
- END
diff --git a/src/lib/lapack/zlaqr2.f b/src/lib/lapack/zlaqr2.f
deleted file mode 100644
index 0add51ae..00000000
--- a/src/lib/lapack/zlaqr2.f
+++ /dev/null
@@ -1,437 +0,0 @@
- SUBROUTINE ZLAQR2( WANTT, WANTZ, N, KTOP, KBOT, NW, H, LDH, ILOZ,
- $ IHIZ, Z, LDZ, NS, ND, SH, V, LDV, NH, T, LDT,
- $ NV, WV, LDWV, WORK, LWORK )
-*
-* -- LAPACK auxiliary routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- INTEGER IHIZ, ILOZ, KBOT, KTOP, LDH, LDT, LDV, LDWV,
- $ LDZ, LWORK, N, ND, NH, NS, NV, NW
- LOGICAL WANTT, WANTZ
-* ..
-* .. Array Arguments ..
- COMPLEX*16 H( LDH, * ), SH( * ), T( LDT, * ), V( LDV, * ),
- $ WORK( * ), WV( LDWV, * ), Z( LDZ, * )
-* ..
-*
-* This subroutine is identical to ZLAQR3 except that it avoids
-* recursion by calling ZLAHQR instead of ZLAQR4.
-*
-*
-* ******************************************************************
-* Aggressive early deflation:
-*
-* This subroutine accepts as input an upper Hessenberg matrix
-* H and performs an unitary similarity transformation
-* designed to detect and deflate fully converged eigenvalues from
-* a trailing principal submatrix. On output H has been over-
-* written by a new Hessenberg matrix that is a perturbation of
-* an unitary similarity transformation of H. It is to be
-* hoped that the final version of H has many zero subdiagonal
-* entries.
-*
-* ******************************************************************
-* WANTT (input) LOGICAL
-* If .TRUE., then the Hessenberg matrix H is fully updated
-* so that the triangular Schur factor may be
-* computed (in cooperation with the calling subroutine).
-* If .FALSE., then only enough of H is updated to preserve
-* the eigenvalues.
-*
-* WANTZ (input) LOGICAL
-* If .TRUE., then the unitary matrix Z is updated so
-* so that the unitary Schur factor may be computed
-* (in cooperation with the calling subroutine).
-* If .FALSE., then Z is not referenced.
-*
-* N (input) INTEGER
-* The order of the matrix H and (if WANTZ is .TRUE.) the
-* order of the unitary matrix Z.
-*
-* KTOP (input) INTEGER
-* It is assumed that either KTOP = 1 or H(KTOP,KTOP-1)=0.
-* KBOT and KTOP together determine an isolated block
-* along the diagonal of the Hessenberg matrix.
-*
-* KBOT (input) INTEGER
-* It is assumed without a check that either
-* KBOT = N or H(KBOT+1,KBOT)=0. KBOT and KTOP together
-* determine an isolated block along the diagonal of the
-* Hessenberg matrix.
-*
-* NW (input) INTEGER
-* Deflation window size. 1 .LE. NW .LE. (KBOT-KTOP+1).
-*
-* H (input/output) COMPLEX*16 array, dimension (LDH,N)
-* On input the initial N-by-N section of H stores the
-* Hessenberg matrix undergoing aggressive early deflation.
-* On output H has been transformed by a unitary
-* similarity transformation, perturbed, and the returned
-* to Hessenberg form that (it is to be hoped) has some
-* zero subdiagonal entries.
-*
-* LDH (input) integer
-* Leading dimension of H just as declared in the calling
-* subroutine. N .LE. LDH
-*
-* ILOZ (input) INTEGER
-* IHIZ (input) INTEGER
-* Specify the rows of Z to which transformations must be
-* applied if WANTZ is .TRUE.. 1 .LE. ILOZ .LE. IHIZ .LE. N.
-*
-* Z (input/output) COMPLEX*16 array, dimension (LDZ,IHI)
-* IF WANTZ is .TRUE., then on output, the unitary
-* similarity transformation mentioned above has been
-* accumulated into Z(ILOZ:IHIZ,ILO:IHI) from the right.
-* If WANTZ is .FALSE., then Z is unreferenced.
-*
-* LDZ (input) integer
-* The leading dimension of Z just as declared in the
-* calling subroutine. 1 .LE. LDZ.
-*
-* NS (output) integer
-* The number of unconverged (ie approximate) eigenvalues
-* returned in SR and SI that may be used as shifts by the
-* calling subroutine.
-*
-* ND (output) integer
-* The number of converged eigenvalues uncovered by this
-* subroutine.
-*
-* SH (output) COMPLEX*16 array, dimension KBOT
-* On output, approximate eigenvalues that may
-* be used for shifts are stored in SH(KBOT-ND-NS+1)
-* through SR(KBOT-ND). Converged eigenvalues are
-* stored in SH(KBOT-ND+1) through SH(KBOT).
-*
-* V (workspace) COMPLEX*16 array, dimension (LDV,NW)
-* An NW-by-NW work array.
-*
-* LDV (input) integer scalar
-* The leading dimension of V just as declared in the
-* calling subroutine. NW .LE. LDV
-*
-* NH (input) integer scalar
-* The number of columns of T. NH.GE.NW.
-*
-* T (workspace) COMPLEX*16 array, dimension (LDT,NW)
-*
-* LDT (input) integer
-* The leading dimension of T just as declared in the
-* calling subroutine. NW .LE. LDT
-*
-* NV (input) integer
-* The number of rows of work array WV available for
-* workspace. NV.GE.NW.
-*
-* WV (workspace) COMPLEX*16 array, dimension (LDWV,NW)
-*
-* LDWV (input) integer
-* The leading dimension of W just as declared in the
-* calling subroutine. NW .LE. LDV
-*
-* WORK (workspace) COMPLEX*16 array, dimension LWORK.
-* On exit, WORK(1) is set to an estimate of the optimal value
-* of LWORK for the given values of N, NW, KTOP and KBOT.
-*
-* LWORK (input) integer
-* The dimension of the work array WORK. LWORK = 2*NW
-* suffices, but greater efficiency may result from larger
-* values of LWORK.
-*
-* If LWORK = -1, then a workspace query is assumed; ZLAQR2
-* only estimates the optimal workspace size for the given
-* values of N, NW, KTOP and KBOT. The estimate is returned
-* in WORK(1). No error message related to LWORK is issued
-* by XERBLA. Neither H nor Z are accessed.
-*
-* ================================================================
-* Based on contributions by
-* Karen Braman and Ralph Byers, Department of Mathematics,
-* University of Kansas, USA
-*
-* ==================================================================
-* .. Parameters ..
- COMPLEX*16 ZERO, ONE
- PARAMETER ( ZERO = ( 0.0d0, 0.0d0 ),
- $ ONE = ( 1.0d0, 0.0d0 ) )
- DOUBLE PRECISION RZERO, RONE
- PARAMETER ( RZERO = 0.0d0, RONE = 1.0d0 )
-* ..
-* .. Local Scalars ..
- COMPLEX*16 BETA, CDUM, S, TAU
- DOUBLE PRECISION FOO, SAFMAX, SAFMIN, SMLNUM, ULP
- INTEGER I, IFST, ILST, INFO, INFQR, J, JW, KCOL, KLN,
- $ KNT, KROW, KWTOP, LTOP, LWK1, LWK2, LWKOPT
-* ..
-* .. External Functions ..
- DOUBLE PRECISION DLAMCH
- EXTERNAL DLAMCH
-* ..
-* .. External Subroutines ..
- EXTERNAL DLABAD, ZCOPY, ZGEHRD, ZGEMM, ZLACPY, ZLAHQR,
- $ ZLARF, ZLARFG, ZLASET, ZTREXC, ZUNGHR
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC ABS, DBLE, DCMPLX, DCONJG, DIMAG, INT, MAX, MIN
-* ..
-* .. Statement Functions ..
- DOUBLE PRECISION CABS1
-* ..
-* .. Statement Function definitions ..
- CABS1( CDUM ) = ABS( DBLE( CDUM ) ) + ABS( DIMAG( CDUM ) )
-* ..
-* .. Executable Statements ..
-*
-* ==== Estimate optimal workspace. ====
-*
- JW = MIN( NW, KBOT-KTOP+1 )
- IF( JW.LE.2 ) THEN
- LWKOPT = 1
- ELSE
-*
-* ==== Workspace query call to ZGEHRD ====
-*
- CALL ZGEHRD( JW, 1, JW-1, T, LDT, WORK, WORK, -1, INFO )
- LWK1 = INT( WORK( 1 ) )
-*
-* ==== Workspace query call to ZUNGHR ====
-*
- CALL ZUNGHR( JW, 1, JW-1, T, LDT, WORK, WORK, -1, INFO )
- LWK2 = INT( WORK( 1 ) )
-*
-* ==== Optimal workspace ====
-*
- LWKOPT = JW + MAX( LWK1, LWK2 )
- END IF
-*
-* ==== Quick return in case of workspace query. ====
-*
- IF( LWORK.EQ.-1 ) THEN
- WORK( 1 ) = DCMPLX( LWKOPT, 0 )
- RETURN
- END IF
-*
-* ==== Nothing to do ...
-* ... for an empty active block ... ====
- NS = 0
- ND = 0
- IF( KTOP.GT.KBOT )
- $ RETURN
-* ... nor for an empty deflation window. ====
- IF( NW.LT.1 )
- $ RETURN
-*
-* ==== Machine constants ====
-*
- SAFMIN = DLAMCH( 'SAFE MINIMUM' )
- SAFMAX = RONE / SAFMIN
- CALL DLABAD( SAFMIN, SAFMAX )
- ULP = DLAMCH( 'PRECISION' )
- SMLNUM = SAFMIN*( DBLE( N ) / ULP )
-*
-* ==== Setup deflation window ====
-*
- JW = MIN( NW, KBOT-KTOP+1 )
- KWTOP = KBOT - JW + 1
- IF( KWTOP.EQ.KTOP ) THEN
- S = ZERO
- ELSE
- S = H( KWTOP, KWTOP-1 )
- END IF
-*
- IF( KBOT.EQ.KWTOP ) THEN
-*
-* ==== 1-by-1 deflation window: not much to do ====
-*
- SH( KWTOP ) = H( KWTOP, KWTOP )
- NS = 1
- ND = 0
- IF( CABS1( S ).LE.MAX( SMLNUM, ULP*CABS1( H( KWTOP,
- $ KWTOP ) ) ) ) THEN
- NS = 0
- ND = 1
- IF( KWTOP.GT.KTOP )
- $ H( KWTOP, KWTOP-1 ) = ZERO
- END IF
- RETURN
- END IF
-*
-* ==== Convert to spike-triangular form. (In case of a
-* . rare QR failure, this routine continues to do
-* . aggressive early deflation using that part of
-* . the deflation window that converged using INFQR
-* . here and there to keep track.) ====
-*
- CALL ZLACPY( 'U', JW, JW, H( KWTOP, KWTOP ), LDH, T, LDT )
- CALL ZCOPY( JW-1, H( KWTOP+1, KWTOP ), LDH+1, T( 2, 1 ), LDT+1 )
-*
- CALL ZLASET( 'A', JW, JW, ZERO, ONE, V, LDV )
- CALL ZLAHQR( .true., .true., JW, 1, JW, T, LDT, SH( KWTOP ), 1,
- $ JW, V, LDV, INFQR )
-*
-* ==== Deflation detection loop ====
-*
- NS = JW
- ILST = INFQR + 1
- DO 10 KNT = INFQR + 1, JW
-*
-* ==== Small spike tip deflation test ====
-*
- FOO = CABS1( T( NS, NS ) )
- IF( FOO.EQ.RZERO )
- $ FOO = CABS1( S )
- IF( CABS1( S )*CABS1( V( 1, NS ) ).LE.MAX( SMLNUM, ULP*FOO ) )
- $ THEN
-*
-* ==== One more converged eigenvalue ====
-*
- NS = NS - 1
- ELSE
-*
-* ==== One undflatable eigenvalue. Move it up out of the
-* . way. (ZTREXC can not fail in this case.) ====
-*
- IFST = NS
- CALL ZTREXC( 'V', JW, T, LDT, V, LDV, IFST, ILST, INFO )
- ILST = ILST + 1
- END IF
- 10 CONTINUE
-*
-* ==== Return to Hessenberg form ====
-*
- IF( NS.EQ.0 )
- $ S = ZERO
-*
- IF( NS.LT.JW ) THEN
-*
-* ==== sorting the diagonal of T improves accuracy for
-* . graded matrices. ====
-*
- DO 30 I = INFQR + 1, NS
- IFST = I
- DO 20 J = I + 1, NS
- IF( CABS1( T( J, J ) ).GT.CABS1( T( IFST, IFST ) ) )
- $ IFST = J
- 20 CONTINUE
- ILST = I
- IF( IFST.NE.ILST )
- $ CALL ZTREXC( 'V', JW, T, LDT, V, LDV, IFST, ILST, INFO )
- 30 CONTINUE
- END IF
-*
-* ==== Restore shift/eigenvalue array from T ====
-*
- DO 40 I = INFQR + 1, JW
- SH( KWTOP+I-1 ) = T( I, I )
- 40 CONTINUE
-*
-*
- IF( NS.LT.JW .OR. S.EQ.ZERO ) THEN
- IF( NS.GT.1 .AND. S.NE.ZERO ) THEN
-*
-* ==== Reflect spike back into lower triangle ====
-*
- CALL ZCOPY( NS, V, LDV, WORK, 1 )
- DO 50 I = 1, NS
- WORK( I ) = DCONJG( WORK( I ) )
- 50 CONTINUE
- BETA = WORK( 1 )
- CALL ZLARFG( NS, BETA, WORK( 2 ), 1, TAU )
- WORK( 1 ) = ONE
-*
- CALL ZLASET( 'L', JW-2, JW-2, ZERO, ZERO, T( 3, 1 ), LDT )
-*
- CALL ZLARF( 'L', NS, JW, WORK, 1, DCONJG( TAU ), T, LDT,
- $ WORK( JW+1 ) )
- CALL ZLARF( 'R', NS, NS, WORK, 1, TAU, T, LDT,
- $ WORK( JW+1 ) )
- CALL ZLARF( 'R', JW, NS, WORK, 1, TAU, V, LDV,
- $ WORK( JW+1 ) )
-*
- CALL ZGEHRD( JW, 1, NS, T, LDT, WORK, WORK( JW+1 ),
- $ LWORK-JW, INFO )
- END IF
-*
-* ==== Copy updated reduced window into place ====
-*
- IF( KWTOP.GT.1 )
- $ H( KWTOP, KWTOP-1 ) = S*DCONJG( V( 1, 1 ) )
- CALL ZLACPY( 'U', JW, JW, T, LDT, H( KWTOP, KWTOP ), LDH )
- CALL ZCOPY( JW-1, T( 2, 1 ), LDT+1, H( KWTOP+1, KWTOP ),
- $ LDH+1 )
-*
-* ==== Accumulate orthogonal matrix in order update
-* . H and Z, if requested. (A modified version
-* . of ZUNGHR that accumulates block Householder
-* . transformations into V directly might be
-* . marginally more efficient than the following.) ====
-*
- IF( NS.GT.1 .AND. S.NE.ZERO ) THEN
- CALL ZUNGHR( JW, 1, NS, T, LDT, WORK, WORK( JW+1 ),
- $ LWORK-JW, INFO )
- CALL ZGEMM( 'N', 'N', JW, NS, NS, ONE, V, LDV, T, LDT, ZERO,
- $ WV, LDWV )
- CALL ZLACPY( 'A', JW, NS, WV, LDWV, V, LDV )
- END IF
-*
-* ==== Update vertical slab in H ====
-*
- IF( WANTT ) THEN
- LTOP = 1
- ELSE
- LTOP = KTOP
- END IF
- DO 60 KROW = LTOP, KWTOP - 1, NV
- KLN = MIN( NV, KWTOP-KROW )
- CALL ZGEMM( 'N', 'N', KLN, JW, JW, ONE, H( KROW, KWTOP ),
- $ LDH, V, LDV, ZERO, WV, LDWV )
- CALL ZLACPY( 'A', KLN, JW, WV, LDWV, H( KROW, KWTOP ), LDH )
- 60 CONTINUE
-*
-* ==== Update horizontal slab in H ====
-*
- IF( WANTT ) THEN
- DO 70 KCOL = KBOT + 1, N, NH
- KLN = MIN( NH, N-KCOL+1 )
- CALL ZGEMM( 'C', 'N', JW, KLN, JW, ONE, V, LDV,
- $ H( KWTOP, KCOL ), LDH, ZERO, T, LDT )
- CALL ZLACPY( 'A', JW, KLN, T, LDT, H( KWTOP, KCOL ),
- $ LDH )
- 70 CONTINUE
- END IF
-*
-* ==== Update vertical slab in Z ====
-*
- IF( WANTZ ) THEN
- DO 80 KROW = ILOZ, IHIZ, NV
- KLN = MIN( NV, IHIZ-KROW+1 )
- CALL ZGEMM( 'N', 'N', KLN, JW, JW, ONE, Z( KROW, KWTOP ),
- $ LDZ, V, LDV, ZERO, WV, LDWV )
- CALL ZLACPY( 'A', KLN, JW, WV, LDWV, Z( KROW, KWTOP ),
- $ LDZ )
- 80 CONTINUE
- END IF
- END IF
-*
-* ==== Return the number of deflations ... ====
-*
- ND = JW - NS
-*
-* ==== ... and the number of shifts. (Subtracting
-* . INFQR from the spike length takes care
-* . of the case of a rare QR failure while
-* . calculating eigenvalues of the deflation
-* . window.) ====
-*
- NS = NS - INFQR
-*
-* ==== Return optimal workspace. ====
-*
- WORK( 1 ) = DCMPLX( LWKOPT, 0 )
-*
-* ==== End of ZLAQR2 ====
-*
- END
diff --git a/src/lib/lapack/zlaqr3.f b/src/lib/lapack/zlaqr3.f
deleted file mode 100644
index e9bf393a..00000000
--- a/src/lib/lapack/zlaqr3.f
+++ /dev/null
@@ -1,448 +0,0 @@
- SUBROUTINE ZLAQR3( WANTT, WANTZ, N, KTOP, KBOT, NW, H, LDH, ILOZ,
- $ IHIZ, Z, LDZ, NS, ND, SH, V, LDV, NH, T, LDT,
- $ NV, WV, LDWV, WORK, LWORK )
-*
-* -- LAPACK auxiliary routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- INTEGER IHIZ, ILOZ, KBOT, KTOP, LDH, LDT, LDV, LDWV,
- $ LDZ, LWORK, N, ND, NH, NS, NV, NW
- LOGICAL WANTT, WANTZ
-* ..
-* .. Array Arguments ..
- COMPLEX*16 H( LDH, * ), SH( * ), T( LDT, * ), V( LDV, * ),
- $ WORK( * ), WV( LDWV, * ), Z( LDZ, * )
-* ..
-*
-* ******************************************************************
-* Aggressive early deflation:
-*
-* This subroutine accepts as input an upper Hessenberg matrix
-* H and performs an unitary similarity transformation
-* designed to detect and deflate fully converged eigenvalues from
-* a trailing principal submatrix. On output H has been over-
-* written by a new Hessenberg matrix that is a perturbation of
-* an unitary similarity transformation of H. It is to be
-* hoped that the final version of H has many zero subdiagonal
-* entries.
-*
-* ******************************************************************
-* WANTT (input) LOGICAL
-* If .TRUE., then the Hessenberg matrix H is fully updated
-* so that the triangular Schur factor may be
-* computed (in cooperation with the calling subroutine).
-* If .FALSE., then only enough of H is updated to preserve
-* the eigenvalues.
-*
-* WANTZ (input) LOGICAL
-* If .TRUE., then the unitary matrix Z is updated so
-* so that the unitary Schur factor may be computed
-* (in cooperation with the calling subroutine).
-* If .FALSE., then Z is not referenced.
-*
-* N (input) INTEGER
-* The order of the matrix H and (if WANTZ is .TRUE.) the
-* order of the unitary matrix Z.
-*
-* KTOP (input) INTEGER
-* It is assumed that either KTOP = 1 or H(KTOP,KTOP-1)=0.
-* KBOT and KTOP together determine an isolated block
-* along the diagonal of the Hessenberg matrix.
-*
-* KBOT (input) INTEGER
-* It is assumed without a check that either
-* KBOT = N or H(KBOT+1,KBOT)=0. KBOT and KTOP together
-* determine an isolated block along the diagonal of the
-* Hessenberg matrix.
-*
-* NW (input) INTEGER
-* Deflation window size. 1 .LE. NW .LE. (KBOT-KTOP+1).
-*
-* H (input/output) COMPLEX*16 array, dimension (LDH,N)
-* On input the initial N-by-N section of H stores the
-* Hessenberg matrix undergoing aggressive early deflation.
-* On output H has been transformed by a unitary
-* similarity transformation, perturbed, and the returned
-* to Hessenberg form that (it is to be hoped) has some
-* zero subdiagonal entries.
-*
-* LDH (input) integer
-* Leading dimension of H just as declared in the calling
-* subroutine. N .LE. LDH
-*
-* ILOZ (input) INTEGER
-* IHIZ (input) INTEGER
-* Specify the rows of Z to which transformations must be
-* applied if WANTZ is .TRUE.. 1 .LE. ILOZ .LE. IHIZ .LE. N.
-*
-* Z (input/output) COMPLEX*16 array, dimension (LDZ,IHI)
-* IF WANTZ is .TRUE., then on output, the unitary
-* similarity transformation mentioned above has been
-* accumulated into Z(ILOZ:IHIZ,ILO:IHI) from the right.
-* If WANTZ is .FALSE., then Z is unreferenced.
-*
-* LDZ (input) integer
-* The leading dimension of Z just as declared in the
-* calling subroutine. 1 .LE. LDZ.
-*
-* NS (output) integer
-* The number of unconverged (ie approximate) eigenvalues
-* returned in SR and SI that may be used as shifts by the
-* calling subroutine.
-*
-* ND (output) integer
-* The number of converged eigenvalues uncovered by this
-* subroutine.
-*
-* SH (output) COMPLEX*16 array, dimension KBOT
-* On output, approximate eigenvalues that may
-* be used for shifts are stored in SH(KBOT-ND-NS+1)
-* through SR(KBOT-ND). Converged eigenvalues are
-* stored in SH(KBOT-ND+1) through SH(KBOT).
-*
-* V (workspace) COMPLEX*16 array, dimension (LDV,NW)
-* An NW-by-NW work array.
-*
-* LDV (input) integer scalar
-* The leading dimension of V just as declared in the
-* calling subroutine. NW .LE. LDV
-*
-* NH (input) integer scalar
-* The number of columns of T. NH.GE.NW.
-*
-* T (workspace) COMPLEX*16 array, dimension (LDT,NW)
-*
-* LDT (input) integer
-* The leading dimension of T just as declared in the
-* calling subroutine. NW .LE. LDT
-*
-* NV (input) integer
-* The number of rows of work array WV available for
-* workspace. NV.GE.NW.
-*
-* WV (workspace) COMPLEX*16 array, dimension (LDWV,NW)
-*
-* LDWV (input) integer
-* The leading dimension of W just as declared in the
-* calling subroutine. NW .LE. LDV
-*
-* WORK (workspace) COMPLEX*16 array, dimension LWORK.
-* On exit, WORK(1) is set to an estimate of the optimal value
-* of LWORK for the given values of N, NW, KTOP and KBOT.
-*
-* LWORK (input) integer
-* The dimension of the work array WORK. LWORK = 2*NW
-* suffices, but greater efficiency may result from larger
-* values of LWORK.
-*
-* If LWORK = -1, then a workspace query is assumed; ZLAQR3
-* only estimates the optimal workspace size for the given
-* values of N, NW, KTOP and KBOT. The estimate is returned
-* in WORK(1). No error message related to LWORK is issued
-* by XERBLA. Neither H nor Z are accessed.
-*
-* ================================================================
-* Based on contributions by
-* Karen Braman and Ralph Byers, Department of Mathematics,
-* University of Kansas, USA
-*
-* ==================================================================
-* .. Parameters ..
- COMPLEX*16 ZERO, ONE
- PARAMETER ( ZERO = ( 0.0d0, 0.0d0 ),
- $ ONE = ( 1.0d0, 0.0d0 ) )
- DOUBLE PRECISION RZERO, RONE
- PARAMETER ( RZERO = 0.0d0, RONE = 1.0d0 )
-* ..
-* .. Local Scalars ..
- COMPLEX*16 BETA, CDUM, S, TAU
- DOUBLE PRECISION FOO, SAFMAX, SAFMIN, SMLNUM, ULP
- INTEGER I, IFST, ILST, INFO, INFQR, J, JW, KCOL, KLN,
- $ KNT, KROW, KWTOP, LTOP, LWK1, LWK2, LWK3,
- $ LWKOPT, NMIN
-* ..
-* .. External Functions ..
- DOUBLE PRECISION DLAMCH
- INTEGER ILAENV
- EXTERNAL DLAMCH, ILAENV
-* ..
-* .. External Subroutines ..
- EXTERNAL DLABAD, ZCOPY, ZGEHRD, ZGEMM, ZLACPY, ZLAHQR,
- $ ZLAQR4, ZLARF, ZLARFG, ZLASET, ZTREXC, ZUNGHR
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC ABS, DBLE, DCMPLX, DCONJG, DIMAG, INT, MAX, MIN
-* ..
-* .. Statement Functions ..
- DOUBLE PRECISION CABS1
-* ..
-* .. Statement Function definitions ..
- CABS1( CDUM ) = ABS( DBLE( CDUM ) ) + ABS( DIMAG( CDUM ) )
-* ..
-* .. Executable Statements ..
-*
-* ==== Estimate optimal workspace. ====
-*
- JW = MIN( NW, KBOT-KTOP+1 )
- IF( JW.LE.2 ) THEN
- LWKOPT = 1
- ELSE
-*
-* ==== Workspace query call to ZGEHRD ====
-*
- CALL ZGEHRD( JW, 1, JW-1, T, LDT, WORK, WORK, -1, INFO )
- LWK1 = INT( WORK( 1 ) )
-*
-* ==== Workspace query call to ZUNGHR ====
-*
- CALL ZUNGHR( JW, 1, JW-1, T, LDT, WORK, WORK, -1, INFO )
- LWK2 = INT( WORK( 1 ) )
-*
-* ==== Workspace query call to ZLAQR4 ====
-*
- CALL ZLAQR4( .true., .true., JW, 1, JW, T, LDT, SH, 1, JW, V,
- $ LDV, WORK, -1, INFQR )
- LWK3 = INT( WORK( 1 ) )
-*
-* ==== Optimal workspace ====
-*
- LWKOPT = MAX( JW+MAX( LWK1, LWK2 ), LWK3 )
- END IF
-*
-* ==== Quick return in case of workspace query. ====
-*
- IF( LWORK.EQ.-1 ) THEN
- WORK( 1 ) = DCMPLX( LWKOPT, 0 )
- RETURN
- END IF
-*
-* ==== Nothing to do ...
-* ... for an empty active block ... ====
- NS = 0
- ND = 0
- IF( KTOP.GT.KBOT )
- $ RETURN
-* ... nor for an empty deflation window. ====
- IF( NW.LT.1 )
- $ RETURN
-*
-* ==== Machine constants ====
-*
- SAFMIN = DLAMCH( 'SAFE MINIMUM' )
- SAFMAX = RONE / SAFMIN
- CALL DLABAD( SAFMIN, SAFMAX )
- ULP = DLAMCH( 'PRECISION' )
- SMLNUM = SAFMIN*( DBLE( N ) / ULP )
-*
-* ==== Setup deflation window ====
-*
- JW = MIN( NW, KBOT-KTOP+1 )
- KWTOP = KBOT - JW + 1
- IF( KWTOP.EQ.KTOP ) THEN
- S = ZERO
- ELSE
- S = H( KWTOP, KWTOP-1 )
- END IF
-*
- IF( KBOT.EQ.KWTOP ) THEN
-*
-* ==== 1-by-1 deflation window: not much to do ====
-*
- SH( KWTOP ) = H( KWTOP, KWTOP )
- NS = 1
- ND = 0
- IF( CABS1( S ).LE.MAX( SMLNUM, ULP*CABS1( H( KWTOP,
- $ KWTOP ) ) ) ) THEN
-
- NS = 0
- ND = 1
- IF( KWTOP.GT.KTOP )
- $ H( KWTOP, KWTOP-1 ) = ZERO
- END IF
- RETURN
- END IF
-*
-* ==== Convert to spike-triangular form. (In case of a
-* . rare QR failure, this routine continues to do
-* . aggressive early deflation using that part of
-* . the deflation window that converged using INFQR
-* . here and there to keep track.) ====
-*
- CALL ZLACPY( 'U', JW, JW, H( KWTOP, KWTOP ), LDH, T, LDT )
- CALL ZCOPY( JW-1, H( KWTOP+1, KWTOP ), LDH+1, T( 2, 1 ), LDT+1 )
-*
- CALL ZLASET( 'A', JW, JW, ZERO, ONE, V, LDV )
- NMIN = ILAENV( 12, 'ZLAQR3', 'SV', JW, 1, JW, LWORK )
- IF( JW.GT.NMIN ) THEN
- CALL ZLAQR4( .true., .true., JW, 1, JW, T, LDT, SH( KWTOP ), 1,
- $ JW, V, LDV, WORK, LWORK, INFQR )
- ELSE
- CALL ZLAHQR( .true., .true., JW, 1, JW, T, LDT, SH( KWTOP ), 1,
- $ JW, V, LDV, INFQR )
- END IF
-*
-* ==== Deflation detection loop ====
-*
- NS = JW
- ILST = INFQR + 1
- DO 10 KNT = INFQR + 1, JW
-*
-* ==== Small spike tip deflation test ====
-*
- FOO = CABS1( T( NS, NS ) )
- IF( FOO.EQ.RZERO )
- $ FOO = CABS1( S )
- IF( CABS1( S )*CABS1( V( 1, NS ) ).LE.MAX( SMLNUM, ULP*FOO ) )
- $ THEN
-*
-* ==== One more converged eigenvalue ====
-*
- NS = NS - 1
- ELSE
-*
-* ==== One undflatable eigenvalue. Move it up out of the
-* . way. (ZTREXC can not fail in this case.) ====
-*
- IFST = NS
- CALL ZTREXC( 'V', JW, T, LDT, V, LDV, IFST, ILST, INFO )
- ILST = ILST + 1
- END IF
- 10 CONTINUE
-*
-* ==== Return to Hessenberg form ====
-*
- IF( NS.EQ.0 )
- $ S = ZERO
-*
- IF( NS.LT.JW ) THEN
-*
-* ==== sorting the diagonal of T improves accuracy for
-* . graded matrices. ====
-*
- DO 30 I = INFQR + 1, NS
- IFST = I
- DO 20 J = I + 1, NS
- IF( CABS1( T( J, J ) ).GT.CABS1( T( IFST, IFST ) ) )
- $ IFST = J
- 20 CONTINUE
- ILST = I
- IF( IFST.NE.ILST )
- $ CALL ZTREXC( 'V', JW, T, LDT, V, LDV, IFST, ILST, INFO )
- 30 CONTINUE
- END IF
-*
-* ==== Restore shift/eigenvalue array from T ====
-*
- DO 40 I = INFQR + 1, JW
- SH( KWTOP+I-1 ) = T( I, I )
- 40 CONTINUE
-*
-*
- IF( NS.LT.JW .OR. S.EQ.ZERO ) THEN
- IF( NS.GT.1 .AND. S.NE.ZERO ) THEN
-*
-* ==== Reflect spike back into lower triangle ====
-*
- CALL ZCOPY( NS, V, LDV, WORK, 1 )
- DO 50 I = 1, NS
- WORK( I ) = DCONJG( WORK( I ) )
- 50 CONTINUE
- BETA = WORK( 1 )
- CALL ZLARFG( NS, BETA, WORK( 2 ), 1, TAU )
- WORK( 1 ) = ONE
-*
- CALL ZLASET( 'L', JW-2, JW-2, ZERO, ZERO, T( 3, 1 ), LDT )
-*
- CALL ZLARF( 'L', NS, JW, WORK, 1, DCONJG( TAU ), T, LDT,
- $ WORK( JW+1 ) )
- CALL ZLARF( 'R', NS, NS, WORK, 1, TAU, T, LDT,
- $ WORK( JW+1 ) )
- CALL ZLARF( 'R', JW, NS, WORK, 1, TAU, V, LDV,
- $ WORK( JW+1 ) )
-*
- CALL ZGEHRD( JW, 1, NS, T, LDT, WORK, WORK( JW+1 ),
- $ LWORK-JW, INFO )
- END IF
-*
-* ==== Copy updated reduced window into place ====
-*
- IF( KWTOP.GT.1 )
- $ H( KWTOP, KWTOP-1 ) = S*DCONJG( V( 1, 1 ) )
- CALL ZLACPY( 'U', JW, JW, T, LDT, H( KWTOP, KWTOP ), LDH )
- CALL ZCOPY( JW-1, T( 2, 1 ), LDT+1, H( KWTOP+1, KWTOP ),
- $ LDH+1 )
-*
-* ==== Accumulate orthogonal matrix in order update
-* . H and Z, if requested. (A modified version
-* . of ZUNGHR that accumulates block Householder
-* . transformations into V directly might be
-* . marginally more efficient than the following.) ====
-*
- IF( NS.GT.1 .AND. S.NE.ZERO ) THEN
- CALL ZUNGHR( JW, 1, NS, T, LDT, WORK, WORK( JW+1 ),
- $ LWORK-JW, INFO )
- CALL ZGEMM( 'N', 'N', JW, NS, NS, ONE, V, LDV, T, LDT, ZERO,
- $ WV, LDWV )
- CALL ZLACPY( 'A', JW, NS, WV, LDWV, V, LDV )
- END IF
-*
-* ==== Update vertical slab in H ====
-*
- IF( WANTT ) THEN
- LTOP = 1
- ELSE
- LTOP = KTOP
- END IF
- DO 60 KROW = LTOP, KWTOP - 1, NV
- KLN = MIN( NV, KWTOP-KROW )
- CALL ZGEMM( 'N', 'N', KLN, JW, JW, ONE, H( KROW, KWTOP ),
- $ LDH, V, LDV, ZERO, WV, LDWV )
- CALL ZLACPY( 'A', KLN, JW, WV, LDWV, H( KROW, KWTOP ), LDH )
- 60 CONTINUE
-*
-* ==== Update horizontal slab in H ====
-*
- IF( WANTT ) THEN
- DO 70 KCOL = KBOT + 1, N, NH
- KLN = MIN( NH, N-KCOL+1 )
- CALL ZGEMM( 'C', 'N', JW, KLN, JW, ONE, V, LDV,
- $ H( KWTOP, KCOL ), LDH, ZERO, T, LDT )
- CALL ZLACPY( 'A', JW, KLN, T, LDT, H( KWTOP, KCOL ),
- $ LDH )
- 70 CONTINUE
- END IF
-*
-* ==== Update vertical slab in Z ====
-*
- IF( WANTZ ) THEN
- DO 80 KROW = ILOZ, IHIZ, NV
- KLN = MIN( NV, IHIZ-KROW+1 )
- CALL ZGEMM( 'N', 'N', KLN, JW, JW, ONE, Z( KROW, KWTOP ),
- $ LDZ, V, LDV, ZERO, WV, LDWV )
- CALL ZLACPY( 'A', KLN, JW, WV, LDWV, Z( KROW, KWTOP ),
- $ LDZ )
- 80 CONTINUE
- END IF
- END IF
-*
-* ==== Return the number of deflations ... ====
-*
- ND = JW - NS
-*
-* ==== ... and the number of shifts. (Subtracting
-* . INFQR from the spike length takes care
-* . of the case of a rare QR failure while
-* . calculating eigenvalues of the deflation
-* . window.) ====
-*
- NS = NS - INFQR
-*
-* ==== Return optimal workspace. ====
-*
- WORK( 1 ) = DCMPLX( LWKOPT, 0 )
-*
-* ==== End of ZLAQR3 ====
-*
- END
diff --git a/src/lib/lapack/zlaqr4.f b/src/lib/lapack/zlaqr4.f
deleted file mode 100644
index eef7f00a..00000000
--- a/src/lib/lapack/zlaqr4.f
+++ /dev/null
@@ -1,602 +0,0 @@
- SUBROUTINE ZLAQR4( WANTT, WANTZ, N, ILO, IHI, H, LDH, W, ILOZ,
- $ IHIZ, Z, LDZ, WORK, LWORK, INFO )
-*
-* -- LAPACK auxiliary routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- INTEGER IHI, IHIZ, ILO, ILOZ, INFO, LDH, LDZ, LWORK, N
- LOGICAL WANTT, WANTZ
-* ..
-* .. Array Arguments ..
- COMPLEX*16 H( LDH, * ), W( * ), WORK( * ), Z( LDZ, * )
-* ..
-*
-* This subroutine implements one level of recursion for ZLAQR0.
-* It is a complete implementation of the small bulge multi-shift
-* QR algorithm. It may be called by ZLAQR0 and, for large enough
-* deflation window size, it may be called by ZLAQR3. This
-* subroutine is identical to ZLAQR0 except that it calls ZLAQR2
-* instead of ZLAQR3.
-*
-* Purpose
-* =======
-*
-* ZLAQR4 computes the eigenvalues of a Hessenberg matrix H
-* and, optionally, the matrices T and Z from the Schur decomposition
-* H = Z T Z**H, where T is an upper triangular matrix (the
-* Schur form), and Z is the unitary matrix of Schur vectors.
-*
-* Optionally Z may be postmultiplied into an input unitary
-* matrix Q so that this routine can give the Schur factorization
-* of a matrix A which has been reduced to the Hessenberg form H
-* by the unitary matrix Q: A = Q*H*Q**H = (QZ)*H*(QZ)**H.
-*
-* Arguments
-* =========
-*
-* WANTT (input) LOGICAL
-* = .TRUE. : the full Schur form T is required;
-* = .FALSE.: only eigenvalues are required.
-*
-* WANTZ (input) LOGICAL
-* = .TRUE. : the matrix of Schur vectors Z is required;
-* = .FALSE.: Schur vectors are not required.
-*
-* N (input) INTEGER
-* The order of the matrix H. N .GE. 0.
-*
-* ILO (input) INTEGER
-* IHI (input) INTEGER
-* It is assumed that H is already upper triangular in rows
-* and columns 1:ILO-1 and IHI+1:N and, if ILO.GT.1,
-* H(ILO,ILO-1) is zero. ILO and IHI are normally set by a
-* previous call to ZGEBAL, and then passed to ZGEHRD when the
-* matrix output by ZGEBAL is reduced to Hessenberg form.
-* Otherwise, ILO and IHI should be set to 1 and N,
-* respectively. If N.GT.0, then 1.LE.ILO.LE.IHI.LE.N.
-* If N = 0, then ILO = 1 and IHI = 0.
-*
-* H (input/output) COMPLEX*16 array, dimension (LDH,N)
-* On entry, the upper Hessenberg matrix H.
-* On exit, if INFO = 0 and WANTT is .TRUE., then H
-* contains the upper triangular matrix T from the Schur
-* decomposition (the Schur form). If INFO = 0 and WANT is
-* .FALSE., then the contents of H are unspecified on exit.
-* (The output value of H when INFO.GT.0 is given under the
-* description of INFO below.)
-*
-* This subroutine may explicitly set H(i,j) = 0 for i.GT.j and
-* j = 1, 2, ... ILO-1 or j = IHI+1, IHI+2, ... N.
-*
-* LDH (input) INTEGER
-* The leading dimension of the array H. LDH .GE. max(1,N).
-*
-* W (output) COMPLEX*16 array, dimension (N)
-* The computed eigenvalues of H(ILO:IHI,ILO:IHI) are stored
-* in W(ILO:IHI). If WANTT is .TRUE., then the eigenvalues are
-* stored in the same order as on the diagonal of the Schur
-* form returned in H, with W(i) = H(i,i).
-*
-* Z (input/output) COMPLEX*16 array, dimension (LDZ,IHI)
-* If WANTZ is .FALSE., then Z is not referenced.
-* If WANTZ is .TRUE., then Z(ILO:IHI,ILOZ:IHIZ) is
-* replaced by Z(ILO:IHI,ILOZ:IHIZ)*U where U is the
-* orthogonal Schur factor of H(ILO:IHI,ILO:IHI).
-* (The output value of Z when INFO.GT.0 is given under
-* the description of INFO below.)
-*
-* LDZ (input) INTEGER
-* The leading dimension of the array Z. if WANTZ is .TRUE.
-* then LDZ.GE.MAX(1,IHIZ). Otherwize, LDZ.GE.1.
-*
-* WORK (workspace/output) COMPLEX*16 array, dimension LWORK
-* On exit, if LWORK = -1, WORK(1) returns an estimate of
-* the optimal value for LWORK.
-*
-* LWORK (input) INTEGER
-* The dimension of the array WORK. LWORK .GE. max(1,N)
-* is sufficient, but LWORK typically as large as 6*N may
-* be required for optimal performance. A workspace query
-* to determine the optimal workspace size is recommended.
-*
-* If LWORK = -1, then ZLAQR4 does a workspace query.
-* In this case, ZLAQR4 checks the input parameters and
-* estimates the optimal workspace size for the given
-* values of N, ILO and IHI. The estimate is returned
-* in WORK(1). No error message related to LWORK is
-* issued by XERBLA. Neither H nor Z are accessed.
-*
-*
-* INFO (output) INTEGER
-* = 0: successful exit
-* .GT. 0: if INFO = i, ZLAQR4 failed to compute all of
-* the eigenvalues. Elements 1:ilo-1 and i+1:n of WR
-* and WI contain those eigenvalues which have been
-* successfully computed. (Failures are rare.)
-*
-* If INFO .GT. 0 and WANT is .FALSE., then on exit,
-* the remaining unconverged eigenvalues are the eigen-
-* values of the upper Hessenberg matrix rows and
-* columns ILO through INFO of the final, output
-* value of H.
-*
-* If INFO .GT. 0 and WANTT is .TRUE., then on exit
-*
-* (*) (initial value of H)*U = U*(final value of H)
-*
-* where U is a unitary matrix. The final
-* value of H is upper Hessenberg and triangular in
-* rows and columns INFO+1 through IHI.
-*
-* If INFO .GT. 0 and WANTZ is .TRUE., then on exit
-*
-* (final value of Z(ILO:IHI,ILOZ:IHIZ)
-* = (initial value of Z(ILO:IHI,ILOZ:IHIZ)*U
-*
-* where U is the unitary matrix in (*) (regard-
-* less of the value of WANTT.)
-*
-* If INFO .GT. 0 and WANTZ is .FALSE., then Z is not
-* accessed.
-*
-* ================================================================
-* Based on contributions by
-* Karen Braman and Ralph Byers, Department of Mathematics,
-* University of Kansas, USA
-*
-* ================================================================
-* References:
-* K. Braman, R. Byers and R. Mathias, The Multi-Shift QR
-* Algorithm Part I: Maintaining Well Focused Shifts, and Level 3
-* Performance, SIAM Journal of Matrix Analysis, volume 23, pages
-* 929--947, 2002.
-*
-* K. Braman, R. Byers and R. Mathias, The Multi-Shift QR
-* Algorithm Part II: Aggressive Early Deflation, SIAM Journal
-* of Matrix Analysis, volume 23, pages 948--973, 2002.
-*
-* ================================================================
-* .. Parameters ..
-*
-* ==== Matrices of order NTINY or smaller must be processed by
-* . ZLAHQR because of insufficient subdiagonal scratch space.
-* . (This is a hard limit.) ====
-*
-* ==== Exceptional deflation windows: try to cure rare
-* . slow convergence by increasing the size of the
-* . deflation window after KEXNW iterations. =====
-*
-* ==== Exceptional shifts: try to cure rare slow convergence
-* . with ad-hoc exceptional shifts every KEXSH iterations.
-* . The constants WILK1 and WILK2 are used to form the
-* . exceptional shifts. ====
-*
- INTEGER NTINY
- PARAMETER ( NTINY = 11 )
- INTEGER KEXNW, KEXSH
- PARAMETER ( KEXNW = 5, KEXSH = 6 )
- DOUBLE PRECISION WILK1
- PARAMETER ( WILK1 = 0.75d0 )
- COMPLEX*16 ZERO, ONE
- PARAMETER ( ZERO = ( 0.0d0, 0.0d0 ),
- $ ONE = ( 1.0d0, 0.0d0 ) )
- DOUBLE PRECISION TWO
- PARAMETER ( TWO = 2.0d0 )
-* ..
-* .. Local Scalars ..
- COMPLEX*16 AA, BB, CC, CDUM, DD, DET, RTDISC, SWAP, TR2
- DOUBLE PRECISION S
- INTEGER I, INF, IT, ITMAX, K, KACC22, KBOT, KDU, KS,
- $ KT, KTOP, KU, KV, KWH, KWTOP, KWV, LD, LS,
- $ LWKOPT, NDFL, NH, NHO, NIBBLE, NMIN, NS, NSMAX,
- $ NSR, NVE, NW, NWMAX, NWR
- LOGICAL NWINC, SORTED
- CHARACTER JBCMPZ*2
-* ..
-* .. External Functions ..
- INTEGER ILAENV
- EXTERNAL ILAENV
-* ..
-* .. Local Arrays ..
- COMPLEX*16 ZDUM( 1, 1 )
-* ..
-* .. External Subroutines ..
- EXTERNAL ZLACPY, ZLAHQR, ZLAQR2, ZLAQR5
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC ABS, DBLE, DCMPLX, DIMAG, INT, MAX, MIN, MOD,
- $ SQRT
-* ..
-* .. Statement Functions ..
- DOUBLE PRECISION CABS1
-* ..
-* .. Statement Function definitions ..
- CABS1( CDUM ) = ABS( DBLE( CDUM ) ) + ABS( DIMAG( CDUM ) )
-* ..
-* .. Executable Statements ..
- INFO = 0
-*
-* ==== Quick return for N = 0: nothing to do. ====
-*
- IF( N.EQ.0 ) THEN
- WORK( 1 ) = ONE
- RETURN
- END IF
-*
-* ==== Set up job flags for ILAENV. ====
-*
- IF( WANTT ) THEN
- JBCMPZ( 1: 1 ) = 'S'
- ELSE
- JBCMPZ( 1: 1 ) = 'E'
- END IF
- IF( WANTZ ) THEN
- JBCMPZ( 2: 2 ) = 'V'
- ELSE
- JBCMPZ( 2: 2 ) = 'N'
- END IF
-*
-* ==== Tiny matrices must use ZLAHQR. ====
-*
- IF( N.LE.NTINY ) THEN
-*
-* ==== Estimate optimal workspace. ====
-*
- LWKOPT = 1
- IF( LWORK.NE.-1 )
- $ CALL ZLAHQR( WANTT, WANTZ, N, ILO, IHI, H, LDH, W, ILOZ,
- $ IHIZ, Z, LDZ, INFO )
- ELSE
-*
-* ==== Use small bulge multi-shift QR with aggressive early
-* . deflation on larger-than-tiny matrices. ====
-*
-* ==== Hope for the best. ====
-*
- INFO = 0
-*
-* ==== NWR = recommended deflation window size. At this
-* . point, N .GT. NTINY = 11, so there is enough
-* . subdiagonal workspace for NWR.GE.2 as required.
-* . (In fact, there is enough subdiagonal space for
-* . NWR.GE.3.) ====
-*
- NWR = ILAENV( 13, 'ZLAQR4', JBCMPZ, N, ILO, IHI, LWORK )
- NWR = MAX( 2, NWR )
- NWR = MIN( IHI-ILO+1, ( N-1 ) / 3, NWR )
- NW = NWR
-*
-* ==== NSR = recommended number of simultaneous shifts.
-* . At this point N .GT. NTINY = 11, so there is at
-* . enough subdiagonal workspace for NSR to be even
-* . and greater than or equal to two as required. ====
-*
- NSR = ILAENV( 15, 'ZLAQR4', JBCMPZ, N, ILO, IHI, LWORK )
- NSR = MIN( NSR, ( N+6 ) / 9, IHI-ILO )
- NSR = MAX( 2, NSR-MOD( NSR, 2 ) )
-*
-* ==== Estimate optimal workspace ====
-*
-* ==== Workspace query call to ZLAQR2 ====
-*
- CALL ZLAQR2( WANTT, WANTZ, N, ILO, IHI, NWR+1, H, LDH, ILOZ,
- $ IHIZ, Z, LDZ, LS, LD, W, H, LDH, N, H, LDH, N, H,
- $ LDH, WORK, -1 )
-*
-* ==== Optimal workspace = MAX(ZLAQR5, ZLAQR2) ====
-*
- LWKOPT = MAX( 3*NSR / 2, INT( WORK( 1 ) ) )
-*
-* ==== Quick return in case of workspace query. ====
-*
- IF( LWORK.EQ.-1 ) THEN
- WORK( 1 ) = DCMPLX( LWKOPT, 0 )
- RETURN
- END IF
-*
-* ==== ZLAHQR/ZLAQR0 crossover point ====
-*
- NMIN = ILAENV( 12, 'ZLAQR4', JBCMPZ, N, ILO, IHI, LWORK )
- NMIN = MAX( NTINY, NMIN )
-*
-* ==== Nibble crossover point ====
-*
- NIBBLE = ILAENV( 14, 'ZLAQR4', JBCMPZ, N, ILO, IHI, LWORK )
- NIBBLE = MAX( 0, NIBBLE )
-*
-* ==== Accumulate reflections during ttswp? Use block
-* . 2-by-2 structure during matrix-matrix multiply? ====
-*
- KACC22 = ILAENV( 16, 'ZLAQR4', JBCMPZ, N, ILO, IHI, LWORK )
- KACC22 = MAX( 0, KACC22 )
- KACC22 = MIN( 2, KACC22 )
-*
-* ==== NWMAX = the largest possible deflation window for
-* . which there is sufficient workspace. ====
-*
- NWMAX = MIN( ( N-1 ) / 3, LWORK / 2 )
-*
-* ==== NSMAX = the Largest number of simultaneous shifts
-* . for which there is sufficient workspace. ====
-*
- NSMAX = MIN( ( N+6 ) / 9, 2*LWORK / 3 )
- NSMAX = NSMAX - MOD( NSMAX, 2 )
-*
-* ==== NDFL: an iteration count restarted at deflation. ====
-*
- NDFL = 1
-*
-* ==== ITMAX = iteration limit ====
-*
- ITMAX = MAX( 30, 2*KEXSH )*MAX( 10, ( IHI-ILO+1 ) )
-*
-* ==== Last row and column in the active block ====
-*
- KBOT = IHI
-*
-* ==== Main Loop ====
-*
- DO 70 IT = 1, ITMAX
-*
-* ==== Done when KBOT falls below ILO ====
-*
- IF( KBOT.LT.ILO )
- $ GO TO 80
-*
-* ==== Locate active block ====
-*
- DO 10 K = KBOT, ILO + 1, -1
- IF( H( K, K-1 ).EQ.ZERO )
- $ GO TO 20
- 10 CONTINUE
- K = ILO
- 20 CONTINUE
- KTOP = K
-*
-* ==== Select deflation window size ====
-*
- NH = KBOT - KTOP + 1
- IF( NDFL.LT.KEXNW .OR. NH.LT.NW ) THEN
-*
-* ==== Typical deflation window. If possible and
-* . advisable, nibble the entire active block.
-* . If not, use size NWR or NWR+1 depending upon
-* . which has the smaller corresponding subdiagonal
-* . entry (a heuristic). ====
-*
- NWINC = .TRUE.
- IF( NH.LE.MIN( NMIN, NWMAX ) ) THEN
- NW = NH
- ELSE
- NW = MIN( NWR, NH, NWMAX )
- IF( NW.LT.NWMAX ) THEN
- IF( NW.GE.NH-1 ) THEN
- NW = NH
- ELSE
- KWTOP = KBOT - NW + 1
- IF( CABS1( H( KWTOP, KWTOP-1 ) ).GT.
- $ CABS1( H( KWTOP-1, KWTOP-2 ) ) )NW = NW + 1
- END IF
- END IF
- END IF
- ELSE
-*
-* ==== Exceptional deflation window. If there have
-* . been no deflations in KEXNW or more iterations,
-* . then vary the deflation window size. At first,
-* . because, larger windows are, in general, more
-* . powerful than smaller ones, rapidly increase the
-* . window up to the maximum reasonable and possible.
-* . Then maybe try a slightly smaller window. ====
-*
- IF( NWINC .AND. NW.LT.MIN( NWMAX, NH ) ) THEN
- NW = MIN( NWMAX, NH, 2*NW )
- ELSE
- NWINC = .FALSE.
- IF( NW.EQ.NH .AND. NH.GT.2 )
- $ NW = NH - 1
- END IF
- END IF
-*
-* ==== Aggressive early deflation:
-* . split workspace under the subdiagonal into
-* . - an nw-by-nw work array V in the lower
-* . left-hand-corner,
-* . - an NW-by-at-least-NW-but-more-is-better
-* . (NW-by-NHO) horizontal work array along
-* . the bottom edge,
-* . - an at-least-NW-but-more-is-better (NHV-by-NW)
-* . vertical work array along the left-hand-edge.
-* . ====
-*
- KV = N - NW + 1
- KT = NW + 1
- NHO = ( N-NW-1 ) - KT + 1
- KWV = NW + 2
- NVE = ( N-NW ) - KWV + 1
-*
-* ==== Aggressive early deflation ====
-*
- CALL ZLAQR2( WANTT, WANTZ, N, KTOP, KBOT, NW, H, LDH, ILOZ,
- $ IHIZ, Z, LDZ, LS, LD, W, H( KV, 1 ), LDH, NHO,
- $ H( KV, KT ), LDH, NVE, H( KWV, 1 ), LDH, WORK,
- $ LWORK )
-*
-* ==== Adjust KBOT accounting for new deflations. ====
-*
- KBOT = KBOT - LD
-*
-* ==== KS points to the shifts. ====
-*
- KS = KBOT - LS + 1
-*
-* ==== Skip an expensive QR sweep if there is a (partly
-* . heuristic) reason to expect that many eigenvalues
-* . will deflate without it. Here, the QR sweep is
-* . skipped if many eigenvalues have just been deflated
-* . or if the remaining active block is small.
-*
- IF( ( LD.EQ.0 ) .OR. ( ( 100*LD.LE.NW*NIBBLE ) .AND. ( KBOT-
- $ KTOP+1.GT.MIN( NMIN, NWMAX ) ) ) ) THEN
-*
-* ==== NS = nominal number of simultaneous shifts.
-* . This may be lowered (slightly) if ZLAQR2
-* . did not provide that many shifts. ====
-*
- NS = MIN( NSMAX, NSR, MAX( 2, KBOT-KTOP ) )
- NS = NS - MOD( NS, 2 )
-*
-* ==== If there have been no deflations
-* . in a multiple of KEXSH iterations,
-* . then try exceptional shifts.
-* . Otherwise use shifts provided by
-* . ZLAQR2 above or from the eigenvalues
-* . of a trailing principal submatrix. ====
-*
- IF( MOD( NDFL, KEXSH ).EQ.0 ) THEN
- KS = KBOT - NS + 1
- DO 30 I = KBOT, KS + 1, -2
- W( I ) = H( I, I ) + WILK1*CABS1( H( I, I-1 ) )
- W( I-1 ) = W( I )
- 30 CONTINUE
- ELSE
-*
-* ==== Got NS/2 or fewer shifts? Use ZLAHQR
-* . on a trailing principal submatrix to
-* . get more. (Since NS.LE.NSMAX.LE.(N+6)/9,
-* . there is enough space below the subdiagonal
-* . to fit an NS-by-NS scratch array.) ====
-*
- IF( KBOT-KS+1.LE.NS / 2 ) THEN
- KS = KBOT - NS + 1
- KT = N - NS + 1
- CALL ZLACPY( 'A', NS, NS, H( KS, KS ), LDH,
- $ H( KT, 1 ), LDH )
- CALL ZLAHQR( .false., .false., NS, 1, NS,
- $ H( KT, 1 ), LDH, W( KS ), 1, 1, ZDUM,
- $ 1, INF )
- KS = KS + INF
-*
-* ==== In case of a rare QR failure use
-* . eigenvalues of the trailing 2-by-2
-* . principal submatrix. Scale to avoid
-* . overflows, underflows and subnormals.
-* . (The scale factor S can not be zero,
-* . because H(KBOT,KBOT-1) is nonzero.) ====
-*
- IF( KS.GE.KBOT ) THEN
- S = CABS1( H( KBOT-1, KBOT-1 ) ) +
- $ CABS1( H( KBOT, KBOT-1 ) ) +
- $ CABS1( H( KBOT-1, KBOT ) ) +
- $ CABS1( H( KBOT, KBOT ) )
- AA = H( KBOT-1, KBOT-1 ) / S
- CC = H( KBOT, KBOT-1 ) / S
- BB = H( KBOT-1, KBOT ) / S
- DD = H( KBOT, KBOT ) / S
- TR2 = ( AA+DD ) / TWO
- DET = ( AA-TR2 )*( DD-TR2 ) - BB*CC
- RTDISC = SQRT( -DET )
- W( KBOT-1 ) = ( TR2+RTDISC )*S
- W( KBOT ) = ( TR2-RTDISC )*S
-*
- KS = KBOT - 1
- END IF
- END IF
-*
- IF( KBOT-KS+1.GT.NS ) THEN
-*
-* ==== Sort the shifts (Helps a little) ====
-*
- SORTED = .false.
- DO 50 K = KBOT, KS + 1, -1
- IF( SORTED )
- $ GO TO 60
- SORTED = .true.
- DO 40 I = KS, K - 1
- IF( CABS1( W( I ) ).LT.CABS1( W( I+1 ) ) )
- $ THEN
- SORTED = .false.
- SWAP = W( I )
- W( I ) = W( I+1 )
- W( I+1 ) = SWAP
- END IF
- 40 CONTINUE
- 50 CONTINUE
- 60 CONTINUE
- END IF
- END IF
-*
-* ==== If there are only two shifts, then use
-* . only one. ====
-*
- IF( KBOT-KS+1.EQ.2 ) THEN
- IF( CABS1( W( KBOT )-H( KBOT, KBOT ) ).LT.
- $ CABS1( W( KBOT-1 )-H( KBOT, KBOT ) ) ) THEN
- W( KBOT-1 ) = W( KBOT )
- ELSE
- W( KBOT ) = W( KBOT-1 )
- END IF
- END IF
-*
-* ==== Use up to NS of the the smallest magnatiude
-* . shifts. If there aren't NS shifts available,
-* . then use them all, possibly dropping one to
-* . make the number of shifts even. ====
-*
- NS = MIN( NS, KBOT-KS+1 )
- NS = NS - MOD( NS, 2 )
- KS = KBOT - NS + 1
-*
-* ==== Small-bulge multi-shift QR sweep:
-* . split workspace under the subdiagonal into
-* . - a KDU-by-KDU work array U in the lower
-* . left-hand-corner,
-* . - a KDU-by-at-least-KDU-but-more-is-better
-* . (KDU-by-NHo) horizontal work array WH along
-* . the bottom edge,
-* . - and an at-least-KDU-but-more-is-better-by-KDU
-* . (NVE-by-KDU) vertical work WV arrow along
-* . the left-hand-edge. ====
-*
- KDU = 3*NS - 3
- KU = N - KDU + 1
- KWH = KDU + 1
- NHO = ( N-KDU+1-4 ) - ( KDU+1 ) + 1
- KWV = KDU + 4
- NVE = N - KDU - KWV + 1
-*
-* ==== Small-bulge multi-shift QR sweep ====
-*
- CALL ZLAQR5( WANTT, WANTZ, KACC22, N, KTOP, KBOT, NS,
- $ W( KS ), H, LDH, ILOZ, IHIZ, Z, LDZ, WORK,
- $ 3, H( KU, 1 ), LDH, NVE, H( KWV, 1 ), LDH,
- $ NHO, H( KU, KWH ), LDH )
- END IF
-*
-* ==== Note progress (or the lack of it). ====
-*
- IF( LD.GT.0 ) THEN
- NDFL = 1
- ELSE
- NDFL = NDFL + 1
- END IF
-*
-* ==== End of main loop ====
- 70 CONTINUE
-*
-* ==== Iteration limit exceeded. Set INFO to show where
-* . the problem occurred and exit. ====
-*
- INFO = KBOT
- 80 CONTINUE
- END IF
-*
-* ==== Return the optimal value of LWORK. ====
-*
- WORK( 1 ) = DCMPLX( LWKOPT, 0 )
-*
-* ==== End of ZLAQR4 ====
-*
- END
diff --git a/src/lib/lapack/zlaqr5.f b/src/lib/lapack/zlaqr5.f
deleted file mode 100644
index fa8de7bb..00000000
--- a/src/lib/lapack/zlaqr5.f
+++ /dev/null
@@ -1,809 +0,0 @@
- SUBROUTINE ZLAQR5( WANTT, WANTZ, KACC22, N, KTOP, KBOT, NSHFTS, S,
- $ H, LDH, ILOZ, IHIZ, Z, LDZ, V, LDV, U, LDU, NV,
- $ WV, LDWV, NH, WH, LDWH )
-*
-* -- LAPACK auxiliary routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- INTEGER IHIZ, ILOZ, KACC22, KBOT, KTOP, LDH, LDU, LDV,
- $ LDWH, LDWV, LDZ, N, NH, NSHFTS, NV
- LOGICAL WANTT, WANTZ
-* ..
-* .. Array Arguments ..
- COMPLEX*16 H( LDH, * ), S( * ), U( LDU, * ), V( LDV, * ),
- $ WH( LDWH, * ), WV( LDWV, * ), Z( LDZ, * )
-* ..
-*
-* This auxiliary subroutine called by ZLAQR0 performs a
-* single small-bulge multi-shift QR sweep.
-*
-* WANTT (input) logical scalar
-* WANTT = .true. if the triangular Schur factor
-* is being computed. WANTT is set to .false. otherwise.
-*
-* WANTZ (input) logical scalar
-* WANTZ = .true. if the unitary Schur factor is being
-* computed. WANTZ is set to .false. otherwise.
-*
-* KACC22 (input) integer with value 0, 1, or 2.
-* Specifies the computation mode of far-from-diagonal
-* orthogonal updates.
-* = 0: ZLAQR5 does not accumulate reflections and does not
-* use matrix-matrix multiply to update far-from-diagonal
-* matrix entries.
-* = 1: ZLAQR5 accumulates reflections and uses matrix-matrix
-* multiply to update the far-from-diagonal matrix entries.
-* = 2: ZLAQR5 accumulates reflections, uses matrix-matrix
-* multiply to update the far-from-diagonal matrix entries,
-* and takes advantage of 2-by-2 block structure during
-* matrix multiplies.
-*
-* N (input) integer scalar
-* N is the order of the Hessenberg matrix H upon which this
-* subroutine operates.
-*
-* KTOP (input) integer scalar
-* KBOT (input) integer scalar
-* These are the first and last rows and columns of an
-* isolated diagonal block upon which the QR sweep is to be
-* applied. It is assumed without a check that
-* either KTOP = 1 or H(KTOP,KTOP-1) = 0
-* and
-* either KBOT = N or H(KBOT+1,KBOT) = 0.
-*
-* NSHFTS (input) integer scalar
-* NSHFTS gives the number of simultaneous shifts. NSHFTS
-* must be positive and even.
-*
-* S (input) COMPLEX*16 array of size (NSHFTS)
-* S contains the shifts of origin that define the multi-
-* shift QR sweep.
-*
-* H (input/output) COMPLEX*16 array of size (LDH,N)
-* On input H contains a Hessenberg matrix. On output a
-* multi-shift QR sweep with shifts SR(J)+i*SI(J) is applied
-* to the isolated diagonal block in rows and columns KTOP
-* through KBOT.
-*
-* LDH (input) integer scalar
-* LDH is the leading dimension of H just as declared in the
-* calling procedure. LDH.GE.MAX(1,N).
-*
-* ILOZ (input) INTEGER
-* IHIZ (input) INTEGER
-* Specify the rows of Z to which transformations must be
-* applied if WANTZ is .TRUE.. 1 .LE. ILOZ .LE. IHIZ .LE. N
-*
-* Z (input/output) COMPLEX*16 array of size (LDZ,IHI)
-* If WANTZ = .TRUE., then the QR Sweep unitary
-* similarity transformation is accumulated into
-* Z(ILOZ:IHIZ,ILO:IHI) from the right.
-* If WANTZ = .FALSE., then Z is unreferenced.
-*
-* LDZ (input) integer scalar
-* LDA is the leading dimension of Z just as declared in
-* the calling procedure. LDZ.GE.N.
-*
-* V (workspace) COMPLEX*16 array of size (LDV,NSHFTS/2)
-*
-* LDV (input) integer scalar
-* LDV is the leading dimension of V as declared in the
-* calling procedure. LDV.GE.3.
-*
-* U (workspace) COMPLEX*16 array of size
-* (LDU,3*NSHFTS-3)
-*
-* LDU (input) integer scalar
-* LDU is the leading dimension of U just as declared in the
-* in the calling subroutine. LDU.GE.3*NSHFTS-3.
-*
-* NH (input) integer scalar
-* NH is the number of columns in array WH available for
-* workspace. NH.GE.1.
-*
-* WH (workspace) COMPLEX*16 array of size (LDWH,NH)
-*
-* LDWH (input) integer scalar
-* Leading dimension of WH just as declared in the
-* calling procedure. LDWH.GE.3*NSHFTS-3.
-*
-* NV (input) integer scalar
-* NV is the number of rows in WV agailable for workspace.
-* NV.GE.1.
-*
-* WV (workspace) COMPLEX*16 array of size
-* (LDWV,3*NSHFTS-3)
-*
-* LDWV (input) integer scalar
-* LDWV is the leading dimension of WV as declared in the
-* in the calling subroutine. LDWV.GE.NV.
-*
-* ================================================================
-* Based on contributions by
-* Karen Braman and Ralph Byers, Department of Mathematics,
-* University of Kansas, USA
-*
-* ============================================================
-* Reference:
-*
-* K. Braman, R. Byers and R. Mathias, The Multi-Shift QR
-* Algorithm Part I: Maintaining Well Focused Shifts, and
-* Level 3 Performance, SIAM Journal of Matrix Analysis,
-* volume 23, pages 929--947, 2002.
-*
-* ============================================================
-* .. Parameters ..
- COMPLEX*16 ZERO, ONE
- PARAMETER ( ZERO = ( 0.0d0, 0.0d0 ),
- $ ONE = ( 1.0d0, 0.0d0 ) )
- DOUBLE PRECISION RZERO, RONE
- PARAMETER ( RZERO = 0.0d0, RONE = 1.0d0 )
-* ..
-* .. Local Scalars ..
- COMPLEX*16 ALPHA, BETA, CDUM, REFSUM
- DOUBLE PRECISION H11, H12, H21, H22, SAFMAX, SAFMIN, SCL,
- $ SMLNUM, TST1, TST2, ULP
- INTEGER I2, I4, INCOL, J, J2, J4, JBOT, JCOL, JLEN,
- $ JROW, JTOP, K, K1, KDU, KMS, KNZ, KRCOL, KZS,
- $ M, M22, MBOT, MEND, MSTART, MTOP, NBMPS, NDCOL,
- $ NS, NU
- LOGICAL ACCUM, BLK22, BMP22
-* ..
-* .. External Functions ..
- DOUBLE PRECISION DLAMCH
- EXTERNAL DLAMCH
-* ..
-* .. Intrinsic Functions ..
-*
- INTRINSIC ABS, DBLE, DCONJG, DIMAG, MAX, MIN, MOD
-* ..
-* .. Local Arrays ..
- COMPLEX*16 VT( 3 )
-* ..
-* .. External Subroutines ..
- EXTERNAL DLABAD, ZGEMM, ZLACPY, ZLAQR1, ZLARFG, ZLASET,
- $ ZTRMM
-* ..
-* .. Statement Functions ..
- DOUBLE PRECISION CABS1
-* ..
-* .. Statement Function definitions ..
- CABS1( CDUM ) = ABS( DBLE( CDUM ) ) + ABS( DIMAG( CDUM ) )
-* ..
-* .. Executable Statements ..
-*
-* ==== If there are no shifts, then there is nothing to do. ====
-*
- IF( NSHFTS.LT.2 )
- $ RETURN
-*
-* ==== If the active block is empty or 1-by-1, then there
-* . is nothing to do. ====
-*
- IF( KTOP.GE.KBOT )
- $ RETURN
-*
-* ==== NSHFTS is supposed to be even, but if is odd,
-* . then simply reduce it by one. ====
-*
- NS = NSHFTS - MOD( NSHFTS, 2 )
-*
-* ==== Machine constants for deflation ====
-*
- SAFMIN = DLAMCH( 'SAFE MINIMUM' )
- SAFMAX = RONE / SAFMIN
- CALL DLABAD( SAFMIN, SAFMAX )
- ULP = DLAMCH( 'PRECISION' )
- SMLNUM = SAFMIN*( DBLE( N ) / ULP )
-*
-* ==== Use accumulated reflections to update far-from-diagonal
-* . entries ? ====
-*
- ACCUM = ( KACC22.EQ.1 ) .OR. ( KACC22.EQ.2 )
-*
-* ==== If so, exploit the 2-by-2 block structure? ====
-*
- BLK22 = ( NS.GT.2 ) .AND. ( KACC22.EQ.2 )
-*
-* ==== clear trash ====
-*
- IF( KTOP+2.LE.KBOT )
- $ H( KTOP+2, KTOP ) = ZERO
-*
-* ==== NBMPS = number of 2-shift bulges in the chain ====
-*
- NBMPS = NS / 2
-*
-* ==== KDU = width of slab ====
-*
- KDU = 6*NBMPS - 3
-*
-* ==== Create and chase chains of NBMPS bulges ====
-*
- DO 210 INCOL = 3*( 1-NBMPS ) + KTOP - 1, KBOT - 2, 3*NBMPS - 2
- NDCOL = INCOL + KDU
- IF( ACCUM )
- $ CALL ZLASET( 'ALL', KDU, KDU, ZERO, ONE, U, LDU )
-*
-* ==== Near-the-diagonal bulge chase. The following loop
-* . performs the near-the-diagonal part of a small bulge
-* . multi-shift QR sweep. Each 6*NBMPS-2 column diagonal
-* . chunk extends from column INCOL to column NDCOL
-* . (including both column INCOL and column NDCOL). The
-* . following loop chases a 3*NBMPS column long chain of
-* . NBMPS bulges 3*NBMPS-2 columns to the right. (INCOL
-* . may be less than KTOP and and NDCOL may be greater than
-* . KBOT indicating phantom columns from which to chase
-* . bulges before they are actually introduced or to which
-* . to chase bulges beyond column KBOT.) ====
-*
- DO 140 KRCOL = INCOL, MIN( INCOL+3*NBMPS-3, KBOT-2 )
-*
-* ==== Bulges number MTOP to MBOT are active double implicit
-* . shift bulges. There may or may not also be small
-* . 2-by-2 bulge, if there is room. The inactive bulges
-* . (if any) must wait until the active bulges have moved
-* . down the diagonal to make room. The phantom matrix
-* . paradigm described above helps keep track. ====
-*
- MTOP = MAX( 1, ( ( KTOP-1 )-KRCOL+2 ) / 3+1 )
- MBOT = MIN( NBMPS, ( KBOT-KRCOL ) / 3 )
- M22 = MBOT + 1
- BMP22 = ( MBOT.LT.NBMPS ) .AND. ( KRCOL+3*( M22-1 ) ).EQ.
- $ ( KBOT-2 )
-*
-* ==== Generate reflections to chase the chain right
-* . one column. (The minimum value of K is KTOP-1.) ====
-*
- DO 10 M = MTOP, MBOT
- K = KRCOL + 3*( M-1 )
- IF( K.EQ.KTOP-1 ) THEN
- CALL ZLAQR1( 3, H( KTOP, KTOP ), LDH, S( 2*M-1 ),
- $ S( 2*M ), V( 1, M ) )
- ALPHA = V( 1, M )
- CALL ZLARFG( 3, ALPHA, V( 2, M ), 1, V( 1, M ) )
- ELSE
- BETA = H( K+1, K )
- V( 2, M ) = H( K+2, K )
- V( 3, M ) = H( K+3, K )
- CALL ZLARFG( 3, BETA, V( 2, M ), 1, V( 1, M ) )
-*
-* ==== A Bulge may collapse because of vigilant
-* . deflation or destructive underflow. (The
-* . initial bulge is always collapsed.) Use
-* . the two-small-subdiagonals trick to try
-* . to get it started again. If V(2,M).NE.0 and
-* . V(3,M) = H(K+3,K+1) = H(K+3,K+2) = 0, then
-* . this bulge is collapsing into a zero
-* . subdiagonal. It will be restarted next
-* . trip through the loop.)
-*
- IF( V( 1, M ).NE.ZERO .AND.
- $ ( V( 3, M ).NE.ZERO .OR. ( H( K+3,
- $ K+1 ).EQ.ZERO .AND. H( K+3, K+2 ).EQ.ZERO ) ) )
- $ THEN
-*
-* ==== Typical case: not collapsed (yet). ====
-*
- H( K+1, K ) = BETA
- H( K+2, K ) = ZERO
- H( K+3, K ) = ZERO
- ELSE
-*
-* ==== Atypical case: collapsed. Attempt to
-* . reintroduce ignoring H(K+1,K). If the
-* . fill resulting from the new reflector
-* . is too large, then abandon it.
-* . Otherwise, use the new one. ====
-*
- CALL ZLAQR1( 3, H( K+1, K+1 ), LDH, S( 2*M-1 ),
- $ S( 2*M ), VT )
- SCL = CABS1( VT( 1 ) ) + CABS1( VT( 2 ) ) +
- $ CABS1( VT( 3 ) )
- IF( SCL.NE.RZERO ) THEN
- VT( 1 ) = VT( 1 ) / SCL
- VT( 2 ) = VT( 2 ) / SCL
- VT( 3 ) = VT( 3 ) / SCL
- END IF
-*
-* ==== The following is the traditional and
-* . conservative two-small-subdiagonals
-* . test. ====
-* .
- IF( CABS1( H( K+1, K ) )*
- $ ( CABS1( VT( 2 ) )+CABS1( VT( 3 ) ) ).GT.ULP*
- $ CABS1( VT( 1 ) )*( CABS1( H( K,
- $ K ) )+CABS1( H( K+1, K+1 ) )+CABS1( H( K+2,
- $ K+2 ) ) ) ) THEN
-*
-* ==== Starting a new bulge here would
-* . create non-negligible fill. If
-* . the old reflector is diagonal (only
-* . possible with underflows), then
-* . change it to I. Otherwise, use
-* . it with trepidation. ====
-*
- IF( V( 2, M ).EQ.ZERO .AND. V( 3, M ).EQ.ZERO )
- $ THEN
- V( 1, M ) = ZERO
- ELSE
- H( K+1, K ) = BETA
- H( K+2, K ) = ZERO
- H( K+3, K ) = ZERO
- END IF
- ELSE
-*
-* ==== Stating a new bulge here would
-* . create only negligible fill.
-* . Replace the old reflector with
-* . the new one. ====
-*
- ALPHA = VT( 1 )
- CALL ZLARFG( 3, ALPHA, VT( 2 ), 1, VT( 1 ) )
- REFSUM = H( K+1, K ) +
- $ H( K+2, K )*DCONJG( VT( 2 ) ) +
- $ H( K+3, K )*DCONJG( VT( 3 ) )
- H( K+1, K ) = H( K+1, K ) -
- $ DCONJG( VT( 1 ) )*REFSUM
- H( K+2, K ) = ZERO
- H( K+3, K ) = ZERO
- V( 1, M ) = VT( 1 )
- V( 2, M ) = VT( 2 )
- V( 3, M ) = VT( 3 )
- END IF
- END IF
- END IF
- 10 CONTINUE
-*
-* ==== Generate a 2-by-2 reflection, if needed. ====
-*
- K = KRCOL + 3*( M22-1 )
- IF( BMP22 ) THEN
- IF( K.EQ.KTOP-1 ) THEN
- CALL ZLAQR1( 2, H( K+1, K+1 ), LDH, S( 2*M22-1 ),
- $ S( 2*M22 ), V( 1, M22 ) )
- BETA = V( 1, M22 )
- CALL ZLARFG( 2, BETA, V( 2, M22 ), 1, V( 1, M22 ) )
- ELSE
- BETA = H( K+1, K )
- V( 2, M22 ) = H( K+2, K )
- CALL ZLARFG( 2, BETA, V( 2, M22 ), 1, V( 1, M22 ) )
- H( K+1, K ) = BETA
- H( K+2, K ) = ZERO
- END IF
- ELSE
-*
-* ==== Initialize V(1,M22) here to avoid possible undefined
-* . variable problems later. ====
-*
- V( 1, M22 ) = ZERO
- END IF
-*
-* ==== Multiply H by reflections from the left ====
-*
- IF( ACCUM ) THEN
- JBOT = MIN( NDCOL, KBOT )
- ELSE IF( WANTT ) THEN
- JBOT = N
- ELSE
- JBOT = KBOT
- END IF
- DO 30 J = MAX( KTOP, KRCOL ), JBOT
- MEND = MIN( MBOT, ( J-KRCOL+2 ) / 3 )
- DO 20 M = MTOP, MEND
- K = KRCOL + 3*( M-1 )
- REFSUM = DCONJG( V( 1, M ) )*
- $ ( H( K+1, J )+DCONJG( V( 2, M ) )*
- $ H( K+2, J )+DCONJG( V( 3, M ) )*H( K+3, J ) )
- H( K+1, J ) = H( K+1, J ) - REFSUM
- H( K+2, J ) = H( K+2, J ) - REFSUM*V( 2, M )
- H( K+3, J ) = H( K+3, J ) - REFSUM*V( 3, M )
- 20 CONTINUE
- 30 CONTINUE
- IF( BMP22 ) THEN
- K = KRCOL + 3*( M22-1 )
- DO 40 J = MAX( K+1, KTOP ), JBOT
- REFSUM = DCONJG( V( 1, M22 ) )*
- $ ( H( K+1, J )+DCONJG( V( 2, M22 ) )*
- $ H( K+2, J ) )
- H( K+1, J ) = H( K+1, J ) - REFSUM
- H( K+2, J ) = H( K+2, J ) - REFSUM*V( 2, M22 )
- 40 CONTINUE
- END IF
-*
-* ==== Multiply H by reflections from the right.
-* . Delay filling in the last row until the
-* . vigilant deflation check is complete. ====
-*
- IF( ACCUM ) THEN
- JTOP = MAX( KTOP, INCOL )
- ELSE IF( WANTT ) THEN
- JTOP = 1
- ELSE
- JTOP = KTOP
- END IF
- DO 80 M = MTOP, MBOT
- IF( V( 1, M ).NE.ZERO ) THEN
- K = KRCOL + 3*( M-1 )
- DO 50 J = JTOP, MIN( KBOT, K+3 )
- REFSUM = V( 1, M )*( H( J, K+1 )+V( 2, M )*
- $ H( J, K+2 )+V( 3, M )*H( J, K+3 ) )
- H( J, K+1 ) = H( J, K+1 ) - REFSUM
- H( J, K+2 ) = H( J, K+2 ) -
- $ REFSUM*DCONJG( V( 2, M ) )
- H( J, K+3 ) = H( J, K+3 ) -
- $ REFSUM*DCONJG( V( 3, M ) )
- 50 CONTINUE
-*
- IF( ACCUM ) THEN
-*
-* ==== Accumulate U. (If necessary, update Z later
-* . with with an efficient matrix-matrix
-* . multiply.) ====
-*
- KMS = K - INCOL
- DO 60 J = MAX( 1, KTOP-INCOL ), KDU
- REFSUM = V( 1, M )*( U( J, KMS+1 )+V( 2, M )*
- $ U( J, KMS+2 )+V( 3, M )*U( J, KMS+3 ) )
- U( J, KMS+1 ) = U( J, KMS+1 ) - REFSUM
- U( J, KMS+2 ) = U( J, KMS+2 ) -
- $ REFSUM*DCONJG( V( 2, M ) )
- U( J, KMS+3 ) = U( J, KMS+3 ) -
- $ REFSUM*DCONJG( V( 3, M ) )
- 60 CONTINUE
- ELSE IF( WANTZ ) THEN
-*
-* ==== U is not accumulated, so update Z
-* . now by multiplying by reflections
-* . from the right. ====
-*
- DO 70 J = ILOZ, IHIZ
- REFSUM = V( 1, M )*( Z( J, K+1 )+V( 2, M )*
- $ Z( J, K+2 )+V( 3, M )*Z( J, K+3 ) )
- Z( J, K+1 ) = Z( J, K+1 ) - REFSUM
- Z( J, K+2 ) = Z( J, K+2 ) -
- $ REFSUM*DCONJG( V( 2, M ) )
- Z( J, K+3 ) = Z( J, K+3 ) -
- $ REFSUM*DCONJG( V( 3, M ) )
- 70 CONTINUE
- END IF
- END IF
- 80 CONTINUE
-*
-* ==== Special case: 2-by-2 reflection (if needed) ====
-*
- K = KRCOL + 3*( M22-1 )
- IF( BMP22 .AND. ( V( 1, M22 ).NE.ZERO ) ) THEN
- DO 90 J = JTOP, MIN( KBOT, K+3 )
- REFSUM = V( 1, M22 )*( H( J, K+1 )+V( 2, M22 )*
- $ H( J, K+2 ) )
- H( J, K+1 ) = H( J, K+1 ) - REFSUM
- H( J, K+2 ) = H( J, K+2 ) -
- $ REFSUM*DCONJG( V( 2, M22 ) )
- 90 CONTINUE
-*
- IF( ACCUM ) THEN
- KMS = K - INCOL
- DO 100 J = MAX( 1, KTOP-INCOL ), KDU
- REFSUM = V( 1, M22 )*( U( J, KMS+1 )+V( 2, M22 )*
- $ U( J, KMS+2 ) )
- U( J, KMS+1 ) = U( J, KMS+1 ) - REFSUM
- U( J, KMS+2 ) = U( J, KMS+2 ) -
- $ REFSUM*DCONJG( V( 2, M22 ) )
- 100 CONTINUE
- ELSE IF( WANTZ ) THEN
- DO 110 J = ILOZ, IHIZ
- REFSUM = V( 1, M22 )*( Z( J, K+1 )+V( 2, M22 )*
- $ Z( J, K+2 ) )
- Z( J, K+1 ) = Z( J, K+1 ) - REFSUM
- Z( J, K+2 ) = Z( J, K+2 ) -
- $ REFSUM*DCONJG( V( 2, M22 ) )
- 110 CONTINUE
- END IF
- END IF
-*
-* ==== Vigilant deflation check ====
-*
- MSTART = MTOP
- IF( KRCOL+3*( MSTART-1 ).LT.KTOP )
- $ MSTART = MSTART + 1
- MEND = MBOT
- IF( BMP22 )
- $ MEND = MEND + 1
- IF( KRCOL.EQ.KBOT-2 )
- $ MEND = MEND + 1
- DO 120 M = MSTART, MEND
- K = MIN( KBOT-1, KRCOL+3*( M-1 ) )
-*
-* ==== The following convergence test requires that
-* . the tradition small-compared-to-nearby-diagonals
-* . criterion and the Ahues & Tisseur (LAWN 122, 1997)
-* . criteria both be satisfied. The latter improves
-* . accuracy in some examples. Falling back on an
-* . alternate convergence criterion when TST1 or TST2
-* . is zero (as done here) is traditional but probably
-* . unnecessary. ====
-*
- IF( H( K+1, K ).NE.ZERO ) THEN
- TST1 = CABS1( H( K, K ) ) + CABS1( H( K+1, K+1 ) )
- IF( TST1.EQ.RZERO ) THEN
- IF( K.GE.KTOP+1 )
- $ TST1 = TST1 + CABS1( H( K, K-1 ) )
- IF( K.GE.KTOP+2 )
- $ TST1 = TST1 + CABS1( H( K, K-2 ) )
- IF( K.GE.KTOP+3 )
- $ TST1 = TST1 + CABS1( H( K, K-3 ) )
- IF( K.LE.KBOT-2 )
- $ TST1 = TST1 + CABS1( H( K+2, K+1 ) )
- IF( K.LE.KBOT-3 )
- $ TST1 = TST1 + CABS1( H( K+3, K+1 ) )
- IF( K.LE.KBOT-4 )
- $ TST1 = TST1 + CABS1( H( K+4, K+1 ) )
- END IF
- IF( CABS1( H( K+1, K ) ).LE.MAX( SMLNUM, ULP*TST1 ) )
- $ THEN
- H12 = MAX( CABS1( H( K+1, K ) ),
- $ CABS1( H( K, K+1 ) ) )
- H21 = MIN( CABS1( H( K+1, K ) ),
- $ CABS1( H( K, K+1 ) ) )
- H11 = MAX( CABS1( H( K+1, K+1 ) ),
- $ CABS1( H( K, K )-H( K+1, K+1 ) ) )
- H22 = MIN( CABS1( H( K+1, K+1 ) ),
- $ CABS1( H( K, K )-H( K+1, K+1 ) ) )
- SCL = H11 + H12
- TST2 = H22*( H11 / SCL )
-*
- IF( TST2.EQ.RZERO .OR. H21*( H12 / SCL ).LE.
- $ MAX( SMLNUM, ULP*TST2 ) )H( K+1, K ) = ZERO
- END IF
- END IF
- 120 CONTINUE
-*
-* ==== Fill in the last row of each bulge. ====
-*
- MEND = MIN( NBMPS, ( KBOT-KRCOL-1 ) / 3 )
- DO 130 M = MTOP, MEND
- K = KRCOL + 3*( M-1 )
- REFSUM = V( 1, M )*V( 3, M )*H( K+4, K+3 )
- H( K+4, K+1 ) = -REFSUM
- H( K+4, K+2 ) = -REFSUM*DCONJG( V( 2, M ) )
- H( K+4, K+3 ) = H( K+4, K+3 ) -
- $ REFSUM*DCONJG( V( 3, M ) )
- 130 CONTINUE
-*
-* ==== End of near-the-diagonal bulge chase. ====
-*
- 140 CONTINUE
-*
-* ==== Use U (if accumulated) to update far-from-diagonal
-* . entries in H. If required, use U to update Z as
-* . well. ====
-*
- IF( ACCUM ) THEN
- IF( WANTT ) THEN
- JTOP = 1
- JBOT = N
- ELSE
- JTOP = KTOP
- JBOT = KBOT
- END IF
- IF( ( .NOT.BLK22 ) .OR. ( INCOL.LT.KTOP ) .OR.
- $ ( NDCOL.GT.KBOT ) .OR. ( NS.LE.2 ) ) THEN
-*
-* ==== Updates not exploiting the 2-by-2 block
-* . structure of U. K1 and NU keep track of
-* . the location and size of U in the special
-* . cases of introducing bulges and chasing
-* . bulges off the bottom. In these special
-* . cases and in case the number of shifts
-* . is NS = 2, there is no 2-by-2 block
-* . structure to exploit. ====
-*
- K1 = MAX( 1, KTOP-INCOL )
- NU = ( KDU-MAX( 0, NDCOL-KBOT ) ) - K1 + 1
-*
-* ==== Horizontal Multiply ====
-*
- DO 150 JCOL = MIN( NDCOL, KBOT ) + 1, JBOT, NH
- JLEN = MIN( NH, JBOT-JCOL+1 )
- CALL ZGEMM( 'C', 'N', NU, JLEN, NU, ONE, U( K1, K1 ),
- $ LDU, H( INCOL+K1, JCOL ), LDH, ZERO, WH,
- $ LDWH )
- CALL ZLACPY( 'ALL', NU, JLEN, WH, LDWH,
- $ H( INCOL+K1, JCOL ), LDH )
- 150 CONTINUE
-*
-* ==== Vertical multiply ====
-*
- DO 160 JROW = JTOP, MAX( KTOP, INCOL ) - 1, NV
- JLEN = MIN( NV, MAX( KTOP, INCOL )-JROW )
- CALL ZGEMM( 'N', 'N', JLEN, NU, NU, ONE,
- $ H( JROW, INCOL+K1 ), LDH, U( K1, K1 ),
- $ LDU, ZERO, WV, LDWV )
- CALL ZLACPY( 'ALL', JLEN, NU, WV, LDWV,
- $ H( JROW, INCOL+K1 ), LDH )
- 160 CONTINUE
-*
-* ==== Z multiply (also vertical) ====
-*
- IF( WANTZ ) THEN
- DO 170 JROW = ILOZ, IHIZ, NV
- JLEN = MIN( NV, IHIZ-JROW+1 )
- CALL ZGEMM( 'N', 'N', JLEN, NU, NU, ONE,
- $ Z( JROW, INCOL+K1 ), LDZ, U( K1, K1 ),
- $ LDU, ZERO, WV, LDWV )
- CALL ZLACPY( 'ALL', JLEN, NU, WV, LDWV,
- $ Z( JROW, INCOL+K1 ), LDZ )
- 170 CONTINUE
- END IF
- ELSE
-*
-* ==== Updates exploiting U's 2-by-2 block structure.
-* . (I2, I4, J2, J4 are the last rows and columns
-* . of the blocks.) ====
-*
- I2 = ( KDU+1 ) / 2
- I4 = KDU
- J2 = I4 - I2
- J4 = KDU
-*
-* ==== KZS and KNZ deal with the band of zeros
-* . along the diagonal of one of the triangular
-* . blocks. ====
-*
- KZS = ( J4-J2 ) - ( NS+1 )
- KNZ = NS + 1
-*
-* ==== Horizontal multiply ====
-*
- DO 180 JCOL = MIN( NDCOL, KBOT ) + 1, JBOT, NH
- JLEN = MIN( NH, JBOT-JCOL+1 )
-*
-* ==== Copy bottom of H to top+KZS of scratch ====
-* (The first KZS rows get multiplied by zero.) ====
-*
- CALL ZLACPY( 'ALL', KNZ, JLEN, H( INCOL+1+J2, JCOL ),
- $ LDH, WH( KZS+1, 1 ), LDWH )
-*
-* ==== Multiply by U21' ====
-*
- CALL ZLASET( 'ALL', KZS, JLEN, ZERO, ZERO, WH, LDWH )
- CALL ZTRMM( 'L', 'U', 'C', 'N', KNZ, JLEN, ONE,
- $ U( J2+1, 1+KZS ), LDU, WH( KZS+1, 1 ),
- $ LDWH )
-*
-* ==== Multiply top of H by U11' ====
-*
- CALL ZGEMM( 'C', 'N', I2, JLEN, J2, ONE, U, LDU,
- $ H( INCOL+1, JCOL ), LDH, ONE, WH, LDWH )
-*
-* ==== Copy top of H bottom of WH ====
-*
- CALL ZLACPY( 'ALL', J2, JLEN, H( INCOL+1, JCOL ), LDH,
- $ WH( I2+1, 1 ), LDWH )
-*
-* ==== Multiply by U21' ====
-*
- CALL ZTRMM( 'L', 'L', 'C', 'N', J2, JLEN, ONE,
- $ U( 1, I2+1 ), LDU, WH( I2+1, 1 ), LDWH )
-*
-* ==== Multiply by U22 ====
-*
- CALL ZGEMM( 'C', 'N', I4-I2, JLEN, J4-J2, ONE,
- $ U( J2+1, I2+1 ), LDU,
- $ H( INCOL+1+J2, JCOL ), LDH, ONE,
- $ WH( I2+1, 1 ), LDWH )
-*
-* ==== Copy it back ====
-*
- CALL ZLACPY( 'ALL', KDU, JLEN, WH, LDWH,
- $ H( INCOL+1, JCOL ), LDH )
- 180 CONTINUE
-*
-* ==== Vertical multiply ====
-*
- DO 190 JROW = JTOP, MAX( INCOL, KTOP ) - 1, NV
- JLEN = MIN( NV, MAX( INCOL, KTOP )-JROW )
-*
-* ==== Copy right of H to scratch (the first KZS
-* . columns get multiplied by zero) ====
-*
- CALL ZLACPY( 'ALL', JLEN, KNZ, H( JROW, INCOL+1+J2 ),
- $ LDH, WV( 1, 1+KZS ), LDWV )
-*
-* ==== Multiply by U21 ====
-*
- CALL ZLASET( 'ALL', JLEN, KZS, ZERO, ZERO, WV, LDWV )
- CALL ZTRMM( 'R', 'U', 'N', 'N', JLEN, KNZ, ONE,
- $ U( J2+1, 1+KZS ), LDU, WV( 1, 1+KZS ),
- $ LDWV )
-*
-* ==== Multiply by U11 ====
-*
- CALL ZGEMM( 'N', 'N', JLEN, I2, J2, ONE,
- $ H( JROW, INCOL+1 ), LDH, U, LDU, ONE, WV,
- $ LDWV )
-*
-* ==== Copy left of H to right of scratch ====
-*
- CALL ZLACPY( 'ALL', JLEN, J2, H( JROW, INCOL+1 ), LDH,
- $ WV( 1, 1+I2 ), LDWV )
-*
-* ==== Multiply by U21 ====
-*
- CALL ZTRMM( 'R', 'L', 'N', 'N', JLEN, I4-I2, ONE,
- $ U( 1, I2+1 ), LDU, WV( 1, 1+I2 ), LDWV )
-*
-* ==== Multiply by U22 ====
-*
- CALL ZGEMM( 'N', 'N', JLEN, I4-I2, J4-J2, ONE,
- $ H( JROW, INCOL+1+J2 ), LDH,
- $ U( J2+1, I2+1 ), LDU, ONE, WV( 1, 1+I2 ),
- $ LDWV )
-*
-* ==== Copy it back ====
-*
- CALL ZLACPY( 'ALL', JLEN, KDU, WV, LDWV,
- $ H( JROW, INCOL+1 ), LDH )
- 190 CONTINUE
-*
-* ==== Multiply Z (also vertical) ====
-*
- IF( WANTZ ) THEN
- DO 200 JROW = ILOZ, IHIZ, NV
- JLEN = MIN( NV, IHIZ-JROW+1 )
-*
-* ==== Copy right of Z to left of scratch (first
-* . KZS columns get multiplied by zero) ====
-*
- CALL ZLACPY( 'ALL', JLEN, KNZ,
- $ Z( JROW, INCOL+1+J2 ), LDZ,
- $ WV( 1, 1+KZS ), LDWV )
-*
-* ==== Multiply by U12 ====
-*
- CALL ZLASET( 'ALL', JLEN, KZS, ZERO, ZERO, WV,
- $ LDWV )
- CALL ZTRMM( 'R', 'U', 'N', 'N', JLEN, KNZ, ONE,
- $ U( J2+1, 1+KZS ), LDU, WV( 1, 1+KZS ),
- $ LDWV )
-*
-* ==== Multiply by U11 ====
-*
- CALL ZGEMM( 'N', 'N', JLEN, I2, J2, ONE,
- $ Z( JROW, INCOL+1 ), LDZ, U, LDU, ONE,
- $ WV, LDWV )
-*
-* ==== Copy left of Z to right of scratch ====
-*
- CALL ZLACPY( 'ALL', JLEN, J2, Z( JROW, INCOL+1 ),
- $ LDZ, WV( 1, 1+I2 ), LDWV )
-*
-* ==== Multiply by U21 ====
-*
- CALL ZTRMM( 'R', 'L', 'N', 'N', JLEN, I4-I2, ONE,
- $ U( 1, I2+1 ), LDU, WV( 1, 1+I2 ),
- $ LDWV )
-*
-* ==== Multiply by U22 ====
-*
- CALL ZGEMM( 'N', 'N', JLEN, I4-I2, J4-J2, ONE,
- $ Z( JROW, INCOL+1+J2 ), LDZ,
- $ U( J2+1, I2+1 ), LDU, ONE,
- $ WV( 1, 1+I2 ), LDWV )
-*
-* ==== Copy the result back to Z ====
-*
- CALL ZLACPY( 'ALL', JLEN, KDU, WV, LDWV,
- $ Z( JROW, INCOL+1 ), LDZ )
- 200 CONTINUE
- END IF
- END IF
- END IF
- 210 CONTINUE
-*
-* ==== End of ZLAQR5 ====
-*
- END
diff --git a/src/lib/lapack/zlarf.f b/src/lib/lapack/zlarf.f
deleted file mode 100644
index d5233c8c..00000000
--- a/src/lib/lapack/zlarf.f
+++ /dev/null
@@ -1,120 +0,0 @@
- SUBROUTINE ZLARF( SIDE, M, N, V, INCV, TAU, C, LDC, WORK )
-*
-* -- LAPACK auxiliary routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- CHARACTER SIDE
- INTEGER INCV, LDC, M, N
- COMPLEX*16 TAU
-* ..
-* .. Array Arguments ..
- COMPLEX*16 C( LDC, * ), V( * ), WORK( * )
-* ..
-*
-* Purpose
-* =======
-*
-* ZLARF applies a complex elementary reflector H to a complex M-by-N
-* matrix C, from either the left or the right. H is represented in the
-* form
-*
-* H = I - tau * v * v'
-*
-* where tau is a complex scalar and v is a complex vector.
-*
-* If tau = 0, then H is taken to be the unit matrix.
-*
-* To apply H' (the conjugate transpose of H), supply conjg(tau) instead
-* tau.
-*
-* Arguments
-* =========
-*
-* SIDE (input) CHARACTER*1
-* = 'L': form H * C
-* = 'R': form C * H
-*
-* M (input) INTEGER
-* The number of rows of the matrix C.
-*
-* N (input) INTEGER
-* The number of columns of the matrix C.
-*
-* V (input) COMPLEX*16 array, dimension
-* (1 + (M-1)*abs(INCV)) if SIDE = 'L'
-* or (1 + (N-1)*abs(INCV)) if SIDE = 'R'
-* The vector v in the representation of H. V is not used if
-* TAU = 0.
-*
-* INCV (input) INTEGER
-* The increment between elements of v. INCV <> 0.
-*
-* TAU (input) COMPLEX*16
-* The value tau in the representation of H.
-*
-* C (input/output) COMPLEX*16 array, dimension (LDC,N)
-* On entry, the M-by-N matrix C.
-* On exit, C is overwritten by the matrix H * C if SIDE = 'L',
-* or C * H if SIDE = 'R'.
-*
-* LDC (input) INTEGER
-* The leading dimension of the array C. LDC >= max(1,M).
-*
-* WORK (workspace) COMPLEX*16 array, dimension
-* (N) if SIDE = 'L'
-* or (M) if SIDE = 'R'
-*
-* =====================================================================
-*
-* .. Parameters ..
- COMPLEX*16 ONE, ZERO
- PARAMETER ( ONE = ( 1.0D+0, 0.0D+0 ),
- $ ZERO = ( 0.0D+0, 0.0D+0 ) )
-* ..
-* .. External Subroutines ..
- EXTERNAL ZGEMV, ZGERC
-* ..
-* .. External Functions ..
- LOGICAL LSAME
- EXTERNAL LSAME
-* ..
-* .. Executable Statements ..
-*
- IF( LSAME( SIDE, 'L' ) ) THEN
-*
-* Form H * C
-*
- IF( TAU.NE.ZERO ) THEN
-*
-* w := C' * v
-*
- CALL ZGEMV( 'Conjugate transpose', M, N, ONE, C, LDC, V,
- $ INCV, ZERO, WORK, 1 )
-*
-* C := C - v * w'
-*
- CALL ZGERC( M, N, -TAU, V, INCV, WORK, 1, C, LDC )
- END IF
- ELSE
-*
-* Form C * H
-*
- IF( TAU.NE.ZERO ) THEN
-*
-* w := C * v
-*
- CALL ZGEMV( 'No transpose', M, N, ONE, C, LDC, V, INCV,
- $ ZERO, WORK, 1 )
-*
-* C := C - w * v'
-*
- CALL ZGERC( M, N, -TAU, WORK, 1, V, INCV, C, LDC )
- END IF
- END IF
- RETURN
-*
-* End of ZLARF
-*
- END
diff --git a/src/lib/lapack/zlarfb.f b/src/lib/lapack/zlarfb.f
deleted file mode 100644
index af93ea58..00000000
--- a/src/lib/lapack/zlarfb.f
+++ /dev/null
@@ -1,608 +0,0 @@
- SUBROUTINE ZLARFB( SIDE, TRANS, DIRECT, STOREV, M, N, K, V, LDV,
- $ T, LDT, C, LDC, WORK, LDWORK )
-*
-* -- LAPACK auxiliary routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- CHARACTER DIRECT, SIDE, STOREV, TRANS
- INTEGER K, LDC, LDT, LDV, LDWORK, M, N
-* ..
-* .. Array Arguments ..
- COMPLEX*16 C( LDC, * ), T( LDT, * ), V( LDV, * ),
- $ WORK( LDWORK, * )
-* ..
-*
-* Purpose
-* =======
-*
-* ZLARFB applies a complex block reflector H or its transpose H' to a
-* complex M-by-N matrix C, from either the left or the right.
-*
-* Arguments
-* =========
-*
-* SIDE (input) CHARACTER*1
-* = 'L': apply H or H' from the Left
-* = 'R': apply H or H' from the Right
-*
-* TRANS (input) CHARACTER*1
-* = 'N': apply H (No transpose)
-* = 'C': apply H' (Conjugate transpose)
-*
-* DIRECT (input) CHARACTER*1
-* Indicates how H is formed from a product of elementary
-* reflectors
-* = 'F': H = H(1) H(2) . . . H(k) (Forward)
-* = 'B': H = H(k) . . . H(2) H(1) (Backward)
-*
-* STOREV (input) CHARACTER*1
-* Indicates how the vectors which define the elementary
-* reflectors are stored:
-* = 'C': Columnwise
-* = 'R': Rowwise
-*
-* M (input) INTEGER
-* The number of rows of the matrix C.
-*
-* N (input) INTEGER
-* The number of columns of the matrix C.
-*
-* K (input) INTEGER
-* The order of the matrix T (= the number of elementary
-* reflectors whose product defines the block reflector).
-*
-* V (input) COMPLEX*16 array, dimension
-* (LDV,K) if STOREV = 'C'
-* (LDV,M) if STOREV = 'R' and SIDE = 'L'
-* (LDV,N) if STOREV = 'R' and SIDE = 'R'
-* The matrix V. See further details.
-*
-* LDV (input) INTEGER
-* The leading dimension of the array V.
-* If STOREV = 'C' and SIDE = 'L', LDV >= max(1,M);
-* if STOREV = 'C' and SIDE = 'R', LDV >= max(1,N);
-* if STOREV = 'R', LDV >= K.
-*
-* T (input) COMPLEX*16 array, dimension (LDT,K)
-* The triangular K-by-K matrix T in the representation of the
-* block reflector.
-*
-* LDT (input) INTEGER
-* The leading dimension of the array T. LDT >= K.
-*
-* C (input/output) COMPLEX*16 array, dimension (LDC,N)
-* On entry, the M-by-N matrix C.
-* On exit, C is overwritten by H*C or H'*C or C*H or C*H'.
-*
-* LDC (input) INTEGER
-* The leading dimension of the array C. LDC >= max(1,M).
-*
-* WORK (workspace) COMPLEX*16 array, dimension (LDWORK,K)
-*
-* LDWORK (input) INTEGER
-* The leading dimension of the array WORK.
-* If SIDE = 'L', LDWORK >= max(1,N);
-* if SIDE = 'R', LDWORK >= max(1,M).
-*
-* =====================================================================
-*
-* .. Parameters ..
- COMPLEX*16 ONE
- PARAMETER ( ONE = ( 1.0D+0, 0.0D+0 ) )
-* ..
-* .. Local Scalars ..
- CHARACTER TRANST
- INTEGER I, J
-* ..
-* .. External Functions ..
- LOGICAL LSAME
- EXTERNAL LSAME
-* ..
-* .. External Subroutines ..
- EXTERNAL ZCOPY, ZGEMM, ZLACGV, ZTRMM
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC DCONJG
-* ..
-* .. Executable Statements ..
-*
-* Quick return if possible
-*
- IF( M.LE.0 .OR. N.LE.0 )
- $ RETURN
-*
- IF( LSAME( TRANS, 'N' ) ) THEN
- TRANST = 'C'
- ELSE
- TRANST = 'N'
- END IF
-*
- IF( LSAME( STOREV, 'C' ) ) THEN
-*
- IF( LSAME( DIRECT, 'F' ) ) THEN
-*
-* Let V = ( V1 ) (first K rows)
-* ( V2 )
-* where V1 is unit lower triangular.
-*
- IF( LSAME( SIDE, 'L' ) ) THEN
-*
-* Form H * C or H' * C where C = ( C1 )
-* ( C2 )
-*
-* W := C' * V = (C1'*V1 + C2'*V2) (stored in WORK)
-*
-* W := C1'
-*
- DO 10 J = 1, K
- CALL ZCOPY( N, C( J, 1 ), LDC, WORK( 1, J ), 1 )
- CALL ZLACGV( N, WORK( 1, J ), 1 )
- 10 CONTINUE
-*
-* W := W * V1
-*
- CALL ZTRMM( 'Right', 'Lower', 'No transpose', 'Unit', N,
- $ K, ONE, V, LDV, WORK, LDWORK )
- IF( M.GT.K ) THEN
-*
-* W := W + C2'*V2
-*
- CALL ZGEMM( 'Conjugate transpose', 'No transpose', N,
- $ K, M-K, ONE, C( K+1, 1 ), LDC,
- $ V( K+1, 1 ), LDV, ONE, WORK, LDWORK )
- END IF
-*
-* W := W * T' or W * T
-*
- CALL ZTRMM( 'Right', 'Upper', TRANST, 'Non-unit', N, K,
- $ ONE, T, LDT, WORK, LDWORK )
-*
-* C := C - V * W'
-*
- IF( M.GT.K ) THEN
-*
-* C2 := C2 - V2 * W'
-*
- CALL ZGEMM( 'No transpose', 'Conjugate transpose',
- $ M-K, N, K, -ONE, V( K+1, 1 ), LDV, WORK,
- $ LDWORK, ONE, C( K+1, 1 ), LDC )
- END IF
-*
-* W := W * V1'
-*
- CALL ZTRMM( 'Right', 'Lower', 'Conjugate transpose',
- $ 'Unit', N, K, ONE, V, LDV, WORK, LDWORK )
-*
-* C1 := C1 - W'
-*
- DO 30 J = 1, K
- DO 20 I = 1, N
- C( J, I ) = C( J, I ) - DCONJG( WORK( I, J ) )
- 20 CONTINUE
- 30 CONTINUE
-*
- ELSE IF( LSAME( SIDE, 'R' ) ) THEN
-*
-* Form C * H or C * H' where C = ( C1 C2 )
-*
-* W := C * V = (C1*V1 + C2*V2) (stored in WORK)
-*
-* W := C1
-*
- DO 40 J = 1, K
- CALL ZCOPY( M, C( 1, J ), 1, WORK( 1, J ), 1 )
- 40 CONTINUE
-*
-* W := W * V1
-*
- CALL ZTRMM( 'Right', 'Lower', 'No transpose', 'Unit', M,
- $ K, ONE, V, LDV, WORK, LDWORK )
- IF( N.GT.K ) THEN
-*
-* W := W + C2 * V2
-*
- CALL ZGEMM( 'No transpose', 'No transpose', M, K, N-K,
- $ ONE, C( 1, K+1 ), LDC, V( K+1, 1 ), LDV,
- $ ONE, WORK, LDWORK )
- END IF
-*
-* W := W * T or W * T'
-*
- CALL ZTRMM( 'Right', 'Upper', TRANS, 'Non-unit', M, K,
- $ ONE, T, LDT, WORK, LDWORK )
-*
-* C := C - W * V'
-*
- IF( N.GT.K ) THEN
-*
-* C2 := C2 - W * V2'
-*
- CALL ZGEMM( 'No transpose', 'Conjugate transpose', M,
- $ N-K, K, -ONE, WORK, LDWORK, V( K+1, 1 ),
- $ LDV, ONE, C( 1, K+1 ), LDC )
- END IF
-*
-* W := W * V1'
-*
- CALL ZTRMM( 'Right', 'Lower', 'Conjugate transpose',
- $ 'Unit', M, K, ONE, V, LDV, WORK, LDWORK )
-*
-* C1 := C1 - W
-*
- DO 60 J = 1, K
- DO 50 I = 1, M
- C( I, J ) = C( I, J ) - WORK( I, J )
- 50 CONTINUE
- 60 CONTINUE
- END IF
-*
- ELSE
-*
-* Let V = ( V1 )
-* ( V2 ) (last K rows)
-* where V2 is unit upper triangular.
-*
- IF( LSAME( SIDE, 'L' ) ) THEN
-*
-* Form H * C or H' * C where C = ( C1 )
-* ( C2 )
-*
-* W := C' * V = (C1'*V1 + C2'*V2) (stored in WORK)
-*
-* W := C2'
-*
- DO 70 J = 1, K
- CALL ZCOPY( N, C( M-K+J, 1 ), LDC, WORK( 1, J ), 1 )
- CALL ZLACGV( N, WORK( 1, J ), 1 )
- 70 CONTINUE
-*
-* W := W * V2
-*
- CALL ZTRMM( 'Right', 'Upper', 'No transpose', 'Unit', N,
- $ K, ONE, V( M-K+1, 1 ), LDV, WORK, LDWORK )
- IF( M.GT.K ) THEN
-*
-* W := W + C1'*V1
-*
- CALL ZGEMM( 'Conjugate transpose', 'No transpose', N,
- $ K, M-K, ONE, C, LDC, V, LDV, ONE, WORK,
- $ LDWORK )
- END IF
-*
-* W := W * T' or W * T
-*
- CALL ZTRMM( 'Right', 'Lower', TRANST, 'Non-unit', N, K,
- $ ONE, T, LDT, WORK, LDWORK )
-*
-* C := C - V * W'
-*
- IF( M.GT.K ) THEN
-*
-* C1 := C1 - V1 * W'
-*
- CALL ZGEMM( 'No transpose', 'Conjugate transpose',
- $ M-K, N, K, -ONE, V, LDV, WORK, LDWORK,
- $ ONE, C, LDC )
- END IF
-*
-* W := W * V2'
-*
- CALL ZTRMM( 'Right', 'Upper', 'Conjugate transpose',
- $ 'Unit', N, K, ONE, V( M-K+1, 1 ), LDV, WORK,
- $ LDWORK )
-*
-* C2 := C2 - W'
-*
- DO 90 J = 1, K
- DO 80 I = 1, N
- C( M-K+J, I ) = C( M-K+J, I ) -
- $ DCONJG( WORK( I, J ) )
- 80 CONTINUE
- 90 CONTINUE
-*
- ELSE IF( LSAME( SIDE, 'R' ) ) THEN
-*
-* Form C * H or C * H' where C = ( C1 C2 )
-*
-* W := C * V = (C1*V1 + C2*V2) (stored in WORK)
-*
-* W := C2
-*
- DO 100 J = 1, K
- CALL ZCOPY( M, C( 1, N-K+J ), 1, WORK( 1, J ), 1 )
- 100 CONTINUE
-*
-* W := W * V2
-*
- CALL ZTRMM( 'Right', 'Upper', 'No transpose', 'Unit', M,
- $ K, ONE, V( N-K+1, 1 ), LDV, WORK, LDWORK )
- IF( N.GT.K ) THEN
-*
-* W := W + C1 * V1
-*
- CALL ZGEMM( 'No transpose', 'No transpose', M, K, N-K,
- $ ONE, C, LDC, V, LDV, ONE, WORK, LDWORK )
- END IF
-*
-* W := W * T or W * T'
-*
- CALL ZTRMM( 'Right', 'Lower', TRANS, 'Non-unit', M, K,
- $ ONE, T, LDT, WORK, LDWORK )
-*
-* C := C - W * V'
-*
- IF( N.GT.K ) THEN
-*
-* C1 := C1 - W * V1'
-*
- CALL ZGEMM( 'No transpose', 'Conjugate transpose', M,
- $ N-K, K, -ONE, WORK, LDWORK, V, LDV, ONE,
- $ C, LDC )
- END IF
-*
-* W := W * V2'
-*
- CALL ZTRMM( 'Right', 'Upper', 'Conjugate transpose',
- $ 'Unit', M, K, ONE, V( N-K+1, 1 ), LDV, WORK,
- $ LDWORK )
-*
-* C2 := C2 - W
-*
- DO 120 J = 1, K
- DO 110 I = 1, M
- C( I, N-K+J ) = C( I, N-K+J ) - WORK( I, J )
- 110 CONTINUE
- 120 CONTINUE
- END IF
- END IF
-*
- ELSE IF( LSAME( STOREV, 'R' ) ) THEN
-*
- IF( LSAME( DIRECT, 'F' ) ) THEN
-*
-* Let V = ( V1 V2 ) (V1: first K columns)
-* where V1 is unit upper triangular.
-*
- IF( LSAME( SIDE, 'L' ) ) THEN
-*
-* Form H * C or H' * C where C = ( C1 )
-* ( C2 )
-*
-* W := C' * V' = (C1'*V1' + C2'*V2') (stored in WORK)
-*
-* W := C1'
-*
- DO 130 J = 1, K
- CALL ZCOPY( N, C( J, 1 ), LDC, WORK( 1, J ), 1 )
- CALL ZLACGV( N, WORK( 1, J ), 1 )
- 130 CONTINUE
-*
-* W := W * V1'
-*
- CALL ZTRMM( 'Right', 'Upper', 'Conjugate transpose',
- $ 'Unit', N, K, ONE, V, LDV, WORK, LDWORK )
- IF( M.GT.K ) THEN
-*
-* W := W + C2'*V2'
-*
- CALL ZGEMM( 'Conjugate transpose',
- $ 'Conjugate transpose', N, K, M-K, ONE,
- $ C( K+1, 1 ), LDC, V( 1, K+1 ), LDV, ONE,
- $ WORK, LDWORK )
- END IF
-*
-* W := W * T' or W * T
-*
- CALL ZTRMM( 'Right', 'Upper', TRANST, 'Non-unit', N, K,
- $ ONE, T, LDT, WORK, LDWORK )
-*
-* C := C - V' * W'
-*
- IF( M.GT.K ) THEN
-*
-* C2 := C2 - V2' * W'
-*
- CALL ZGEMM( 'Conjugate transpose',
- $ 'Conjugate transpose', M-K, N, K, -ONE,
- $ V( 1, K+1 ), LDV, WORK, LDWORK, ONE,
- $ C( K+1, 1 ), LDC )
- END IF
-*
-* W := W * V1
-*
- CALL ZTRMM( 'Right', 'Upper', 'No transpose', 'Unit', N,
- $ K, ONE, V, LDV, WORK, LDWORK )
-*
-* C1 := C1 - W'
-*
- DO 150 J = 1, K
- DO 140 I = 1, N
- C( J, I ) = C( J, I ) - DCONJG( WORK( I, J ) )
- 140 CONTINUE
- 150 CONTINUE
-*
- ELSE IF( LSAME( SIDE, 'R' ) ) THEN
-*
-* Form C * H or C * H' where C = ( C1 C2 )
-*
-* W := C * V' = (C1*V1' + C2*V2') (stored in WORK)
-*
-* W := C1
-*
- DO 160 J = 1, K
- CALL ZCOPY( M, C( 1, J ), 1, WORK( 1, J ), 1 )
- 160 CONTINUE
-*
-* W := W * V1'
-*
- CALL ZTRMM( 'Right', 'Upper', 'Conjugate transpose',
- $ 'Unit', M, K, ONE, V, LDV, WORK, LDWORK )
- IF( N.GT.K ) THEN
-*
-* W := W + C2 * V2'
-*
- CALL ZGEMM( 'No transpose', 'Conjugate transpose', M,
- $ K, N-K, ONE, C( 1, K+1 ), LDC,
- $ V( 1, K+1 ), LDV, ONE, WORK, LDWORK )
- END IF
-*
-* W := W * T or W * T'
-*
- CALL ZTRMM( 'Right', 'Upper', TRANS, 'Non-unit', M, K,
- $ ONE, T, LDT, WORK, LDWORK )
-*
-* C := C - W * V
-*
- IF( N.GT.K ) THEN
-*
-* C2 := C2 - W * V2
-*
- CALL ZGEMM( 'No transpose', 'No transpose', M, N-K, K,
- $ -ONE, WORK, LDWORK, V( 1, K+1 ), LDV, ONE,
- $ C( 1, K+1 ), LDC )
- END IF
-*
-* W := W * V1
-*
- CALL ZTRMM( 'Right', 'Upper', 'No transpose', 'Unit', M,
- $ K, ONE, V, LDV, WORK, LDWORK )
-*
-* C1 := C1 - W
-*
- DO 180 J = 1, K
- DO 170 I = 1, M
- C( I, J ) = C( I, J ) - WORK( I, J )
- 170 CONTINUE
- 180 CONTINUE
-*
- END IF
-*
- ELSE
-*
-* Let V = ( V1 V2 ) (V2: last K columns)
-* where V2 is unit lower triangular.
-*
- IF( LSAME( SIDE, 'L' ) ) THEN
-*
-* Form H * C or H' * C where C = ( C1 )
-* ( C2 )
-*
-* W := C' * V' = (C1'*V1' + C2'*V2') (stored in WORK)
-*
-* W := C2'
-*
- DO 190 J = 1, K
- CALL ZCOPY( N, C( M-K+J, 1 ), LDC, WORK( 1, J ), 1 )
- CALL ZLACGV( N, WORK( 1, J ), 1 )
- 190 CONTINUE
-*
-* W := W * V2'
-*
- CALL ZTRMM( 'Right', 'Lower', 'Conjugate transpose',
- $ 'Unit', N, K, ONE, V( 1, M-K+1 ), LDV, WORK,
- $ LDWORK )
- IF( M.GT.K ) THEN
-*
-* W := W + C1'*V1'
-*
- CALL ZGEMM( 'Conjugate transpose',
- $ 'Conjugate transpose', N, K, M-K, ONE, C,
- $ LDC, V, LDV, ONE, WORK, LDWORK )
- END IF
-*
-* W := W * T' or W * T
-*
- CALL ZTRMM( 'Right', 'Lower', TRANST, 'Non-unit', N, K,
- $ ONE, T, LDT, WORK, LDWORK )
-*
-* C := C - V' * W'
-*
- IF( M.GT.K ) THEN
-*
-* C1 := C1 - V1' * W'
-*
- CALL ZGEMM( 'Conjugate transpose',
- $ 'Conjugate transpose', M-K, N, K, -ONE, V,
- $ LDV, WORK, LDWORK, ONE, C, LDC )
- END IF
-*
-* W := W * V2
-*
- CALL ZTRMM( 'Right', 'Lower', 'No transpose', 'Unit', N,
- $ K, ONE, V( 1, M-K+1 ), LDV, WORK, LDWORK )
-*
-* C2 := C2 - W'
-*
- DO 210 J = 1, K
- DO 200 I = 1, N
- C( M-K+J, I ) = C( M-K+J, I ) -
- $ DCONJG( WORK( I, J ) )
- 200 CONTINUE
- 210 CONTINUE
-*
- ELSE IF( LSAME( SIDE, 'R' ) ) THEN
-*
-* Form C * H or C * H' where C = ( C1 C2 )
-*
-* W := C * V' = (C1*V1' + C2*V2') (stored in WORK)
-*
-* W := C2
-*
- DO 220 J = 1, K
- CALL ZCOPY( M, C( 1, N-K+J ), 1, WORK( 1, J ), 1 )
- 220 CONTINUE
-*
-* W := W * V2'
-*
- CALL ZTRMM( 'Right', 'Lower', 'Conjugate transpose',
- $ 'Unit', M, K, ONE, V( 1, N-K+1 ), LDV, WORK,
- $ LDWORK )
- IF( N.GT.K ) THEN
-*
-* W := W + C1 * V1'
-*
- CALL ZGEMM( 'No transpose', 'Conjugate transpose', M,
- $ K, N-K, ONE, C, LDC, V, LDV, ONE, WORK,
- $ LDWORK )
- END IF
-*
-* W := W * T or W * T'
-*
- CALL ZTRMM( 'Right', 'Lower', TRANS, 'Non-unit', M, K,
- $ ONE, T, LDT, WORK, LDWORK )
-*
-* C := C - W * V
-*
- IF( N.GT.K ) THEN
-*
-* C1 := C1 - W * V1
-*
- CALL ZGEMM( 'No transpose', 'No transpose', M, N-K, K,
- $ -ONE, WORK, LDWORK, V, LDV, ONE, C, LDC )
- END IF
-*
-* W := W * V2
-*
- CALL ZTRMM( 'Right', 'Lower', 'No transpose', 'Unit', M,
- $ K, ONE, V( 1, N-K+1 ), LDV, WORK, LDWORK )
-*
-* C1 := C1 - W
-*
- DO 240 J = 1, K
- DO 230 I = 1, M
- C( I, N-K+J ) = C( I, N-K+J ) - WORK( I, J )
- 230 CONTINUE
- 240 CONTINUE
-*
- END IF
-*
- END IF
- END IF
-*
- RETURN
-*
-* End of ZLARFB
-*
- END
diff --git a/src/lib/lapack/zlarfg.f b/src/lib/lapack/zlarfg.f
deleted file mode 100644
index d024f928..00000000
--- a/src/lib/lapack/zlarfg.f
+++ /dev/null
@@ -1,145 +0,0 @@
- SUBROUTINE ZLARFG( N, ALPHA, X, INCX, TAU )
-*
-* -- LAPACK auxiliary routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- INTEGER INCX, N
- COMPLEX*16 ALPHA, TAU
-* ..
-* .. Array Arguments ..
- COMPLEX*16 X( * )
-* ..
-*
-* Purpose
-* =======
-*
-* ZLARFG generates a complex elementary reflector H of order n, such
-* that
-*
-* H' * ( alpha ) = ( beta ), H' * H = I.
-* ( x ) ( 0 )
-*
-* where alpha and beta are scalars, with beta real, and x is an
-* (n-1)-element complex vector. H is represented in the form
-*
-* H = I - tau * ( 1 ) * ( 1 v' ) ,
-* ( v )
-*
-* where tau is a complex scalar and v is a complex (n-1)-element
-* vector. Note that H is not hermitian.
-*
-* If the elements of x are all zero and alpha is real, then tau = 0
-* and H is taken to be the unit matrix.
-*
-* Otherwise 1 <= real(tau) <= 2 and abs(tau-1) <= 1 .
-*
-* Arguments
-* =========
-*
-* N (input) INTEGER
-* The order of the elementary reflector.
-*
-* ALPHA (input/output) COMPLEX*16
-* On entry, the value alpha.
-* On exit, it is overwritten with the value beta.
-*
-* X (input/output) COMPLEX*16 array, dimension
-* (1+(N-2)*abs(INCX))
-* On entry, the vector x.
-* On exit, it is overwritten with the vector v.
-*
-* INCX (input) INTEGER
-* The increment between elements of X. INCX > 0.
-*
-* TAU (output) COMPLEX*16
-* The value tau.
-*
-* =====================================================================
-*
-* .. Parameters ..
- DOUBLE PRECISION ONE, ZERO
- PARAMETER ( ONE = 1.0D+0, ZERO = 0.0D+0 )
-* ..
-* .. Local Scalars ..
- INTEGER J, KNT
- DOUBLE PRECISION ALPHI, ALPHR, BETA, RSAFMN, SAFMIN, XNORM
-* ..
-* .. External Functions ..
- DOUBLE PRECISION DLAMCH, DLAPY3, DZNRM2
- COMPLEX*16 ZLADIV
- EXTERNAL DLAMCH, DLAPY3, DZNRM2, ZLADIV
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC ABS, DBLE, DCMPLX, DIMAG, SIGN
-* ..
-* .. External Subroutines ..
- EXTERNAL ZDSCAL, ZSCAL
-* ..
-* .. Executable Statements ..
-*
- IF( N.LE.0 ) THEN
- TAU = ZERO
- RETURN
- END IF
-*
- XNORM = DZNRM2( N-1, X, INCX )
- ALPHR = DBLE( ALPHA )
- ALPHI = DIMAG( ALPHA )
-*
- IF( XNORM.EQ.ZERO .AND. ALPHI.EQ.ZERO ) THEN
-*
-* H = I
-*
- TAU = ZERO
- ELSE
-*
-* general case
-*
- BETA = -SIGN( DLAPY3( ALPHR, ALPHI, XNORM ), ALPHR )
- SAFMIN = DLAMCH( 'S' ) / DLAMCH( 'E' )
- RSAFMN = ONE / SAFMIN
-*
- IF( ABS( BETA ).LT.SAFMIN ) THEN
-*
-* XNORM, BETA may be inaccurate; scale X and recompute them
-*
- KNT = 0
- 10 CONTINUE
- KNT = KNT + 1
- CALL ZDSCAL( N-1, RSAFMN, X, INCX )
- BETA = BETA*RSAFMN
- ALPHI = ALPHI*RSAFMN
- ALPHR = ALPHR*RSAFMN
- IF( ABS( BETA ).LT.SAFMIN )
- $ GO TO 10
-*
-* New BETA is at most 1, at least SAFMIN
-*
- XNORM = DZNRM2( N-1, X, INCX )
- ALPHA = DCMPLX( ALPHR, ALPHI )
- BETA = -SIGN( DLAPY3( ALPHR, ALPHI, XNORM ), ALPHR )
- TAU = DCMPLX( ( BETA-ALPHR ) / BETA, -ALPHI / BETA )
- ALPHA = ZLADIV( DCMPLX( ONE ), ALPHA-BETA )
- CALL ZSCAL( N-1, ALPHA, X, INCX )
-*
-* If ALPHA is subnormal, it may lose relative accuracy
-*
- ALPHA = BETA
- DO 20 J = 1, KNT
- ALPHA = ALPHA*SAFMIN
- 20 CONTINUE
- ELSE
- TAU = DCMPLX( ( BETA-ALPHR ) / BETA, -ALPHI / BETA )
- ALPHA = ZLADIV( DCMPLX( ONE ), ALPHA-BETA )
- CALL ZSCAL( N-1, ALPHA, X, INCX )
- ALPHA = BETA
- END IF
- END IF
-*
- RETURN
-*
-* End of ZLARFG
-*
- END
diff --git a/src/lib/lapack/zlarft.f b/src/lib/lapack/zlarft.f
deleted file mode 100644
index 412265e3..00000000
--- a/src/lib/lapack/zlarft.f
+++ /dev/null
@@ -1,224 +0,0 @@
- SUBROUTINE ZLARFT( DIRECT, STOREV, N, K, V, LDV, TAU, T, LDT )
-*
-* -- LAPACK auxiliary routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- CHARACTER DIRECT, STOREV
- INTEGER K, LDT, LDV, N
-* ..
-* .. Array Arguments ..
- COMPLEX*16 T( LDT, * ), TAU( * ), V( LDV, * )
-* ..
-*
-* Purpose
-* =======
-*
-* ZLARFT forms the triangular factor T of a complex block reflector H
-* of order n, which is defined as a product of k elementary reflectors.
-*
-* If DIRECT = 'F', H = H(1) H(2) . . . H(k) and T is upper triangular;
-*
-* If DIRECT = 'B', H = H(k) . . . H(2) H(1) and T is lower triangular.
-*
-* If STOREV = 'C', the vector which defines the elementary reflector
-* H(i) is stored in the i-th column of the array V, and
-*
-* H = I - V * T * V'
-*
-* If STOREV = 'R', the vector which defines the elementary reflector
-* H(i) is stored in the i-th row of the array V, and
-*
-* H = I - V' * T * V
-*
-* Arguments
-* =========
-*
-* DIRECT (input) CHARACTER*1
-* Specifies the order in which the elementary reflectors are
-* multiplied to form the block reflector:
-* = 'F': H = H(1) H(2) . . . H(k) (Forward)
-* = 'B': H = H(k) . . . H(2) H(1) (Backward)
-*
-* STOREV (input) CHARACTER*1
-* Specifies how the vectors which define the elementary
-* reflectors are stored (see also Further Details):
-* = 'C': columnwise
-* = 'R': rowwise
-*
-* N (input) INTEGER
-* The order of the block reflector H. N >= 0.
-*
-* K (input) INTEGER
-* The order of the triangular factor T (= the number of
-* elementary reflectors). K >= 1.
-*
-* V (input/output) COMPLEX*16 array, dimension
-* (LDV,K) if STOREV = 'C'
-* (LDV,N) if STOREV = 'R'
-* The matrix V. See further details.
-*
-* LDV (input) INTEGER
-* The leading dimension of the array V.
-* If STOREV = 'C', LDV >= max(1,N); if STOREV = 'R', LDV >= K.
-*
-* TAU (input) COMPLEX*16 array, dimension (K)
-* TAU(i) must contain the scalar factor of the elementary
-* reflector H(i).
-*
-* T (output) COMPLEX*16 array, dimension (LDT,K)
-* The k by k triangular factor T of the block reflector.
-* If DIRECT = 'F', T is upper triangular; if DIRECT = 'B', T is
-* lower triangular. The rest of the array is not used.
-*
-* LDT (input) INTEGER
-* The leading dimension of the array T. LDT >= K.
-*
-* Further Details
-* ===============
-*
-* The shape of the matrix V and the storage of the vectors which define
-* the H(i) is best illustrated by the following example with n = 5 and
-* k = 3. The elements equal to 1 are not stored; the corresponding
-* array elements are modified but restored on exit. The rest of the
-* array is not used.
-*
-* DIRECT = 'F' and STOREV = 'C': DIRECT = 'F' and STOREV = 'R':
-*
-* V = ( 1 ) V = ( 1 v1 v1 v1 v1 )
-* ( v1 1 ) ( 1 v2 v2 v2 )
-* ( v1 v2 1 ) ( 1 v3 v3 )
-* ( v1 v2 v3 )
-* ( v1 v2 v3 )
-*
-* DIRECT = 'B' and STOREV = 'C': DIRECT = 'B' and STOREV = 'R':
-*
-* V = ( v1 v2 v3 ) V = ( v1 v1 1 )
-* ( v1 v2 v3 ) ( v2 v2 v2 1 )
-* ( 1 v2 v3 ) ( v3 v3 v3 v3 1 )
-* ( 1 v3 )
-* ( 1 )
-*
-* =====================================================================
-*
-* .. Parameters ..
- COMPLEX*16 ONE, ZERO
- PARAMETER ( ONE = ( 1.0D+0, 0.0D+0 ),
- $ ZERO = ( 0.0D+0, 0.0D+0 ) )
-* ..
-* .. Local Scalars ..
- INTEGER I, J
- COMPLEX*16 VII
-* ..
-* .. External Subroutines ..
- EXTERNAL ZGEMV, ZLACGV, ZTRMV
-* ..
-* .. External Functions ..
- LOGICAL LSAME
- EXTERNAL LSAME
-* ..
-* .. Executable Statements ..
-*
-* Quick return if possible
-*
- IF( N.EQ.0 )
- $ RETURN
-*
- IF( LSAME( DIRECT, 'F' ) ) THEN
- DO 20 I = 1, K
- IF( TAU( I ).EQ.ZERO ) THEN
-*
-* H(i) = I
-*
- DO 10 J = 1, I
- T( J, I ) = ZERO
- 10 CONTINUE
- ELSE
-*
-* general case
-*
- VII = V( I, I )
- V( I, I ) = ONE
- IF( LSAME( STOREV, 'C' ) ) THEN
-*
-* T(1:i-1,i) := - tau(i) * V(i:n,1:i-1)' * V(i:n,i)
-*
- CALL ZGEMV( 'Conjugate transpose', N-I+1, I-1,
- $ -TAU( I ), V( I, 1 ), LDV, V( I, I ), 1,
- $ ZERO, T( 1, I ), 1 )
- ELSE
-*
-* T(1:i-1,i) := - tau(i) * V(1:i-1,i:n) * V(i,i:n)'
-*
- IF( I.LT.N )
- $ CALL ZLACGV( N-I, V( I, I+1 ), LDV )
- CALL ZGEMV( 'No transpose', I-1, N-I+1, -TAU( I ),
- $ V( 1, I ), LDV, V( I, I ), LDV, ZERO,
- $ T( 1, I ), 1 )
- IF( I.LT.N )
- $ CALL ZLACGV( N-I, V( I, I+1 ), LDV )
- END IF
- V( I, I ) = VII
-*
-* T(1:i-1,i) := T(1:i-1,1:i-1) * T(1:i-1,i)
-*
- CALL ZTRMV( 'Upper', 'No transpose', 'Non-unit', I-1, T,
- $ LDT, T( 1, I ), 1 )
- T( I, I ) = TAU( I )
- END IF
- 20 CONTINUE
- ELSE
- DO 40 I = K, 1, -1
- IF( TAU( I ).EQ.ZERO ) THEN
-*
-* H(i) = I
-*
- DO 30 J = I, K
- T( J, I ) = ZERO
- 30 CONTINUE
- ELSE
-*
-* general case
-*
- IF( I.LT.K ) THEN
- IF( LSAME( STOREV, 'C' ) ) THEN
- VII = V( N-K+I, I )
- V( N-K+I, I ) = ONE
-*
-* T(i+1:k,i) :=
-* - tau(i) * V(1:n-k+i,i+1:k)' * V(1:n-k+i,i)
-*
- CALL ZGEMV( 'Conjugate transpose', N-K+I, K-I,
- $ -TAU( I ), V( 1, I+1 ), LDV, V( 1, I ),
- $ 1, ZERO, T( I+1, I ), 1 )
- V( N-K+I, I ) = VII
- ELSE
- VII = V( I, N-K+I )
- V( I, N-K+I ) = ONE
-*
-* T(i+1:k,i) :=
-* - tau(i) * V(i+1:k,1:n-k+i) * V(i,1:n-k+i)'
-*
- CALL ZLACGV( N-K+I-1, V( I, 1 ), LDV )
- CALL ZGEMV( 'No transpose', K-I, N-K+I, -TAU( I ),
- $ V( I+1, 1 ), LDV, V( I, 1 ), LDV, ZERO,
- $ T( I+1, I ), 1 )
- CALL ZLACGV( N-K+I-1, V( I, 1 ), LDV )
- V( I, N-K+I ) = VII
- END IF
-*
-* T(i+1:k,i) := T(i+1:k,i+1:k) * T(i+1:k,i)
-*
- CALL ZTRMV( 'Lower', 'No transpose', 'Non-unit', K-I,
- $ T( I+1, I+1 ), LDT, T( I+1, I ), 1 )
- END IF
- T( I, I ) = TAU( I )
- END IF
- 40 CONTINUE
- END IF
- RETURN
-*
-* End of ZLARFT
-*
- END
diff --git a/src/lib/lapack/zlarfx.f b/src/lib/lapack/zlarfx.f
deleted file mode 100644
index 327b9d03..00000000
--- a/src/lib/lapack/zlarfx.f
+++ /dev/null
@@ -1,641 +0,0 @@
- SUBROUTINE ZLARFX( SIDE, M, N, V, TAU, C, LDC, WORK )
-*
-* -- LAPACK auxiliary routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- CHARACTER SIDE
- INTEGER LDC, M, N
- COMPLEX*16 TAU
-* ..
-* .. Array Arguments ..
- COMPLEX*16 C( LDC, * ), V( * ), WORK( * )
-* ..
-*
-* Purpose
-* =======
-*
-* ZLARFX applies a complex elementary reflector H to a complex m by n
-* matrix C, from either the left or the right. H is represented in the
-* form
-*
-* H = I - tau * v * v'
-*
-* where tau is a complex scalar and v is a complex vector.
-*
-* If tau = 0, then H is taken to be the unit matrix
-*
-* This version uses inline code if H has order < 11.
-*
-* Arguments
-* =========
-*
-* SIDE (input) CHARACTER*1
-* = 'L': form H * C
-* = 'R': form C * H
-*
-* M (input) INTEGER
-* The number of rows of the matrix C.
-*
-* N (input) INTEGER
-* The number of columns of the matrix C.
-*
-* V (input) COMPLEX*16 array, dimension (M) if SIDE = 'L'
-* or (N) if SIDE = 'R'
-* The vector v in the representation of H.
-*
-* TAU (input) COMPLEX*16
-* The value tau in the representation of H.
-*
-* C (input/output) COMPLEX*16 array, dimension (LDC,N)
-* On entry, the m by n matrix C.
-* On exit, C is overwritten by the matrix H * C if SIDE = 'L',
-* or C * H if SIDE = 'R'.
-*
-* LDC (input) INTEGER
-* The leading dimension of the array C. LDA >= max(1,M).
-*
-* WORK (workspace) COMPLEX*16 array, dimension (N) if SIDE = 'L'
-* or (M) if SIDE = 'R'
-* WORK is not referenced if H has order < 11.
-*
-* =====================================================================
-*
-* .. Parameters ..
- COMPLEX*16 ZERO, ONE
- PARAMETER ( ZERO = ( 0.0D+0, 0.0D+0 ),
- $ ONE = ( 1.0D+0, 0.0D+0 ) )
-* ..
-* .. Local Scalars ..
- INTEGER J
- COMPLEX*16 SUM, T1, T10, T2, T3, T4, T5, T6, T7, T8, T9,
- $ V1, V10, V2, V3, V4, V5, V6, V7, V8, V9
-* ..
-* .. External Functions ..
- LOGICAL LSAME
- EXTERNAL LSAME
-* ..
-* .. External Subroutines ..
- EXTERNAL ZGEMV, ZGERC
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC DCONJG
-* ..
-* .. Executable Statements ..
-*
- IF( TAU.EQ.ZERO )
- $ RETURN
- IF( LSAME( SIDE, 'L' ) ) THEN
-*
-* Form H * C, where H has order m.
-*
- GO TO ( 10, 30, 50, 70, 90, 110, 130, 150,
- $ 170, 190 )M
-*
-* Code for general M
-*
-* w := C'*v
-*
- CALL ZGEMV( 'Conjugate transpose', M, N, ONE, C, LDC, V, 1,
- $ ZERO, WORK, 1 )
-*
-* C := C - tau * v * w'
-*
- CALL ZGERC( M, N, -TAU, V, 1, WORK, 1, C, LDC )
- GO TO 410
- 10 CONTINUE
-*
-* Special code for 1 x 1 Householder
-*
- T1 = ONE - TAU*V( 1 )*DCONJG( V( 1 ) )
- DO 20 J = 1, N
- C( 1, J ) = T1*C( 1, J )
- 20 CONTINUE
- GO TO 410
- 30 CONTINUE
-*
-* Special code for 2 x 2 Householder
-*
- V1 = DCONJG( V( 1 ) )
- T1 = TAU*DCONJG( V1 )
- V2 = DCONJG( V( 2 ) )
- T2 = TAU*DCONJG( V2 )
- DO 40 J = 1, N
- SUM = V1*C( 1, J ) + V2*C( 2, J )
- C( 1, J ) = C( 1, J ) - SUM*T1
- C( 2, J ) = C( 2, J ) - SUM*T2
- 40 CONTINUE
- GO TO 410
- 50 CONTINUE
-*
-* Special code for 3 x 3 Householder
-*
- V1 = DCONJG( V( 1 ) )
- T1 = TAU*DCONJG( V1 )
- V2 = DCONJG( V( 2 ) )
- T2 = TAU*DCONJG( V2 )
- V3 = DCONJG( V( 3 ) )
- T3 = TAU*DCONJG( V3 )
- DO 60 J = 1, N
- SUM = V1*C( 1, J ) + V2*C( 2, J ) + V3*C( 3, J )
- C( 1, J ) = C( 1, J ) - SUM*T1
- C( 2, J ) = C( 2, J ) - SUM*T2
- C( 3, J ) = C( 3, J ) - SUM*T3
- 60 CONTINUE
- GO TO 410
- 70 CONTINUE
-*
-* Special code for 4 x 4 Householder
-*
- V1 = DCONJG( V( 1 ) )
- T1 = TAU*DCONJG( V1 )
- V2 = DCONJG( V( 2 ) )
- T2 = TAU*DCONJG( V2 )
- V3 = DCONJG( V( 3 ) )
- T3 = TAU*DCONJG( V3 )
- V4 = DCONJG( V( 4 ) )
- T4 = TAU*DCONJG( V4 )
- DO 80 J = 1, N
- SUM = V1*C( 1, J ) + V2*C( 2, J ) + V3*C( 3, J ) +
- $ V4*C( 4, J )
- C( 1, J ) = C( 1, J ) - SUM*T1
- C( 2, J ) = C( 2, J ) - SUM*T2
- C( 3, J ) = C( 3, J ) - SUM*T3
- C( 4, J ) = C( 4, J ) - SUM*T4
- 80 CONTINUE
- GO TO 410
- 90 CONTINUE
-*
-* Special code for 5 x 5 Householder
-*
- V1 = DCONJG( V( 1 ) )
- T1 = TAU*DCONJG( V1 )
- V2 = DCONJG( V( 2 ) )
- T2 = TAU*DCONJG( V2 )
- V3 = DCONJG( V( 3 ) )
- T3 = TAU*DCONJG( V3 )
- V4 = DCONJG( V( 4 ) )
- T4 = TAU*DCONJG( V4 )
- V5 = DCONJG( V( 5 ) )
- T5 = TAU*DCONJG( V5 )
- DO 100 J = 1, N
- SUM = V1*C( 1, J ) + V2*C( 2, J ) + V3*C( 3, J ) +
- $ V4*C( 4, J ) + V5*C( 5, J )
- C( 1, J ) = C( 1, J ) - SUM*T1
- C( 2, J ) = C( 2, J ) - SUM*T2
- C( 3, J ) = C( 3, J ) - SUM*T3
- C( 4, J ) = C( 4, J ) - SUM*T4
- C( 5, J ) = C( 5, J ) - SUM*T5
- 100 CONTINUE
- GO TO 410
- 110 CONTINUE
-*
-* Special code for 6 x 6 Householder
-*
- V1 = DCONJG( V( 1 ) )
- T1 = TAU*DCONJG( V1 )
- V2 = DCONJG( V( 2 ) )
- T2 = TAU*DCONJG( V2 )
- V3 = DCONJG( V( 3 ) )
- T3 = TAU*DCONJG( V3 )
- V4 = DCONJG( V( 4 ) )
- T4 = TAU*DCONJG( V4 )
- V5 = DCONJG( V( 5 ) )
- T5 = TAU*DCONJG( V5 )
- V6 = DCONJG( V( 6 ) )
- T6 = TAU*DCONJG( V6 )
- DO 120 J = 1, N
- SUM = V1*C( 1, J ) + V2*C( 2, J ) + V3*C( 3, J ) +
- $ V4*C( 4, J ) + V5*C( 5, J ) + V6*C( 6, J )
- C( 1, J ) = C( 1, J ) - SUM*T1
- C( 2, J ) = C( 2, J ) - SUM*T2
- C( 3, J ) = C( 3, J ) - SUM*T3
- C( 4, J ) = C( 4, J ) - SUM*T4
- C( 5, J ) = C( 5, J ) - SUM*T5
- C( 6, J ) = C( 6, J ) - SUM*T6
- 120 CONTINUE
- GO TO 410
- 130 CONTINUE
-*
-* Special code for 7 x 7 Householder
-*
- V1 = DCONJG( V( 1 ) )
- T1 = TAU*DCONJG( V1 )
- V2 = DCONJG( V( 2 ) )
- T2 = TAU*DCONJG( V2 )
- V3 = DCONJG( V( 3 ) )
- T3 = TAU*DCONJG( V3 )
- V4 = DCONJG( V( 4 ) )
- T4 = TAU*DCONJG( V4 )
- V5 = DCONJG( V( 5 ) )
- T5 = TAU*DCONJG( V5 )
- V6 = DCONJG( V( 6 ) )
- T6 = TAU*DCONJG( V6 )
- V7 = DCONJG( V( 7 ) )
- T7 = TAU*DCONJG( V7 )
- DO 140 J = 1, N
- SUM = V1*C( 1, J ) + V2*C( 2, J ) + V3*C( 3, J ) +
- $ V4*C( 4, J ) + V5*C( 5, J ) + V6*C( 6, J ) +
- $ V7*C( 7, J )
- C( 1, J ) = C( 1, J ) - SUM*T1
- C( 2, J ) = C( 2, J ) - SUM*T2
- C( 3, J ) = C( 3, J ) - SUM*T3
- C( 4, J ) = C( 4, J ) - SUM*T4
- C( 5, J ) = C( 5, J ) - SUM*T5
- C( 6, J ) = C( 6, J ) - SUM*T6
- C( 7, J ) = C( 7, J ) - SUM*T7
- 140 CONTINUE
- GO TO 410
- 150 CONTINUE
-*
-* Special code for 8 x 8 Householder
-*
- V1 = DCONJG( V( 1 ) )
- T1 = TAU*DCONJG( V1 )
- V2 = DCONJG( V( 2 ) )
- T2 = TAU*DCONJG( V2 )
- V3 = DCONJG( V( 3 ) )
- T3 = TAU*DCONJG( V3 )
- V4 = DCONJG( V( 4 ) )
- T4 = TAU*DCONJG( V4 )
- V5 = DCONJG( V( 5 ) )
- T5 = TAU*DCONJG( V5 )
- V6 = DCONJG( V( 6 ) )
- T6 = TAU*DCONJG( V6 )
- V7 = DCONJG( V( 7 ) )
- T7 = TAU*DCONJG( V7 )
- V8 = DCONJG( V( 8 ) )
- T8 = TAU*DCONJG( V8 )
- DO 160 J = 1, N
- SUM = V1*C( 1, J ) + V2*C( 2, J ) + V3*C( 3, J ) +
- $ V4*C( 4, J ) + V5*C( 5, J ) + V6*C( 6, J ) +
- $ V7*C( 7, J ) + V8*C( 8, J )
- C( 1, J ) = C( 1, J ) - SUM*T1
- C( 2, J ) = C( 2, J ) - SUM*T2
- C( 3, J ) = C( 3, J ) - SUM*T3
- C( 4, J ) = C( 4, J ) - SUM*T4
- C( 5, J ) = C( 5, J ) - SUM*T5
- C( 6, J ) = C( 6, J ) - SUM*T6
- C( 7, J ) = C( 7, J ) - SUM*T7
- C( 8, J ) = C( 8, J ) - SUM*T8
- 160 CONTINUE
- GO TO 410
- 170 CONTINUE
-*
-* Special code for 9 x 9 Householder
-*
- V1 = DCONJG( V( 1 ) )
- T1 = TAU*DCONJG( V1 )
- V2 = DCONJG( V( 2 ) )
- T2 = TAU*DCONJG( V2 )
- V3 = DCONJG( V( 3 ) )
- T3 = TAU*DCONJG( V3 )
- V4 = DCONJG( V( 4 ) )
- T4 = TAU*DCONJG( V4 )
- V5 = DCONJG( V( 5 ) )
- T5 = TAU*DCONJG( V5 )
- V6 = DCONJG( V( 6 ) )
- T6 = TAU*DCONJG( V6 )
- V7 = DCONJG( V( 7 ) )
- T7 = TAU*DCONJG( V7 )
- V8 = DCONJG( V( 8 ) )
- T8 = TAU*DCONJG( V8 )
- V9 = DCONJG( V( 9 ) )
- T9 = TAU*DCONJG( V9 )
- DO 180 J = 1, N
- SUM = V1*C( 1, J ) + V2*C( 2, J ) + V3*C( 3, J ) +
- $ V4*C( 4, J ) + V5*C( 5, J ) + V6*C( 6, J ) +
- $ V7*C( 7, J ) + V8*C( 8, J ) + V9*C( 9, J )
- C( 1, J ) = C( 1, J ) - SUM*T1
- C( 2, J ) = C( 2, J ) - SUM*T2
- C( 3, J ) = C( 3, J ) - SUM*T3
- C( 4, J ) = C( 4, J ) - SUM*T4
- C( 5, J ) = C( 5, J ) - SUM*T5
- C( 6, J ) = C( 6, J ) - SUM*T6
- C( 7, J ) = C( 7, J ) - SUM*T7
- C( 8, J ) = C( 8, J ) - SUM*T8
- C( 9, J ) = C( 9, J ) - SUM*T9
- 180 CONTINUE
- GO TO 410
- 190 CONTINUE
-*
-* Special code for 10 x 10 Householder
-*
- V1 = DCONJG( V( 1 ) )
- T1 = TAU*DCONJG( V1 )
- V2 = DCONJG( V( 2 ) )
- T2 = TAU*DCONJG( V2 )
- V3 = DCONJG( V( 3 ) )
- T3 = TAU*DCONJG( V3 )
- V4 = DCONJG( V( 4 ) )
- T4 = TAU*DCONJG( V4 )
- V5 = DCONJG( V( 5 ) )
- T5 = TAU*DCONJG( V5 )
- V6 = DCONJG( V( 6 ) )
- T6 = TAU*DCONJG( V6 )
- V7 = DCONJG( V( 7 ) )
- T7 = TAU*DCONJG( V7 )
- V8 = DCONJG( V( 8 ) )
- T8 = TAU*DCONJG( V8 )
- V9 = DCONJG( V( 9 ) )
- T9 = TAU*DCONJG( V9 )
- V10 = DCONJG( V( 10 ) )
- T10 = TAU*DCONJG( V10 )
- DO 200 J = 1, N
- SUM = V1*C( 1, J ) + V2*C( 2, J ) + V3*C( 3, J ) +
- $ V4*C( 4, J ) + V5*C( 5, J ) + V6*C( 6, J ) +
- $ V7*C( 7, J ) + V8*C( 8, J ) + V9*C( 9, J ) +
- $ V10*C( 10, J )
- C( 1, J ) = C( 1, J ) - SUM*T1
- C( 2, J ) = C( 2, J ) - SUM*T2
- C( 3, J ) = C( 3, J ) - SUM*T3
- C( 4, J ) = C( 4, J ) - SUM*T4
- C( 5, J ) = C( 5, J ) - SUM*T5
- C( 6, J ) = C( 6, J ) - SUM*T6
- C( 7, J ) = C( 7, J ) - SUM*T7
- C( 8, J ) = C( 8, J ) - SUM*T8
- C( 9, J ) = C( 9, J ) - SUM*T9
- C( 10, J ) = C( 10, J ) - SUM*T10
- 200 CONTINUE
- GO TO 410
- ELSE
-*
-* Form C * H, where H has order n.
-*
- GO TO ( 210, 230, 250, 270, 290, 310, 330, 350,
- $ 370, 390 )N
-*
-* Code for general N
-*
-* w := C * v
-*
- CALL ZGEMV( 'No transpose', M, N, ONE, C, LDC, V, 1, ZERO,
- $ WORK, 1 )
-*
-* C := C - tau * w * v'
-*
- CALL ZGERC( M, N, -TAU, WORK, 1, V, 1, C, LDC )
- GO TO 410
- 210 CONTINUE
-*
-* Special code for 1 x 1 Householder
-*
- T1 = ONE - TAU*V( 1 )*DCONJG( V( 1 ) )
- DO 220 J = 1, M
- C( J, 1 ) = T1*C( J, 1 )
- 220 CONTINUE
- GO TO 410
- 230 CONTINUE
-*
-* Special code for 2 x 2 Householder
-*
- V1 = V( 1 )
- T1 = TAU*DCONJG( V1 )
- V2 = V( 2 )
- T2 = TAU*DCONJG( V2 )
- DO 240 J = 1, M
- SUM = V1*C( J, 1 ) + V2*C( J, 2 )
- C( J, 1 ) = C( J, 1 ) - SUM*T1
- C( J, 2 ) = C( J, 2 ) - SUM*T2
- 240 CONTINUE
- GO TO 410
- 250 CONTINUE
-*
-* Special code for 3 x 3 Householder
-*
- V1 = V( 1 )
- T1 = TAU*DCONJG( V1 )
- V2 = V( 2 )
- T2 = TAU*DCONJG( V2 )
- V3 = V( 3 )
- T3 = TAU*DCONJG( V3 )
- DO 260 J = 1, M
- SUM = V1*C( J, 1 ) + V2*C( J, 2 ) + V3*C( J, 3 )
- C( J, 1 ) = C( J, 1 ) - SUM*T1
- C( J, 2 ) = C( J, 2 ) - SUM*T2
- C( J, 3 ) = C( J, 3 ) - SUM*T3
- 260 CONTINUE
- GO TO 410
- 270 CONTINUE
-*
-* Special code for 4 x 4 Householder
-*
- V1 = V( 1 )
- T1 = TAU*DCONJG( V1 )
- V2 = V( 2 )
- T2 = TAU*DCONJG( V2 )
- V3 = V( 3 )
- T3 = TAU*DCONJG( V3 )
- V4 = V( 4 )
- T4 = TAU*DCONJG( V4 )
- DO 280 J = 1, M
- SUM = V1*C( J, 1 ) + V2*C( J, 2 ) + V3*C( J, 3 ) +
- $ V4*C( J, 4 )
- C( J, 1 ) = C( J, 1 ) - SUM*T1
- C( J, 2 ) = C( J, 2 ) - SUM*T2
- C( J, 3 ) = C( J, 3 ) - SUM*T3
- C( J, 4 ) = C( J, 4 ) - SUM*T4
- 280 CONTINUE
- GO TO 410
- 290 CONTINUE
-*
-* Special code for 5 x 5 Householder
-*
- V1 = V( 1 )
- T1 = TAU*DCONJG( V1 )
- V2 = V( 2 )
- T2 = TAU*DCONJG( V2 )
- V3 = V( 3 )
- T3 = TAU*DCONJG( V3 )
- V4 = V( 4 )
- T4 = TAU*DCONJG( V4 )
- V5 = V( 5 )
- T5 = TAU*DCONJG( V5 )
- DO 300 J = 1, M
- SUM = V1*C( J, 1 ) + V2*C( J, 2 ) + V3*C( J, 3 ) +
- $ V4*C( J, 4 ) + V5*C( J, 5 )
- C( J, 1 ) = C( J, 1 ) - SUM*T1
- C( J, 2 ) = C( J, 2 ) - SUM*T2
- C( J, 3 ) = C( J, 3 ) - SUM*T3
- C( J, 4 ) = C( J, 4 ) - SUM*T4
- C( J, 5 ) = C( J, 5 ) - SUM*T5
- 300 CONTINUE
- GO TO 410
- 310 CONTINUE
-*
-* Special code for 6 x 6 Householder
-*
- V1 = V( 1 )
- T1 = TAU*DCONJG( V1 )
- V2 = V( 2 )
- T2 = TAU*DCONJG( V2 )
- V3 = V( 3 )
- T3 = TAU*DCONJG( V3 )
- V4 = V( 4 )
- T4 = TAU*DCONJG( V4 )
- V5 = V( 5 )
- T5 = TAU*DCONJG( V5 )
- V6 = V( 6 )
- T6 = TAU*DCONJG( V6 )
- DO 320 J = 1, M
- SUM = V1*C( J, 1 ) + V2*C( J, 2 ) + V3*C( J, 3 ) +
- $ V4*C( J, 4 ) + V5*C( J, 5 ) + V6*C( J, 6 )
- C( J, 1 ) = C( J, 1 ) - SUM*T1
- C( J, 2 ) = C( J, 2 ) - SUM*T2
- C( J, 3 ) = C( J, 3 ) - SUM*T3
- C( J, 4 ) = C( J, 4 ) - SUM*T4
- C( J, 5 ) = C( J, 5 ) - SUM*T5
- C( J, 6 ) = C( J, 6 ) - SUM*T6
- 320 CONTINUE
- GO TO 410
- 330 CONTINUE
-*
-* Special code for 7 x 7 Householder
-*
- V1 = V( 1 )
- T1 = TAU*DCONJG( V1 )
- V2 = V( 2 )
- T2 = TAU*DCONJG( V2 )
- V3 = V( 3 )
- T3 = TAU*DCONJG( V3 )
- V4 = V( 4 )
- T4 = TAU*DCONJG( V4 )
- V5 = V( 5 )
- T5 = TAU*DCONJG( V5 )
- V6 = V( 6 )
- T6 = TAU*DCONJG( V6 )
- V7 = V( 7 )
- T7 = TAU*DCONJG( V7 )
- DO 340 J = 1, M
- SUM = V1*C( J, 1 ) + V2*C( J, 2 ) + V3*C( J, 3 ) +
- $ V4*C( J, 4 ) + V5*C( J, 5 ) + V6*C( J, 6 ) +
- $ V7*C( J, 7 )
- C( J, 1 ) = C( J, 1 ) - SUM*T1
- C( J, 2 ) = C( J, 2 ) - SUM*T2
- C( J, 3 ) = C( J, 3 ) - SUM*T3
- C( J, 4 ) = C( J, 4 ) - SUM*T4
- C( J, 5 ) = C( J, 5 ) - SUM*T5
- C( J, 6 ) = C( J, 6 ) - SUM*T6
- C( J, 7 ) = C( J, 7 ) - SUM*T7
- 340 CONTINUE
- GO TO 410
- 350 CONTINUE
-*
-* Special code for 8 x 8 Householder
-*
- V1 = V( 1 )
- T1 = TAU*DCONJG( V1 )
- V2 = V( 2 )
- T2 = TAU*DCONJG( V2 )
- V3 = V( 3 )
- T3 = TAU*DCONJG( V3 )
- V4 = V( 4 )
- T4 = TAU*DCONJG( V4 )
- V5 = V( 5 )
- T5 = TAU*DCONJG( V5 )
- V6 = V( 6 )
- T6 = TAU*DCONJG( V6 )
- V7 = V( 7 )
- T7 = TAU*DCONJG( V7 )
- V8 = V( 8 )
- T8 = TAU*DCONJG( V8 )
- DO 360 J = 1, M
- SUM = V1*C( J, 1 ) + V2*C( J, 2 ) + V3*C( J, 3 ) +
- $ V4*C( J, 4 ) + V5*C( J, 5 ) + V6*C( J, 6 ) +
- $ V7*C( J, 7 ) + V8*C( J, 8 )
- C( J, 1 ) = C( J, 1 ) - SUM*T1
- C( J, 2 ) = C( J, 2 ) - SUM*T2
- C( J, 3 ) = C( J, 3 ) - SUM*T3
- C( J, 4 ) = C( J, 4 ) - SUM*T4
- C( J, 5 ) = C( J, 5 ) - SUM*T5
- C( J, 6 ) = C( J, 6 ) - SUM*T6
- C( J, 7 ) = C( J, 7 ) - SUM*T7
- C( J, 8 ) = C( J, 8 ) - SUM*T8
- 360 CONTINUE
- GO TO 410
- 370 CONTINUE
-*
-* Special code for 9 x 9 Householder
-*
- V1 = V( 1 )
- T1 = TAU*DCONJG( V1 )
- V2 = V( 2 )
- T2 = TAU*DCONJG( V2 )
- V3 = V( 3 )
- T3 = TAU*DCONJG( V3 )
- V4 = V( 4 )
- T4 = TAU*DCONJG( V4 )
- V5 = V( 5 )
- T5 = TAU*DCONJG( V5 )
- V6 = V( 6 )
- T6 = TAU*DCONJG( V6 )
- V7 = V( 7 )
- T7 = TAU*DCONJG( V7 )
- V8 = V( 8 )
- T8 = TAU*DCONJG( V8 )
- V9 = V( 9 )
- T9 = TAU*DCONJG( V9 )
- DO 380 J = 1, M
- SUM = V1*C( J, 1 ) + V2*C( J, 2 ) + V3*C( J, 3 ) +
- $ V4*C( J, 4 ) + V5*C( J, 5 ) + V6*C( J, 6 ) +
- $ V7*C( J, 7 ) + V8*C( J, 8 ) + V9*C( J, 9 )
- C( J, 1 ) = C( J, 1 ) - SUM*T1
- C( J, 2 ) = C( J, 2 ) - SUM*T2
- C( J, 3 ) = C( J, 3 ) - SUM*T3
- C( J, 4 ) = C( J, 4 ) - SUM*T4
- C( J, 5 ) = C( J, 5 ) - SUM*T5
- C( J, 6 ) = C( J, 6 ) - SUM*T6
- C( J, 7 ) = C( J, 7 ) - SUM*T7
- C( J, 8 ) = C( J, 8 ) - SUM*T8
- C( J, 9 ) = C( J, 9 ) - SUM*T9
- 380 CONTINUE
- GO TO 410
- 390 CONTINUE
-*
-* Special code for 10 x 10 Householder
-*
- V1 = V( 1 )
- T1 = TAU*DCONJG( V1 )
- V2 = V( 2 )
- T2 = TAU*DCONJG( V2 )
- V3 = V( 3 )
- T3 = TAU*DCONJG( V3 )
- V4 = V( 4 )
- T4 = TAU*DCONJG( V4 )
- V5 = V( 5 )
- T5 = TAU*DCONJG( V5 )
- V6 = V( 6 )
- T6 = TAU*DCONJG( V6 )
- V7 = V( 7 )
- T7 = TAU*DCONJG( V7 )
- V8 = V( 8 )
- T8 = TAU*DCONJG( V8 )
- V9 = V( 9 )
- T9 = TAU*DCONJG( V9 )
- V10 = V( 10 )
- T10 = TAU*DCONJG( V10 )
- DO 400 J = 1, M
- SUM = V1*C( J, 1 ) + V2*C( J, 2 ) + V3*C( J, 3 ) +
- $ V4*C( J, 4 ) + V5*C( J, 5 ) + V6*C( J, 6 ) +
- $ V7*C( J, 7 ) + V8*C( J, 8 ) + V9*C( J, 9 ) +
- $ V10*C( J, 10 )
- C( J, 1 ) = C( J, 1 ) - SUM*T1
- C( J, 2 ) = C( J, 2 ) - SUM*T2
- C( J, 3 ) = C( J, 3 ) - SUM*T3
- C( J, 4 ) = C( J, 4 ) - SUM*T4
- C( J, 5 ) = C( J, 5 ) - SUM*T5
- C( J, 6 ) = C( J, 6 ) - SUM*T6
- C( J, 7 ) = C( J, 7 ) - SUM*T7
- C( J, 8 ) = C( J, 8 ) - SUM*T8
- C( J, 9 ) = C( J, 9 ) - SUM*T9
- C( J, 10 ) = C( J, 10 ) - SUM*T10
- 400 CONTINUE
- GO TO 410
- END IF
- 410 CONTINUE
- RETURN
-*
-* End of ZLARFX
-*
- END
diff --git a/src/lib/lapack/zlartg.f b/src/lib/lapack/zlartg.f
deleted file mode 100644
index 6d3a850e..00000000
--- a/src/lib/lapack/zlartg.f
+++ /dev/null
@@ -1,195 +0,0 @@
- SUBROUTINE ZLARTG( F, G, CS, SN, R )
-*
-* -- LAPACK auxiliary routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- DOUBLE PRECISION CS
- COMPLEX*16 F, G, R, SN
-* ..
-*
-* Purpose
-* =======
-*
-* ZLARTG generates a plane rotation so that
-*
-* [ CS SN ] [ F ] [ R ]
-* [ __ ] . [ ] = [ ] where CS**2 + |SN|**2 = 1.
-* [ -SN CS ] [ G ] [ 0 ]
-*
-* This is a faster version of the BLAS1 routine ZROTG, except for
-* the following differences:
-* F and G are unchanged on return.
-* If G=0, then CS=1 and SN=0.
-* If F=0, then CS=0 and SN is chosen so that R is real.
-*
-* Arguments
-* =========
-*
-* F (input) COMPLEX*16
-* The first component of vector to be rotated.
-*
-* G (input) COMPLEX*16
-* The second component of vector to be rotated.
-*
-* CS (output) DOUBLE PRECISION
-* The cosine of the rotation.
-*
-* SN (output) COMPLEX*16
-* The sine of the rotation.
-*
-* R (output) COMPLEX*16
-* The nonzero component of the rotated vector.
-*
-* Further Details
-* ======= =======
-*
-* 3-5-96 - Modified with a new algorithm by W. Kahan and J. Demmel
-*
-* This version has a few statements commented out for thread safety
-* (machine parameters are computed on each entry). 10 feb 03, SJH.
-*
-* =====================================================================
-*
-* .. Parameters ..
- DOUBLE PRECISION TWO, ONE, ZERO
- PARAMETER ( TWO = 2.0D+0, ONE = 1.0D+0, ZERO = 0.0D+0 )
- COMPLEX*16 CZERO
- PARAMETER ( CZERO = ( 0.0D+0, 0.0D+0 ) )
-* ..
-* .. Local Scalars ..
-* LOGICAL FIRST
- INTEGER COUNT, I
- DOUBLE PRECISION D, DI, DR, EPS, F2, F2S, G2, G2S, SAFMIN,
- $ SAFMN2, SAFMX2, SCALE
- COMPLEX*16 FF, FS, GS
-* ..
-* .. External Functions ..
- DOUBLE PRECISION DLAMCH, DLAPY2
- EXTERNAL DLAMCH, DLAPY2
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC ABS, DBLE, DCMPLX, DCONJG, DIMAG, INT, LOG,
- $ MAX, SQRT
-* ..
-* .. Statement Functions ..
- DOUBLE PRECISION ABS1, ABSSQ
-* ..
-* .. Save statement ..
-* SAVE FIRST, SAFMX2, SAFMIN, SAFMN2
-* ..
-* .. Data statements ..
-* DATA FIRST / .TRUE. /
-* ..
-* .. Statement Function definitions ..
- ABS1( FF ) = MAX( ABS( DBLE( FF ) ), ABS( DIMAG( FF ) ) )
- ABSSQ( FF ) = DBLE( FF )**2 + DIMAG( FF )**2
-* ..
-* .. Executable Statements ..
-*
-* IF( FIRST ) THEN
- SAFMIN = DLAMCH( 'S' )
- EPS = DLAMCH( 'E' )
- SAFMN2 = DLAMCH( 'B' )**INT( LOG( SAFMIN / EPS ) /
- $ LOG( DLAMCH( 'B' ) ) / TWO )
- SAFMX2 = ONE / SAFMN2
-* FIRST = .FALSE.
-* END IF
- SCALE = MAX( ABS1( F ), ABS1( G ) )
- FS = F
- GS = G
- COUNT = 0
- IF( SCALE.GE.SAFMX2 ) THEN
- 10 CONTINUE
- COUNT = COUNT + 1
- FS = FS*SAFMN2
- GS = GS*SAFMN2
- SCALE = SCALE*SAFMN2
- IF( SCALE.GE.SAFMX2 )
- $ GO TO 10
- ELSE IF( SCALE.LE.SAFMN2 ) THEN
- IF( G.EQ.CZERO ) THEN
- CS = ONE
- SN = CZERO
- R = F
- RETURN
- END IF
- 20 CONTINUE
- COUNT = COUNT - 1
- FS = FS*SAFMX2
- GS = GS*SAFMX2
- SCALE = SCALE*SAFMX2
- IF( SCALE.LE.SAFMN2 )
- $ GO TO 20
- END IF
- F2 = ABSSQ( FS )
- G2 = ABSSQ( GS )
- IF( F2.LE.MAX( G2, ONE )*SAFMIN ) THEN
-*
-* This is a rare case: F is very small.
-*
- IF( F.EQ.CZERO ) THEN
- CS = ZERO
- R = DLAPY2( DBLE( G ), DIMAG( G ) )
-* Do complex/real division explicitly with two real divisions
- D = DLAPY2( DBLE( GS ), DIMAG( GS ) )
- SN = DCMPLX( DBLE( GS ) / D, -DIMAG( GS ) / D )
- RETURN
- END IF
- F2S = DLAPY2( DBLE( FS ), DIMAG( FS ) )
-* G2 and G2S are accurate
-* G2 is at least SAFMIN, and G2S is at least SAFMN2
- G2S = SQRT( G2 )
-* Error in CS from underflow in F2S is at most
-* UNFL / SAFMN2 .lt. sqrt(UNFL*EPS) .lt. EPS
-* If MAX(G2,ONE)=G2, then F2 .lt. G2*SAFMIN,
-* and so CS .lt. sqrt(SAFMIN)
-* If MAX(G2,ONE)=ONE, then F2 .lt. SAFMIN
-* and so CS .lt. sqrt(SAFMIN)/SAFMN2 = sqrt(EPS)
-* Therefore, CS = F2S/G2S / sqrt( 1 + (F2S/G2S)**2 ) = F2S/G2S
- CS = F2S / G2S
-* Make sure abs(FF) = 1
-* Do complex/real division explicitly with 2 real divisions
- IF( ABS1( F ).GT.ONE ) THEN
- D = DLAPY2( DBLE( F ), DIMAG( F ) )
- FF = DCMPLX( DBLE( F ) / D, DIMAG( F ) / D )
- ELSE
- DR = SAFMX2*DBLE( F )
- DI = SAFMX2*DIMAG( F )
- D = DLAPY2( DR, DI )
- FF = DCMPLX( DR / D, DI / D )
- END IF
- SN = FF*DCMPLX( DBLE( GS ) / G2S, -DIMAG( GS ) / G2S )
- R = CS*F + SN*G
- ELSE
-*
-* This is the most common case.
-* Neither F2 nor F2/G2 are less than SAFMIN
-* F2S cannot overflow, and it is accurate
-*
- F2S = SQRT( ONE+G2 / F2 )
-* Do the F2S(real)*FS(complex) multiply with two real multiplies
- R = DCMPLX( F2S*DBLE( FS ), F2S*DIMAG( FS ) )
- CS = ONE / F2S
- D = F2 + G2
-* Do complex/real division explicitly with two real divisions
- SN = DCMPLX( DBLE( R ) / D, DIMAG( R ) / D )
- SN = SN*DCONJG( GS )
- IF( COUNT.NE.0 ) THEN
- IF( COUNT.GT.0 ) THEN
- DO 30 I = 1, COUNT
- R = R*SAFMX2
- 30 CONTINUE
- ELSE
- DO 40 I = 1, -COUNT
- R = R*SAFMN2
- 40 CONTINUE
- END IF
- END IF
- END IF
- RETURN
-*
-* End of ZLARTG
-*
- END
diff --git a/src/lib/lapack/zlarz.f b/src/lib/lapack/zlarz.f
deleted file mode 100644
index 18124672..00000000
--- a/src/lib/lapack/zlarz.f
+++ /dev/null
@@ -1,157 +0,0 @@
- SUBROUTINE ZLARZ( SIDE, M, N, L, V, INCV, TAU, C, LDC, WORK )
-*
-* -- LAPACK routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- CHARACTER SIDE
- INTEGER INCV, L, LDC, M, N
- COMPLEX*16 TAU
-* ..
-* .. Array Arguments ..
- COMPLEX*16 C( LDC, * ), V( * ), WORK( * )
-* ..
-*
-* Purpose
-* =======
-*
-* ZLARZ applies a complex elementary reflector H to a complex
-* M-by-N matrix C, from either the left or the right. H is represented
-* in the form
-*
-* H = I - tau * v * v'
-*
-* where tau is a complex scalar and v is a complex vector.
-*
-* If tau = 0, then H is taken to be the unit matrix.
-*
-* To apply H' (the conjugate transpose of H), supply conjg(tau) instead
-* tau.
-*
-* H is a product of k elementary reflectors as returned by ZTZRZF.
-*
-* Arguments
-* =========
-*
-* SIDE (input) CHARACTER*1
-* = 'L': form H * C
-* = 'R': form C * H
-*
-* M (input) INTEGER
-* The number of rows of the matrix C.
-*
-* N (input) INTEGER
-* The number of columns of the matrix C.
-*
-* L (input) INTEGER
-* The number of entries of the vector V containing
-* the meaningful part of the Householder vectors.
-* If SIDE = 'L', M >= L >= 0, if SIDE = 'R', N >= L >= 0.
-*
-* V (input) COMPLEX*16 array, dimension (1+(L-1)*abs(INCV))
-* The vector v in the representation of H as returned by
-* ZTZRZF. V is not used if TAU = 0.
-*
-* INCV (input) INTEGER
-* The increment between elements of v. INCV <> 0.
-*
-* TAU (input) COMPLEX*16
-* The value tau in the representation of H.
-*
-* C (input/output) COMPLEX*16 array, dimension (LDC,N)
-* On entry, the M-by-N matrix C.
-* On exit, C is overwritten by the matrix H * C if SIDE = 'L',
-* or C * H if SIDE = 'R'.
-*
-* LDC (input) INTEGER
-* The leading dimension of the array C. LDC >= max(1,M).
-*
-* WORK (workspace) COMPLEX*16 array, dimension
-* (N) if SIDE = 'L'
-* or (M) if SIDE = 'R'
-*
-* Further Details
-* ===============
-*
-* Based on contributions by
-* A. Petitet, Computer Science Dept., Univ. of Tenn., Knoxville, USA
-*
-* =====================================================================
-*
-* .. Parameters ..
- COMPLEX*16 ONE, ZERO
- PARAMETER ( ONE = ( 1.0D+0, 0.0D+0 ),
- $ ZERO = ( 0.0D+0, 0.0D+0 ) )
-* ..
-* .. External Subroutines ..
- EXTERNAL ZAXPY, ZCOPY, ZGEMV, ZGERC, ZGERU, ZLACGV
-* ..
-* .. External Functions ..
- LOGICAL LSAME
- EXTERNAL LSAME
-* ..
-* .. Executable Statements ..
-*
- IF( LSAME( SIDE, 'L' ) ) THEN
-*
-* Form H * C
-*
- IF( TAU.NE.ZERO ) THEN
-*
-* w( 1:n ) = conjg( C( 1, 1:n ) )
-*
- CALL ZCOPY( N, C, LDC, WORK, 1 )
- CALL ZLACGV( N, WORK, 1 )
-*
-* w( 1:n ) = conjg( w( 1:n ) + C( m-l+1:m, 1:n )' * v( 1:l ) )
-*
- CALL ZGEMV( 'Conjugate transpose', L, N, ONE, C( M-L+1, 1 ),
- $ LDC, V, INCV, ONE, WORK, 1 )
- CALL ZLACGV( N, WORK, 1 )
-*
-* C( 1, 1:n ) = C( 1, 1:n ) - tau * w( 1:n )
-*
- CALL ZAXPY( N, -TAU, WORK, 1, C, LDC )
-*
-* C( m-l+1:m, 1:n ) = C( m-l+1:m, 1:n ) - ...
-* tau * v( 1:l ) * conjg( w( 1:n )' )
-*
- CALL ZGERU( L, N, -TAU, V, INCV, WORK, 1, C( M-L+1, 1 ),
- $ LDC )
- END IF
-*
- ELSE
-*
-* Form C * H
-*
- IF( TAU.NE.ZERO ) THEN
-*
-* w( 1:m ) = C( 1:m, 1 )
-*
- CALL ZCOPY( M, C, 1, WORK, 1 )
-*
-* w( 1:m ) = w( 1:m ) + C( 1:m, n-l+1:n, 1:n ) * v( 1:l )
-*
- CALL ZGEMV( 'No transpose', M, L, ONE, C( 1, N-L+1 ), LDC,
- $ V, INCV, ONE, WORK, 1 )
-*
-* C( 1:m, 1 ) = C( 1:m, 1 ) - tau * w( 1:m )
-*
- CALL ZAXPY( M, -TAU, WORK, 1, C, 1 )
-*
-* C( 1:m, n-l+1:n ) = C( 1:m, n-l+1:n ) - ...
-* tau * w( 1:m ) * v( 1:l )'
-*
- CALL ZGERC( M, L, -TAU, WORK, 1, V, INCV, C( 1, N-L+1 ),
- $ LDC )
-*
- END IF
-*
- END IF
-*
- RETURN
-*
-* End of ZLARZ
-*
- END
diff --git a/src/lib/lapack/zlarzb.f b/src/lib/lapack/zlarzb.f
deleted file mode 100644
index 05d2a0e3..00000000
--- a/src/lib/lapack/zlarzb.f
+++ /dev/null
@@ -1,234 +0,0 @@
- SUBROUTINE ZLARZB( SIDE, TRANS, DIRECT, STOREV, M, N, K, L, V,
- $ LDV, T, LDT, C, LDC, WORK, LDWORK )
-*
-* -- LAPACK routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- CHARACTER DIRECT, SIDE, STOREV, TRANS
- INTEGER K, L, LDC, LDT, LDV, LDWORK, M, N
-* ..
-* .. Array Arguments ..
- COMPLEX*16 C( LDC, * ), T( LDT, * ), V( LDV, * ),
- $ WORK( LDWORK, * )
-* ..
-*
-* Purpose
-* =======
-*
-* ZLARZB applies a complex block reflector H or its transpose H**H
-* to a complex distributed M-by-N C from the left or the right.
-*
-* Currently, only STOREV = 'R' and DIRECT = 'B' are supported.
-*
-* Arguments
-* =========
-*
-* SIDE (input) CHARACTER*1
-* = 'L': apply H or H' from the Left
-* = 'R': apply H or H' from the Right
-*
-* TRANS (input) CHARACTER*1
-* = 'N': apply H (No transpose)
-* = 'C': apply H' (Conjugate transpose)
-*
-* DIRECT (input) CHARACTER*1
-* Indicates how H is formed from a product of elementary
-* reflectors
-* = 'F': H = H(1) H(2) . . . H(k) (Forward, not supported yet)
-* = 'B': H = H(k) . . . H(2) H(1) (Backward)
-*
-* STOREV (input) CHARACTER*1
-* Indicates how the vectors which define the elementary
-* reflectors are stored:
-* = 'C': Columnwise (not supported yet)
-* = 'R': Rowwise
-*
-* M (input) INTEGER
-* The number of rows of the matrix C.
-*
-* N (input) INTEGER
-* The number of columns of the matrix C.
-*
-* K (input) INTEGER
-* The order of the matrix T (= the number of elementary
-* reflectors whose product defines the block reflector).
-*
-* L (input) INTEGER
-* The number of columns of the matrix V containing the
-* meaningful part of the Householder reflectors.
-* If SIDE = 'L', M >= L >= 0, if SIDE = 'R', N >= L >= 0.
-*
-* V (input) COMPLEX*16 array, dimension (LDV,NV).
-* If STOREV = 'C', NV = K; if STOREV = 'R', NV = L.
-*
-* LDV (input) INTEGER
-* The leading dimension of the array V.
-* If STOREV = 'C', LDV >= L; if STOREV = 'R', LDV >= K.
-*
-* T (input) COMPLEX*16 array, dimension (LDT,K)
-* The triangular K-by-K matrix T in the representation of the
-* block reflector.
-*
-* LDT (input) INTEGER
-* The leading dimension of the array T. LDT >= K.
-*
-* C (input/output) COMPLEX*16 array, dimension (LDC,N)
-* On entry, the M-by-N matrix C.
-* On exit, C is overwritten by H*C or H'*C or C*H or C*H'.
-*
-* LDC (input) INTEGER
-* The leading dimension of the array C. LDC >= max(1,M).
-*
-* WORK (workspace) COMPLEX*16 array, dimension (LDWORK,K)
-*
-* LDWORK (input) INTEGER
-* The leading dimension of the array WORK.
-* If SIDE = 'L', LDWORK >= max(1,N);
-* if SIDE = 'R', LDWORK >= max(1,M).
-*
-* Further Details
-* ===============
-*
-* Based on contributions by
-* A. Petitet, Computer Science Dept., Univ. of Tenn., Knoxville, USA
-*
-* =====================================================================
-*
-* .. Parameters ..
- COMPLEX*16 ONE
- PARAMETER ( ONE = ( 1.0D+0, 0.0D+0 ) )
-* ..
-* .. Local Scalars ..
- CHARACTER TRANST
- INTEGER I, INFO, J
-* ..
-* .. External Functions ..
- LOGICAL LSAME
- EXTERNAL LSAME
-* ..
-* .. External Subroutines ..
- EXTERNAL XERBLA, ZCOPY, ZGEMM, ZLACGV, ZTRMM
-* ..
-* .. Executable Statements ..
-*
-* Quick return if possible
-*
- IF( M.LE.0 .OR. N.LE.0 )
- $ RETURN
-*
-* Check for currently supported options
-*
- INFO = 0
- IF( .NOT.LSAME( DIRECT, 'B' ) ) THEN
- INFO = -3
- ELSE IF( .NOT.LSAME( STOREV, 'R' ) ) THEN
- INFO = -4
- END IF
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'ZLARZB', -INFO )
- RETURN
- END IF
-*
- IF( LSAME( TRANS, 'N' ) ) THEN
- TRANST = 'C'
- ELSE
- TRANST = 'N'
- END IF
-*
- IF( LSAME( SIDE, 'L' ) ) THEN
-*
-* Form H * C or H' * C
-*
-* W( 1:n, 1:k ) = conjg( C( 1:k, 1:n )' )
-*
- DO 10 J = 1, K
- CALL ZCOPY( N, C( J, 1 ), LDC, WORK( 1, J ), 1 )
- 10 CONTINUE
-*
-* W( 1:n, 1:k ) = W( 1:n, 1:k ) + ...
-* conjg( C( m-l+1:m, 1:n )' ) * V( 1:k, 1:l )'
-*
- IF( L.GT.0 )
- $ CALL ZGEMM( 'Transpose', 'Conjugate transpose', N, K, L,
- $ ONE, C( M-L+1, 1 ), LDC, V, LDV, ONE, WORK,
- $ LDWORK )
-*
-* W( 1:n, 1:k ) = W( 1:n, 1:k ) * T' or W( 1:m, 1:k ) * T
-*
- CALL ZTRMM( 'Right', 'Lower', TRANST, 'Non-unit', N, K, ONE, T,
- $ LDT, WORK, LDWORK )
-*
-* C( 1:k, 1:n ) = C( 1:k, 1:n ) - conjg( W( 1:n, 1:k )' )
-*
- DO 30 J = 1, N
- DO 20 I = 1, K
- C( I, J ) = C( I, J ) - WORK( J, I )
- 20 CONTINUE
- 30 CONTINUE
-*
-* C( m-l+1:m, 1:n ) = C( m-l+1:m, 1:n ) - ...
-* conjg( V( 1:k, 1:l )' ) * conjg( W( 1:n, 1:k )' )
-*
- IF( L.GT.0 )
- $ CALL ZGEMM( 'Transpose', 'Transpose', L, N, K, -ONE, V, LDV,
- $ WORK, LDWORK, ONE, C( M-L+1, 1 ), LDC )
-*
- ELSE IF( LSAME( SIDE, 'R' ) ) THEN
-*
-* Form C * H or C * H'
-*
-* W( 1:m, 1:k ) = C( 1:m, 1:k )
-*
- DO 40 J = 1, K
- CALL ZCOPY( M, C( 1, J ), 1, WORK( 1, J ), 1 )
- 40 CONTINUE
-*
-* W( 1:m, 1:k ) = W( 1:m, 1:k ) + ...
-* C( 1:m, n-l+1:n ) * conjg( V( 1:k, 1:l )' )
-*
- IF( L.GT.0 )
- $ CALL ZGEMM( 'No transpose', 'Transpose', M, K, L, ONE,
- $ C( 1, N-L+1 ), LDC, V, LDV, ONE, WORK, LDWORK )
-*
-* W( 1:m, 1:k ) = W( 1:m, 1:k ) * conjg( T ) or
-* W( 1:m, 1:k ) * conjg( T' )
-*
- DO 50 J = 1, K
- CALL ZLACGV( K-J+1, T( J, J ), 1 )
- 50 CONTINUE
- CALL ZTRMM( 'Right', 'Lower', TRANS, 'Non-unit', M, K, ONE, T,
- $ LDT, WORK, LDWORK )
- DO 60 J = 1, K
- CALL ZLACGV( K-J+1, T( J, J ), 1 )
- 60 CONTINUE
-*
-* C( 1:m, 1:k ) = C( 1:m, 1:k ) - W( 1:m, 1:k )
-*
- DO 80 J = 1, K
- DO 70 I = 1, M
- C( I, J ) = C( I, J ) - WORK( I, J )
- 70 CONTINUE
- 80 CONTINUE
-*
-* C( 1:m, n-l+1:n ) = C( 1:m, n-l+1:n ) - ...
-* W( 1:m, 1:k ) * conjg( V( 1:k, 1:l ) )
-*
- DO 90 J = 1, L
- CALL ZLACGV( K, V( 1, J ), 1 )
- 90 CONTINUE
- IF( L.GT.0 )
- $ CALL ZGEMM( 'No transpose', 'No transpose', M, L, K, -ONE,
- $ WORK, LDWORK, V, LDV, ONE, C( 1, N-L+1 ), LDC )
- DO 100 J = 1, L
- CALL ZLACGV( K, V( 1, J ), 1 )
- 100 CONTINUE
-*
- END IF
-*
- RETURN
-*
-* End of ZLARZB
-*
- END
diff --git a/src/lib/lapack/zlarzt.f b/src/lib/lapack/zlarzt.f
deleted file mode 100644
index 9242ed36..00000000
--- a/src/lib/lapack/zlarzt.f
+++ /dev/null
@@ -1,186 +0,0 @@
- SUBROUTINE ZLARZT( DIRECT, STOREV, N, K, V, LDV, TAU, T, LDT )
-*
-* -- LAPACK routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- CHARACTER DIRECT, STOREV
- INTEGER K, LDT, LDV, N
-* ..
-* .. Array Arguments ..
- COMPLEX*16 T( LDT, * ), TAU( * ), V( LDV, * )
-* ..
-*
-* Purpose
-* =======
-*
-* ZLARZT forms the triangular factor T of a complex block reflector
-* H of order > n, which is defined as a product of k elementary
-* reflectors.
-*
-* If DIRECT = 'F', H = H(1) H(2) . . . H(k) and T is upper triangular;
-*
-* If DIRECT = 'B', H = H(k) . . . H(2) H(1) and T is lower triangular.
-*
-* If STOREV = 'C', the vector which defines the elementary reflector
-* H(i) is stored in the i-th column of the array V, and
-*
-* H = I - V * T * V'
-*
-* If STOREV = 'R', the vector which defines the elementary reflector
-* H(i) is stored in the i-th row of the array V, and
-*
-* H = I - V' * T * V
-*
-* Currently, only STOREV = 'R' and DIRECT = 'B' are supported.
-*
-* Arguments
-* =========
-*
-* DIRECT (input) CHARACTER*1
-* Specifies the order in which the elementary reflectors are
-* multiplied to form the block reflector:
-* = 'F': H = H(1) H(2) . . . H(k) (Forward, not supported yet)
-* = 'B': H = H(k) . . . H(2) H(1) (Backward)
-*
-* STOREV (input) CHARACTER*1
-* Specifies how the vectors which define the elementary
-* reflectors are stored (see also Further Details):
-* = 'C': columnwise (not supported yet)
-* = 'R': rowwise
-*
-* N (input) INTEGER
-* The order of the block reflector H. N >= 0.
-*
-* K (input) INTEGER
-* The order of the triangular factor T (= the number of
-* elementary reflectors). K >= 1.
-*
-* V (input/output) COMPLEX*16 array, dimension
-* (LDV,K) if STOREV = 'C'
-* (LDV,N) if STOREV = 'R'
-* The matrix V. See further details.
-*
-* LDV (input) INTEGER
-* The leading dimension of the array V.
-* If STOREV = 'C', LDV >= max(1,N); if STOREV = 'R', LDV >= K.
-*
-* TAU (input) COMPLEX*16 array, dimension (K)
-* TAU(i) must contain the scalar factor of the elementary
-* reflector H(i).
-*
-* T (output) COMPLEX*16 array, dimension (LDT,K)
-* The k by k triangular factor T of the block reflector.
-* If DIRECT = 'F', T is upper triangular; if DIRECT = 'B', T is
-* lower triangular. The rest of the array is not used.
-*
-* LDT (input) INTEGER
-* The leading dimension of the array T. LDT >= K.
-*
-* Further Details
-* ===============
-*
-* Based on contributions by
-* A. Petitet, Computer Science Dept., Univ. of Tenn., Knoxville, USA
-*
-* The shape of the matrix V and the storage of the vectors which define
-* the H(i) is best illustrated by the following example with n = 5 and
-* k = 3. The elements equal to 1 are not stored; the corresponding
-* array elements are modified but restored on exit. The rest of the
-* array is not used.
-*
-* DIRECT = 'F' and STOREV = 'C': DIRECT = 'F' and STOREV = 'R':
-*
-* ______V_____
-* ( v1 v2 v3 ) / \
-* ( v1 v2 v3 ) ( v1 v1 v1 v1 v1 . . . . 1 )
-* V = ( v1 v2 v3 ) ( v2 v2 v2 v2 v2 . . . 1 )
-* ( v1 v2 v3 ) ( v3 v3 v3 v3 v3 . . 1 )
-* ( v1 v2 v3 )
-* . . .
-* . . .
-* 1 . .
-* 1 .
-* 1
-*
-* DIRECT = 'B' and STOREV = 'C': DIRECT = 'B' and STOREV = 'R':
-*
-* ______V_____
-* 1 / \
-* . 1 ( 1 . . . . v1 v1 v1 v1 v1 )
-* . . 1 ( . 1 . . . v2 v2 v2 v2 v2 )
-* . . . ( . . 1 . . v3 v3 v3 v3 v3 )
-* . . .
-* ( v1 v2 v3 )
-* ( v1 v2 v3 )
-* V = ( v1 v2 v3 )
-* ( v1 v2 v3 )
-* ( v1 v2 v3 )
-*
-* =====================================================================
-*
-* .. Parameters ..
- COMPLEX*16 ZERO
- PARAMETER ( ZERO = ( 0.0D+0, 0.0D+0 ) )
-* ..
-* .. Local Scalars ..
- INTEGER I, INFO, J
-* ..
-* .. External Subroutines ..
- EXTERNAL XERBLA, ZGEMV, ZLACGV, ZTRMV
-* ..
-* .. External Functions ..
- LOGICAL LSAME
- EXTERNAL LSAME
-* ..
-* .. Executable Statements ..
-*
-* Check for currently supported options
-*
- INFO = 0
- IF( .NOT.LSAME( DIRECT, 'B' ) ) THEN
- INFO = -1
- ELSE IF( .NOT.LSAME( STOREV, 'R' ) ) THEN
- INFO = -2
- END IF
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'ZLARZT', -INFO )
- RETURN
- END IF
-*
- DO 20 I = K, 1, -1
- IF( TAU( I ).EQ.ZERO ) THEN
-*
-* H(i) = I
-*
- DO 10 J = I, K
- T( J, I ) = ZERO
- 10 CONTINUE
- ELSE
-*
-* general case
-*
- IF( I.LT.K ) THEN
-*
-* T(i+1:k,i) = - tau(i) * V(i+1:k,1:n) * V(i,1:n)'
-*
- CALL ZLACGV( N, V( I, 1 ), LDV )
- CALL ZGEMV( 'No transpose', K-I, N, -TAU( I ),
- $ V( I+1, 1 ), LDV, V( I, 1 ), LDV, ZERO,
- $ T( I+1, I ), 1 )
- CALL ZLACGV( N, V( I, 1 ), LDV )
-*
-* T(i+1:k,i) = T(i+1:k,i+1:k) * T(i+1:k,i)
-*
- CALL ZTRMV( 'Lower', 'No transpose', 'Non-unit', K-I,
- $ T( I+1, I+1 ), LDT, T( I+1, I ), 1 )
- END IF
- T( I, I ) = TAU( I )
- END IF
- 20 CONTINUE
- RETURN
-*
-* End of ZLARZT
-*
- END
diff --git a/src/lib/lapack/zlascl.f b/src/lib/lapack/zlascl.f
deleted file mode 100644
index 36bb2445..00000000
--- a/src/lib/lapack/zlascl.f
+++ /dev/null
@@ -1,267 +0,0 @@
- SUBROUTINE ZLASCL( TYPE, KL, KU, CFROM, CTO, M, N, A, LDA, INFO )
-*
-* -- LAPACK auxiliary routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- CHARACTER TYPE
- INTEGER INFO, KL, KU, LDA, M, N
- DOUBLE PRECISION CFROM, CTO
-* ..
-* .. Array Arguments ..
- COMPLEX*16 A( LDA, * )
-* ..
-*
-* Purpose
-* =======
-*
-* ZLASCL multiplies the M by N complex matrix A by the real scalar
-* CTO/CFROM. This is done without over/underflow as long as the final
-* result CTO*A(I,J)/CFROM does not over/underflow. TYPE specifies that
-* A may be full, upper triangular, lower triangular, upper Hessenberg,
-* or banded.
-*
-* Arguments
-* =========
-*
-* TYPE (input) CHARACTER*1
-* TYPE indices the storage type of the input matrix.
-* = 'G': A is a full matrix.
-* = 'L': A is a lower triangular matrix.
-* = 'U': A is an upper triangular matrix.
-* = 'H': A is an upper Hessenberg matrix.
-* = 'B': A is a symmetric band matrix with lower bandwidth KL
-* and upper bandwidth KU and with the only the lower
-* half stored.
-* = 'Q': A is a symmetric band matrix with lower bandwidth KL
-* and upper bandwidth KU and with the only the upper
-* half stored.
-* = 'Z': A is a band matrix with lower bandwidth KL and upper
-* bandwidth KU.
-*
-* KL (input) INTEGER
-* The lower bandwidth of A. Referenced only if TYPE = 'B',
-* 'Q' or 'Z'.
-*
-* KU (input) INTEGER
-* The upper bandwidth of A. Referenced only if TYPE = 'B',
-* 'Q' or 'Z'.
-*
-* CFROM (input) DOUBLE PRECISION
-* CTO (input) DOUBLE PRECISION
-* The matrix A is multiplied by CTO/CFROM. A(I,J) is computed
-* without over/underflow if the final result CTO*A(I,J)/CFROM
-* can be represented without over/underflow. CFROM must be
-* nonzero.
-*
-* M (input) INTEGER
-* The number of rows of the matrix A. M >= 0.
-*
-* N (input) INTEGER
-* The number of columns of the matrix A. N >= 0.
-*
-* A (input/output) COMPLEX*16 array, dimension (LDA,N)
-* The matrix to be multiplied by CTO/CFROM. See TYPE for the
-* storage type.
-*
-* LDA (input) INTEGER
-* The leading dimension of the array A. LDA >= max(1,M).
-*
-* INFO (output) INTEGER
-* 0 - successful exit
-* <0 - if INFO = -i, the i-th argument had an illegal value.
-*
-* =====================================================================
-*
-* .. Parameters ..
- DOUBLE PRECISION ZERO, ONE
- PARAMETER ( ZERO = 0.0D0, ONE = 1.0D0 )
-* ..
-* .. Local Scalars ..
- LOGICAL DONE
- INTEGER I, ITYPE, J, K1, K2, K3, K4
- DOUBLE PRECISION BIGNUM, CFROM1, CFROMC, CTO1, CTOC, MUL, SMLNUM
-* ..
-* .. External Functions ..
- LOGICAL LSAME
- DOUBLE PRECISION DLAMCH
- EXTERNAL LSAME, DLAMCH
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC ABS, MAX, MIN
-* ..
-* .. External Subroutines ..
- EXTERNAL XERBLA
-* ..
-* .. Executable Statements ..
-*
-* Test the input arguments
-*
- INFO = 0
-*
- IF( LSAME( TYPE, 'G' ) ) THEN
- ITYPE = 0
- ELSE IF( LSAME( TYPE, 'L' ) ) THEN
- ITYPE = 1
- ELSE IF( LSAME( TYPE, 'U' ) ) THEN
- ITYPE = 2
- ELSE IF( LSAME( TYPE, 'H' ) ) THEN
- ITYPE = 3
- ELSE IF( LSAME( TYPE, 'B' ) ) THEN
- ITYPE = 4
- ELSE IF( LSAME( TYPE, 'Q' ) ) THEN
- ITYPE = 5
- ELSE IF( LSAME( TYPE, 'Z' ) ) THEN
- ITYPE = 6
- ELSE
- ITYPE = -1
- END IF
-*
- IF( ITYPE.EQ.-1 ) THEN
- INFO = -1
- ELSE IF( CFROM.EQ.ZERO ) THEN
- INFO = -4
- ELSE IF( M.LT.0 ) THEN
- INFO = -6
- ELSE IF( N.LT.0 .OR. ( ITYPE.EQ.4 .AND. N.NE.M ) .OR.
- $ ( ITYPE.EQ.5 .AND. N.NE.M ) ) THEN
- INFO = -7
- ELSE IF( ITYPE.LE.3 .AND. LDA.LT.MAX( 1, M ) ) THEN
- INFO = -9
- ELSE IF( ITYPE.GE.4 ) THEN
- IF( KL.LT.0 .OR. KL.GT.MAX( M-1, 0 ) ) THEN
- INFO = -2
- ELSE IF( KU.LT.0 .OR. KU.GT.MAX( N-1, 0 ) .OR.
- $ ( ( ITYPE.EQ.4 .OR. ITYPE.EQ.5 ) .AND. KL.NE.KU ) )
- $ THEN
- INFO = -3
- ELSE IF( ( ITYPE.EQ.4 .AND. LDA.LT.KL+1 ) .OR.
- $ ( ITYPE.EQ.5 .AND. LDA.LT.KU+1 ) .OR.
- $ ( ITYPE.EQ.6 .AND. LDA.LT.2*KL+KU+1 ) ) THEN
- INFO = -9
- END IF
- END IF
-*
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'ZLASCL', -INFO )
- RETURN
- END IF
-*
-* Quick return if possible
-*
- IF( N.EQ.0 .OR. M.EQ.0 )
- $ RETURN
-*
-* Get machine parameters
-*
- SMLNUM = DLAMCH( 'S' )
- BIGNUM = ONE / SMLNUM
-*
- CFROMC = CFROM
- CTOC = CTO
-*
- 10 CONTINUE
- CFROM1 = CFROMC*SMLNUM
- CTO1 = CTOC / BIGNUM
- IF( ABS( CFROM1 ).GT.ABS( CTOC ) .AND. CTOC.NE.ZERO ) THEN
- MUL = SMLNUM
- DONE = .FALSE.
- CFROMC = CFROM1
- ELSE IF( ABS( CTO1 ).GT.ABS( CFROMC ) ) THEN
- MUL = BIGNUM
- DONE = .FALSE.
- CTOC = CTO1
- ELSE
- MUL = CTOC / CFROMC
- DONE = .TRUE.
- END IF
-*
- IF( ITYPE.EQ.0 ) THEN
-*
-* Full matrix
-*
- DO 30 J = 1, N
- DO 20 I = 1, M
- A( I, J ) = A( I, J )*MUL
- 20 CONTINUE
- 30 CONTINUE
-*
- ELSE IF( ITYPE.EQ.1 ) THEN
-*
-* Lower triangular matrix
-*
- DO 50 J = 1, N
- DO 40 I = J, M
- A( I, J ) = A( I, J )*MUL
- 40 CONTINUE
- 50 CONTINUE
-*
- ELSE IF( ITYPE.EQ.2 ) THEN
-*
-* Upper triangular matrix
-*
- DO 70 J = 1, N
- DO 60 I = 1, MIN( J, M )
- A( I, J ) = A( I, J )*MUL
- 60 CONTINUE
- 70 CONTINUE
-*
- ELSE IF( ITYPE.EQ.3 ) THEN
-*
-* Upper Hessenberg matrix
-*
- DO 90 J = 1, N
- DO 80 I = 1, MIN( J+1, M )
- A( I, J ) = A( I, J )*MUL
- 80 CONTINUE
- 90 CONTINUE
-*
- ELSE IF( ITYPE.EQ.4 ) THEN
-*
-* Lower half of a symmetric band matrix
-*
- K3 = KL + 1
- K4 = N + 1
- DO 110 J = 1, N
- DO 100 I = 1, MIN( K3, K4-J )
- A( I, J ) = A( I, J )*MUL
- 100 CONTINUE
- 110 CONTINUE
-*
- ELSE IF( ITYPE.EQ.5 ) THEN
-*
-* Upper half of a symmetric band matrix
-*
- K1 = KU + 2
- K3 = KU + 1
- DO 130 J = 1, N
- DO 120 I = MAX( K1-J, 1 ), K3
- A( I, J ) = A( I, J )*MUL
- 120 CONTINUE
- 130 CONTINUE
-*
- ELSE IF( ITYPE.EQ.6 ) THEN
-*
-* Band matrix
-*
- K1 = KL + KU + 2
- K2 = KL + 1
- K3 = 2*KL + KU + 1
- K4 = KL + KU + 1 + M
- DO 150 J = 1, N
- DO 140 I = MAX( K1-J, K2 ), MIN( K3, K4-J )
- A( I, J ) = A( I, J )*MUL
- 140 CONTINUE
- 150 CONTINUE
-*
- END IF
-*
- IF( .NOT.DONE )
- $ GO TO 10
-*
- RETURN
-*
-* End of ZLASCL
-*
- END
diff --git a/src/lib/lapack/zlaset.f b/src/lib/lapack/zlaset.f
deleted file mode 100644
index 88fc21b2..00000000
--- a/src/lib/lapack/zlaset.f
+++ /dev/null
@@ -1,114 +0,0 @@
- SUBROUTINE ZLASET( UPLO, M, N, ALPHA, BETA, A, LDA )
-*
-* -- LAPACK auxiliary routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- CHARACTER UPLO
- INTEGER LDA, M, N
- COMPLEX*16 ALPHA, BETA
-* ..
-* .. Array Arguments ..
- COMPLEX*16 A( LDA, * )
-* ..
-*
-* Purpose
-* =======
-*
-* ZLASET initializes a 2-D array A to BETA on the diagonal and
-* ALPHA on the offdiagonals.
-*
-* Arguments
-* =========
-*
-* UPLO (input) CHARACTER*1
-* Specifies the part of the matrix A to be set.
-* = 'U': Upper triangular part is set. The lower triangle
-* is unchanged.
-* = 'L': Lower triangular part is set. The upper triangle
-* is unchanged.
-* Otherwise: All of the matrix A is set.
-*
-* M (input) INTEGER
-* On entry, M specifies the number of rows of A.
-*
-* N (input) INTEGER
-* On entry, N specifies the number of columns of A.
-*
-* ALPHA (input) COMPLEX*16
-* All the offdiagonal array elements are set to ALPHA.
-*
-* BETA (input) COMPLEX*16
-* All the diagonal array elements are set to BETA.
-*
-* A (input/output) COMPLEX*16 array, dimension (LDA,N)
-* On entry, the m by n matrix A.
-* On exit, A(i,j) = ALPHA, 1 <= i <= m, 1 <= j <= n, i.ne.j;
-* A(i,i) = BETA , 1 <= i <= min(m,n)
-*
-* LDA (input) INTEGER
-* The leading dimension of the array A. LDA >= max(1,M).
-*
-* =====================================================================
-*
-* .. Local Scalars ..
- INTEGER I, J
-* ..
-* .. External Functions ..
- LOGICAL LSAME
- EXTERNAL LSAME
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC MIN
-* ..
-* .. Executable Statements ..
-*
- IF( LSAME( UPLO, 'U' ) ) THEN
-*
-* Set the diagonal to BETA and the strictly upper triangular
-* part of the array to ALPHA.
-*
- DO 20 J = 2, N
- DO 10 I = 1, MIN( J-1, M )
- A( I, J ) = ALPHA
- 10 CONTINUE
- 20 CONTINUE
- DO 30 I = 1, MIN( N, M )
- A( I, I ) = BETA
- 30 CONTINUE
-*
- ELSE IF( LSAME( UPLO, 'L' ) ) THEN
-*
-* Set the diagonal to BETA and the strictly lower triangular
-* part of the array to ALPHA.
-*
- DO 50 J = 1, MIN( M, N )
- DO 40 I = J + 1, M
- A( I, J ) = ALPHA
- 40 CONTINUE
- 50 CONTINUE
- DO 60 I = 1, MIN( N, M )
- A( I, I ) = BETA
- 60 CONTINUE
-*
- ELSE
-*
-* Set the array to BETA on the diagonal and ALPHA on the
-* offdiagonal.
-*
- DO 80 J = 1, N
- DO 70 I = 1, M
- A( I, J ) = ALPHA
- 70 CONTINUE
- 80 CONTINUE
- DO 90 I = 1, MIN( M, N )
- A( I, I ) = BETA
- 90 CONTINUE
- END IF
-*
- RETURN
-*
-* End of ZLASET
-*
- END
diff --git a/src/lib/lapack/zlasr.f b/src/lib/lapack/zlasr.f
deleted file mode 100644
index 507a20c4..00000000
--- a/src/lib/lapack/zlasr.f
+++ /dev/null
@@ -1,363 +0,0 @@
- SUBROUTINE ZLASR( SIDE, PIVOT, DIRECT, M, N, C, S, A, LDA )
-*
-* -- LAPACK auxiliary routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- CHARACTER DIRECT, PIVOT, SIDE
- INTEGER LDA, M, N
-* ..
-* .. Array Arguments ..
- DOUBLE PRECISION C( * ), S( * )
- COMPLEX*16 A( LDA, * )
-* ..
-*
-* Purpose
-* =======
-*
-* ZLASR applies a sequence of real plane rotations to a complex matrix
-* A, from either the left or the right.
-*
-* When SIDE = 'L', the transformation takes the form
-*
-* A := P*A
-*
-* and when SIDE = 'R', the transformation takes the form
-*
-* A := A*P**T
-*
-* where P is an orthogonal matrix consisting of a sequence of z plane
-* rotations, with z = M when SIDE = 'L' and z = N when SIDE = 'R',
-* and P**T is the transpose of P.
-*
-* When DIRECT = 'F' (Forward sequence), then
-*
-* P = P(z-1) * ... * P(2) * P(1)
-*
-* and when DIRECT = 'B' (Backward sequence), then
-*
-* P = P(1) * P(2) * ... * P(z-1)
-*
-* where P(k) is a plane rotation matrix defined by the 2-by-2 rotation
-*
-* R(k) = ( c(k) s(k) )
-* = ( -s(k) c(k) ).
-*
-* When PIVOT = 'V' (Variable pivot), the rotation is performed
-* for the plane (k,k+1), i.e., P(k) has the form
-*
-* P(k) = ( 1 )
-* ( ... )
-* ( 1 )
-* ( c(k) s(k) )
-* ( -s(k) c(k) )
-* ( 1 )
-* ( ... )
-* ( 1 )
-*
-* where R(k) appears as a rank-2 modification to the identity matrix in
-* rows and columns k and k+1.
-*
-* When PIVOT = 'T' (Top pivot), the rotation is performed for the
-* plane (1,k+1), so P(k) has the form
-*
-* P(k) = ( c(k) s(k) )
-* ( 1 )
-* ( ... )
-* ( 1 )
-* ( -s(k) c(k) )
-* ( 1 )
-* ( ... )
-* ( 1 )
-*
-* where R(k) appears in rows and columns 1 and k+1.
-*
-* Similarly, when PIVOT = 'B' (Bottom pivot), the rotation is
-* performed for the plane (k,z), giving P(k) the form
-*
-* P(k) = ( 1 )
-* ( ... )
-* ( 1 )
-* ( c(k) s(k) )
-* ( 1 )
-* ( ... )
-* ( 1 )
-* ( -s(k) c(k) )
-*
-* where R(k) appears in rows and columns k and z. The rotations are
-* performed without ever forming P(k) explicitly.
-*
-* Arguments
-* =========
-*
-* SIDE (input) CHARACTER*1
-* Specifies whether the plane rotation matrix P is applied to
-* A on the left or the right.
-* = 'L': Left, compute A := P*A
-* = 'R': Right, compute A:= A*P**T
-*
-* PIVOT (input) CHARACTER*1
-* Specifies the plane for which P(k) is a plane rotation
-* matrix.
-* = 'V': Variable pivot, the plane (k,k+1)
-* = 'T': Top pivot, the plane (1,k+1)
-* = 'B': Bottom pivot, the plane (k,z)
-*
-* DIRECT (input) CHARACTER*1
-* Specifies whether P is a forward or backward sequence of
-* plane rotations.
-* = 'F': Forward, P = P(z-1)*...*P(2)*P(1)
-* = 'B': Backward, P = P(1)*P(2)*...*P(z-1)
-*
-* M (input) INTEGER
-* The number of rows of the matrix A. If m <= 1, an immediate
-* return is effected.
-*
-* N (input) INTEGER
-* The number of columns of the matrix A. If n <= 1, an
-* immediate return is effected.
-*
-* C (input) DOUBLE PRECISION array, dimension
-* (M-1) if SIDE = 'L'
-* (N-1) if SIDE = 'R'
-* The cosines c(k) of the plane rotations.
-*
-* S (input) DOUBLE PRECISION array, dimension
-* (M-1) if SIDE = 'L'
-* (N-1) if SIDE = 'R'
-* The sines s(k) of the plane rotations. The 2-by-2 plane
-* rotation part of the matrix P(k), R(k), has the form
-* R(k) = ( c(k) s(k) )
-* ( -s(k) c(k) ).
-*
-* A (input/output) COMPLEX*16 array, dimension (LDA,N)
-* The M-by-N matrix A. On exit, A is overwritten by P*A if
-* SIDE = 'R' or by A*P**T if SIDE = 'L'.
-*
-* LDA (input) INTEGER
-* The leading dimension of the array A. LDA >= max(1,M).
-*
-* =====================================================================
-*
-* .. Parameters ..
- DOUBLE PRECISION ONE, ZERO
- PARAMETER ( ONE = 1.0D+0, ZERO = 0.0D+0 )
-* ..
-* .. Local Scalars ..
- INTEGER I, INFO, J
- DOUBLE PRECISION CTEMP, STEMP
- COMPLEX*16 TEMP
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC MAX
-* ..
-* .. External Functions ..
- LOGICAL LSAME
- EXTERNAL LSAME
-* ..
-* .. External Subroutines ..
- EXTERNAL XERBLA
-* ..
-* .. Executable Statements ..
-*
-* Test the input parameters
-*
- INFO = 0
- IF( .NOT.( LSAME( SIDE, 'L' ) .OR. LSAME( SIDE, 'R' ) ) ) THEN
- INFO = 1
- ELSE IF( .NOT.( LSAME( PIVOT, 'V' ) .OR. LSAME( PIVOT,
- $ 'T' ) .OR. LSAME( PIVOT, 'B' ) ) ) THEN
- INFO = 2
- ELSE IF( .NOT.( LSAME( DIRECT, 'F' ) .OR. LSAME( DIRECT, 'B' ) ) )
- $ THEN
- INFO = 3
- ELSE IF( M.LT.0 ) THEN
- INFO = 4
- ELSE IF( N.LT.0 ) THEN
- INFO = 5
- ELSE IF( LDA.LT.MAX( 1, M ) ) THEN
- INFO = 9
- END IF
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'ZLASR ', INFO )
- RETURN
- END IF
-*
-* Quick return if possible
-*
- IF( ( M.EQ.0 ) .OR. ( N.EQ.0 ) )
- $ RETURN
- IF( LSAME( SIDE, 'L' ) ) THEN
-*
-* Form P * A
-*
- IF( LSAME( PIVOT, 'V' ) ) THEN
- IF( LSAME( DIRECT, 'F' ) ) THEN
- DO 20 J = 1, M - 1
- CTEMP = C( J )
- STEMP = S( J )
- IF( ( CTEMP.NE.ONE ) .OR. ( STEMP.NE.ZERO ) ) THEN
- DO 10 I = 1, N
- TEMP = A( J+1, I )
- A( J+1, I ) = CTEMP*TEMP - STEMP*A( J, I )
- A( J, I ) = STEMP*TEMP + CTEMP*A( J, I )
- 10 CONTINUE
- END IF
- 20 CONTINUE
- ELSE IF( LSAME( DIRECT, 'B' ) ) THEN
- DO 40 J = M - 1, 1, -1
- CTEMP = C( J )
- STEMP = S( J )
- IF( ( CTEMP.NE.ONE ) .OR. ( STEMP.NE.ZERO ) ) THEN
- DO 30 I = 1, N
- TEMP = A( J+1, I )
- A( J+1, I ) = CTEMP*TEMP - STEMP*A( J, I )
- A( J, I ) = STEMP*TEMP + CTEMP*A( J, I )
- 30 CONTINUE
- END IF
- 40 CONTINUE
- END IF
- ELSE IF( LSAME( PIVOT, 'T' ) ) THEN
- IF( LSAME( DIRECT, 'F' ) ) THEN
- DO 60 J = 2, M
- CTEMP = C( J-1 )
- STEMP = S( J-1 )
- IF( ( CTEMP.NE.ONE ) .OR. ( STEMP.NE.ZERO ) ) THEN
- DO 50 I = 1, N
- TEMP = A( J, I )
- A( J, I ) = CTEMP*TEMP - STEMP*A( 1, I )
- A( 1, I ) = STEMP*TEMP + CTEMP*A( 1, I )
- 50 CONTINUE
- END IF
- 60 CONTINUE
- ELSE IF( LSAME( DIRECT, 'B' ) ) THEN
- DO 80 J = M, 2, -1
- CTEMP = C( J-1 )
- STEMP = S( J-1 )
- IF( ( CTEMP.NE.ONE ) .OR. ( STEMP.NE.ZERO ) ) THEN
- DO 70 I = 1, N
- TEMP = A( J, I )
- A( J, I ) = CTEMP*TEMP - STEMP*A( 1, I )
- A( 1, I ) = STEMP*TEMP + CTEMP*A( 1, I )
- 70 CONTINUE
- END IF
- 80 CONTINUE
- END IF
- ELSE IF( LSAME( PIVOT, 'B' ) ) THEN
- IF( LSAME( DIRECT, 'F' ) ) THEN
- DO 100 J = 1, M - 1
- CTEMP = C( J )
- STEMP = S( J )
- IF( ( CTEMP.NE.ONE ) .OR. ( STEMP.NE.ZERO ) ) THEN
- DO 90 I = 1, N
- TEMP = A( J, I )
- A( J, I ) = STEMP*A( M, I ) + CTEMP*TEMP
- A( M, I ) = CTEMP*A( M, I ) - STEMP*TEMP
- 90 CONTINUE
- END IF
- 100 CONTINUE
- ELSE IF( LSAME( DIRECT, 'B' ) ) THEN
- DO 120 J = M - 1, 1, -1
- CTEMP = C( J )
- STEMP = S( J )
- IF( ( CTEMP.NE.ONE ) .OR. ( STEMP.NE.ZERO ) ) THEN
- DO 110 I = 1, N
- TEMP = A( J, I )
- A( J, I ) = STEMP*A( M, I ) + CTEMP*TEMP
- A( M, I ) = CTEMP*A( M, I ) - STEMP*TEMP
- 110 CONTINUE
- END IF
- 120 CONTINUE
- END IF
- END IF
- ELSE IF( LSAME( SIDE, 'R' ) ) THEN
-*
-* Form A * P'
-*
- IF( LSAME( PIVOT, 'V' ) ) THEN
- IF( LSAME( DIRECT, 'F' ) ) THEN
- DO 140 J = 1, N - 1
- CTEMP = C( J )
- STEMP = S( J )
- IF( ( CTEMP.NE.ONE ) .OR. ( STEMP.NE.ZERO ) ) THEN
- DO 130 I = 1, M
- TEMP = A( I, J+1 )
- A( I, J+1 ) = CTEMP*TEMP - STEMP*A( I, J )
- A( I, J ) = STEMP*TEMP + CTEMP*A( I, J )
- 130 CONTINUE
- END IF
- 140 CONTINUE
- ELSE IF( LSAME( DIRECT, 'B' ) ) THEN
- DO 160 J = N - 1, 1, -1
- CTEMP = C( J )
- STEMP = S( J )
- IF( ( CTEMP.NE.ONE ) .OR. ( STEMP.NE.ZERO ) ) THEN
- DO 150 I = 1, M
- TEMP = A( I, J+1 )
- A( I, J+1 ) = CTEMP*TEMP - STEMP*A( I, J )
- A( I, J ) = STEMP*TEMP + CTEMP*A( I, J )
- 150 CONTINUE
- END IF
- 160 CONTINUE
- END IF
- ELSE IF( LSAME( PIVOT, 'T' ) ) THEN
- IF( LSAME( DIRECT, 'F' ) ) THEN
- DO 180 J = 2, N
- CTEMP = C( J-1 )
- STEMP = S( J-1 )
- IF( ( CTEMP.NE.ONE ) .OR. ( STEMP.NE.ZERO ) ) THEN
- DO 170 I = 1, M
- TEMP = A( I, J )
- A( I, J ) = CTEMP*TEMP - STEMP*A( I, 1 )
- A( I, 1 ) = STEMP*TEMP + CTEMP*A( I, 1 )
- 170 CONTINUE
- END IF
- 180 CONTINUE
- ELSE IF( LSAME( DIRECT, 'B' ) ) THEN
- DO 200 J = N, 2, -1
- CTEMP = C( J-1 )
- STEMP = S( J-1 )
- IF( ( CTEMP.NE.ONE ) .OR. ( STEMP.NE.ZERO ) ) THEN
- DO 190 I = 1, M
- TEMP = A( I, J )
- A( I, J ) = CTEMP*TEMP - STEMP*A( I, 1 )
- A( I, 1 ) = STEMP*TEMP + CTEMP*A( I, 1 )
- 190 CONTINUE
- END IF
- 200 CONTINUE
- END IF
- ELSE IF( LSAME( PIVOT, 'B' ) ) THEN
- IF( LSAME( DIRECT, 'F' ) ) THEN
- DO 220 J = 1, N - 1
- CTEMP = C( J )
- STEMP = S( J )
- IF( ( CTEMP.NE.ONE ) .OR. ( STEMP.NE.ZERO ) ) THEN
- DO 210 I = 1, M
- TEMP = A( I, J )
- A( I, J ) = STEMP*A( I, N ) + CTEMP*TEMP
- A( I, N ) = CTEMP*A( I, N ) - STEMP*TEMP
- 210 CONTINUE
- END IF
- 220 CONTINUE
- ELSE IF( LSAME( DIRECT, 'B' ) ) THEN
- DO 240 J = N - 1, 1, -1
- CTEMP = C( J )
- STEMP = S( J )
- IF( ( CTEMP.NE.ONE ) .OR. ( STEMP.NE.ZERO ) ) THEN
- DO 230 I = 1, M
- TEMP = A( I, J )
- A( I, J ) = STEMP*A( I, N ) + CTEMP*TEMP
- A( I, N ) = CTEMP*A( I, N ) - STEMP*TEMP
- 230 CONTINUE
- END IF
- 240 CONTINUE
- END IF
- END IF
- END IF
-*
- RETURN
-*
-* End of ZLASR
-*
- END
diff --git a/src/lib/lapack/zlassq.f b/src/lib/lapack/zlassq.f
deleted file mode 100644
index a209984b..00000000
--- a/src/lib/lapack/zlassq.f
+++ /dev/null
@@ -1,101 +0,0 @@
- SUBROUTINE ZLASSQ( N, X, INCX, SCALE, SUMSQ )
-*
-* -- LAPACK auxiliary routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- INTEGER INCX, N
- DOUBLE PRECISION SCALE, SUMSQ
-* ..
-* .. Array Arguments ..
- COMPLEX*16 X( * )
-* ..
-*
-* Purpose
-* =======
-*
-* ZLASSQ returns the values scl and ssq such that
-*
-* ( scl**2 )*ssq = x( 1 )**2 +...+ x( n )**2 + ( scale**2 )*sumsq,
-*
-* where x( i ) = abs( X( 1 + ( i - 1 )*INCX ) ). The value of sumsq is
-* assumed to be at least unity and the value of ssq will then satisfy
-*
-* 1.0 .le. ssq .le. ( sumsq + 2*n ).
-*
-* scale is assumed to be non-negative and scl returns the value
-*
-* scl = max( scale, abs( real( x( i ) ) ), abs( aimag( x( i ) ) ) ),
-* i
-*
-* scale and sumsq must be supplied in SCALE and SUMSQ respectively.
-* SCALE and SUMSQ are overwritten by scl and ssq respectively.
-*
-* The routine makes only one pass through the vector X.
-*
-* Arguments
-* =========
-*
-* N (input) INTEGER
-* The number of elements to be used from the vector X.
-*
-* X (input) COMPLEX*16 array, dimension (N)
-* The vector x as described above.
-* x( i ) = X( 1 + ( i - 1 )*INCX ), 1 <= i <= n.
-*
-* INCX (input) INTEGER
-* The increment between successive values of the vector X.
-* INCX > 0.
-*
-* SCALE (input/output) DOUBLE PRECISION
-* On entry, the value scale in the equation above.
-* On exit, SCALE is overwritten with the value scl .
-*
-* SUMSQ (input/output) DOUBLE PRECISION
-* On entry, the value sumsq in the equation above.
-* On exit, SUMSQ is overwritten with the value ssq .
-*
-* =====================================================================
-*
-* .. Parameters ..
- DOUBLE PRECISION ZERO
- PARAMETER ( ZERO = 0.0D+0 )
-* ..
-* .. Local Scalars ..
- INTEGER IX
- DOUBLE PRECISION TEMP1
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC ABS, DBLE, DIMAG
-* ..
-* .. Executable Statements ..
-*
- IF( N.GT.0 ) THEN
- DO 10 IX = 1, 1 + ( N-1 )*INCX, INCX
- IF( DBLE( X( IX ) ).NE.ZERO ) THEN
- TEMP1 = ABS( DBLE( X( IX ) ) )
- IF( SCALE.LT.TEMP1 ) THEN
- SUMSQ = 1 + SUMSQ*( SCALE / TEMP1 )**2
- SCALE = TEMP1
- ELSE
- SUMSQ = SUMSQ + ( TEMP1 / SCALE )**2
- END IF
- END IF
- IF( DIMAG( X( IX ) ).NE.ZERO ) THEN
- TEMP1 = ABS( DIMAG( X( IX ) ) )
- IF( SCALE.LT.TEMP1 ) THEN
- SUMSQ = 1 + SUMSQ*( SCALE / TEMP1 )**2
- SCALE = TEMP1
- ELSE
- SUMSQ = SUMSQ + ( TEMP1 / SCALE )**2
- END IF
- END IF
- 10 CONTINUE
- END IF
-*
- RETURN
-*
-* End of ZLASSQ
-*
- END
diff --git a/src/lib/lapack/zlaswp.f b/src/lib/lapack/zlaswp.f
deleted file mode 100644
index 8b07e48b..00000000
--- a/src/lib/lapack/zlaswp.f
+++ /dev/null
@@ -1,119 +0,0 @@
- SUBROUTINE ZLASWP( N, A, LDA, K1, K2, IPIV, INCX )
-*
-* -- LAPACK auxiliary routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- INTEGER INCX, K1, K2, LDA, N
-* ..
-* .. Array Arguments ..
- INTEGER IPIV( * )
- COMPLEX*16 A( LDA, * )
-* ..
-*
-* Purpose
-* =======
-*
-* ZLASWP performs a series of row interchanges on the matrix A.
-* One row interchange is initiated for each of rows K1 through K2 of A.
-*
-* Arguments
-* =========
-*
-* N (input) INTEGER
-* The number of columns of the matrix A.
-*
-* A (input/output) COMPLEX*16 array, dimension (LDA,N)
-* On entry, the matrix of column dimension N to which the row
-* interchanges will be applied.
-* On exit, the permuted matrix.
-*
-* LDA (input) INTEGER
-* The leading dimension of the array A.
-*
-* K1 (input) INTEGER
-* The first element of IPIV for which a row interchange will
-* be done.
-*
-* K2 (input) INTEGER
-* The last element of IPIV for which a row interchange will
-* be done.
-*
-* IPIV (input) INTEGER array, dimension (K2*abs(INCX))
-* The vector of pivot indices. Only the elements in positions
-* K1 through K2 of IPIV are accessed.
-* IPIV(K) = L implies rows K and L are to be interchanged.
-*
-* INCX (input) INTEGER
-* The increment between successive values of IPIV. If IPIV
-* is negative, the pivots are applied in reverse order.
-*
-* Further Details
-* ===============
-*
-* Modified by
-* R. C. Whaley, Computer Science Dept., Univ. of Tenn., Knoxville, USA
-*
-* =====================================================================
-*
-* .. Local Scalars ..
- INTEGER I, I1, I2, INC, IP, IX, IX0, J, K, N32
- COMPLEX*16 TEMP
-* ..
-* .. Executable Statements ..
-*
-* Interchange row I with row IPIV(I) for each of rows K1 through K2.
-*
- IF( INCX.GT.0 ) THEN
- IX0 = K1
- I1 = K1
- I2 = K2
- INC = 1
- ELSE IF( INCX.LT.0 ) THEN
- IX0 = 1 + ( 1-K2 )*INCX
- I1 = K2
- I2 = K1
- INC = -1
- ELSE
- RETURN
- END IF
-*
- N32 = ( N / 32 )*32
- IF( N32.NE.0 ) THEN
- DO 30 J = 1, N32, 32
- IX = IX0
- DO 20 I = I1, I2, INC
- IP = IPIV( IX )
- IF( IP.NE.I ) THEN
- DO 10 K = J, J + 31
- TEMP = A( I, K )
- A( I, K ) = A( IP, K )
- A( IP, K ) = TEMP
- 10 CONTINUE
- END IF
- IX = IX + INCX
- 20 CONTINUE
- 30 CONTINUE
- END IF
- IF( N32.NE.N ) THEN
- N32 = N32 + 1
- IX = IX0
- DO 50 I = I1, I2, INC
- IP = IPIV( IX )
- IF( IP.NE.I ) THEN
- DO 40 K = N32, N
- TEMP = A( I, K )
- A( I, K ) = A( IP, K )
- A( IP, K ) = TEMP
- 40 CONTINUE
- END IF
- IX = IX + INCX
- 50 CONTINUE
- END IF
-*
- RETURN
-*
-* End of ZLASWP
-*
- END
diff --git a/src/lib/lapack/zlatdf.f b/src/lib/lapack/zlatdf.f
deleted file mode 100644
index d637b8f1..00000000
--- a/src/lib/lapack/zlatdf.f
+++ /dev/null
@@ -1,241 +0,0 @@
- SUBROUTINE ZLATDF( IJOB, N, Z, LDZ, RHS, RDSUM, RDSCAL, IPIV,
- $ JPIV )
-*
-* -- LAPACK auxiliary routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- INTEGER IJOB, LDZ, N
- DOUBLE PRECISION RDSCAL, RDSUM
-* ..
-* .. Array Arguments ..
- INTEGER IPIV( * ), JPIV( * )
- COMPLEX*16 RHS( * ), Z( LDZ, * )
-* ..
-*
-* Purpose
-* =======
-*
-* ZLATDF computes the contribution to the reciprocal Dif-estimate
-* by solving for x in Z * x = b, where b is chosen such that the norm
-* of x is as large as possible. It is assumed that LU decomposition
-* of Z has been computed by ZGETC2. On entry RHS = f holds the
-* contribution from earlier solved sub-systems, and on return RHS = x.
-*
-* The factorization of Z returned by ZGETC2 has the form
-* Z = P * L * U * Q, where P and Q are permutation matrices. L is lower
-* triangular with unit diagonal elements and U is upper triangular.
-*
-* Arguments
-* =========
-*
-* IJOB (input) INTEGER
-* IJOB = 2: First compute an approximative null-vector e
-* of Z using ZGECON, e is normalized and solve for
-* Zx = +-e - f with the sign giving the greater value of
-* 2-norm(x). About 5 times as expensive as Default.
-* IJOB .ne. 2: Local look ahead strategy where
-* all entries of the r.h.s. b is choosen as either +1 or
-* -1. Default.
-*
-* N (input) INTEGER
-* The number of columns of the matrix Z.
-*
-* Z (input) DOUBLE PRECISION array, dimension (LDZ, N)
-* On entry, the LU part of the factorization of the n-by-n
-* matrix Z computed by ZGETC2: Z = P * L * U * Q
-*
-* LDZ (input) INTEGER
-* The leading dimension of the array Z. LDA >= max(1, N).
-*
-* RHS (input/output) DOUBLE PRECISION array, dimension (N).
-* On entry, RHS contains contributions from other subsystems.
-* On exit, RHS contains the solution of the subsystem with
-* entries according to the value of IJOB (see above).
-*
-* RDSUM (input/output) DOUBLE PRECISION
-* On entry, the sum of squares of computed contributions to
-* the Dif-estimate under computation by ZTGSYL, where the
-* scaling factor RDSCAL (see below) has been factored out.
-* On exit, the corresponding sum of squares updated with the
-* contributions from the current sub-system.
-* If TRANS = 'T' RDSUM is not touched.
-* NOTE: RDSUM only makes sense when ZTGSY2 is called by CTGSYL.
-*
-* RDSCAL (input/output) DOUBLE PRECISION
-* On entry, scaling factor used to prevent overflow in RDSUM.
-* On exit, RDSCAL is updated w.r.t. the current contributions
-* in RDSUM.
-* If TRANS = 'T', RDSCAL is not touched.
-* NOTE: RDSCAL only makes sense when ZTGSY2 is called by
-* ZTGSYL.
-*
-* IPIV (input) INTEGER array, dimension (N).
-* The pivot indices; for 1 <= i <= N, row i of the
-* matrix has been interchanged with row IPIV(i).
-*
-* JPIV (input) INTEGER array, dimension (N).
-* The pivot indices; for 1 <= j <= N, column j of the
-* matrix has been interchanged with column JPIV(j).
-*
-* Further Details
-* ===============
-*
-* Based on contributions by
-* Bo Kagstrom and Peter Poromaa, Department of Computing Science,
-* Umea University, S-901 87 Umea, Sweden.
-*
-* This routine is a further developed implementation of algorithm
-* BSOLVE in [1] using complete pivoting in the LU factorization.
-*
-* [1] Bo Kagstrom and Lars Westin,
-* Generalized Schur Methods with Condition Estimators for
-* Solving the Generalized Sylvester Equation, IEEE Transactions
-* on Automatic Control, Vol. 34, No. 7, July 1989, pp 745-751.
-*
-* [2] Peter Poromaa,
-* On Efficient and Robust Estimators for the Separation
-* between two Regular Matrix Pairs with Applications in
-* Condition Estimation. Report UMINF-95.05, Department of
-* Computing Science, Umea University, S-901 87 Umea, Sweden,
-* 1995.
-*
-* =====================================================================
-*
-* .. Parameters ..
- INTEGER MAXDIM
- PARAMETER ( MAXDIM = 2 )
- DOUBLE PRECISION ZERO, ONE
- PARAMETER ( ZERO = 0.0D+0, ONE = 1.0D+0 )
- COMPLEX*16 CONE
- PARAMETER ( CONE = ( 1.0D+0, 0.0D+0 ) )
-* ..
-* .. Local Scalars ..
- INTEGER I, INFO, J, K
- DOUBLE PRECISION RTEMP, SCALE, SMINU, SPLUS
- COMPLEX*16 BM, BP, PMONE, TEMP
-* ..
-* .. Local Arrays ..
- DOUBLE PRECISION RWORK( MAXDIM )
- COMPLEX*16 WORK( 4*MAXDIM ), XM( MAXDIM ), XP( MAXDIM )
-* ..
-* .. External Subroutines ..
- EXTERNAL ZAXPY, ZCOPY, ZGECON, ZGESC2, ZLASSQ, ZLASWP,
- $ ZSCAL
-* ..
-* .. External Functions ..
- DOUBLE PRECISION DZASUM
- COMPLEX*16 ZDOTC
- EXTERNAL DZASUM, ZDOTC
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC ABS, DBLE, SQRT
-* ..
-* .. Executable Statements ..
-*
- IF( IJOB.NE.2 ) THEN
-*
-* Apply permutations IPIV to RHS
-*
- CALL ZLASWP( 1, RHS, LDZ, 1, N-1, IPIV, 1 )
-*
-* Solve for L-part choosing RHS either to +1 or -1.
-*
- PMONE = -CONE
- DO 10 J = 1, N - 1
- BP = RHS( J ) + CONE
- BM = RHS( J ) - CONE
- SPLUS = ONE
-*
-* Lockahead for L- part RHS(1:N-1) = +-1
-* SPLUS and SMIN computed more efficiently than in BSOLVE[1].
-*
- SPLUS = SPLUS + DBLE( ZDOTC( N-J, Z( J+1, J ), 1, Z( J+1,
- $ J ), 1 ) )
- SMINU = DBLE( ZDOTC( N-J, Z( J+1, J ), 1, RHS( J+1 ), 1 ) )
- SPLUS = SPLUS*DBLE( RHS( J ) )
- IF( SPLUS.GT.SMINU ) THEN
- RHS( J ) = BP
- ELSE IF( SMINU.GT.SPLUS ) THEN
- RHS( J ) = BM
- ELSE
-*
-* In this case the updating sums are equal and we can
-* choose RHS(J) +1 or -1. The first time this happens we
-* choose -1, thereafter +1. This is a simple way to get
-* good estimates of matrices like Byers well-known example
-* (see [1]). (Not done in BSOLVE.)
-*
- RHS( J ) = RHS( J ) + PMONE
- PMONE = CONE
- END IF
-*
-* Compute the remaining r.h.s.
-*
- TEMP = -RHS( J )
- CALL ZAXPY( N-J, TEMP, Z( J+1, J ), 1, RHS( J+1 ), 1 )
- 10 CONTINUE
-*
-* Solve for U- part, lockahead for RHS(N) = +-1. This is not done
-* In BSOLVE and will hopefully give us a better estimate because
-* any ill-conditioning of the original matrix is transfered to U
-* and not to L. U(N, N) is an approximation to sigma_min(LU).
-*
- CALL ZCOPY( N-1, RHS, 1, WORK, 1 )
- WORK( N ) = RHS( N ) + CONE
- RHS( N ) = RHS( N ) - CONE
- SPLUS = ZERO
- SMINU = ZERO
- DO 30 I = N, 1, -1
- TEMP = CONE / Z( I, I )
- WORK( I ) = WORK( I )*TEMP
- RHS( I ) = RHS( I )*TEMP
- DO 20 K = I + 1, N
- WORK( I ) = WORK( I ) - WORK( K )*( Z( I, K )*TEMP )
- RHS( I ) = RHS( I ) - RHS( K )*( Z( I, K )*TEMP )
- 20 CONTINUE
- SPLUS = SPLUS + ABS( WORK( I ) )
- SMINU = SMINU + ABS( RHS( I ) )
- 30 CONTINUE
- IF( SPLUS.GT.SMINU )
- $ CALL ZCOPY( N, WORK, 1, RHS, 1 )
-*
-* Apply the permutations JPIV to the computed solution (RHS)
-*
- CALL ZLASWP( 1, RHS, LDZ, 1, N-1, JPIV, -1 )
-*
-* Compute the sum of squares
-*
- CALL ZLASSQ( N, RHS, 1, RDSCAL, RDSUM )
- RETURN
- END IF
-*
-* ENTRY IJOB = 2
-*
-* Compute approximate nullvector XM of Z
-*
- CALL ZGECON( 'I', N, Z, LDZ, ONE, RTEMP, WORK, RWORK, INFO )
- CALL ZCOPY( N, WORK( N+1 ), 1, XM, 1 )
-*
-* Compute RHS
-*
- CALL ZLASWP( 1, XM, LDZ, 1, N-1, IPIV, -1 )
- TEMP = CONE / SQRT( ZDOTC( N, XM, 1, XM, 1 ) )
- CALL ZSCAL( N, TEMP, XM, 1 )
- CALL ZCOPY( N, XM, 1, XP, 1 )
- CALL ZAXPY( N, CONE, RHS, 1, XP, 1 )
- CALL ZAXPY( N, -CONE, XM, 1, RHS, 1 )
- CALL ZGESC2( N, Z, LDZ, RHS, IPIV, JPIV, SCALE )
- CALL ZGESC2( N, Z, LDZ, XP, IPIV, JPIV, SCALE )
- IF( DZASUM( N, XP, 1 ).GT.DZASUM( N, RHS, 1 ) )
- $ CALL ZCOPY( N, XP, 1, RHS, 1 )
-*
-* Compute the sum of squares
-*
- CALL ZLASSQ( N, RHS, 1, RDSCAL, RDSUM )
- RETURN
-*
-* End of ZLATDF
-*
- END
diff --git a/src/lib/lapack/zlatrd.f b/src/lib/lapack/zlatrd.f
deleted file mode 100644
index 5fef7b5c..00000000
--- a/src/lib/lapack/zlatrd.f
+++ /dev/null
@@ -1,279 +0,0 @@
- SUBROUTINE ZLATRD( UPLO, N, NB, A, LDA, E, TAU, W, LDW )
-*
-* -- LAPACK auxiliary routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- CHARACTER UPLO
- INTEGER LDA, LDW, N, NB
-* ..
-* .. Array Arguments ..
- DOUBLE PRECISION E( * )
- COMPLEX*16 A( LDA, * ), TAU( * ), W( LDW, * )
-* ..
-*
-* Purpose
-* =======
-*
-* ZLATRD reduces NB rows and columns of a complex Hermitian matrix A to
-* Hermitian tridiagonal form by a unitary similarity
-* transformation Q' * A * Q, and returns the matrices V and W which are
-* needed to apply the transformation to the unreduced part of A.
-*
-* If UPLO = 'U', ZLATRD reduces the last NB rows and columns of a
-* matrix, of which the upper triangle is supplied;
-* if UPLO = 'L', ZLATRD reduces the first NB rows and columns of a
-* matrix, of which the lower triangle is supplied.
-*
-* This is an auxiliary routine called by ZHETRD.
-*
-* Arguments
-* =========
-*
-* UPLO (input) CHARACTER*1
-* Specifies whether the upper or lower triangular part of the
-* Hermitian matrix A is stored:
-* = 'U': Upper triangular
-* = 'L': Lower triangular
-*
-* N (input) INTEGER
-* The order of the matrix A.
-*
-* NB (input) INTEGER
-* The number of rows and columns to be reduced.
-*
-* A (input/output) COMPLEX*16 array, dimension (LDA,N)
-* On entry, the Hermitian matrix A. If UPLO = 'U', the leading
-* n-by-n upper triangular part of A contains the upper
-* triangular part of the matrix A, and the strictly lower
-* triangular part of A is not referenced. If UPLO = 'L', the
-* leading n-by-n lower triangular part of A contains the lower
-* triangular part of the matrix A, and the strictly upper
-* triangular part of A is not referenced.
-* On exit:
-* if UPLO = 'U', the last NB columns have been reduced to
-* tridiagonal form, with the diagonal elements overwriting
-* the diagonal elements of A; the elements above the diagonal
-* with the array TAU, represent the unitary matrix Q as a
-* product of elementary reflectors;
-* if UPLO = 'L', the first NB columns have been reduced to
-* tridiagonal form, with the diagonal elements overwriting
-* the diagonal elements of A; the elements below the diagonal
-* with the array TAU, represent the unitary matrix Q as a
-* product of elementary reflectors.
-* See Further Details.
-*
-* LDA (input) INTEGER
-* The leading dimension of the array A. LDA >= max(1,N).
-*
-* E (output) DOUBLE PRECISION array, dimension (N-1)
-* If UPLO = 'U', E(n-nb:n-1) contains the superdiagonal
-* elements of the last NB columns of the reduced matrix;
-* if UPLO = 'L', E(1:nb) contains the subdiagonal elements of
-* the first NB columns of the reduced matrix.
-*
-* TAU (output) COMPLEX*16 array, dimension (N-1)
-* The scalar factors of the elementary reflectors, stored in
-* TAU(n-nb:n-1) if UPLO = 'U', and in TAU(1:nb) if UPLO = 'L'.
-* See Further Details.
-*
-* W (output) COMPLEX*16 array, dimension (LDW,NB)
-* The n-by-nb matrix W required to update the unreduced part
-* of A.
-*
-* LDW (input) INTEGER
-* The leading dimension of the array W. LDW >= max(1,N).
-*
-* Further Details
-* ===============
-*
-* If UPLO = 'U', the matrix Q is represented as a product of elementary
-* reflectors
-*
-* Q = H(n) H(n-1) . . . H(n-nb+1).
-*
-* Each H(i) has the form
-*
-* H(i) = I - tau * v * v'
-*
-* where tau is a complex scalar, and v is a complex vector with
-* v(i:n) = 0 and v(i-1) = 1; v(1:i-1) is stored on exit in A(1:i-1,i),
-* and tau in TAU(i-1).
-*
-* If UPLO = 'L', the matrix Q is represented as a product of elementary
-* reflectors
-*
-* Q = H(1) H(2) . . . H(nb).
-*
-* Each H(i) has the form
-*
-* H(i) = I - tau * v * v'
-*
-* where tau is a complex scalar, and v is a complex vector with
-* v(1:i) = 0 and v(i+1) = 1; v(i+1:n) is stored on exit in A(i+1:n,i),
-* and tau in TAU(i).
-*
-* The elements of the vectors v together form the n-by-nb matrix V
-* which is needed, with W, to apply the transformation to the unreduced
-* part of the matrix, using a Hermitian rank-2k update of the form:
-* A := A - V*W' - W*V'.
-*
-* The contents of A on exit are illustrated by the following examples
-* with n = 5 and nb = 2:
-*
-* if UPLO = 'U': if UPLO = 'L':
-*
-* ( a a a v4 v5 ) ( d )
-* ( a a v4 v5 ) ( 1 d )
-* ( a 1 v5 ) ( v1 1 a )
-* ( d 1 ) ( v1 v2 a a )
-* ( d ) ( v1 v2 a a a )
-*
-* where d denotes a diagonal element of the reduced matrix, a denotes
-* an element of the original matrix that is unchanged, and vi denotes
-* an element of the vector defining H(i).
-*
-* =====================================================================
-*
-* .. Parameters ..
- COMPLEX*16 ZERO, ONE, HALF
- PARAMETER ( ZERO = ( 0.0D+0, 0.0D+0 ),
- $ ONE = ( 1.0D+0, 0.0D+0 ),
- $ HALF = ( 0.5D+0, 0.0D+0 ) )
-* ..
-* .. Local Scalars ..
- INTEGER I, IW
- COMPLEX*16 ALPHA
-* ..
-* .. External Subroutines ..
- EXTERNAL ZAXPY, ZGEMV, ZHEMV, ZLACGV, ZLARFG, ZSCAL
-* ..
-* .. External Functions ..
- LOGICAL LSAME
- COMPLEX*16 ZDOTC
- EXTERNAL LSAME, ZDOTC
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC DBLE, MIN
-* ..
-* .. Executable Statements ..
-*
-* Quick return if possible
-*
- IF( N.LE.0 )
- $ RETURN
-*
- IF( LSAME( UPLO, 'U' ) ) THEN
-*
-* Reduce last NB columns of upper triangle
-*
- DO 10 I = N, N - NB + 1, -1
- IW = I - N + NB
- IF( I.LT.N ) THEN
-*
-* Update A(1:i,i)
-*
- A( I, I ) = DBLE( A( I, I ) )
- CALL ZLACGV( N-I, W( I, IW+1 ), LDW )
- CALL ZGEMV( 'No transpose', I, N-I, -ONE, A( 1, I+1 ),
- $ LDA, W( I, IW+1 ), LDW, ONE, A( 1, I ), 1 )
- CALL ZLACGV( N-I, W( I, IW+1 ), LDW )
- CALL ZLACGV( N-I, A( I, I+1 ), LDA )
- CALL ZGEMV( 'No transpose', I, N-I, -ONE, W( 1, IW+1 ),
- $ LDW, A( I, I+1 ), LDA, ONE, A( 1, I ), 1 )
- CALL ZLACGV( N-I, A( I, I+1 ), LDA )
- A( I, I ) = DBLE( A( I, I ) )
- END IF
- IF( I.GT.1 ) THEN
-*
-* Generate elementary reflector H(i) to annihilate
-* A(1:i-2,i)
-*
- ALPHA = A( I-1, I )
- CALL ZLARFG( I-1, ALPHA, A( 1, I ), 1, TAU( I-1 ) )
- E( I-1 ) = ALPHA
- A( I-1, I ) = ONE
-*
-* Compute W(1:i-1,i)
-*
- CALL ZHEMV( 'Upper', I-1, ONE, A, LDA, A( 1, I ), 1,
- $ ZERO, W( 1, IW ), 1 )
- IF( I.LT.N ) THEN
- CALL ZGEMV( 'Conjugate transpose', I-1, N-I, ONE,
- $ W( 1, IW+1 ), LDW, A( 1, I ), 1, ZERO,
- $ W( I+1, IW ), 1 )
- CALL ZGEMV( 'No transpose', I-1, N-I, -ONE,
- $ A( 1, I+1 ), LDA, W( I+1, IW ), 1, ONE,
- $ W( 1, IW ), 1 )
- CALL ZGEMV( 'Conjugate transpose', I-1, N-I, ONE,
- $ A( 1, I+1 ), LDA, A( 1, I ), 1, ZERO,
- $ W( I+1, IW ), 1 )
- CALL ZGEMV( 'No transpose', I-1, N-I, -ONE,
- $ W( 1, IW+1 ), LDW, W( I+1, IW ), 1, ONE,
- $ W( 1, IW ), 1 )
- END IF
- CALL ZSCAL( I-1, TAU( I-1 ), W( 1, IW ), 1 )
- ALPHA = -HALF*TAU( I-1 )*ZDOTC( I-1, W( 1, IW ), 1,
- $ A( 1, I ), 1 )
- CALL ZAXPY( I-1, ALPHA, A( 1, I ), 1, W( 1, IW ), 1 )
- END IF
-*
- 10 CONTINUE
- ELSE
-*
-* Reduce first NB columns of lower triangle
-*
- DO 20 I = 1, NB
-*
-* Update A(i:n,i)
-*
- A( I, I ) = DBLE( A( I, I ) )
- CALL ZLACGV( I-1, W( I, 1 ), LDW )
- CALL ZGEMV( 'No transpose', N-I+1, I-1, -ONE, A( I, 1 ),
- $ LDA, W( I, 1 ), LDW, ONE, A( I, I ), 1 )
- CALL ZLACGV( I-1, W( I, 1 ), LDW )
- CALL ZLACGV( I-1, A( I, 1 ), LDA )
- CALL ZGEMV( 'No transpose', N-I+1, I-1, -ONE, W( I, 1 ),
- $ LDW, A( I, 1 ), LDA, ONE, A( I, I ), 1 )
- CALL ZLACGV( I-1, A( I, 1 ), LDA )
- A( I, I ) = DBLE( A( I, I ) )
- IF( I.LT.N ) THEN
-*
-* Generate elementary reflector H(i) to annihilate
-* A(i+2:n,i)
-*
- ALPHA = A( I+1, I )
- CALL ZLARFG( N-I, ALPHA, A( MIN( I+2, N ), I ), 1,
- $ TAU( I ) )
- E( I ) = ALPHA
- A( I+1, I ) = ONE
-*
-* Compute W(i+1:n,i)
-*
- CALL ZHEMV( 'Lower', N-I, ONE, A( I+1, I+1 ), LDA,
- $ A( I+1, I ), 1, ZERO, W( I+1, I ), 1 )
- CALL ZGEMV( 'Conjugate transpose', N-I, I-1, ONE,
- $ W( I+1, 1 ), LDW, A( I+1, I ), 1, ZERO,
- $ W( 1, I ), 1 )
- CALL ZGEMV( 'No transpose', N-I, I-1, -ONE, A( I+1, 1 ),
- $ LDA, W( 1, I ), 1, ONE, W( I+1, I ), 1 )
- CALL ZGEMV( 'Conjugate transpose', N-I, I-1, ONE,
- $ A( I+1, 1 ), LDA, A( I+1, I ), 1, ZERO,
- $ W( 1, I ), 1 )
- CALL ZGEMV( 'No transpose', N-I, I-1, -ONE, W( I+1, 1 ),
- $ LDW, W( 1, I ), 1, ONE, W( I+1, I ), 1 )
- CALL ZSCAL( N-I, TAU( I ), W( I+1, I ), 1 )
- ALPHA = -HALF*TAU( I )*ZDOTC( N-I, W( I+1, I ), 1,
- $ A( I+1, I ), 1 )
- CALL ZAXPY( N-I, ALPHA, A( I+1, I ), 1, W( I+1, I ), 1 )
- END IF
-*
- 20 CONTINUE
- END IF
-*
- RETURN
-*
-* End of ZLATRD
-*
- END
diff --git a/src/lib/lapack/zlatrs.f b/src/lib/lapack/zlatrs.f
deleted file mode 100644
index 7466096c..00000000
--- a/src/lib/lapack/zlatrs.f
+++ /dev/null
@@ -1,879 +0,0 @@
- SUBROUTINE ZLATRS( UPLO, TRANS, DIAG, NORMIN, N, A, LDA, X, SCALE,
- $ CNORM, INFO )
-*
-* -- LAPACK auxiliary routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- CHARACTER DIAG, NORMIN, TRANS, UPLO
- INTEGER INFO, LDA, N
- DOUBLE PRECISION SCALE
-* ..
-* .. Array Arguments ..
- DOUBLE PRECISION CNORM( * )
- COMPLEX*16 A( LDA, * ), X( * )
-* ..
-*
-* Purpose
-* =======
-*
-* ZLATRS solves one of the triangular systems
-*
-* A * x = s*b, A**T * x = s*b, or A**H * x = s*b,
-*
-* with scaling to prevent overflow. Here A is an upper or lower
-* triangular matrix, A**T denotes the transpose of A, A**H denotes the
-* conjugate transpose of A, x and b are n-element vectors, and s is a
-* scaling factor, usually less than or equal to 1, chosen so that the
-* components of x will be less than the overflow threshold. If the
-* unscaled problem will not cause overflow, the Level 2 BLAS routine
-* ZTRSV is called. If the matrix A is singular (A(j,j) = 0 for some j),
-* then s is set to 0 and a non-trivial solution to A*x = 0 is returned.
-*
-* Arguments
-* =========
-*
-* UPLO (input) CHARACTER*1
-* Specifies whether the matrix A is upper or lower triangular.
-* = 'U': Upper triangular
-* = 'L': Lower triangular
-*
-* TRANS (input) CHARACTER*1
-* Specifies the operation applied to A.
-* = 'N': Solve A * x = s*b (No transpose)
-* = 'T': Solve A**T * x = s*b (Transpose)
-* = 'C': Solve A**H * x = s*b (Conjugate transpose)
-*
-* DIAG (input) CHARACTER*1
-* Specifies whether or not the matrix A is unit triangular.
-* = 'N': Non-unit triangular
-* = 'U': Unit triangular
-*
-* NORMIN (input) CHARACTER*1
-* Specifies whether CNORM has been set or not.
-* = 'Y': CNORM contains the column norms on entry
-* = 'N': CNORM is not set on entry. On exit, the norms will
-* be computed and stored in CNORM.
-*
-* N (input) INTEGER
-* The order of the matrix A. N >= 0.
-*
-* A (input) COMPLEX*16 array, dimension (LDA,N)
-* The triangular matrix A. If UPLO = 'U', the leading n by n
-* upper triangular part of the array A contains the upper
-* triangular matrix, and the strictly lower triangular part of
-* A is not referenced. If UPLO = 'L', the leading n by n lower
-* triangular part of the array A contains the lower triangular
-* matrix, and the strictly upper triangular part of A is not
-* referenced. If DIAG = 'U', the diagonal elements of A are
-* also not referenced and are assumed to be 1.
-*
-* LDA (input) INTEGER
-* The leading dimension of the array A. LDA >= max (1,N).
-*
-* X (input/output) COMPLEX*16 array, dimension (N)
-* On entry, the right hand side b of the triangular system.
-* On exit, X is overwritten by the solution vector x.
-*
-* SCALE (output) DOUBLE PRECISION
-* The scaling factor s for the triangular system
-* A * x = s*b, A**T * x = s*b, or A**H * x = s*b.
-* If SCALE = 0, the matrix A is singular or badly scaled, and
-* the vector x is an exact or approximate solution to A*x = 0.
-*
-* CNORM (input or output) DOUBLE PRECISION array, dimension (N)
-*
-* If NORMIN = 'Y', CNORM is an input argument and CNORM(j)
-* contains the norm of the off-diagonal part of the j-th column
-* of A. If TRANS = 'N', CNORM(j) must be greater than or equal
-* to the infinity-norm, and if TRANS = 'T' or 'C', CNORM(j)
-* must be greater than or equal to the 1-norm.
-*
-* If NORMIN = 'N', CNORM is an output argument and CNORM(j)
-* returns the 1-norm of the offdiagonal part of the j-th column
-* of A.
-*
-* INFO (output) INTEGER
-* = 0: successful exit
-* < 0: if INFO = -k, the k-th argument had an illegal value
-*
-* Further Details
-* ======= =======
-*
-* A rough bound on x is computed; if that is less than overflow, ZTRSV
-* is called, otherwise, specific code is used which checks for possible
-* overflow or divide-by-zero at every operation.
-*
-* A columnwise scheme is used for solving A*x = b. The basic algorithm
-* if A is lower triangular is
-*
-* x[1:n] := b[1:n]
-* for j = 1, ..., n
-* x(j) := x(j) / A(j,j)
-* x[j+1:n] := x[j+1:n] - x(j) * A[j+1:n,j]
-* end
-*
-* Define bounds on the components of x after j iterations of the loop:
-* M(j) = bound on x[1:j]
-* G(j) = bound on x[j+1:n]
-* Initially, let M(0) = 0 and G(0) = max{x(i), i=1,...,n}.
-*
-* Then for iteration j+1 we have
-* M(j+1) <= G(j) / | A(j+1,j+1) |
-* G(j+1) <= G(j) + M(j+1) * | A[j+2:n,j+1] |
-* <= G(j) ( 1 + CNORM(j+1) / | A(j+1,j+1) | )
-*
-* where CNORM(j+1) is greater than or equal to the infinity-norm of
-* column j+1 of A, not counting the diagonal. Hence
-*
-* G(j) <= G(0) product ( 1 + CNORM(i) / | A(i,i) | )
-* 1<=i<=j
-* and
-*
-* |x(j)| <= ( G(0) / |A(j,j)| ) product ( 1 + CNORM(i) / |A(i,i)| )
-* 1<=i< j
-*
-* Since |x(j)| <= M(j), we use the Level 2 BLAS routine ZTRSV if the
-* reciprocal of the largest M(j), j=1,..,n, is larger than
-* max(underflow, 1/overflow).
-*
-* The bound on x(j) is also used to determine when a step in the
-* columnwise method can be performed without fear of overflow. If
-* the computed bound is greater than a large constant, x is scaled to
-* prevent overflow, but if the bound overflows, x is set to 0, x(j) to
-* 1, and scale to 0, and a non-trivial solution to A*x = 0 is found.
-*
-* Similarly, a row-wise scheme is used to solve A**T *x = b or
-* A**H *x = b. The basic algorithm for A upper triangular is
-*
-* for j = 1, ..., n
-* x(j) := ( b(j) - A[1:j-1,j]' * x[1:j-1] ) / A(j,j)
-* end
-*
-* We simultaneously compute two bounds
-* G(j) = bound on ( b(i) - A[1:i-1,i]' * x[1:i-1] ), 1<=i<=j
-* M(j) = bound on x(i), 1<=i<=j
-*
-* The initial values are G(0) = 0, M(0) = max{b(i), i=1,..,n}, and we
-* add the constraint G(j) >= G(j-1) and M(j) >= M(j-1) for j >= 1.
-* Then the bound on x(j) is
-*
-* M(j) <= M(j-1) * ( 1 + CNORM(j) ) / | A(j,j) |
-*
-* <= M(0) * product ( ( 1 + CNORM(i) ) / |A(i,i)| )
-* 1<=i<=j
-*
-* and we can safely call ZTRSV if 1/M(n) and 1/G(n) are both greater
-* than max(underflow, 1/overflow).
-*
-* =====================================================================
-*
-* .. Parameters ..
- DOUBLE PRECISION ZERO, HALF, ONE, TWO
- PARAMETER ( ZERO = 0.0D+0, HALF = 0.5D+0, ONE = 1.0D+0,
- $ TWO = 2.0D+0 )
-* ..
-* .. Local Scalars ..
- LOGICAL NOTRAN, NOUNIT, UPPER
- INTEGER I, IMAX, J, JFIRST, JINC, JLAST
- DOUBLE PRECISION BIGNUM, GROW, REC, SMLNUM, TJJ, TMAX, TSCAL,
- $ XBND, XJ, XMAX
- COMPLEX*16 CSUMJ, TJJS, USCAL, ZDUM
-* ..
-* .. External Functions ..
- LOGICAL LSAME
- INTEGER IDAMAX, IZAMAX
- DOUBLE PRECISION DLAMCH, DZASUM
- COMPLEX*16 ZDOTC, ZDOTU, ZLADIV
- EXTERNAL LSAME, IDAMAX, IZAMAX, DLAMCH, DZASUM, ZDOTC,
- $ ZDOTU, ZLADIV
-* ..
-* .. External Subroutines ..
- EXTERNAL DSCAL, XERBLA, ZAXPY, ZDSCAL, ZTRSV
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC ABS, DBLE, DCMPLX, DCONJG, DIMAG, MAX, MIN
-* ..
-* .. Statement Functions ..
- DOUBLE PRECISION CABS1, CABS2
-* ..
-* .. Statement Function definitions ..
- CABS1( ZDUM ) = ABS( DBLE( ZDUM ) ) + ABS( DIMAG( ZDUM ) )
- CABS2( ZDUM ) = ABS( DBLE( ZDUM ) / 2.D0 ) +
- $ ABS( DIMAG( ZDUM ) / 2.D0 )
-* ..
-* .. Executable Statements ..
-*
- INFO = 0
- UPPER = LSAME( UPLO, 'U' )
- NOTRAN = LSAME( TRANS, 'N' )
- NOUNIT = LSAME( DIAG, 'N' )
-*
-* Test the input parameters.
-*
- IF( .NOT.UPPER .AND. .NOT.LSAME( UPLO, 'L' ) ) THEN
- INFO = -1
- ELSE IF( .NOT.NOTRAN .AND. .NOT.LSAME( TRANS, 'T' ) .AND. .NOT.
- $ LSAME( TRANS, 'C' ) ) THEN
- INFO = -2
- ELSE IF( .NOT.NOUNIT .AND. .NOT.LSAME( DIAG, 'U' ) ) THEN
- INFO = -3
- ELSE IF( .NOT.LSAME( NORMIN, 'Y' ) .AND. .NOT.
- $ LSAME( NORMIN, 'N' ) ) THEN
- INFO = -4
- ELSE IF( N.LT.0 ) THEN
- INFO = -5
- ELSE IF( LDA.LT.MAX( 1, N ) ) THEN
- INFO = -7
- END IF
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'ZLATRS', -INFO )
- RETURN
- END IF
-*
-* Quick return if possible
-*
- IF( N.EQ.0 )
- $ RETURN
-*
-* Determine machine dependent parameters to control overflow.
-*
- SMLNUM = DLAMCH( 'Safe minimum' )
- BIGNUM = ONE / SMLNUM
- CALL DLABAD( SMLNUM, BIGNUM )
- SMLNUM = SMLNUM / DLAMCH( 'Precision' )
- BIGNUM = ONE / SMLNUM
- SCALE = ONE
-*
- IF( LSAME( NORMIN, 'N' ) ) THEN
-*
-* Compute the 1-norm of each column, not including the diagonal.
-*
- IF( UPPER ) THEN
-*
-* A is upper triangular.
-*
- DO 10 J = 1, N
- CNORM( J ) = DZASUM( J-1, A( 1, J ), 1 )
- 10 CONTINUE
- ELSE
-*
-* A is lower triangular.
-*
- DO 20 J = 1, N - 1
- CNORM( J ) = DZASUM( N-J, A( J+1, J ), 1 )
- 20 CONTINUE
- CNORM( N ) = ZERO
- END IF
- END IF
-*
-* Scale the column norms by TSCAL if the maximum element in CNORM is
-* greater than BIGNUM/2.
-*
- IMAX = IDAMAX( N, CNORM, 1 )
- TMAX = CNORM( IMAX )
- IF( TMAX.LE.BIGNUM*HALF ) THEN
- TSCAL = ONE
- ELSE
- TSCAL = HALF / ( SMLNUM*TMAX )
- CALL DSCAL( N, TSCAL, CNORM, 1 )
- END IF
-*
-* Compute a bound on the computed solution vector to see if the
-* Level 2 BLAS routine ZTRSV can be used.
-*
- XMAX = ZERO
- DO 30 J = 1, N
- XMAX = MAX( XMAX, CABS2( X( J ) ) )
- 30 CONTINUE
- XBND = XMAX
-*
- IF( NOTRAN ) THEN
-*
-* Compute the growth in A * x = b.
-*
- IF( UPPER ) THEN
- JFIRST = N
- JLAST = 1
- JINC = -1
- ELSE
- JFIRST = 1
- JLAST = N
- JINC = 1
- END IF
-*
- IF( TSCAL.NE.ONE ) THEN
- GROW = ZERO
- GO TO 60
- END IF
-*
- IF( NOUNIT ) THEN
-*
-* A is non-unit triangular.
-*
-* Compute GROW = 1/G(j) and XBND = 1/M(j).
-* Initially, G(0) = max{x(i), i=1,...,n}.
-*
- GROW = HALF / MAX( XBND, SMLNUM )
- XBND = GROW
- DO 40 J = JFIRST, JLAST, JINC
-*
-* Exit the loop if the growth factor is too small.
-*
- IF( GROW.LE.SMLNUM )
- $ GO TO 60
-*
- TJJS = A( J, J )
- TJJ = CABS1( TJJS )
-*
- IF( TJJ.GE.SMLNUM ) THEN
-*
-* M(j) = G(j-1) / abs(A(j,j))
-*
- XBND = MIN( XBND, MIN( ONE, TJJ )*GROW )
- ELSE
-*
-* M(j) could overflow, set XBND to 0.
-*
- XBND = ZERO
- END IF
-*
- IF( TJJ+CNORM( J ).GE.SMLNUM ) THEN
-*
-* G(j) = G(j-1)*( 1 + CNORM(j) / abs(A(j,j)) )
-*
- GROW = GROW*( TJJ / ( TJJ+CNORM( J ) ) )
- ELSE
-*
-* G(j) could overflow, set GROW to 0.
-*
- GROW = ZERO
- END IF
- 40 CONTINUE
- GROW = XBND
- ELSE
-*
-* A is unit triangular.
-*
-* Compute GROW = 1/G(j), where G(0) = max{x(i), i=1,...,n}.
-*
- GROW = MIN( ONE, HALF / MAX( XBND, SMLNUM ) )
- DO 50 J = JFIRST, JLAST, JINC
-*
-* Exit the loop if the growth factor is too small.
-*
- IF( GROW.LE.SMLNUM )
- $ GO TO 60
-*
-* G(j) = G(j-1)*( 1 + CNORM(j) )
-*
- GROW = GROW*( ONE / ( ONE+CNORM( J ) ) )
- 50 CONTINUE
- END IF
- 60 CONTINUE
-*
- ELSE
-*
-* Compute the growth in A**T * x = b or A**H * x = b.
-*
- IF( UPPER ) THEN
- JFIRST = 1
- JLAST = N
- JINC = 1
- ELSE
- JFIRST = N
- JLAST = 1
- JINC = -1
- END IF
-*
- IF( TSCAL.NE.ONE ) THEN
- GROW = ZERO
- GO TO 90
- END IF
-*
- IF( NOUNIT ) THEN
-*
-* A is non-unit triangular.
-*
-* Compute GROW = 1/G(j) and XBND = 1/M(j).
-* Initially, M(0) = max{x(i), i=1,...,n}.
-*
- GROW = HALF / MAX( XBND, SMLNUM )
- XBND = GROW
- DO 70 J = JFIRST, JLAST, JINC
-*
-* Exit the loop if the growth factor is too small.
-*
- IF( GROW.LE.SMLNUM )
- $ GO TO 90
-*
-* G(j) = max( G(j-1), M(j-1)*( 1 + CNORM(j) ) )
-*
- XJ = ONE + CNORM( J )
- GROW = MIN( GROW, XBND / XJ )
-*
- TJJS = A( J, J )
- TJJ = CABS1( TJJS )
-*
- IF( TJJ.GE.SMLNUM ) THEN
-*
-* M(j) = M(j-1)*( 1 + CNORM(j) ) / abs(A(j,j))
-*
- IF( XJ.GT.TJJ )
- $ XBND = XBND*( TJJ / XJ )
- ELSE
-*
-* M(j) could overflow, set XBND to 0.
-*
- XBND = ZERO
- END IF
- 70 CONTINUE
- GROW = MIN( GROW, XBND )
- ELSE
-*
-* A is unit triangular.
-*
-* Compute GROW = 1/G(j), where G(0) = max{x(i), i=1,...,n}.
-*
- GROW = MIN( ONE, HALF / MAX( XBND, SMLNUM ) )
- DO 80 J = JFIRST, JLAST, JINC
-*
-* Exit the loop if the growth factor is too small.
-*
- IF( GROW.LE.SMLNUM )
- $ GO TO 90
-*
-* G(j) = ( 1 + CNORM(j) )*G(j-1)
-*
- XJ = ONE + CNORM( J )
- GROW = GROW / XJ
- 80 CONTINUE
- END IF
- 90 CONTINUE
- END IF
-*
- IF( ( GROW*TSCAL ).GT.SMLNUM ) THEN
-*
-* Use the Level 2 BLAS solve if the reciprocal of the bound on
-* elements of X is not too small.
-*
- CALL ZTRSV( UPLO, TRANS, DIAG, N, A, LDA, X, 1 )
- ELSE
-*
-* Use a Level 1 BLAS solve, scaling intermediate results.
-*
- IF( XMAX.GT.BIGNUM*HALF ) THEN
-*
-* Scale X so that its components are less than or equal to
-* BIGNUM in absolute value.
-*
- SCALE = ( BIGNUM*HALF ) / XMAX
- CALL ZDSCAL( N, SCALE, X, 1 )
- XMAX = BIGNUM
- ELSE
- XMAX = XMAX*TWO
- END IF
-*
- IF( NOTRAN ) THEN
-*
-* Solve A * x = b
-*
- DO 120 J = JFIRST, JLAST, JINC
-*
-* Compute x(j) = b(j) / A(j,j), scaling x if necessary.
-*
- XJ = CABS1( X( J ) )
- IF( NOUNIT ) THEN
- TJJS = A( J, J )*TSCAL
- ELSE
- TJJS = TSCAL
- IF( TSCAL.EQ.ONE )
- $ GO TO 110
- END IF
- TJJ = CABS1( TJJS )
- IF( TJJ.GT.SMLNUM ) THEN
-*
-* abs(A(j,j)) > SMLNUM:
-*
- IF( TJJ.LT.ONE ) THEN
- IF( XJ.GT.TJJ*BIGNUM ) THEN
-*
-* Scale x by 1/b(j).
-*
- REC = ONE / XJ
- CALL ZDSCAL( N, REC, X, 1 )
- SCALE = SCALE*REC
- XMAX = XMAX*REC
- END IF
- END IF
- X( J ) = ZLADIV( X( J ), TJJS )
- XJ = CABS1( X( J ) )
- ELSE IF( TJJ.GT.ZERO ) THEN
-*
-* 0 < abs(A(j,j)) <= SMLNUM:
-*
- IF( XJ.GT.TJJ*BIGNUM ) THEN
-*
-* Scale x by (1/abs(x(j)))*abs(A(j,j))*BIGNUM
-* to avoid overflow when dividing by A(j,j).
-*
- REC = ( TJJ*BIGNUM ) / XJ
- IF( CNORM( J ).GT.ONE ) THEN
-*
-* Scale by 1/CNORM(j) to avoid overflow when
-* multiplying x(j) times column j.
-*
- REC = REC / CNORM( J )
- END IF
- CALL ZDSCAL( N, REC, X, 1 )
- SCALE = SCALE*REC
- XMAX = XMAX*REC
- END IF
- X( J ) = ZLADIV( X( J ), TJJS )
- XJ = CABS1( X( J ) )
- ELSE
-*
-* A(j,j) = 0: Set x(1:n) = 0, x(j) = 1, and
-* scale = 0, and compute a solution to A*x = 0.
-*
- DO 100 I = 1, N
- X( I ) = ZERO
- 100 CONTINUE
- X( J ) = ONE
- XJ = ONE
- SCALE = ZERO
- XMAX = ZERO
- END IF
- 110 CONTINUE
-*
-* Scale x if necessary to avoid overflow when adding a
-* multiple of column j of A.
-*
- IF( XJ.GT.ONE ) THEN
- REC = ONE / XJ
- IF( CNORM( J ).GT.( BIGNUM-XMAX )*REC ) THEN
-*
-* Scale x by 1/(2*abs(x(j))).
-*
- REC = REC*HALF
- CALL ZDSCAL( N, REC, X, 1 )
- SCALE = SCALE*REC
- END IF
- ELSE IF( XJ*CNORM( J ).GT.( BIGNUM-XMAX ) ) THEN
-*
-* Scale x by 1/2.
-*
- CALL ZDSCAL( N, HALF, X, 1 )
- SCALE = SCALE*HALF
- END IF
-*
- IF( UPPER ) THEN
- IF( J.GT.1 ) THEN
-*
-* Compute the update
-* x(1:j-1) := x(1:j-1) - x(j) * A(1:j-1,j)
-*
- CALL ZAXPY( J-1, -X( J )*TSCAL, A( 1, J ), 1, X,
- $ 1 )
- I = IZAMAX( J-1, X, 1 )
- XMAX = CABS1( X( I ) )
- END IF
- ELSE
- IF( J.LT.N ) THEN
-*
-* Compute the update
-* x(j+1:n) := x(j+1:n) - x(j) * A(j+1:n,j)
-*
- CALL ZAXPY( N-J, -X( J )*TSCAL, A( J+1, J ), 1,
- $ X( J+1 ), 1 )
- I = J + IZAMAX( N-J, X( J+1 ), 1 )
- XMAX = CABS1( X( I ) )
- END IF
- END IF
- 120 CONTINUE
-*
- ELSE IF( LSAME( TRANS, 'T' ) ) THEN
-*
-* Solve A**T * x = b
-*
- DO 170 J = JFIRST, JLAST, JINC
-*
-* Compute x(j) = b(j) - sum A(k,j)*x(k).
-* k<>j
-*
- XJ = CABS1( X( J ) )
- USCAL = TSCAL
- REC = ONE / MAX( XMAX, ONE )
- IF( CNORM( J ).GT.( BIGNUM-XJ )*REC ) THEN
-*
-* If x(j) could overflow, scale x by 1/(2*XMAX).
-*
- REC = REC*HALF
- IF( NOUNIT ) THEN
- TJJS = A( J, J )*TSCAL
- ELSE
- TJJS = TSCAL
- END IF
- TJJ = CABS1( TJJS )
- IF( TJJ.GT.ONE ) THEN
-*
-* Divide by A(j,j) when scaling x if A(j,j) > 1.
-*
- REC = MIN( ONE, REC*TJJ )
- USCAL = ZLADIV( USCAL, TJJS )
- END IF
- IF( REC.LT.ONE ) THEN
- CALL ZDSCAL( N, REC, X, 1 )
- SCALE = SCALE*REC
- XMAX = XMAX*REC
- END IF
- END IF
-*
- CSUMJ = ZERO
- IF( USCAL.EQ.DCMPLX( ONE ) ) THEN
-*
-* If the scaling needed for A in the dot product is 1,
-* call ZDOTU to perform the dot product.
-*
- IF( UPPER ) THEN
- CSUMJ = ZDOTU( J-1, A( 1, J ), 1, X, 1 )
- ELSE IF( J.LT.N ) THEN
- CSUMJ = ZDOTU( N-J, A( J+1, J ), 1, X( J+1 ), 1 )
- END IF
- ELSE
-*
-* Otherwise, use in-line code for the dot product.
-*
- IF( UPPER ) THEN
- DO 130 I = 1, J - 1
- CSUMJ = CSUMJ + ( A( I, J )*USCAL )*X( I )
- 130 CONTINUE
- ELSE IF( J.LT.N ) THEN
- DO 140 I = J + 1, N
- CSUMJ = CSUMJ + ( A( I, J )*USCAL )*X( I )
- 140 CONTINUE
- END IF
- END IF
-*
- IF( USCAL.EQ.DCMPLX( TSCAL ) ) THEN
-*
-* Compute x(j) := ( x(j) - CSUMJ ) / A(j,j) if 1/A(j,j)
-* was not used to scale the dotproduct.
-*
- X( J ) = X( J ) - CSUMJ
- XJ = CABS1( X( J ) )
- IF( NOUNIT ) THEN
- TJJS = A( J, J )*TSCAL
- ELSE
- TJJS = TSCAL
- IF( TSCAL.EQ.ONE )
- $ GO TO 160
- END IF
-*
-* Compute x(j) = x(j) / A(j,j), scaling if necessary.
-*
- TJJ = CABS1( TJJS )
- IF( TJJ.GT.SMLNUM ) THEN
-*
-* abs(A(j,j)) > SMLNUM:
-*
- IF( TJJ.LT.ONE ) THEN
- IF( XJ.GT.TJJ*BIGNUM ) THEN
-*
-* Scale X by 1/abs(x(j)).
-*
- REC = ONE / XJ
- CALL ZDSCAL( N, REC, X, 1 )
- SCALE = SCALE*REC
- XMAX = XMAX*REC
- END IF
- END IF
- X( J ) = ZLADIV( X( J ), TJJS )
- ELSE IF( TJJ.GT.ZERO ) THEN
-*
-* 0 < abs(A(j,j)) <= SMLNUM:
-*
- IF( XJ.GT.TJJ*BIGNUM ) THEN
-*
-* Scale x by (1/abs(x(j)))*abs(A(j,j))*BIGNUM.
-*
- REC = ( TJJ*BIGNUM ) / XJ
- CALL ZDSCAL( N, REC, X, 1 )
- SCALE = SCALE*REC
- XMAX = XMAX*REC
- END IF
- X( J ) = ZLADIV( X( J ), TJJS )
- ELSE
-*
-* A(j,j) = 0: Set x(1:n) = 0, x(j) = 1, and
-* scale = 0 and compute a solution to A**T *x = 0.
-*
- DO 150 I = 1, N
- X( I ) = ZERO
- 150 CONTINUE
- X( J ) = ONE
- SCALE = ZERO
- XMAX = ZERO
- END IF
- 160 CONTINUE
- ELSE
-*
-* Compute x(j) := x(j) / A(j,j) - CSUMJ if the dot
-* product has already been divided by 1/A(j,j).
-*
- X( J ) = ZLADIV( X( J ), TJJS ) - CSUMJ
- END IF
- XMAX = MAX( XMAX, CABS1( X( J ) ) )
- 170 CONTINUE
-*
- ELSE
-*
-* Solve A**H * x = b
-*
- DO 220 J = JFIRST, JLAST, JINC
-*
-* Compute x(j) = b(j) - sum A(k,j)*x(k).
-* k<>j
-*
- XJ = CABS1( X( J ) )
- USCAL = TSCAL
- REC = ONE / MAX( XMAX, ONE )
- IF( CNORM( J ).GT.( BIGNUM-XJ )*REC ) THEN
-*
-* If x(j) could overflow, scale x by 1/(2*XMAX).
-*
- REC = REC*HALF
- IF( NOUNIT ) THEN
- TJJS = DCONJG( A( J, J ) )*TSCAL
- ELSE
- TJJS = TSCAL
- END IF
- TJJ = CABS1( TJJS )
- IF( TJJ.GT.ONE ) THEN
-*
-* Divide by A(j,j) when scaling x if A(j,j) > 1.
-*
- REC = MIN( ONE, REC*TJJ )
- USCAL = ZLADIV( USCAL, TJJS )
- END IF
- IF( REC.LT.ONE ) THEN
- CALL ZDSCAL( N, REC, X, 1 )
- SCALE = SCALE*REC
- XMAX = XMAX*REC
- END IF
- END IF
-*
- CSUMJ = ZERO
- IF( USCAL.EQ.DCMPLX( ONE ) ) THEN
-*
-* If the scaling needed for A in the dot product is 1,
-* call ZDOTC to perform the dot product.
-*
- IF( UPPER ) THEN
- CSUMJ = ZDOTC( J-1, A( 1, J ), 1, X, 1 )
- ELSE IF( J.LT.N ) THEN
- CSUMJ = ZDOTC( N-J, A( J+1, J ), 1, X( J+1 ), 1 )
- END IF
- ELSE
-*
-* Otherwise, use in-line code for the dot product.
-*
- IF( UPPER ) THEN
- DO 180 I = 1, J - 1
- CSUMJ = CSUMJ + ( DCONJG( A( I, J ) )*USCAL )*
- $ X( I )
- 180 CONTINUE
- ELSE IF( J.LT.N ) THEN
- DO 190 I = J + 1, N
- CSUMJ = CSUMJ + ( DCONJG( A( I, J ) )*USCAL )*
- $ X( I )
- 190 CONTINUE
- END IF
- END IF
-*
- IF( USCAL.EQ.DCMPLX( TSCAL ) ) THEN
-*
-* Compute x(j) := ( x(j) - CSUMJ ) / A(j,j) if 1/A(j,j)
-* was not used to scale the dotproduct.
-*
- X( J ) = X( J ) - CSUMJ
- XJ = CABS1( X( J ) )
- IF( NOUNIT ) THEN
- TJJS = DCONJG( A( J, J ) )*TSCAL
- ELSE
- TJJS = TSCAL
- IF( TSCAL.EQ.ONE )
- $ GO TO 210
- END IF
-*
-* Compute x(j) = x(j) / A(j,j), scaling if necessary.
-*
- TJJ = CABS1( TJJS )
- IF( TJJ.GT.SMLNUM ) THEN
-*
-* abs(A(j,j)) > SMLNUM:
-*
- IF( TJJ.LT.ONE ) THEN
- IF( XJ.GT.TJJ*BIGNUM ) THEN
-*
-* Scale X by 1/abs(x(j)).
-*
- REC = ONE / XJ
- CALL ZDSCAL( N, REC, X, 1 )
- SCALE = SCALE*REC
- XMAX = XMAX*REC
- END IF
- END IF
- X( J ) = ZLADIV( X( J ), TJJS )
- ELSE IF( TJJ.GT.ZERO ) THEN
-*
-* 0 < abs(A(j,j)) <= SMLNUM:
-*
- IF( XJ.GT.TJJ*BIGNUM ) THEN
-*
-* Scale x by (1/abs(x(j)))*abs(A(j,j))*BIGNUM.
-*
- REC = ( TJJ*BIGNUM ) / XJ
- CALL ZDSCAL( N, REC, X, 1 )
- SCALE = SCALE*REC
- XMAX = XMAX*REC
- END IF
- X( J ) = ZLADIV( X( J ), TJJS )
- ELSE
-*
-* A(j,j) = 0: Set x(1:n) = 0, x(j) = 1, and
-* scale = 0 and compute a solution to A**H *x = 0.
-*
- DO 200 I = 1, N
- X( I ) = ZERO
- 200 CONTINUE
- X( J ) = ONE
- SCALE = ZERO
- XMAX = ZERO
- END IF
- 210 CONTINUE
- ELSE
-*
-* Compute x(j) := x(j) / A(j,j) - CSUMJ if the dot
-* product has already been divided by 1/A(j,j).
-*
- X( J ) = ZLADIV( X( J ), TJJS ) - CSUMJ
- END IF
- XMAX = MAX( XMAX, CABS1( X( J ) ) )
- 220 CONTINUE
- END IF
- SCALE = SCALE / TSCAL
- END IF
-*
-* Scale the column norms by 1/TSCAL for return.
-*
- IF( TSCAL.NE.ONE ) THEN
- CALL DSCAL( N, ONE / TSCAL, CNORM, 1 )
- END IF
-*
- RETURN
-*
-* End of ZLATRS
-*
- END
diff --git a/src/lib/lapack/zlatrz.f b/src/lib/lapack/zlatrz.f
deleted file mode 100644
index c1c7aab3..00000000
--- a/src/lib/lapack/zlatrz.f
+++ /dev/null
@@ -1,133 +0,0 @@
- SUBROUTINE ZLATRZ( M, N, L, A, LDA, TAU, WORK )
-*
-* -- LAPACK routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- INTEGER L, LDA, M, N
-* ..
-* .. Array Arguments ..
- COMPLEX*16 A( LDA, * ), TAU( * ), WORK( * )
-* ..
-*
-* Purpose
-* =======
-*
-* ZLATRZ factors the M-by-(M+L) complex upper trapezoidal matrix
-* [ A1 A2 ] = [ A(1:M,1:M) A(1:M,N-L+1:N) ] as ( R 0 ) * Z by means
-* of unitary transformations, where Z is an (M+L)-by-(M+L) unitary
-* matrix and, R and A1 are M-by-M upper triangular matrices.
-*
-* Arguments
-* =========
-*
-* M (input) INTEGER
-* The number of rows of the matrix A. M >= 0.
-*
-* N (input) INTEGER
-* The number of columns of the matrix A. N >= 0.
-*
-* L (input) INTEGER
-* The number of columns of the matrix A containing the
-* meaningful part of the Householder vectors. N-M >= L >= 0.
-*
-* A (input/output) COMPLEX*16 array, dimension (LDA,N)
-* On entry, the leading M-by-N upper trapezoidal part of the
-* array A must contain the matrix to be factorized.
-* On exit, the leading M-by-M upper triangular part of A
-* contains the upper triangular matrix R, and elements N-L+1 to
-* N of the first M rows of A, with the array TAU, represent the
-* unitary matrix Z as a product of M elementary reflectors.
-*
-* LDA (input) INTEGER
-* The leading dimension of the array A. LDA >= max(1,M).
-*
-* TAU (output) COMPLEX*16 array, dimension (M)
-* The scalar factors of the elementary reflectors.
-*
-* WORK (workspace) COMPLEX*16 array, dimension (M)
-*
-* Further Details
-* ===============
-*
-* Based on contributions by
-* A. Petitet, Computer Science Dept., Univ. of Tenn., Knoxville, USA
-*
-* The factorization is obtained by Householder's method. The kth
-* transformation matrix, Z( k ), which is used to introduce zeros into
-* the ( m - k + 1 )th row of A, is given in the form
-*
-* Z( k ) = ( I 0 ),
-* ( 0 T( k ) )
-*
-* where
-*
-* T( k ) = I - tau*u( k )*u( k )', u( k ) = ( 1 ),
-* ( 0 )
-* ( z( k ) )
-*
-* tau is a scalar and z( k ) is an l element vector. tau and z( k )
-* are chosen to annihilate the elements of the kth row of A2.
-*
-* The scalar tau is returned in the kth element of TAU and the vector
-* u( k ) in the kth row of A2, such that the elements of z( k ) are
-* in a( k, l + 1 ), ..., a( k, n ). The elements of R are returned in
-* the upper triangular part of A1.
-*
-* Z is given by
-*
-* Z = Z( 1 ) * Z( 2 ) * ... * Z( m ).
-*
-* =====================================================================
-*
-* .. Parameters ..
- COMPLEX*16 ZERO
- PARAMETER ( ZERO = ( 0.0D+0, 0.0D+0 ) )
-* ..
-* .. Local Scalars ..
- INTEGER I
- COMPLEX*16 ALPHA
-* ..
-* .. External Subroutines ..
- EXTERNAL ZLACGV, ZLARFG, ZLARZ
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC DCONJG
-* ..
-* .. Executable Statements ..
-*
-* Quick return if possible
-*
- IF( M.EQ.0 ) THEN
- RETURN
- ELSE IF( M.EQ.N ) THEN
- DO 10 I = 1, N
- TAU( I ) = ZERO
- 10 CONTINUE
- RETURN
- END IF
-*
- DO 20 I = M, 1, -1
-*
-* Generate elementary reflector H(i) to annihilate
-* [ A(i,i) A(i,n-l+1:n) ]
-*
- CALL ZLACGV( L, A( I, N-L+1 ), LDA )
- ALPHA = DCONJG( A( I, I ) )
- CALL ZLARFG( L+1, ALPHA, A( I, N-L+1 ), LDA, TAU( I ) )
- TAU( I ) = DCONJG( TAU( I ) )
-*
-* Apply H(i) to A(1:i-1,i:n) from the right
-*
- CALL ZLARZ( 'Right', I-1, N-I+1, L, A( I, N-L+1 ), LDA,
- $ DCONJG( TAU( I ) ), A( 1, I ), LDA, WORK )
- A( I, I ) = DCONJG( ALPHA )
-*
- 20 CONTINUE
-*
- RETURN
-*
-* End of ZLATRZ
-*
- END
diff --git a/src/lib/lapack/zpotf2.f b/src/lib/lapack/zpotf2.f
deleted file mode 100644
index ca9df447..00000000
--- a/src/lib/lapack/zpotf2.f
+++ /dev/null
@@ -1,174 +0,0 @@
- SUBROUTINE ZPOTF2( UPLO, N, A, LDA, INFO )
-*
-* -- LAPACK routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- CHARACTER UPLO
- INTEGER INFO, LDA, N
-* ..
-* .. Array Arguments ..
- COMPLEX*16 A( LDA, * )
-* ..
-*
-* Purpose
-* =======
-*
-* ZPOTF2 computes the Cholesky factorization of a complex Hermitian
-* positive definite matrix A.
-*
-* The factorization has the form
-* A = U' * U , if UPLO = 'U', or
-* A = L * L', if UPLO = 'L',
-* where U is an upper triangular matrix and L is lower triangular.
-*
-* This is the unblocked version of the algorithm, calling Level 2 BLAS.
-*
-* Arguments
-* =========
-*
-* UPLO (input) CHARACTER*1
-* Specifies whether the upper or lower triangular part of the
-* Hermitian matrix A is stored.
-* = 'U': Upper triangular
-* = 'L': Lower triangular
-*
-* N (input) INTEGER
-* The order of the matrix A. N >= 0.
-*
-* A (input/output) COMPLEX*16 array, dimension (LDA,N)
-* On entry, the Hermitian matrix A. If UPLO = 'U', the leading
-* n by n upper triangular part of A contains the upper
-* triangular part of the matrix A, and the strictly lower
-* triangular part of A is not referenced. If UPLO = 'L', the
-* leading n by n lower triangular part of A contains the lower
-* triangular part of the matrix A, and the strictly upper
-* triangular part of A is not referenced.
-*
-* On exit, if INFO = 0, the factor U or L from the Cholesky
-* factorization A = U'*U or A = L*L'.
-*
-* LDA (input) INTEGER
-* The leading dimension of the array A. LDA >= max(1,N).
-*
-* INFO (output) INTEGER
-* = 0: successful exit
-* < 0: if INFO = -k, the k-th argument had an illegal value
-* > 0: if INFO = k, the leading minor of order k is not
-* positive definite, and the factorization could not be
-* completed.
-*
-* =====================================================================
-*
-* .. Parameters ..
- DOUBLE PRECISION ONE, ZERO
- PARAMETER ( ONE = 1.0D+0, ZERO = 0.0D+0 )
- COMPLEX*16 CONE
- PARAMETER ( CONE = ( 1.0D+0, 0.0D+0 ) )
-* ..
-* .. Local Scalars ..
- LOGICAL UPPER
- INTEGER J
- DOUBLE PRECISION AJJ
-* ..
-* .. External Functions ..
- LOGICAL LSAME
- COMPLEX*16 ZDOTC
- EXTERNAL LSAME, ZDOTC
-* ..
-* .. External Subroutines ..
- EXTERNAL XERBLA, ZDSCAL, ZGEMV, ZLACGV
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC DBLE, MAX, SQRT
-* ..
-* .. Executable Statements ..
-*
-* Test the input parameters.
-*
- INFO = 0
- UPPER = LSAME( UPLO, 'U' )
- IF( .NOT.UPPER .AND. .NOT.LSAME( UPLO, 'L' ) ) THEN
- INFO = -1
- ELSE IF( N.LT.0 ) THEN
- INFO = -2
- ELSE IF( LDA.LT.MAX( 1, N ) ) THEN
- INFO = -4
- END IF
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'ZPOTF2', -INFO )
- RETURN
- END IF
-*
-* Quick return if possible
-*
- IF( N.EQ.0 )
- $ RETURN
-*
- IF( UPPER ) THEN
-*
-* Compute the Cholesky factorization A = U'*U.
-*
- DO 10 J = 1, N
-*
-* Compute U(J,J) and test for non-positive-definiteness.
-*
- AJJ = DBLE( A( J, J ) ) - ZDOTC( J-1, A( 1, J ), 1,
- $ A( 1, J ), 1 )
- IF( AJJ.LE.ZERO ) THEN
- A( J, J ) = AJJ
- GO TO 30
- END IF
- AJJ = SQRT( AJJ )
- A( J, J ) = AJJ
-*
-* Compute elements J+1:N of row J.
-*
- IF( J.LT.N ) THEN
- CALL ZLACGV( J-1, A( 1, J ), 1 )
- CALL ZGEMV( 'Transpose', J-1, N-J, -CONE, A( 1, J+1 ),
- $ LDA, A( 1, J ), 1, CONE, A( J, J+1 ), LDA )
- CALL ZLACGV( J-1, A( 1, J ), 1 )
- CALL ZDSCAL( N-J, ONE / AJJ, A( J, J+1 ), LDA )
- END IF
- 10 CONTINUE
- ELSE
-*
-* Compute the Cholesky factorization A = L*L'.
-*
- DO 20 J = 1, N
-*
-* Compute L(J,J) and test for non-positive-definiteness.
-*
- AJJ = DBLE( A( J, J ) ) - ZDOTC( J-1, A( J, 1 ), LDA,
- $ A( J, 1 ), LDA )
- IF( AJJ.LE.ZERO ) THEN
- A( J, J ) = AJJ
- GO TO 30
- END IF
- AJJ = SQRT( AJJ )
- A( J, J ) = AJJ
-*
-* Compute elements J+1:N of column J.
-*
- IF( J.LT.N ) THEN
- CALL ZLACGV( J-1, A( J, 1 ), LDA )
- CALL ZGEMV( 'No transpose', N-J, J-1, -CONE, A( J+1, 1 ),
- $ LDA, A( J, 1 ), LDA, CONE, A( J+1, J ), 1 )
- CALL ZLACGV( J-1, A( J, 1 ), LDA )
- CALL ZDSCAL( N-J, ONE / AJJ, A( J+1, J ), 1 )
- END IF
- 20 CONTINUE
- END IF
- GO TO 40
-*
- 30 CONTINUE
- INFO = J
-*
- 40 CONTINUE
- RETURN
-*
-* End of ZPOTF2
-*
- END
diff --git a/src/lib/lapack/zpotrf.f b/src/lib/lapack/zpotrf.f
deleted file mode 100644
index 86772608..00000000
--- a/src/lib/lapack/zpotrf.f
+++ /dev/null
@@ -1,186 +0,0 @@
- SUBROUTINE ZPOTRF( UPLO, N, A, LDA, INFO )
-*
-* -- LAPACK routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- CHARACTER UPLO
- INTEGER INFO, LDA, N
-* ..
-* .. Array Arguments ..
- COMPLEX*16 A( LDA, * )
-* ..
-*
-* Purpose
-* =======
-*
-* ZPOTRF computes the Cholesky factorization of a complex Hermitian
-* positive definite matrix A.
-*
-* The factorization has the form
-* A = U**H * U, if UPLO = 'U', or
-* A = L * L**H, if UPLO = 'L',
-* where U is an upper triangular matrix and L is lower triangular.
-*
-* This is the block version of the algorithm, calling Level 3 BLAS.
-*
-* Arguments
-* =========
-*
-* UPLO (input) CHARACTER*1
-* = 'U': Upper triangle of A is stored;
-* = 'L': Lower triangle of A is stored.
-*
-* N (input) INTEGER
-* The order of the matrix A. N >= 0.
-*
-* A (input/output) COMPLEX*16 array, dimension (LDA,N)
-* On entry, the Hermitian matrix A. If UPLO = 'U', the leading
-* N-by-N upper triangular part of A contains the upper
-* triangular part of the matrix A, and the strictly lower
-* triangular part of A is not referenced. If UPLO = 'L', the
-* leading N-by-N lower triangular part of A contains the lower
-* triangular part of the matrix A, and the strictly upper
-* triangular part of A is not referenced.
-*
-* On exit, if INFO = 0, the factor U or L from the Cholesky
-* factorization A = U**H*U or A = L*L**H.
-*
-* LDA (input) INTEGER
-* The leading dimension of the array A. LDA >= max(1,N).
-*
-* INFO (output) INTEGER
-* = 0: successful exit
-* < 0: if INFO = -i, the i-th argument had an illegal value
-* > 0: if INFO = i, the leading minor of order i is not
-* positive definite, and the factorization could not be
-* completed.
-*
-* =====================================================================
-*
-* .. Parameters ..
- DOUBLE PRECISION ONE
- COMPLEX*16 CONE
- PARAMETER ( ONE = 1.0D+0, CONE = ( 1.0D+0, 0.0D+0 ) )
-* ..
-* .. Local Scalars ..
- LOGICAL UPPER
- INTEGER J, JB, NB
-* ..
-* .. External Functions ..
- LOGICAL LSAME
- INTEGER ILAENV
- EXTERNAL LSAME, ILAENV
-* ..
-* .. External Subroutines ..
- EXTERNAL XERBLA, ZGEMM, ZHERK, ZPOTF2, ZTRSM
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC MAX, MIN
-* ..
-* .. Executable Statements ..
-*
-* Test the input parameters.
-*
- INFO = 0
- UPPER = LSAME( UPLO, 'U' )
- IF( .NOT.UPPER .AND. .NOT.LSAME( UPLO, 'L' ) ) THEN
- INFO = -1
- ELSE IF( N.LT.0 ) THEN
- INFO = -2
- ELSE IF( LDA.LT.MAX( 1, N ) ) THEN
- INFO = -4
- END IF
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'ZPOTRF', -INFO )
- RETURN
- END IF
-*
-* Quick return if possible
-*
- IF( N.EQ.0 )
- $ RETURN
-*
-* Determine the block size for this environment.
-*
- NB = ILAENV( 1, 'ZPOTRF', UPLO, N, -1, -1, -1 )
- IF( NB.LE.1 .OR. NB.GE.N ) THEN
-*
-* Use unblocked code.
-*
- CALL ZPOTF2( UPLO, N, A, LDA, INFO )
- ELSE
-*
-* Use blocked code.
-*
- IF( UPPER ) THEN
-*
-* Compute the Cholesky factorization A = U'*U.
-*
- DO 10 J = 1, N, NB
-*
-* Update and factorize the current diagonal block and test
-* for non-positive-definiteness.
-*
- JB = MIN( NB, N-J+1 )
- CALL ZHERK( 'Upper', 'Conjugate transpose', JB, J-1,
- $ -ONE, A( 1, J ), LDA, ONE, A( J, J ), LDA )
- CALL ZPOTF2( 'Upper', JB, A( J, J ), LDA, INFO )
- IF( INFO.NE.0 )
- $ GO TO 30
- IF( J+JB.LE.N ) THEN
-*
-* Compute the current block row.
-*
- CALL ZGEMM( 'Conjugate transpose', 'No transpose', JB,
- $ N-J-JB+1, J-1, -CONE, A( 1, J ), LDA,
- $ A( 1, J+JB ), LDA, CONE, A( J, J+JB ),
- $ LDA )
- CALL ZTRSM( 'Left', 'Upper', 'Conjugate transpose',
- $ 'Non-unit', JB, N-J-JB+1, CONE, A( J, J ),
- $ LDA, A( J, J+JB ), LDA )
- END IF
- 10 CONTINUE
-*
- ELSE
-*
-* Compute the Cholesky factorization A = L*L'.
-*
- DO 20 J = 1, N, NB
-*
-* Update and factorize the current diagonal block and test
-* for non-positive-definiteness.
-*
- JB = MIN( NB, N-J+1 )
- CALL ZHERK( 'Lower', 'No transpose', JB, J-1, -ONE,
- $ A( J, 1 ), LDA, ONE, A( J, J ), LDA )
- CALL ZPOTF2( 'Lower', JB, A( J, J ), LDA, INFO )
- IF( INFO.NE.0 )
- $ GO TO 30
- IF( J+JB.LE.N ) THEN
-*
-* Compute the current block column.
-*
- CALL ZGEMM( 'No transpose', 'Conjugate transpose',
- $ N-J-JB+1, JB, J-1, -CONE, A( J+JB, 1 ),
- $ LDA, A( J, 1 ), LDA, CONE, A( J+JB, J ),
- $ LDA )
- CALL ZTRSM( 'Right', 'Lower', 'Conjugate transpose',
- $ 'Non-unit', N-J-JB+1, JB, CONE, A( J, J ),
- $ LDA, A( J+JB, J ), LDA )
- END IF
- 20 CONTINUE
- END IF
- END IF
- GO TO 40
-*
- 30 CONTINUE
- INFO = INFO + J - 1
-*
- 40 CONTINUE
- RETURN
-*
-* End of ZPOTRF
-*
- END
diff --git a/src/lib/lapack/zrot.f b/src/lib/lapack/zrot.f
deleted file mode 100644
index 9c548e23..00000000
--- a/src/lib/lapack/zrot.f
+++ /dev/null
@@ -1,91 +0,0 @@
- SUBROUTINE ZROT( N, CX, INCX, CY, INCY, C, S )
-*
-* -- LAPACK auxiliary routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- INTEGER INCX, INCY, N
- DOUBLE PRECISION C
- COMPLEX*16 S
-* ..
-* .. Array Arguments ..
- COMPLEX*16 CX( * ), CY( * )
-* ..
-*
-* Purpose
-* =======
-*
-* ZROT applies a plane rotation, where the cos (C) is real and the
-* sin (S) is complex, and the vectors CX and CY are complex.
-*
-* Arguments
-* =========
-*
-* N (input) INTEGER
-* The number of elements in the vectors CX and CY.
-*
-* CX (input/output) COMPLEX*16 array, dimension (N)
-* On input, the vector X.
-* On output, CX is overwritten with C*X + S*Y.
-*
-* INCX (input) INTEGER
-* The increment between successive values of CY. INCX <> 0.
-*
-* CY (input/output) COMPLEX*16 array, dimension (N)
-* On input, the vector Y.
-* On output, CY is overwritten with -CONJG(S)*X + C*Y.
-*
-* INCY (input) INTEGER
-* The increment between successive values of CY. INCX <> 0.
-*
-* C (input) DOUBLE PRECISION
-* S (input) COMPLEX*16
-* C and S define a rotation
-* [ C S ]
-* [ -conjg(S) C ]
-* where C*C + S*CONJG(S) = 1.0.
-*
-* =====================================================================
-*
-* .. Local Scalars ..
- INTEGER I, IX, IY
- COMPLEX*16 STEMP
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC DCONJG
-* ..
-* .. Executable Statements ..
-*
- IF( N.LE.0 )
- $ RETURN
- IF( INCX.EQ.1 .AND. INCY.EQ.1 )
- $ GO TO 20
-*
-* Code for unequal increments or equal increments not equal to 1
-*
- IX = 1
- IY = 1
- IF( INCX.LT.0 )
- $ IX = ( -N+1 )*INCX + 1
- IF( INCY.LT.0 )
- $ IY = ( -N+1 )*INCY + 1
- DO 10 I = 1, N
- STEMP = C*CX( IX ) + S*CY( IY )
- CY( IY ) = C*CY( IY ) - DCONJG( S )*CX( IX )
- CX( IX ) = STEMP
- IX = IX + INCX
- IY = IY + INCY
- 10 CONTINUE
- RETURN
-*
-* Code for both increments equal to 1
-*
- 20 CONTINUE
- DO 30 I = 1, N
- STEMP = C*CX( I ) + S*CY( I )
- CY( I ) = C*CY( I ) - DCONJG( S )*CX( I )
- CX( I ) = STEMP
- 30 CONTINUE
- RETURN
- END
diff --git a/src/lib/lapack/zsteqr.f b/src/lib/lapack/zsteqr.f
deleted file mode 100644
index a72fdd96..00000000
--- a/src/lib/lapack/zsteqr.f
+++ /dev/null
@@ -1,503 +0,0 @@
- SUBROUTINE ZSTEQR( COMPZ, N, D, E, Z, LDZ, WORK, INFO )
-*
-* -- LAPACK routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- CHARACTER COMPZ
- INTEGER INFO, LDZ, N
-* ..
-* .. Array Arguments ..
- DOUBLE PRECISION D( * ), E( * ), WORK( * )
- COMPLEX*16 Z( LDZ, * )
-* ..
-*
-* Purpose
-* =======
-*
-* ZSTEQR computes all eigenvalues and, optionally, eigenvectors of a
-* symmetric tridiagonal matrix using the implicit QL or QR method.
-* The eigenvectors of a full or band complex Hermitian matrix can also
-* be found if ZHETRD or ZHPTRD or ZHBTRD has been used to reduce this
-* matrix to tridiagonal form.
-*
-* Arguments
-* =========
-*
-* COMPZ (input) CHARACTER*1
-* = 'N': Compute eigenvalues only.
-* = 'V': Compute eigenvalues and eigenvectors of the original
-* Hermitian matrix. On entry, Z must contain the
-* unitary matrix used to reduce the original matrix
-* to tridiagonal form.
-* = 'I': Compute eigenvalues and eigenvectors of the
-* tridiagonal matrix. Z is initialized to the identity
-* matrix.
-*
-* N (input) INTEGER
-* The order of the matrix. N >= 0.
-*
-* D (input/output) DOUBLE PRECISION array, dimension (N)
-* On entry, the diagonal elements of the tridiagonal matrix.
-* On exit, if INFO = 0, the eigenvalues in ascending order.
-*
-* E (input/output) DOUBLE PRECISION array, dimension (N-1)
-* On entry, the (n-1) subdiagonal elements of the tridiagonal
-* matrix.
-* On exit, E has been destroyed.
-*
-* Z (input/output) COMPLEX*16 array, dimension (LDZ, N)
-* On entry, if COMPZ = 'V', then Z contains the unitary
-* matrix used in the reduction to tridiagonal form.
-* On exit, if INFO = 0, then if COMPZ = 'V', Z contains the
-* orthonormal eigenvectors of the original Hermitian matrix,
-* and if COMPZ = 'I', Z contains the orthonormal eigenvectors
-* of the symmetric tridiagonal matrix.
-* If COMPZ = 'N', then Z is not referenced.
-*
-* LDZ (input) INTEGER
-* The leading dimension of the array Z. LDZ >= 1, and if
-* eigenvectors are desired, then LDZ >= max(1,N).
-*
-* WORK (workspace) DOUBLE PRECISION array, dimension (max(1,2*N-2))
-* If COMPZ = 'N', then WORK is not referenced.
-*
-* INFO (output) INTEGER
-* = 0: successful exit
-* < 0: if INFO = -i, the i-th argument had an illegal value
-* > 0: the algorithm has failed to find all the eigenvalues in
-* a total of 30*N iterations; if INFO = i, then i
-* elements of E have not converged to zero; on exit, D
-* and E contain the elements of a symmetric tridiagonal
-* matrix which is unitarily similar to the original
-* matrix.
-*
-* =====================================================================
-*
-* .. Parameters ..
- DOUBLE PRECISION ZERO, ONE, TWO, THREE
- PARAMETER ( ZERO = 0.0D0, ONE = 1.0D0, TWO = 2.0D0,
- $ THREE = 3.0D0 )
- COMPLEX*16 CZERO, CONE
- PARAMETER ( CZERO = ( 0.0D0, 0.0D0 ),
- $ CONE = ( 1.0D0, 0.0D0 ) )
- INTEGER MAXIT
- PARAMETER ( MAXIT = 30 )
-* ..
-* .. Local Scalars ..
- INTEGER I, ICOMPZ, II, ISCALE, J, JTOT, K, L, L1, LEND,
- $ LENDM1, LENDP1, LENDSV, LM1, LSV, M, MM, MM1,
- $ NM1, NMAXIT
- DOUBLE PRECISION ANORM, B, C, EPS, EPS2, F, G, P, R, RT1, RT2,
- $ S, SAFMAX, SAFMIN, SSFMAX, SSFMIN, TST
-* ..
-* .. External Functions ..
- LOGICAL LSAME
- DOUBLE PRECISION DLAMCH, DLANST, DLAPY2
- EXTERNAL LSAME, DLAMCH, DLANST, DLAPY2
-* ..
-* .. External Subroutines ..
- EXTERNAL DLAE2, DLAEV2, DLARTG, DLASCL, DLASRT, XERBLA,
- $ ZLASET, ZLASR, ZSWAP
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC ABS, MAX, SIGN, SQRT
-* ..
-* .. Executable Statements ..
-*
-* Test the input parameters.
-*
- INFO = 0
-*
- IF( LSAME( COMPZ, 'N' ) ) THEN
- ICOMPZ = 0
- ELSE IF( LSAME( COMPZ, 'V' ) ) THEN
- ICOMPZ = 1
- ELSE IF( LSAME( COMPZ, 'I' ) ) THEN
- ICOMPZ = 2
- ELSE
- ICOMPZ = -1
- END IF
- IF( ICOMPZ.LT.0 ) THEN
- INFO = -1
- ELSE IF( N.LT.0 ) THEN
- INFO = -2
- ELSE IF( ( LDZ.LT.1 ) .OR. ( ICOMPZ.GT.0 .AND. LDZ.LT.MAX( 1,
- $ N ) ) ) THEN
- INFO = -6
- END IF
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'ZSTEQR', -INFO )
- RETURN
- END IF
-*
-* Quick return if possible
-*
- IF( N.EQ.0 )
- $ RETURN
-*
- IF( N.EQ.1 ) THEN
- IF( ICOMPZ.EQ.2 )
- $ Z( 1, 1 ) = CONE
- RETURN
- END IF
-*
-* Determine the unit roundoff and over/underflow thresholds.
-*
- EPS = DLAMCH( 'E' )
- EPS2 = EPS**2
- SAFMIN = DLAMCH( 'S' )
- SAFMAX = ONE / SAFMIN
- SSFMAX = SQRT( SAFMAX ) / THREE
- SSFMIN = SQRT( SAFMIN ) / EPS2
-*
-* Compute the eigenvalues and eigenvectors of the tridiagonal
-* matrix.
-*
- IF( ICOMPZ.EQ.2 )
- $ CALL ZLASET( 'Full', N, N, CZERO, CONE, Z, LDZ )
-*
- NMAXIT = N*MAXIT
- JTOT = 0
-*
-* Determine where the matrix splits and choose QL or QR iteration
-* for each block, according to whether top or bottom diagonal
-* element is smaller.
-*
- L1 = 1
- NM1 = N - 1
-*
- 10 CONTINUE
- IF( L1.GT.N )
- $ GO TO 160
- IF( L1.GT.1 )
- $ E( L1-1 ) = ZERO
- IF( L1.LE.NM1 ) THEN
- DO 20 M = L1, NM1
- TST = ABS( E( M ) )
- IF( TST.EQ.ZERO )
- $ GO TO 30
- IF( TST.LE.( SQRT( ABS( D( M ) ) )*SQRT( ABS( D( M+
- $ 1 ) ) ) )*EPS ) THEN
- E( M ) = ZERO
- GO TO 30
- END IF
- 20 CONTINUE
- END IF
- M = N
-*
- 30 CONTINUE
- L = L1
- LSV = L
- LEND = M
- LENDSV = LEND
- L1 = M + 1
- IF( LEND.EQ.L )
- $ GO TO 10
-*
-* Scale submatrix in rows and columns L to LEND
-*
- ANORM = DLANST( 'I', LEND-L+1, D( L ), E( L ) )
- ISCALE = 0
- IF( ANORM.EQ.ZERO )
- $ GO TO 10
- IF( ANORM.GT.SSFMAX ) THEN
- ISCALE = 1
- CALL DLASCL( 'G', 0, 0, ANORM, SSFMAX, LEND-L+1, 1, D( L ), N,
- $ INFO )
- CALL DLASCL( 'G', 0, 0, ANORM, SSFMAX, LEND-L, 1, E( L ), N,
- $ INFO )
- ELSE IF( ANORM.LT.SSFMIN ) THEN
- ISCALE = 2
- CALL DLASCL( 'G', 0, 0, ANORM, SSFMIN, LEND-L+1, 1, D( L ), N,
- $ INFO )
- CALL DLASCL( 'G', 0, 0, ANORM, SSFMIN, LEND-L, 1, E( L ), N,
- $ INFO )
- END IF
-*
-* Choose between QL and QR iteration
-*
- IF( ABS( D( LEND ) ).LT.ABS( D( L ) ) ) THEN
- LEND = LSV
- L = LENDSV
- END IF
-*
- IF( LEND.GT.L ) THEN
-*
-* QL Iteration
-*
-* Look for small subdiagonal element.
-*
- 40 CONTINUE
- IF( L.NE.LEND ) THEN
- LENDM1 = LEND - 1
- DO 50 M = L, LENDM1
- TST = ABS( E( M ) )**2
- IF( TST.LE.( EPS2*ABS( D( M ) ) )*ABS( D( M+1 ) )+
- $ SAFMIN )GO TO 60
- 50 CONTINUE
- END IF
-*
- M = LEND
-*
- 60 CONTINUE
- IF( M.LT.LEND )
- $ E( M ) = ZERO
- P = D( L )
- IF( M.EQ.L )
- $ GO TO 80
-*
-* If remaining matrix is 2-by-2, use DLAE2 or SLAEV2
-* to compute its eigensystem.
-*
- IF( M.EQ.L+1 ) THEN
- IF( ICOMPZ.GT.0 ) THEN
- CALL DLAEV2( D( L ), E( L ), D( L+1 ), RT1, RT2, C, S )
- WORK( L ) = C
- WORK( N-1+L ) = S
- CALL ZLASR( 'R', 'V', 'B', N, 2, WORK( L ),
- $ WORK( N-1+L ), Z( 1, L ), LDZ )
- ELSE
- CALL DLAE2( D( L ), E( L ), D( L+1 ), RT1, RT2 )
- END IF
- D( L ) = RT1
- D( L+1 ) = RT2
- E( L ) = ZERO
- L = L + 2
- IF( L.LE.LEND )
- $ GO TO 40
- GO TO 140
- END IF
-*
- IF( JTOT.EQ.NMAXIT )
- $ GO TO 140
- JTOT = JTOT + 1
-*
-* Form shift.
-*
- G = ( D( L+1 )-P ) / ( TWO*E( L ) )
- R = DLAPY2( G, ONE )
- G = D( M ) - P + ( E( L ) / ( G+SIGN( R, G ) ) )
-*
- S = ONE
- C = ONE
- P = ZERO
-*
-* Inner loop
-*
- MM1 = M - 1
- DO 70 I = MM1, L, -1
- F = S*E( I )
- B = C*E( I )
- CALL DLARTG( G, F, C, S, R )
- IF( I.NE.M-1 )
- $ E( I+1 ) = R
- G = D( I+1 ) - P
- R = ( D( I )-G )*S + TWO*C*B
- P = S*R
- D( I+1 ) = G + P
- G = C*R - B
-*
-* If eigenvectors are desired, then save rotations.
-*
- IF( ICOMPZ.GT.0 ) THEN
- WORK( I ) = C
- WORK( N-1+I ) = -S
- END IF
-*
- 70 CONTINUE
-*
-* If eigenvectors are desired, then apply saved rotations.
-*
- IF( ICOMPZ.GT.0 ) THEN
- MM = M - L + 1
- CALL ZLASR( 'R', 'V', 'B', N, MM, WORK( L ), WORK( N-1+L ),
- $ Z( 1, L ), LDZ )
- END IF
-*
- D( L ) = D( L ) - P
- E( L ) = G
- GO TO 40
-*
-* Eigenvalue found.
-*
- 80 CONTINUE
- D( L ) = P
-*
- L = L + 1
- IF( L.LE.LEND )
- $ GO TO 40
- GO TO 140
-*
- ELSE
-*
-* QR Iteration
-*
-* Look for small superdiagonal element.
-*
- 90 CONTINUE
- IF( L.NE.LEND ) THEN
- LENDP1 = LEND + 1
- DO 100 M = L, LENDP1, -1
- TST = ABS( E( M-1 ) )**2
- IF( TST.LE.( EPS2*ABS( D( M ) ) )*ABS( D( M-1 ) )+
- $ SAFMIN )GO TO 110
- 100 CONTINUE
- END IF
-*
- M = LEND
-*
- 110 CONTINUE
- IF( M.GT.LEND )
- $ E( M-1 ) = ZERO
- P = D( L )
- IF( M.EQ.L )
- $ GO TO 130
-*
-* If remaining matrix is 2-by-2, use DLAE2 or SLAEV2
-* to compute its eigensystem.
-*
- IF( M.EQ.L-1 ) THEN
- IF( ICOMPZ.GT.0 ) THEN
- CALL DLAEV2( D( L-1 ), E( L-1 ), D( L ), RT1, RT2, C, S )
- WORK( M ) = C
- WORK( N-1+M ) = S
- CALL ZLASR( 'R', 'V', 'F', N, 2, WORK( M ),
- $ WORK( N-1+M ), Z( 1, L-1 ), LDZ )
- ELSE
- CALL DLAE2( D( L-1 ), E( L-1 ), D( L ), RT1, RT2 )
- END IF
- D( L-1 ) = RT1
- D( L ) = RT2
- E( L-1 ) = ZERO
- L = L - 2
- IF( L.GE.LEND )
- $ GO TO 90
- GO TO 140
- END IF
-*
- IF( JTOT.EQ.NMAXIT )
- $ GO TO 140
- JTOT = JTOT + 1
-*
-* Form shift.
-*
- G = ( D( L-1 )-P ) / ( TWO*E( L-1 ) )
- R = DLAPY2( G, ONE )
- G = D( M ) - P + ( E( L-1 ) / ( G+SIGN( R, G ) ) )
-*
- S = ONE
- C = ONE
- P = ZERO
-*
-* Inner loop
-*
- LM1 = L - 1
- DO 120 I = M, LM1
- F = S*E( I )
- B = C*E( I )
- CALL DLARTG( G, F, C, S, R )
- IF( I.NE.M )
- $ E( I-1 ) = R
- G = D( I ) - P
- R = ( D( I+1 )-G )*S + TWO*C*B
- P = S*R
- D( I ) = G + P
- G = C*R - B
-*
-* If eigenvectors are desired, then save rotations.
-*
- IF( ICOMPZ.GT.0 ) THEN
- WORK( I ) = C
- WORK( N-1+I ) = S
- END IF
-*
- 120 CONTINUE
-*
-* If eigenvectors are desired, then apply saved rotations.
-*
- IF( ICOMPZ.GT.0 ) THEN
- MM = L - M + 1
- CALL ZLASR( 'R', 'V', 'F', N, MM, WORK( M ), WORK( N-1+M ),
- $ Z( 1, M ), LDZ )
- END IF
-*
- D( L ) = D( L ) - P
- E( LM1 ) = G
- GO TO 90
-*
-* Eigenvalue found.
-*
- 130 CONTINUE
- D( L ) = P
-*
- L = L - 1
- IF( L.GE.LEND )
- $ GO TO 90
- GO TO 140
-*
- END IF
-*
-* Undo scaling if necessary
-*
- 140 CONTINUE
- IF( ISCALE.EQ.1 ) THEN
- CALL DLASCL( 'G', 0, 0, SSFMAX, ANORM, LENDSV-LSV+1, 1,
- $ D( LSV ), N, INFO )
- CALL DLASCL( 'G', 0, 0, SSFMAX, ANORM, LENDSV-LSV, 1, E( LSV ),
- $ N, INFO )
- ELSE IF( ISCALE.EQ.2 ) THEN
- CALL DLASCL( 'G', 0, 0, SSFMIN, ANORM, LENDSV-LSV+1, 1,
- $ D( LSV ), N, INFO )
- CALL DLASCL( 'G', 0, 0, SSFMIN, ANORM, LENDSV-LSV, 1, E( LSV ),
- $ N, INFO )
- END IF
-*
-* Check for no convergence to an eigenvalue after a total
-* of N*MAXIT iterations.
-*
- IF( JTOT.EQ.NMAXIT ) THEN
- DO 150 I = 1, N - 1
- IF( E( I ).NE.ZERO )
- $ INFO = INFO + 1
- 150 CONTINUE
- RETURN
- END IF
- GO TO 10
-*
-* Order eigenvalues and eigenvectors.
-*
- 160 CONTINUE
- IF( ICOMPZ.EQ.0 ) THEN
-*
-* Use Quick Sort
-*
- CALL DLASRT( 'I', N, D, INFO )
-*
- ELSE
-*
-* Use Selection Sort to minimize swaps of eigenvectors
-*
- DO 180 II = 2, N
- I = II - 1
- K = I
- P = D( I )
- DO 170 J = II, N
- IF( D( J ).LT.P ) THEN
- K = J
- P = D( J )
- END IF
- 170 CONTINUE
- IF( K.NE.I ) THEN
- D( K ) = D( I )
- D( I ) = P
- CALL ZSWAP( N, Z( 1, I ), 1, Z( 1, K ), 1 )
- END IF
- 180 CONTINUE
- END IF
- RETURN
-*
-* End of ZSTEQR
-*
- END
diff --git a/src/lib/lapack/ztgevc.f b/src/lib/lapack/ztgevc.f
deleted file mode 100644
index b8da962d..00000000
--- a/src/lib/lapack/ztgevc.f
+++ /dev/null
@@ -1,633 +0,0 @@
- SUBROUTINE ZTGEVC( SIDE, HOWMNY, SELECT, N, S, LDS, P, LDP, VL,
- $ LDVL, VR, LDVR, MM, M, WORK, RWORK, INFO )
-*
-* -- LAPACK routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- CHARACTER HOWMNY, SIDE
- INTEGER INFO, LDP, LDS, LDVL, LDVR, M, MM, N
-* ..
-* .. Array Arguments ..
- LOGICAL SELECT( * )
- DOUBLE PRECISION RWORK( * )
- COMPLEX*16 P( LDP, * ), S( LDS, * ), VL( LDVL, * ),
- $ VR( LDVR, * ), WORK( * )
-* ..
-*
-*
-* Purpose
-* =======
-*
-* ZTGEVC computes some or all of the right and/or left eigenvectors of
-* a pair of complex matrices (S,P), where S and P are upper triangular.
-* Matrix pairs of this type are produced by the generalized Schur
-* factorization of a complex matrix pair (A,B):
-*
-* A = Q*S*Z**H, B = Q*P*Z**H
-*
-* as computed by ZGGHRD + ZHGEQZ.
-*
-* The right eigenvector x and the left eigenvector y of (S,P)
-* corresponding to an eigenvalue w are defined by:
-*
-* S*x = w*P*x, (y**H)*S = w*(y**H)*P,
-*
-* where y**H denotes the conjugate tranpose of y.
-* The eigenvalues are not input to this routine, but are computed
-* directly from the diagonal elements of S and P.
-*
-* This routine returns the matrices X and/or Y of right and left
-* eigenvectors of (S,P), or the products Z*X and/or Q*Y,
-* where Z and Q are input matrices.
-* If Q and Z are the unitary factors from the generalized Schur
-* factorization of a matrix pair (A,B), then Z*X and Q*Y
-* are the matrices of right and left eigenvectors of (A,B).
-*
-* Arguments
-* =========
-*
-* SIDE (input) CHARACTER*1
-* = 'R': compute right eigenvectors only;
-* = 'L': compute left eigenvectors only;
-* = 'B': compute both right and left eigenvectors.
-*
-* HOWMNY (input) CHARACTER*1
-* = 'A': compute all right and/or left eigenvectors;
-* = 'B': compute all right and/or left eigenvectors,
-* backtransformed by the matrices in VR and/or VL;
-* = 'S': compute selected right and/or left eigenvectors,
-* specified by the logical array SELECT.
-*
-* SELECT (input) LOGICAL array, dimension (N)
-* If HOWMNY='S', SELECT specifies the eigenvectors to be
-* computed. The eigenvector corresponding to the j-th
-* eigenvalue is computed if SELECT(j) = .TRUE..
-* Not referenced if HOWMNY = 'A' or 'B'.
-*
-* N (input) INTEGER
-* The order of the matrices S and P. N >= 0.
-*
-* S (input) COMPLEX*16 array, dimension (LDS,N)
-* The upper triangular matrix S from a generalized Schur
-* factorization, as computed by ZHGEQZ.
-*
-* LDS (input) INTEGER
-* The leading dimension of array S. LDS >= max(1,N).
-*
-* P (input) COMPLEX*16 array, dimension (LDP,N)
-* The upper triangular matrix P from a generalized Schur
-* factorization, as computed by ZHGEQZ. P must have real
-* diagonal elements.
-*
-* LDP (input) INTEGER
-* The leading dimension of array P. LDP >= max(1,N).
-*
-* VL (input/output) COMPLEX*16 array, dimension (LDVL,MM)
-* On entry, if SIDE = 'L' or 'B' and HOWMNY = 'B', VL must
-* contain an N-by-N matrix Q (usually the unitary matrix Q
-* of left Schur vectors returned by ZHGEQZ).
-* On exit, if SIDE = 'L' or 'B', VL contains:
-* if HOWMNY = 'A', the matrix Y of left eigenvectors of (S,P);
-* if HOWMNY = 'B', the matrix Q*Y;
-* if HOWMNY = 'S', the left eigenvectors of (S,P) specified by
-* SELECT, stored consecutively in the columns of
-* VL, in the same order as their eigenvalues.
-* Not referenced if SIDE = 'R'.
-*
-* LDVL (input) INTEGER
-* The leading dimension of array VL. LDVL >= 1, and if
-* SIDE = 'L' or 'l' or 'B' or 'b', LDVL >= N.
-*
-* VR (input/output) COMPLEX*16 array, dimension (LDVR,MM)
-* On entry, if SIDE = 'R' or 'B' and HOWMNY = 'B', VR must
-* contain an N-by-N matrix Q (usually the unitary matrix Z
-* of right Schur vectors returned by ZHGEQZ).
-* On exit, if SIDE = 'R' or 'B', VR contains:
-* if HOWMNY = 'A', the matrix X of right eigenvectors of (S,P);
-* if HOWMNY = 'B', the matrix Z*X;
-* if HOWMNY = 'S', the right eigenvectors of (S,P) specified by
-* SELECT, stored consecutively in the columns of
-* VR, in the same order as their eigenvalues.
-* Not referenced if SIDE = 'L'.
-*
-* LDVR (input) INTEGER
-* The leading dimension of the array VR. LDVR >= 1, and if
-* SIDE = 'R' or 'B', LDVR >= N.
-*
-* MM (input) INTEGER
-* The number of columns in the arrays VL and/or VR. MM >= M.
-*
-* M (output) INTEGER
-* The number of columns in the arrays VL and/or VR actually
-* used to store the eigenvectors. If HOWMNY = 'A' or 'B', M
-* is set to N. Each selected eigenvector occupies one column.
-*
-* WORK (workspace) COMPLEX*16 array, dimension (2*N)
-*
-* RWORK (workspace) DOUBLE PRECISION array, dimension (2*N)
-*
-* INFO (output) INTEGER
-* = 0: successful exit.
-* < 0: if INFO = -i, the i-th argument had an illegal value.
-*
-* =====================================================================
-*
-* .. Parameters ..
- DOUBLE PRECISION ZERO, ONE
- PARAMETER ( ZERO = 0.0D+0, ONE = 1.0D+0 )
- COMPLEX*16 CZERO, CONE
- PARAMETER ( CZERO = ( 0.0D+0, 0.0D+0 ),
- $ CONE = ( 1.0D+0, 0.0D+0 ) )
-* ..
-* .. Local Scalars ..
- LOGICAL COMPL, COMPR, ILALL, ILBACK, ILBBAD, ILCOMP,
- $ LSA, LSB
- INTEGER I, IBEG, IEIG, IEND, IHWMNY, IM, ISIDE, ISRC,
- $ J, JE, JR
- DOUBLE PRECISION ACOEFA, ACOEFF, ANORM, ASCALE, BCOEFA, BIG,
- $ BIGNUM, BNORM, BSCALE, DMIN, SAFMIN, SBETA,
- $ SCALE, SMALL, TEMP, ULP, XMAX
- COMPLEX*16 BCOEFF, CA, CB, D, SALPHA, SUM, SUMA, SUMB, X
-* ..
-* .. External Functions ..
- LOGICAL LSAME
- DOUBLE PRECISION DLAMCH
- COMPLEX*16 ZLADIV
- EXTERNAL LSAME, DLAMCH, ZLADIV
-* ..
-* .. External Subroutines ..
- EXTERNAL DLABAD, XERBLA, ZGEMV
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC ABS, DBLE, DCMPLX, DCONJG, DIMAG, MAX, MIN
-* ..
-* .. Statement Functions ..
- DOUBLE PRECISION ABS1
-* ..
-* .. Statement Function definitions ..
- ABS1( X ) = ABS( DBLE( X ) ) + ABS( DIMAG( X ) )
-* ..
-* .. Executable Statements ..
-*
-* Decode and Test the input parameters
-*
- IF( LSAME( HOWMNY, 'A' ) ) THEN
- IHWMNY = 1
- ILALL = .TRUE.
- ILBACK = .FALSE.
- ELSE IF( LSAME( HOWMNY, 'S' ) ) THEN
- IHWMNY = 2
- ILALL = .FALSE.
- ILBACK = .FALSE.
- ELSE IF( LSAME( HOWMNY, 'B' ) ) THEN
- IHWMNY = 3
- ILALL = .TRUE.
- ILBACK = .TRUE.
- ELSE
- IHWMNY = -1
- END IF
-*
- IF( LSAME( SIDE, 'R' ) ) THEN
- ISIDE = 1
- COMPL = .FALSE.
- COMPR = .TRUE.
- ELSE IF( LSAME( SIDE, 'L' ) ) THEN
- ISIDE = 2
- COMPL = .TRUE.
- COMPR = .FALSE.
- ELSE IF( LSAME( SIDE, 'B' ) ) THEN
- ISIDE = 3
- COMPL = .TRUE.
- COMPR = .TRUE.
- ELSE
- ISIDE = -1
- END IF
-*
- INFO = 0
- IF( ISIDE.LT.0 ) THEN
- INFO = -1
- ELSE IF( IHWMNY.LT.0 ) THEN
- INFO = -2
- ELSE IF( N.LT.0 ) THEN
- INFO = -4
- ELSE IF( LDS.LT.MAX( 1, N ) ) THEN
- INFO = -6
- ELSE IF( LDP.LT.MAX( 1, N ) ) THEN
- INFO = -8
- END IF
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'ZTGEVC', -INFO )
- RETURN
- END IF
-*
-* Count the number of eigenvectors
-*
- IF( .NOT.ILALL ) THEN
- IM = 0
- DO 10 J = 1, N
- IF( SELECT( J ) )
- $ IM = IM + 1
- 10 CONTINUE
- ELSE
- IM = N
- END IF
-*
-* Check diagonal of B
-*
- ILBBAD = .FALSE.
- DO 20 J = 1, N
- IF( DIMAG( P( J, J ) ).NE.ZERO )
- $ ILBBAD = .TRUE.
- 20 CONTINUE
-*
- IF( ILBBAD ) THEN
- INFO = -7
- ELSE IF( COMPL .AND. LDVL.LT.N .OR. LDVL.LT.1 ) THEN
- INFO = -10
- ELSE IF( COMPR .AND. LDVR.LT.N .OR. LDVR.LT.1 ) THEN
- INFO = -12
- ELSE IF( MM.LT.IM ) THEN
- INFO = -13
- END IF
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'ZTGEVC', -INFO )
- RETURN
- END IF
-*
-* Quick return if possible
-*
- M = IM
- IF( N.EQ.0 )
- $ RETURN
-*
-* Machine Constants
-*
- SAFMIN = DLAMCH( 'Safe minimum' )
- BIG = ONE / SAFMIN
- CALL DLABAD( SAFMIN, BIG )
- ULP = DLAMCH( 'Epsilon' )*DLAMCH( 'Base' )
- SMALL = SAFMIN*N / ULP
- BIG = ONE / SMALL
- BIGNUM = ONE / ( SAFMIN*N )
-*
-* Compute the 1-norm of each column of the strictly upper triangular
-* part of A and B to check for possible overflow in the triangular
-* solver.
-*
- ANORM = ABS1( S( 1, 1 ) )
- BNORM = ABS1( P( 1, 1 ) )
- RWORK( 1 ) = ZERO
- RWORK( N+1 ) = ZERO
- DO 40 J = 2, N
- RWORK( J ) = ZERO
- RWORK( N+J ) = ZERO
- DO 30 I = 1, J - 1
- RWORK( J ) = RWORK( J ) + ABS1( S( I, J ) )
- RWORK( N+J ) = RWORK( N+J ) + ABS1( P( I, J ) )
- 30 CONTINUE
- ANORM = MAX( ANORM, RWORK( J )+ABS1( S( J, J ) ) )
- BNORM = MAX( BNORM, RWORK( N+J )+ABS1( P( J, J ) ) )
- 40 CONTINUE
-*
- ASCALE = ONE / MAX( ANORM, SAFMIN )
- BSCALE = ONE / MAX( BNORM, SAFMIN )
-*
-* Left eigenvectors
-*
- IF( COMPL ) THEN
- IEIG = 0
-*
-* Main loop over eigenvalues
-*
- DO 140 JE = 1, N
- IF( ILALL ) THEN
- ILCOMP = .TRUE.
- ELSE
- ILCOMP = SELECT( JE )
- END IF
- IF( ILCOMP ) THEN
- IEIG = IEIG + 1
-*
- IF( ABS1( S( JE, JE ) ).LE.SAFMIN .AND.
- $ ABS( DBLE( P( JE, JE ) ) ).LE.SAFMIN ) THEN
-*
-* Singular matrix pencil -- return unit eigenvector
-*
- DO 50 JR = 1, N
- VL( JR, IEIG ) = CZERO
- 50 CONTINUE
- VL( IEIG, IEIG ) = CONE
- GO TO 140
- END IF
-*
-* Non-singular eigenvalue:
-* Compute coefficients a and b in
-* H
-* y ( a A - b B ) = 0
-*
- TEMP = ONE / MAX( ABS1( S( JE, JE ) )*ASCALE,
- $ ABS( DBLE( P( JE, JE ) ) )*BSCALE, SAFMIN )
- SALPHA = ( TEMP*S( JE, JE ) )*ASCALE
- SBETA = ( TEMP*DBLE( P( JE, JE ) ) )*BSCALE
- ACOEFF = SBETA*ASCALE
- BCOEFF = SALPHA*BSCALE
-*
-* Scale to avoid underflow
-*
- LSA = ABS( SBETA ).GE.SAFMIN .AND. ABS( ACOEFF ).LT.SMALL
- LSB = ABS1( SALPHA ).GE.SAFMIN .AND. ABS1( BCOEFF ).LT.
- $ SMALL
-*
- SCALE = ONE
- IF( LSA )
- $ SCALE = ( SMALL / ABS( SBETA ) )*MIN( ANORM, BIG )
- IF( LSB )
- $ SCALE = MAX( SCALE, ( SMALL / ABS1( SALPHA ) )*
- $ MIN( BNORM, BIG ) )
- IF( LSA .OR. LSB ) THEN
- SCALE = MIN( SCALE, ONE /
- $ ( SAFMIN*MAX( ONE, ABS( ACOEFF ),
- $ ABS1( BCOEFF ) ) ) )
- IF( LSA ) THEN
- ACOEFF = ASCALE*( SCALE*SBETA )
- ELSE
- ACOEFF = SCALE*ACOEFF
- END IF
- IF( LSB ) THEN
- BCOEFF = BSCALE*( SCALE*SALPHA )
- ELSE
- BCOEFF = SCALE*BCOEFF
- END IF
- END IF
-*
- ACOEFA = ABS( ACOEFF )
- BCOEFA = ABS1( BCOEFF )
- XMAX = ONE
- DO 60 JR = 1, N
- WORK( JR ) = CZERO
- 60 CONTINUE
- WORK( JE ) = CONE
- DMIN = MAX( ULP*ACOEFA*ANORM, ULP*BCOEFA*BNORM, SAFMIN )
-*
-* H
-* Triangular solve of (a A - b B) y = 0
-*
-* H
-* (rowwise in (a A - b B) , or columnwise in a A - b B)
-*
- DO 100 J = JE + 1, N
-*
-* Compute
-* j-1
-* SUM = sum conjg( a*S(k,j) - b*P(k,j) )*x(k)
-* k=je
-* (Scale if necessary)
-*
- TEMP = ONE / XMAX
- IF( ACOEFA*RWORK( J )+BCOEFA*RWORK( N+J ).GT.BIGNUM*
- $ TEMP ) THEN
- DO 70 JR = JE, J - 1
- WORK( JR ) = TEMP*WORK( JR )
- 70 CONTINUE
- XMAX = ONE
- END IF
- SUMA = CZERO
- SUMB = CZERO
-*
- DO 80 JR = JE, J - 1
- SUMA = SUMA + DCONJG( S( JR, J ) )*WORK( JR )
- SUMB = SUMB + DCONJG( P( JR, J ) )*WORK( JR )
- 80 CONTINUE
- SUM = ACOEFF*SUMA - DCONJG( BCOEFF )*SUMB
-*
-* Form x(j) = - SUM / conjg( a*S(j,j) - b*P(j,j) )
-*
-* with scaling and perturbation of the denominator
-*
- D = DCONJG( ACOEFF*S( J, J )-BCOEFF*P( J, J ) )
- IF( ABS1( D ).LE.DMIN )
- $ D = DCMPLX( DMIN )
-*
- IF( ABS1( D ).LT.ONE ) THEN
- IF( ABS1( SUM ).GE.BIGNUM*ABS1( D ) ) THEN
- TEMP = ONE / ABS1( SUM )
- DO 90 JR = JE, J - 1
- WORK( JR ) = TEMP*WORK( JR )
- 90 CONTINUE
- XMAX = TEMP*XMAX
- SUM = TEMP*SUM
- END IF
- END IF
- WORK( J ) = ZLADIV( -SUM, D )
- XMAX = MAX( XMAX, ABS1( WORK( J ) ) )
- 100 CONTINUE
-*
-* Back transform eigenvector if HOWMNY='B'.
-*
- IF( ILBACK ) THEN
- CALL ZGEMV( 'N', N, N+1-JE, CONE, VL( 1, JE ), LDVL,
- $ WORK( JE ), 1, CZERO, WORK( N+1 ), 1 )
- ISRC = 2
- IBEG = 1
- ELSE
- ISRC = 1
- IBEG = JE
- END IF
-*
-* Copy and scale eigenvector into column of VL
-*
- XMAX = ZERO
- DO 110 JR = IBEG, N
- XMAX = MAX( XMAX, ABS1( WORK( ( ISRC-1 )*N+JR ) ) )
- 110 CONTINUE
-*
- IF( XMAX.GT.SAFMIN ) THEN
- TEMP = ONE / XMAX
- DO 120 JR = IBEG, N
- VL( JR, IEIG ) = TEMP*WORK( ( ISRC-1 )*N+JR )
- 120 CONTINUE
- ELSE
- IBEG = N + 1
- END IF
-*
- DO 130 JR = 1, IBEG - 1
- VL( JR, IEIG ) = CZERO
- 130 CONTINUE
-*
- END IF
- 140 CONTINUE
- END IF
-*
-* Right eigenvectors
-*
- IF( COMPR ) THEN
- IEIG = IM + 1
-*
-* Main loop over eigenvalues
-*
- DO 250 JE = N, 1, -1
- IF( ILALL ) THEN
- ILCOMP = .TRUE.
- ELSE
- ILCOMP = SELECT( JE )
- END IF
- IF( ILCOMP ) THEN
- IEIG = IEIG - 1
-*
- IF( ABS1( S( JE, JE ) ).LE.SAFMIN .AND.
- $ ABS( DBLE( P( JE, JE ) ) ).LE.SAFMIN ) THEN
-*
-* Singular matrix pencil -- return unit eigenvector
-*
- DO 150 JR = 1, N
- VR( JR, IEIG ) = CZERO
- 150 CONTINUE
- VR( IEIG, IEIG ) = CONE
- GO TO 250
- END IF
-*
-* Non-singular eigenvalue:
-* Compute coefficients a and b in
-*
-* ( a A - b B ) x = 0
-*
- TEMP = ONE / MAX( ABS1( S( JE, JE ) )*ASCALE,
- $ ABS( DBLE( P( JE, JE ) ) )*BSCALE, SAFMIN )
- SALPHA = ( TEMP*S( JE, JE ) )*ASCALE
- SBETA = ( TEMP*DBLE( P( JE, JE ) ) )*BSCALE
- ACOEFF = SBETA*ASCALE
- BCOEFF = SALPHA*BSCALE
-*
-* Scale to avoid underflow
-*
- LSA = ABS( SBETA ).GE.SAFMIN .AND. ABS( ACOEFF ).LT.SMALL
- LSB = ABS1( SALPHA ).GE.SAFMIN .AND. ABS1( BCOEFF ).LT.
- $ SMALL
-*
- SCALE = ONE
- IF( LSA )
- $ SCALE = ( SMALL / ABS( SBETA ) )*MIN( ANORM, BIG )
- IF( LSB )
- $ SCALE = MAX( SCALE, ( SMALL / ABS1( SALPHA ) )*
- $ MIN( BNORM, BIG ) )
- IF( LSA .OR. LSB ) THEN
- SCALE = MIN( SCALE, ONE /
- $ ( SAFMIN*MAX( ONE, ABS( ACOEFF ),
- $ ABS1( BCOEFF ) ) ) )
- IF( LSA ) THEN
- ACOEFF = ASCALE*( SCALE*SBETA )
- ELSE
- ACOEFF = SCALE*ACOEFF
- END IF
- IF( LSB ) THEN
- BCOEFF = BSCALE*( SCALE*SALPHA )
- ELSE
- BCOEFF = SCALE*BCOEFF
- END IF
- END IF
-*
- ACOEFA = ABS( ACOEFF )
- BCOEFA = ABS1( BCOEFF )
- XMAX = ONE
- DO 160 JR = 1, N
- WORK( JR ) = CZERO
- 160 CONTINUE
- WORK( JE ) = CONE
- DMIN = MAX( ULP*ACOEFA*ANORM, ULP*BCOEFA*BNORM, SAFMIN )
-*
-* Triangular solve of (a A - b B) x = 0 (columnwise)
-*
-* WORK(1:j-1) contains sums w,
-* WORK(j+1:JE) contains x
-*
- DO 170 JR = 1, JE - 1
- WORK( JR ) = ACOEFF*S( JR, JE ) - BCOEFF*P( JR, JE )
- 170 CONTINUE
- WORK( JE ) = CONE
-*
- DO 210 J = JE - 1, 1, -1
-*
-* Form x(j) := - w(j) / d
-* with scaling and perturbation of the denominator
-*
- D = ACOEFF*S( J, J ) - BCOEFF*P( J, J )
- IF( ABS1( D ).LE.DMIN )
- $ D = DCMPLX( DMIN )
-*
- IF( ABS1( D ).LT.ONE ) THEN
- IF( ABS1( WORK( J ) ).GE.BIGNUM*ABS1( D ) ) THEN
- TEMP = ONE / ABS1( WORK( J ) )
- DO 180 JR = 1, JE
- WORK( JR ) = TEMP*WORK( JR )
- 180 CONTINUE
- END IF
- END IF
-*
- WORK( J ) = ZLADIV( -WORK( J ), D )
-*
- IF( J.GT.1 ) THEN
-*
-* w = w + x(j)*(a S(*,j) - b P(*,j) ) with scaling
-*
- IF( ABS1( WORK( J ) ).GT.ONE ) THEN
- TEMP = ONE / ABS1( WORK( J ) )
- IF( ACOEFA*RWORK( J )+BCOEFA*RWORK( N+J ).GE.
- $ BIGNUM*TEMP ) THEN
- DO 190 JR = 1, JE
- WORK( JR ) = TEMP*WORK( JR )
- 190 CONTINUE
- END IF
- END IF
-*
- CA = ACOEFF*WORK( J )
- CB = BCOEFF*WORK( J )
- DO 200 JR = 1, J - 1
- WORK( JR ) = WORK( JR ) + CA*S( JR, J ) -
- $ CB*P( JR, J )
- 200 CONTINUE
- END IF
- 210 CONTINUE
-*
-* Back transform eigenvector if HOWMNY='B'.
-*
- IF( ILBACK ) THEN
- CALL ZGEMV( 'N', N, JE, CONE, VR, LDVR, WORK, 1,
- $ CZERO, WORK( N+1 ), 1 )
- ISRC = 2
- IEND = N
- ELSE
- ISRC = 1
- IEND = JE
- END IF
-*
-* Copy and scale eigenvector into column of VR
-*
- XMAX = ZERO
- DO 220 JR = 1, IEND
- XMAX = MAX( XMAX, ABS1( WORK( ( ISRC-1 )*N+JR ) ) )
- 220 CONTINUE
-*
- IF( XMAX.GT.SAFMIN ) THEN
- TEMP = ONE / XMAX
- DO 230 JR = 1, IEND
- VR( JR, IEIG ) = TEMP*WORK( ( ISRC-1 )*N+JR )
- 230 CONTINUE
- ELSE
- IEND = 0
- END IF
-*
- DO 240 JR = IEND + 1, N
- VR( JR, IEIG ) = CZERO
- 240 CONTINUE
-*
- END IF
- 250 CONTINUE
- END IF
-*
- RETURN
-*
-* End of ZTGEVC
-*
- END
diff --git a/src/lib/lapack/ztgex2.f b/src/lib/lapack/ztgex2.f
deleted file mode 100644
index a0c42aad..00000000
--- a/src/lib/lapack/ztgex2.f
+++ /dev/null
@@ -1,265 +0,0 @@
- SUBROUTINE ZTGEX2( WANTQ, WANTZ, N, A, LDA, B, LDB, Q, LDQ, Z,
- $ LDZ, J1, INFO )
-*
-* -- LAPACK auxiliary routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- LOGICAL WANTQ, WANTZ
- INTEGER INFO, J1, LDA, LDB, LDQ, LDZ, N
-* ..
-* .. Array Arguments ..
- COMPLEX*16 A( LDA, * ), B( LDB, * ), Q( LDQ, * ),
- $ Z( LDZ, * )
-* ..
-*
-* Purpose
-* =======
-*
-* ZTGEX2 swaps adjacent diagonal 1 by 1 blocks (A11,B11) and (A22,B22)
-* in an upper triangular matrix pair (A, B) by an unitary equivalence
-* transformation.
-*
-* (A, B) must be in generalized Schur canonical form, that is, A and
-* B are both upper triangular.
-*
-* Optionally, the matrices Q and Z of generalized Schur vectors are
-* updated.
-*
-* Q(in) * A(in) * Z(in)' = Q(out) * A(out) * Z(out)'
-* Q(in) * B(in) * Z(in)' = Q(out) * B(out) * Z(out)'
-*
-*
-* Arguments
-* =========
-*
-* WANTQ (input) LOGICAL
-* .TRUE. : update the left transformation matrix Q;
-* .FALSE.: do not update Q.
-*
-* WANTZ (input) LOGICAL
-* .TRUE. : update the right transformation matrix Z;
-* .FALSE.: do not update Z.
-*
-* N (input) INTEGER
-* The order of the matrices A and B. N >= 0.
-*
-* A (input/output) COMPLEX*16 arrays, dimensions (LDA,N)
-* On entry, the matrix A in the pair (A, B).
-* On exit, the updated matrix A.
-*
-* LDA (input) INTEGER
-* The leading dimension of the array A. LDA >= max(1,N).
-*
-* B (input/output) COMPLEX*16 arrays, dimensions (LDB,N)
-* On entry, the matrix B in the pair (A, B).
-* On exit, the updated matrix B.
-*
-* LDB (input) INTEGER
-* The leading dimension of the array B. LDB >= max(1,N).
-*
-* Q (input/output) COMPLEX*16 array, dimension (LDZ,N)
-* If WANTQ = .TRUE, on entry, the unitary matrix Q. On exit,
-* the updated matrix Q.
-* Not referenced if WANTQ = .FALSE..
-*
-* LDQ (input) INTEGER
-* The leading dimension of the array Q. LDQ >= 1;
-* If WANTQ = .TRUE., LDQ >= N.
-*
-* Z (input/output) COMPLEX*16 array, dimension (LDZ,N)
-* If WANTZ = .TRUE, on entry, the unitary matrix Z. On exit,
-* the updated matrix Z.
-* Not referenced if WANTZ = .FALSE..
-*
-* LDZ (input) INTEGER
-* The leading dimension of the array Z. LDZ >= 1;
-* If WANTZ = .TRUE., LDZ >= N.
-*
-* J1 (input) INTEGER
-* The index to the first block (A11, B11).
-*
-* INFO (output) INTEGER
-* =0: Successful exit.
-* =1: The transformed matrix pair (A, B) would be too far
-* from generalized Schur form; the problem is ill-
-* conditioned.
-*
-*
-* Further Details
-* ===============
-*
-* Based on contributions by
-* Bo Kagstrom and Peter Poromaa, Department of Computing Science,
-* Umea University, S-901 87 Umea, Sweden.
-*
-* In the current code both weak and strong stability tests are
-* performed. The user can omit the strong stability test by changing
-* the internal logical parameter WANDS to .FALSE.. See ref. [2] for
-* details.
-*
-* [1] B. Kagstrom; A Direct Method for Reordering Eigenvalues in the
-* Generalized Real Schur Form of a Regular Matrix Pair (A, B), in
-* M.S. Moonen et al (eds), Linear Algebra for Large Scale and
-* Real-Time Applications, Kluwer Academic Publ. 1993, pp 195-218.
-*
-* [2] B. Kagstrom and P. Poromaa; Computing Eigenspaces with Specified
-* Eigenvalues of a Regular Matrix Pair (A, B) and Condition
-* Estimation: Theory, Algorithms and Software, Report UMINF-94.04,
-* Department of Computing Science, Umea University, S-901 87 Umea,
-* Sweden, 1994. Also as LAPACK Working Note 87. To appear in
-* Numerical Algorithms, 1996.
-*
-* =====================================================================
-*
-* .. Parameters ..
- COMPLEX*16 CZERO, CONE
- PARAMETER ( CZERO = ( 0.0D+0, 0.0D+0 ),
- $ CONE = ( 1.0D+0, 0.0D+0 ) )
- DOUBLE PRECISION TEN
- PARAMETER ( TEN = 10.0D+0 )
- INTEGER LDST
- PARAMETER ( LDST = 2 )
- LOGICAL WANDS
- PARAMETER ( WANDS = .TRUE. )
-* ..
-* .. Local Scalars ..
- LOGICAL DTRONG, WEAK
- INTEGER I, M
- DOUBLE PRECISION CQ, CZ, EPS, SA, SB, SCALE, SMLNUM, SS, SUM,
- $ THRESH, WS
- COMPLEX*16 CDUM, F, G, SQ, SZ
-* ..
-* .. Local Arrays ..
- COMPLEX*16 S( LDST, LDST ), T( LDST, LDST ), WORK( 8 )
-* ..
-* .. External Functions ..
- DOUBLE PRECISION DLAMCH
- EXTERNAL DLAMCH
-* ..
-* .. External Subroutines ..
- EXTERNAL ZLACPY, ZLARTG, ZLASSQ, ZROT
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC ABS, DBLE, DCONJG, MAX, SQRT
-* ..
-* .. Executable Statements ..
-*
- INFO = 0
-*
-* Quick return if possible
-*
- IF( N.LE.1 )
- $ RETURN
-*
- M = LDST
- WEAK = .FALSE.
- DTRONG = .FALSE.
-*
-* Make a local copy of selected block in (A, B)
-*
- CALL ZLACPY( 'Full', M, M, A( J1, J1 ), LDA, S, LDST )
- CALL ZLACPY( 'Full', M, M, B( J1, J1 ), LDB, T, LDST )
-*
-* Compute the threshold for testing the acceptance of swapping.
-*
- EPS = DLAMCH( 'P' )
- SMLNUM = DLAMCH( 'S' ) / EPS
- SCALE = DBLE( CZERO )
- SUM = DBLE( CONE )
- CALL ZLACPY( 'Full', M, M, S, LDST, WORK, M )
- CALL ZLACPY( 'Full', M, M, T, LDST, WORK( M*M+1 ), M )
- CALL ZLASSQ( 2*M*M, WORK, 1, SCALE, SUM )
- SA = SCALE*SQRT( SUM )
- THRESH = MAX( TEN*EPS*SA, SMLNUM )
-*
-* Compute unitary QL and RQ that swap 1-by-1 and 1-by-1 blocks
-* using Givens rotations and perform the swap tentatively.
-*
- F = S( 2, 2 )*T( 1, 1 ) - T( 2, 2 )*S( 1, 1 )
- G = S( 2, 2 )*T( 1, 2 ) - T( 2, 2 )*S( 1, 2 )
- SA = ABS( S( 2, 2 ) )
- SB = ABS( T( 2, 2 ) )
- CALL ZLARTG( G, F, CZ, SZ, CDUM )
- SZ = -SZ
- CALL ZROT( 2, S( 1, 1 ), 1, S( 1, 2 ), 1, CZ, DCONJG( SZ ) )
- CALL ZROT( 2, T( 1, 1 ), 1, T( 1, 2 ), 1, CZ, DCONJG( SZ ) )
- IF( SA.GE.SB ) THEN
- CALL ZLARTG( S( 1, 1 ), S( 2, 1 ), CQ, SQ, CDUM )
- ELSE
- CALL ZLARTG( T( 1, 1 ), T( 2, 1 ), CQ, SQ, CDUM )
- END IF
- CALL ZROT( 2, S( 1, 1 ), LDST, S( 2, 1 ), LDST, CQ, SQ )
- CALL ZROT( 2, T( 1, 1 ), LDST, T( 2, 1 ), LDST, CQ, SQ )
-*
-* Weak stability test: |S21| + |T21| <= O(EPS F-norm((S, T)))
-*
- WS = ABS( S( 2, 1 ) ) + ABS( T( 2, 1 ) )
- WEAK = WS.LE.THRESH
- IF( .NOT.WEAK )
- $ GO TO 20
-*
- IF( WANDS ) THEN
-*
-* Strong stability test:
-* F-norm((A-QL'*S*QR, B-QL'*T*QR)) <= O(EPS*F-norm((A, B)))
-*
- CALL ZLACPY( 'Full', M, M, S, LDST, WORK, M )
- CALL ZLACPY( 'Full', M, M, T, LDST, WORK( M*M+1 ), M )
- CALL ZROT( 2, WORK, 1, WORK( 3 ), 1, CZ, -DCONJG( SZ ) )
- CALL ZROT( 2, WORK( 5 ), 1, WORK( 7 ), 1, CZ, -DCONJG( SZ ) )
- CALL ZROT( 2, WORK, 2, WORK( 2 ), 2, CQ, -SQ )
- CALL ZROT( 2, WORK( 5 ), 2, WORK( 6 ), 2, CQ, -SQ )
- DO 10 I = 1, 2
- WORK( I ) = WORK( I ) - A( J1+I-1, J1 )
- WORK( I+2 ) = WORK( I+2 ) - A( J1+I-1, J1+1 )
- WORK( I+4 ) = WORK( I+4 ) - B( J1+I-1, J1 )
- WORK( I+6 ) = WORK( I+6 ) - B( J1+I-1, J1+1 )
- 10 CONTINUE
- SCALE = DBLE( CZERO )
- SUM = DBLE( CONE )
- CALL ZLASSQ( 2*M*M, WORK, 1, SCALE, SUM )
- SS = SCALE*SQRT( SUM )
- DTRONG = SS.LE.THRESH
- IF( .NOT.DTRONG )
- $ GO TO 20
- END IF
-*
-* If the swap is accepted ("weakly" and "strongly"), apply the
-* equivalence transformations to the original matrix pair (A,B)
-*
- CALL ZROT( J1+1, A( 1, J1 ), 1, A( 1, J1+1 ), 1, CZ,
- $ DCONJG( SZ ) )
- CALL ZROT( J1+1, B( 1, J1 ), 1, B( 1, J1+1 ), 1, CZ,
- $ DCONJG( SZ ) )
- CALL ZROT( N-J1+1, A( J1, J1 ), LDA, A( J1+1, J1 ), LDA, CQ, SQ )
- CALL ZROT( N-J1+1, B( J1, J1 ), LDB, B( J1+1, J1 ), LDB, CQ, SQ )
-*
-* Set N1 by N2 (2,1) blocks to 0
-*
- A( J1+1, J1 ) = CZERO
- B( J1+1, J1 ) = CZERO
-*
-* Accumulate transformations into Q and Z if requested.
-*
- IF( WANTZ )
- $ CALL ZROT( N, Z( 1, J1 ), 1, Z( 1, J1+1 ), 1, CZ,
- $ DCONJG( SZ ) )
- IF( WANTQ )
- $ CALL ZROT( N, Q( 1, J1 ), 1, Q( 1, J1+1 ), 1, CQ,
- $ DCONJG( SQ ) )
-*
-* Exit with INFO = 0 if swap was successfully performed.
-*
- RETURN
-*
-* Exit with INFO = 1 if swap was rejected.
-*
- 20 CONTINUE
- INFO = 1
- RETURN
-*
-* End of ZTGEX2
-*
- END
diff --git a/src/lib/lapack/ztgexc.f b/src/lib/lapack/ztgexc.f
deleted file mode 100644
index 0f57939c..00000000
--- a/src/lib/lapack/ztgexc.f
+++ /dev/null
@@ -1,206 +0,0 @@
- SUBROUTINE ZTGEXC( WANTQ, WANTZ, N, A, LDA, B, LDB, Q, LDQ, Z,
- $ LDZ, IFST, ILST, INFO )
-*
-* -- LAPACK routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- LOGICAL WANTQ, WANTZ
- INTEGER IFST, ILST, INFO, LDA, LDB, LDQ, LDZ, N
-* ..
-* .. Array Arguments ..
- COMPLEX*16 A( LDA, * ), B( LDB, * ), Q( LDQ, * ),
- $ Z( LDZ, * )
-* ..
-*
-* Purpose
-* =======
-*
-* ZTGEXC reorders the generalized Schur decomposition of a complex
-* matrix pair (A,B), using an unitary equivalence transformation
-* (A, B) := Q * (A, B) * Z', so that the diagonal block of (A, B) with
-* row index IFST is moved to row ILST.
-*
-* (A, B) must be in generalized Schur canonical form, that is, A and
-* B are both upper triangular.
-*
-* Optionally, the matrices Q and Z of generalized Schur vectors are
-* updated.
-*
-* Q(in) * A(in) * Z(in)' = Q(out) * A(out) * Z(out)'
-* Q(in) * B(in) * Z(in)' = Q(out) * B(out) * Z(out)'
-*
-* Arguments
-* =========
-*
-* WANTQ (input) LOGICAL
-* .TRUE. : update the left transformation matrix Q;
-* .FALSE.: do not update Q.
-*
-* WANTZ (input) LOGICAL
-* .TRUE. : update the right transformation matrix Z;
-* .FALSE.: do not update Z.
-*
-* N (input) INTEGER
-* The order of the matrices A and B. N >= 0.
-*
-* A (input/output) COMPLEX*16 array, dimension (LDA,N)
-* On entry, the upper triangular matrix A in the pair (A, B).
-* On exit, the updated matrix A.
-*
-* LDA (input) INTEGER
-* The leading dimension of the array A. LDA >= max(1,N).
-*
-* B (input/output) COMPLEX*16 array, dimension (LDB,N)
-* On entry, the upper triangular matrix B in the pair (A, B).
-* On exit, the updated matrix B.
-*
-* LDB (input) INTEGER
-* The leading dimension of the array B. LDB >= max(1,N).
-*
-* Q (input/output) COMPLEX*16 array, dimension (LDZ,N)
-* On entry, if WANTQ = .TRUE., the unitary matrix Q.
-* On exit, the updated matrix Q.
-* If WANTQ = .FALSE., Q is not referenced.
-*
-* LDQ (input) INTEGER
-* The leading dimension of the array Q. LDQ >= 1;
-* If WANTQ = .TRUE., LDQ >= N.
-*
-* Z (input/output) COMPLEX*16 array, dimension (LDZ,N)
-* On entry, if WANTZ = .TRUE., the unitary matrix Z.
-* On exit, the updated matrix Z.
-* If WANTZ = .FALSE., Z is not referenced.
-*
-* LDZ (input) INTEGER
-* The leading dimension of the array Z. LDZ >= 1;
-* If WANTZ = .TRUE., LDZ >= N.
-*
-* IFST (input) INTEGER
-* ILST (input/output) INTEGER
-* Specify the reordering of the diagonal blocks of (A, B).
-* The block with row index IFST is moved to row ILST, by a
-* sequence of swapping between adjacent blocks.
-*
-* INFO (output) INTEGER
-* =0: Successful exit.
-* <0: if INFO = -i, the i-th argument had an illegal value.
-* =1: The transformed matrix pair (A, B) would be too far
-* from generalized Schur form; the problem is ill-
-* conditioned. (A, B) may have been partially reordered,
-* and ILST points to the first row of the current
-* position of the block being moved.
-*
-*
-* Further Details
-* ===============
-*
-* Based on contributions by
-* Bo Kagstrom and Peter Poromaa, Department of Computing Science,
-* Umea University, S-901 87 Umea, Sweden.
-*
-* [1] B. Kagstrom; A Direct Method for Reordering Eigenvalues in the
-* Generalized Real Schur Form of a Regular Matrix Pair (A, B), in
-* M.S. Moonen et al (eds), Linear Algebra for Large Scale and
-* Real-Time Applications, Kluwer Academic Publ. 1993, pp 195-218.
-*
-* [2] B. Kagstrom and P. Poromaa; Computing Eigenspaces with Specified
-* Eigenvalues of a Regular Matrix Pair (A, B) and Condition
-* Estimation: Theory, Algorithms and Software, Report
-* UMINF - 94.04, Department of Computing Science, Umea University,
-* S-901 87 Umea, Sweden, 1994. Also as LAPACK Working Note 87.
-* To appear in Numerical Algorithms, 1996.
-*
-* [3] B. Kagstrom and P. Poromaa, LAPACK-Style Algorithms and Software
-* for Solving the Generalized Sylvester Equation and Estimating the
-* Separation between Regular Matrix Pairs, Report UMINF - 93.23,
-* Department of Computing Science, Umea University, S-901 87 Umea,
-* Sweden, December 1993, Revised April 1994, Also as LAPACK working
-* Note 75. To appear in ACM Trans. on Math. Software, Vol 22, No 1,
-* 1996.
-*
-* =====================================================================
-*
-* .. Local Scalars ..
- INTEGER HERE
-* ..
-* .. External Subroutines ..
- EXTERNAL XERBLA, ZTGEX2
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC MAX
-* ..
-* .. Executable Statements ..
-*
-* Decode and test input arguments.
- INFO = 0
- IF( N.LT.0 ) THEN
- INFO = -3
- ELSE IF( LDA.LT.MAX( 1, N ) ) THEN
- INFO = -5
- ELSE IF( LDB.LT.MAX( 1, N ) ) THEN
- INFO = -7
- ELSE IF( LDQ.LT.1 .OR. WANTQ .AND. ( LDQ.LT.MAX( 1, N ) ) ) THEN
- INFO = -9
- ELSE IF( LDZ.LT.1 .OR. WANTZ .AND. ( LDZ.LT.MAX( 1, N ) ) ) THEN
- INFO = -11
- ELSE IF( IFST.LT.1 .OR. IFST.GT.N ) THEN
- INFO = -12
- ELSE IF( ILST.LT.1 .OR. ILST.GT.N ) THEN
- INFO = -13
- END IF
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'ZTGEXC', -INFO )
- RETURN
- END IF
-*
-* Quick return if possible
-*
- IF( N.LE.1 )
- $ RETURN
- IF( IFST.EQ.ILST )
- $ RETURN
-*
- IF( IFST.LT.ILST ) THEN
-*
- HERE = IFST
-*
- 10 CONTINUE
-*
-* Swap with next one below
-*
- CALL ZTGEX2( WANTQ, WANTZ, N, A, LDA, B, LDB, Q, LDQ, Z, LDZ,
- $ HERE, INFO )
- IF( INFO.NE.0 ) THEN
- ILST = HERE
- RETURN
- END IF
- HERE = HERE + 1
- IF( HERE.LT.ILST )
- $ GO TO 10
- HERE = HERE - 1
- ELSE
- HERE = IFST - 1
-*
- 20 CONTINUE
-*
-* Swap with next one above
-*
- CALL ZTGEX2( WANTQ, WANTZ, N, A, LDA, B, LDB, Q, LDQ, Z, LDZ,
- $ HERE, INFO )
- IF( INFO.NE.0 ) THEN
- ILST = HERE
- RETURN
- END IF
- HERE = HERE - 1
- IF( HERE.GE.ILST )
- $ GO TO 20
- HERE = HERE + 1
- END IF
- ILST = HERE
- RETURN
-*
-* End of ZTGEXC
-*
- END
diff --git a/src/lib/lapack/ztgsen.f b/src/lib/lapack/ztgsen.f
deleted file mode 100644
index 71ee4cd0..00000000
--- a/src/lib/lapack/ztgsen.f
+++ /dev/null
@@ -1,652 +0,0 @@
- SUBROUTINE ZTGSEN( IJOB, WANTQ, WANTZ, SELECT, N, A, LDA, B, LDB,
- $ ALPHA, BETA, Q, LDQ, Z, LDZ, M, PL, PR, DIF,
- $ WORK, LWORK, IWORK, LIWORK, INFO )
-*
-* -- LAPACK routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* Modified to call ZLACN2 in place of ZLACON, 10 Feb 03, SJH.
-*
-* .. Scalar Arguments ..
- LOGICAL WANTQ, WANTZ
- INTEGER IJOB, INFO, LDA, LDB, LDQ, LDZ, LIWORK, LWORK,
- $ M, N
- DOUBLE PRECISION PL, PR
-* ..
-* .. Array Arguments ..
- LOGICAL SELECT( * )
- INTEGER IWORK( * )
- DOUBLE PRECISION DIF( * )
- COMPLEX*16 A( LDA, * ), ALPHA( * ), B( LDB, * ),
- $ BETA( * ), Q( LDQ, * ), WORK( * ), Z( LDZ, * )
-* ..
-*
-* Purpose
-* =======
-*
-* ZTGSEN reorders the generalized Schur decomposition of a complex
-* matrix pair (A, B) (in terms of an unitary equivalence trans-
-* formation Q' * (A, B) * Z), so that a selected cluster of eigenvalues
-* appears in the leading diagonal blocks of the pair (A,B). The leading
-* columns of Q and Z form unitary bases of the corresponding left and
-* right eigenspaces (deflating subspaces). (A, B) must be in
-* generalized Schur canonical form, that is, A and B are both upper
-* triangular.
-*
-* ZTGSEN also computes the generalized eigenvalues
-*
-* w(j)= ALPHA(j) / BETA(j)
-*
-* of the reordered matrix pair (A, B).
-*
-* Optionally, the routine computes estimates of reciprocal condition
-* numbers for eigenvalues and eigenspaces. These are Difu[(A11,B11),
-* (A22,B22)] and Difl[(A11,B11), (A22,B22)], i.e. the separation(s)
-* between the matrix pairs (A11, B11) and (A22,B22) that correspond to
-* the selected cluster and the eigenvalues outside the cluster, resp.,
-* and norms of "projections" onto left and right eigenspaces w.r.t.
-* the selected cluster in the (1,1)-block.
-*
-*
-* Arguments
-* =========
-*
-* IJOB (input) integer
-* Specifies whether condition numbers are required for the
-* cluster of eigenvalues (PL and PR) or the deflating subspaces
-* (Difu and Difl):
-* =0: Only reorder w.r.t. SELECT. No extras.
-* =1: Reciprocal of norms of "projections" onto left and right
-* eigenspaces w.r.t. the selected cluster (PL and PR).
-* =2: Upper bounds on Difu and Difl. F-norm-based estimate
-* (DIF(1:2)).
-* =3: Estimate of Difu and Difl. 1-norm-based estimate
-* (DIF(1:2)).
-* About 5 times as expensive as IJOB = 2.
-* =4: Compute PL, PR and DIF (i.e. 0, 1 and 2 above): Economic
-* version to get it all.
-* =5: Compute PL, PR and DIF (i.e. 0, 1 and 3 above)
-*
-* WANTQ (input) LOGICAL
-* .TRUE. : update the left transformation matrix Q;
-* .FALSE.: do not update Q.
-*
-* WANTZ (input) LOGICAL
-* .TRUE. : update the right transformation matrix Z;
-* .FALSE.: do not update Z.
-*
-* SELECT (input) LOGICAL array, dimension (N)
-* SELECT specifies the eigenvalues in the selected cluster. To
-* select an eigenvalue w(j), SELECT(j) must be set to
-* .TRUE..
-*
-* N (input) INTEGER
-* The order of the matrices A and B. N >= 0.
-*
-* A (input/output) COMPLEX*16 array, dimension(LDA,N)
-* On entry, the upper triangular matrix A, in generalized
-* Schur canonical form.
-* On exit, A is overwritten by the reordered matrix A.
-*
-* LDA (input) INTEGER
-* The leading dimension of the array A. LDA >= max(1,N).
-*
-* B (input/output) COMPLEX*16 array, dimension(LDB,N)
-* On entry, the upper triangular matrix B, in generalized
-* Schur canonical form.
-* On exit, B is overwritten by the reordered matrix B.
-*
-* LDB (input) INTEGER
-* The leading dimension of the array B. LDB >= max(1,N).
-*
-* ALPHA (output) COMPLEX*16 array, dimension (N)
-* BETA (output) COMPLEX*16 array, dimension (N)
-* The diagonal elements of A and B, respectively,
-* when the pair (A,B) has been reduced to generalized Schur
-* form. ALPHA(i)/BETA(i) i=1,...,N are the generalized
-* eigenvalues.
-*
-* Q (input/output) COMPLEX*16 array, dimension (LDQ,N)
-* On entry, if WANTQ = .TRUE., Q is an N-by-N matrix.
-* On exit, Q has been postmultiplied by the left unitary
-* transformation matrix which reorder (A, B); The leading M
-* columns of Q form orthonormal bases for the specified pair of
-* left eigenspaces (deflating subspaces).
-* If WANTQ = .FALSE., Q is not referenced.
-*
-* LDQ (input) INTEGER
-* The leading dimension of the array Q. LDQ >= 1.
-* If WANTQ = .TRUE., LDQ >= N.
-*
-* Z (input/output) COMPLEX*16 array, dimension (LDZ,N)
-* On entry, if WANTZ = .TRUE., Z is an N-by-N matrix.
-* On exit, Z has been postmultiplied by the left unitary
-* transformation matrix which reorder (A, B); The leading M
-* columns of Z form orthonormal bases for the specified pair of
-* left eigenspaces (deflating subspaces).
-* If WANTZ = .FALSE., Z is not referenced.
-*
-* LDZ (input) INTEGER
-* The leading dimension of the array Z. LDZ >= 1.
-* If WANTZ = .TRUE., LDZ >= N.
-*
-* M (output) INTEGER
-* The dimension of the specified pair of left and right
-* eigenspaces, (deflating subspaces) 0 <= M <= N.
-*
-* PL (output) DOUBLE PRECISION
-* PR (output) DOUBLE PRECISION
-* If IJOB = 1, 4 or 5, PL, PR are lower bounds on the
-* reciprocal of the norm of "projections" onto left and right
-* eigenspace with respect to the selected cluster.
-* 0 < PL, PR <= 1.
-* If M = 0 or M = N, PL = PR = 1.
-* If IJOB = 0, 2 or 3 PL, PR are not referenced.
-*
-* DIF (output) DOUBLE PRECISION array, dimension (2).
-* If IJOB >= 2, DIF(1:2) store the estimates of Difu and Difl.
-* If IJOB = 2 or 4, DIF(1:2) are F-norm-based upper bounds on
-* Difu and Difl. If IJOB = 3 or 5, DIF(1:2) are 1-norm-based
-* estimates of Difu and Difl, computed using reversed
-* communication with ZLACN2.
-* If M = 0 or N, DIF(1:2) = F-norm([A, B]).
-* If IJOB = 0 or 1, DIF is not referenced.
-*
-* WORK (workspace/output) COMPLEX*16 array, dimension (MAX(1,LWORK))
-* IF IJOB = 0, WORK is not referenced. Otherwise,
-* on exit, if INFO = 0, WORK(1) returns the optimal LWORK.
-*
-* LWORK (input) INTEGER
-* The dimension of the array WORK. LWORK >= 1
-* If IJOB = 1, 2 or 4, LWORK >= 2*M*(N-M)
-* If IJOB = 3 or 5, LWORK >= 4*M*(N-M)
-*
-* If LWORK = -1, then a workspace query is assumed; the routine
-* only calculates the optimal size of the WORK array, returns
-* this value as the first entry of the WORK array, and no error
-* message related to LWORK is issued by XERBLA.
-*
-* IWORK (workspace/output) INTEGER array, dimension (MAX(1,LIWORK))
-* IF IJOB = 0, IWORK is not referenced. Otherwise,
-* on exit, if INFO = 0, IWORK(1) returns the optimal LIWORK.
-*
-* LIWORK (input) INTEGER
-* The dimension of the array IWORK. LIWORK >= 1.
-* If IJOB = 1, 2 or 4, LIWORK >= N+2;
-* If IJOB = 3 or 5, LIWORK >= MAX(N+2, 2*M*(N-M));
-*
-* If LIWORK = -1, then a workspace query is assumed; the
-* routine only calculates the optimal size of the IWORK array,
-* returns this value as the first entry of the IWORK array, and
-* no error message related to LIWORK is issued by XERBLA.
-*
-* INFO (output) INTEGER
-* =0: Successful exit.
-* <0: If INFO = -i, the i-th argument had an illegal value.
-* =1: Reordering of (A, B) failed because the transformed
-* matrix pair (A, B) would be too far from generalized
-* Schur form; the problem is very ill-conditioned.
-* (A, B) may have been partially reordered.
-* If requested, 0 is returned in DIF(*), PL and PR.
-*
-*
-* Further Details
-* ===============
-*
-* ZTGSEN first collects the selected eigenvalues by computing unitary
-* U and W that move them to the top left corner of (A, B). In other
-* words, the selected eigenvalues are the eigenvalues of (A11, B11) in
-*
-* U'*(A, B)*W = (A11 A12) (B11 B12) n1
-* ( 0 A22),( 0 B22) n2
-* n1 n2 n1 n2
-*
-* where N = n1+n2 and U' means the conjugate transpose of U. The first
-* n1 columns of U and W span the specified pair of left and right
-* eigenspaces (deflating subspaces) of (A, B).
-*
-* If (A, B) has been obtained from the generalized real Schur
-* decomposition of a matrix pair (C, D) = Q*(A, B)*Z', then the
-* reordered generalized Schur form of (C, D) is given by
-*
-* (C, D) = (Q*U)*(U'*(A, B)*W)*(Z*W)',
-*
-* and the first n1 columns of Q*U and Z*W span the corresponding
-* deflating subspaces of (C, D) (Q and Z store Q*U and Z*W, resp.).
-*
-* Note that if the selected eigenvalue is sufficiently ill-conditioned,
-* then its value may differ significantly from its value before
-* reordering.
-*
-* The reciprocal condition numbers of the left and right eigenspaces
-* spanned by the first n1 columns of U and W (or Q*U and Z*W) may
-* be returned in DIF(1:2), corresponding to Difu and Difl, resp.
-*
-* The Difu and Difl are defined as:
-*
-* Difu[(A11, B11), (A22, B22)] = sigma-min( Zu )
-* and
-* Difl[(A11, B11), (A22, B22)] = Difu[(A22, B22), (A11, B11)],
-*
-* where sigma-min(Zu) is the smallest singular value of the
-* (2*n1*n2)-by-(2*n1*n2) matrix
-*
-* Zu = [ kron(In2, A11) -kron(A22', In1) ]
-* [ kron(In2, B11) -kron(B22', In1) ].
-*
-* Here, Inx is the identity matrix of size nx and A22' is the
-* transpose of A22. kron(X, Y) is the Kronecker product between
-* the matrices X and Y.
-*
-* When DIF(2) is small, small changes in (A, B) can cause large changes
-* in the deflating subspace. An approximate (asymptotic) bound on the
-* maximum angular error in the computed deflating subspaces is
-*
-* EPS * norm((A, B)) / DIF(2),
-*
-* where EPS is the machine precision.
-*
-* The reciprocal norm of the projectors on the left and right
-* eigenspaces associated with (A11, B11) may be returned in PL and PR.
-* They are computed as follows. First we compute L and R so that
-* P*(A, B)*Q is block diagonal, where
-*
-* P = ( I -L ) n1 Q = ( I R ) n1
-* ( 0 I ) n2 and ( 0 I ) n2
-* n1 n2 n1 n2
-*
-* and (L, R) is the solution to the generalized Sylvester equation
-*
-* A11*R - L*A22 = -A12
-* B11*R - L*B22 = -B12
-*
-* Then PL = (F-norm(L)**2+1)**(-1/2) and PR = (F-norm(R)**2+1)**(-1/2).
-* An approximate (asymptotic) bound on the average absolute error of
-* the selected eigenvalues is
-*
-* EPS * norm((A, B)) / PL.
-*
-* There are also global error bounds which valid for perturbations up
-* to a certain restriction: A lower bound (x) on the smallest
-* F-norm(E,F) for which an eigenvalue of (A11, B11) may move and
-* coalesce with an eigenvalue of (A22, B22) under perturbation (E,F),
-* (i.e. (A + E, B + F), is
-*
-* x = min(Difu,Difl)/((1/(PL*PL)+1/(PR*PR))**(1/2)+2*max(1/PL,1/PR)).
-*
-* An approximate bound on x can be computed from DIF(1:2), PL and PR.
-*
-* If y = ( F-norm(E,F) / x) <= 1, the angles between the perturbed
-* (L', R') and unperturbed (L, R) left and right deflating subspaces
-* associated with the selected cluster in the (1,1)-blocks can be
-* bounded as
-*
-* max-angle(L, L') <= arctan( y * PL / (1 - y * (1 - PL * PL)**(1/2))
-* max-angle(R, R') <= arctan( y * PR / (1 - y * (1 - PR * PR)**(1/2))
-*
-* See LAPACK User's Guide section 4.11 or the following references
-* for more information.
-*
-* Note that if the default method for computing the Frobenius-norm-
-* based estimate DIF is not wanted (see ZLATDF), then the parameter
-* IDIFJB (see below) should be changed from 3 to 4 (routine ZLATDF
-* (IJOB = 2 will be used)). See ZTGSYL for more details.
-*
-* Based on contributions by
-* Bo Kagstrom and Peter Poromaa, Department of Computing Science,
-* Umea University, S-901 87 Umea, Sweden.
-*
-* References
-* ==========
-*
-* [1] B. Kagstrom; A Direct Method for Reordering Eigenvalues in the
-* Generalized Real Schur Form of a Regular Matrix Pair (A, B), in
-* M.S. Moonen et al (eds), Linear Algebra for Large Scale and
-* Real-Time Applications, Kluwer Academic Publ. 1993, pp 195-218.
-*
-* [2] B. Kagstrom and P. Poromaa; Computing Eigenspaces with Specified
-* Eigenvalues of a Regular Matrix Pair (A, B) and Condition
-* Estimation: Theory, Algorithms and Software, Report
-* UMINF - 94.04, Department of Computing Science, Umea University,
-* S-901 87 Umea, Sweden, 1994. Also as LAPACK Working Note 87.
-* To appear in Numerical Algorithms, 1996.
-*
-* [3] B. Kagstrom and P. Poromaa, LAPACK-Style Algorithms and Software
-* for Solving the Generalized Sylvester Equation and Estimating the
-* Separation between Regular Matrix Pairs, Report UMINF - 93.23,
-* Department of Computing Science, Umea University, S-901 87 Umea,
-* Sweden, December 1993, Revised April 1994, Also as LAPACK working
-* Note 75. To appear in ACM Trans. on Math. Software, Vol 22, No 1,
-* 1996.
-*
-* =====================================================================
-*
-* .. Parameters ..
- INTEGER IDIFJB
- PARAMETER ( IDIFJB = 3 )
- DOUBLE PRECISION ZERO, ONE
- PARAMETER ( ZERO = 0.0D+0, ONE = 1.0D+0 )
-* ..
-* .. Local Scalars ..
- LOGICAL LQUERY, SWAP, WANTD, WANTD1, WANTD2, WANTP
- INTEGER I, IERR, IJB, K, KASE, KS, LIWMIN, LWMIN, MN2,
- $ N1, N2
- DOUBLE PRECISION DSCALE, DSUM, RDSCAL, SAFMIN
-* ..
-* .. Local Arrays ..
- INTEGER ISAVE( 3 )
-* ..
-* .. External Subroutines ..
- EXTERNAL XERBLA, ZLACN2, ZLACPY, ZLASSQ, ZSCAL, ZTGEXC,
- $ ZTGSYL
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC ABS, DCMPLX, DCONJG, MAX, SQRT
-* ..
-* .. External Functions ..
- DOUBLE PRECISION DLAMCH
- EXTERNAL DLAMCH
-* ..
-* .. Executable Statements ..
-*
-* Decode and test the input parameters
-*
- INFO = 0
- LQUERY = ( LWORK.EQ.-1 .OR. LIWORK.EQ.-1 )
-*
- IF( IJOB.LT.0 .OR. IJOB.GT.5 ) THEN
- INFO = -1
- ELSE IF( N.LT.0 ) THEN
- INFO = -5
- ELSE IF( LDA.LT.MAX( 1, N ) ) THEN
- INFO = -7
- ELSE IF( LDB.LT.MAX( 1, N ) ) THEN
- INFO = -9
- ELSE IF( LDQ.LT.1 .OR. ( WANTQ .AND. LDQ.LT.N ) ) THEN
- INFO = -13
- ELSE IF( LDZ.LT.1 .OR. ( WANTZ .AND. LDZ.LT.N ) ) THEN
- INFO = -15
- END IF
-*
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'ZTGSEN', -INFO )
- RETURN
- END IF
-*
- IERR = 0
-*
- WANTP = IJOB.EQ.1 .OR. IJOB.GE.4
- WANTD1 = IJOB.EQ.2 .OR. IJOB.EQ.4
- WANTD2 = IJOB.EQ.3 .OR. IJOB.EQ.5
- WANTD = WANTD1 .OR. WANTD2
-*
-* Set M to the dimension of the specified pair of deflating
-* subspaces.
-*
- M = 0
- DO 10 K = 1, N
- ALPHA( K ) = A( K, K )
- BETA( K ) = B( K, K )
- IF( K.LT.N ) THEN
- IF( SELECT( K ) )
- $ M = M + 1
- ELSE
- IF( SELECT( N ) )
- $ M = M + 1
- END IF
- 10 CONTINUE
-*
- IF( IJOB.EQ.1 .OR. IJOB.EQ.2 .OR. IJOB.EQ.4 ) THEN
- LWMIN = MAX( 1, 2*M*( N-M ) )
- LIWMIN = MAX( 1, N+2 )
- ELSE IF( IJOB.EQ.3 .OR. IJOB.EQ.5 ) THEN
- LWMIN = MAX( 1, 4*M*( N-M ) )
- LIWMIN = MAX( 1, 2*M*( N-M ), N+2 )
- ELSE
- LWMIN = 1
- LIWMIN = 1
- END IF
-*
- WORK( 1 ) = LWMIN
- IWORK( 1 ) = LIWMIN
-*
- IF( LWORK.LT.LWMIN .AND. .NOT.LQUERY ) THEN
- INFO = -21
- ELSE IF( LIWORK.LT.LIWMIN .AND. .NOT.LQUERY ) THEN
- INFO = -23
- END IF
-*
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'ZTGSEN', -INFO )
- RETURN
- ELSE IF( LQUERY ) THEN
- RETURN
- END IF
-*
-* Quick return if possible.
-*
- IF( M.EQ.N .OR. M.EQ.0 ) THEN
- IF( WANTP ) THEN
- PL = ONE
- PR = ONE
- END IF
- IF( WANTD ) THEN
- DSCALE = ZERO
- DSUM = ONE
- DO 20 I = 1, N
- CALL ZLASSQ( N, A( 1, I ), 1, DSCALE, DSUM )
- CALL ZLASSQ( N, B( 1, I ), 1, DSCALE, DSUM )
- 20 CONTINUE
- DIF( 1 ) = DSCALE*SQRT( DSUM )
- DIF( 2 ) = DIF( 1 )
- END IF
- GO TO 70
- END IF
-*
-* Get machine constant
-*
- SAFMIN = DLAMCH( 'S' )
-*
-* Collect the selected blocks at the top-left corner of (A, B).
-*
- KS = 0
- DO 30 K = 1, N
- SWAP = SELECT( K )
- IF( SWAP ) THEN
- KS = KS + 1
-*
-* Swap the K-th block to position KS. Compute unitary Q
-* and Z that will swap adjacent diagonal blocks in (A, B).
-*
- IF( K.NE.KS )
- $ CALL ZTGEXC( WANTQ, WANTZ, N, A, LDA, B, LDB, Q, LDQ, Z,
- $ LDZ, K, KS, IERR )
-*
- IF( IERR.GT.0 ) THEN
-*
-* Swap is rejected: exit.
-*
- INFO = 1
- IF( WANTP ) THEN
- PL = ZERO
- PR = ZERO
- END IF
- IF( WANTD ) THEN
- DIF( 1 ) = ZERO
- DIF( 2 ) = ZERO
- END IF
- GO TO 70
- END IF
- END IF
- 30 CONTINUE
- IF( WANTP ) THEN
-*
-* Solve generalized Sylvester equation for R and L:
-* A11 * R - L * A22 = A12
-* B11 * R - L * B22 = B12
-*
- N1 = M
- N2 = N - M
- I = N1 + 1
- CALL ZLACPY( 'Full', N1, N2, A( 1, I ), LDA, WORK, N1 )
- CALL ZLACPY( 'Full', N1, N2, B( 1, I ), LDB, WORK( N1*N2+1 ),
- $ N1 )
- IJB = 0
- CALL ZTGSYL( 'N', IJB, N1, N2, A, LDA, A( I, I ), LDA, WORK,
- $ N1, B, LDB, B( I, I ), LDB, WORK( N1*N2+1 ), N1,
- $ DSCALE, DIF( 1 ), WORK( N1*N2*2+1 ),
- $ LWORK-2*N1*N2, IWORK, IERR )
-*
-* Estimate the reciprocal of norms of "projections" onto
-* left and right eigenspaces
-*
- RDSCAL = ZERO
- DSUM = ONE
- CALL ZLASSQ( N1*N2, WORK, 1, RDSCAL, DSUM )
- PL = RDSCAL*SQRT( DSUM )
- IF( PL.EQ.ZERO ) THEN
- PL = ONE
- ELSE
- PL = DSCALE / ( SQRT( DSCALE*DSCALE / PL+PL )*SQRT( PL ) )
- END IF
- RDSCAL = ZERO
- DSUM = ONE
- CALL ZLASSQ( N1*N2, WORK( N1*N2+1 ), 1, RDSCAL, DSUM )
- PR = RDSCAL*SQRT( DSUM )
- IF( PR.EQ.ZERO ) THEN
- PR = ONE
- ELSE
- PR = DSCALE / ( SQRT( DSCALE*DSCALE / PR+PR )*SQRT( PR ) )
- END IF
- END IF
- IF( WANTD ) THEN
-*
-* Compute estimates Difu and Difl.
-*
- IF( WANTD1 ) THEN
- N1 = M
- N2 = N - M
- I = N1 + 1
- IJB = IDIFJB
-*
-* Frobenius norm-based Difu estimate.
-*
- CALL ZTGSYL( 'N', IJB, N1, N2, A, LDA, A( I, I ), LDA, WORK,
- $ N1, B, LDB, B( I, I ), LDB, WORK( N1*N2+1 ),
- $ N1, DSCALE, DIF( 1 ), WORK( N1*N2*2+1 ),
- $ LWORK-2*N1*N2, IWORK, IERR )
-*
-* Frobenius norm-based Difl estimate.
-*
- CALL ZTGSYL( 'N', IJB, N2, N1, A( I, I ), LDA, A, LDA, WORK,
- $ N2, B( I, I ), LDB, B, LDB, WORK( N1*N2+1 ),
- $ N2, DSCALE, DIF( 2 ), WORK( N1*N2*2+1 ),
- $ LWORK-2*N1*N2, IWORK, IERR )
- ELSE
-*
-* Compute 1-norm-based estimates of Difu and Difl using
-* reversed communication with ZLACN2. In each step a
-* generalized Sylvester equation or a transposed variant
-* is solved.
-*
- KASE = 0
- N1 = M
- N2 = N - M
- I = N1 + 1
- IJB = 0
- MN2 = 2*N1*N2
-*
-* 1-norm-based estimate of Difu.
-*
- 40 CONTINUE
- CALL ZLACN2( MN2, WORK( MN2+1 ), WORK, DIF( 1 ), KASE,
- $ ISAVE )
- IF( KASE.NE.0 ) THEN
- IF( KASE.EQ.1 ) THEN
-*
-* Solve generalized Sylvester equation
-*
- CALL ZTGSYL( 'N', IJB, N1, N2, A, LDA, A( I, I ), LDA,
- $ WORK, N1, B, LDB, B( I, I ), LDB,
- $ WORK( N1*N2+1 ), N1, DSCALE, DIF( 1 ),
- $ WORK( N1*N2*2+1 ), LWORK-2*N1*N2, IWORK,
- $ IERR )
- ELSE
-*
-* Solve the transposed variant.
-*
- CALL ZTGSYL( 'C', IJB, N1, N2, A, LDA, A( I, I ), LDA,
- $ WORK, N1, B, LDB, B( I, I ), LDB,
- $ WORK( N1*N2+1 ), N1, DSCALE, DIF( 1 ),
- $ WORK( N1*N2*2+1 ), LWORK-2*N1*N2, IWORK,
- $ IERR )
- END IF
- GO TO 40
- END IF
- DIF( 1 ) = DSCALE / DIF( 1 )
-*
-* 1-norm-based estimate of Difl.
-*
- 50 CONTINUE
- CALL ZLACN2( MN2, WORK( MN2+1 ), WORK, DIF( 2 ), KASE,
- $ ISAVE )
- IF( KASE.NE.0 ) THEN
- IF( KASE.EQ.1 ) THEN
-*
-* Solve generalized Sylvester equation
-*
- CALL ZTGSYL( 'N', IJB, N2, N1, A( I, I ), LDA, A, LDA,
- $ WORK, N2, B( I, I ), LDB, B, LDB,
- $ WORK( N1*N2+1 ), N2, DSCALE, DIF( 2 ),
- $ WORK( N1*N2*2+1 ), LWORK-2*N1*N2, IWORK,
- $ IERR )
- ELSE
-*
-* Solve the transposed variant.
-*
- CALL ZTGSYL( 'C', IJB, N2, N1, A( I, I ), LDA, A, LDA,
- $ WORK, N2, B, LDB, B( I, I ), LDB,
- $ WORK( N1*N2+1 ), N2, DSCALE, DIF( 2 ),
- $ WORK( N1*N2*2+1 ), LWORK-2*N1*N2, IWORK,
- $ IERR )
- END IF
- GO TO 50
- END IF
- DIF( 2 ) = DSCALE / DIF( 2 )
- END IF
- END IF
-*
-* If B(K,K) is complex, make it real and positive (normalization
-* of the generalized Schur form) and Store the generalized
-* eigenvalues of reordered pair (A, B)
-*
- DO 60 K = 1, N
- DSCALE = ABS( B( K, K ) )
- IF( DSCALE.GT.SAFMIN ) THEN
- WORK( 1 ) = DCONJG( B( K, K ) / DSCALE )
- WORK( 2 ) = B( K, K ) / DSCALE
- B( K, K ) = DSCALE
- CALL ZSCAL( N-K, WORK( 1 ), B( K, K+1 ), LDB )
- CALL ZSCAL( N-K+1, WORK( 1 ), A( K, K ), LDA )
- IF( WANTQ )
- $ CALL ZSCAL( N, WORK( 2 ), Q( 1, K ), 1 )
- ELSE
- B( K, K ) = DCMPLX( ZERO, ZERO )
- END IF
-*
- ALPHA( K ) = A( K, K )
- BETA( K ) = B( K, K )
-*
- 60 CONTINUE
-*
- 70 CONTINUE
-*
- WORK( 1 ) = LWMIN
- IWORK( 1 ) = LIWMIN
-*
- RETURN
-*
-* End of ZTGSEN
-*
- END
diff --git a/src/lib/lapack/ztgsy2.f b/src/lib/lapack/ztgsy2.f
deleted file mode 100644
index 82ec5eb1..00000000
--- a/src/lib/lapack/ztgsy2.f
+++ /dev/null
@@ -1,361 +0,0 @@
- SUBROUTINE ZTGSY2( TRANS, IJOB, M, N, A, LDA, B, LDB, C, LDC, D,
- $ LDD, E, LDE, F, LDF, SCALE, RDSUM, RDSCAL,
- $ INFO )
-*
-* -- LAPACK auxiliary routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- CHARACTER TRANS
- INTEGER IJOB, INFO, LDA, LDB, LDC, LDD, LDE, LDF, M, N
- DOUBLE PRECISION RDSCAL, RDSUM, SCALE
-* ..
-* .. Array Arguments ..
- COMPLEX*16 A( LDA, * ), B( LDB, * ), C( LDC, * ),
- $ D( LDD, * ), E( LDE, * ), F( LDF, * )
-* ..
-*
-* Purpose
-* =======
-*
-* ZTGSY2 solves the generalized Sylvester equation
-*
-* A * R - L * B = scale * C (1)
-* D * R - L * E = scale * F
-*
-* using Level 1 and 2 BLAS, where R and L are unknown M-by-N matrices,
-* (A, D), (B, E) and (C, F) are given matrix pairs of size M-by-M,
-* N-by-N and M-by-N, respectively. A, B, D and E are upper triangular
-* (i.e., (A,D) and (B,E) in generalized Schur form).
-*
-* The solution (R, L) overwrites (C, F). 0 <= SCALE <= 1 is an output
-* scaling factor chosen to avoid overflow.
-*
-* In matrix notation solving equation (1) corresponds to solve
-* Zx = scale * b, where Z is defined as
-*
-* Z = [ kron(In, A) -kron(B', Im) ] (2)
-* [ kron(In, D) -kron(E', Im) ],
-*
-* Ik is the identity matrix of size k and X' is the transpose of X.
-* kron(X, Y) is the Kronecker product between the matrices X and Y.
-*
-* If TRANS = 'C', y in the conjugate transposed system Z'y = scale*b
-* is solved for, which is equivalent to solve for R and L in
-*
-* A' * R + D' * L = scale * C (3)
-* R * B' + L * E' = scale * -F
-*
-* This case is used to compute an estimate of Dif[(A, D), (B, E)] =
-* = sigma_min(Z) using reverse communicaton with ZLACON.
-*
-* ZTGSY2 also (IJOB >= 1) contributes to the computation in ZTGSYL
-* of an upper bound on the separation between to matrix pairs. Then
-* the input (A, D), (B, E) are sub-pencils of two matrix pairs in
-* ZTGSYL.
-*
-* Arguments
-* =========
-*
-* TRANS (input) CHARACTER*1
-* = 'N', solve the generalized Sylvester equation (1).
-* = 'T': solve the 'transposed' system (3).
-*
-* IJOB (input) INTEGER
-* Specifies what kind of functionality to be performed.
-* =0: solve (1) only.
-* =1: A contribution from this subsystem to a Frobenius
-* norm-based estimate of the separation between two matrix
-* pairs is computed. (look ahead strategy is used).
-* =2: A contribution from this subsystem to a Frobenius
-* norm-based estimate of the separation between two matrix
-* pairs is computed. (DGECON on sub-systems is used.)
-* Not referenced if TRANS = 'T'.
-*
-* M (input) INTEGER
-* On entry, M specifies the order of A and D, and the row
-* dimension of C, F, R and L.
-*
-* N (input) INTEGER
-* On entry, N specifies the order of B and E, and the column
-* dimension of C, F, R and L.
-*
-* A (input) COMPLEX*16 array, dimension (LDA, M)
-* On entry, A contains an upper triangular matrix.
-*
-* LDA (input) INTEGER
-* The leading dimension of the matrix A. LDA >= max(1, M).
-*
-* B (input) COMPLEX*16 array, dimension (LDB, N)
-* On entry, B contains an upper triangular matrix.
-*
-* LDB (input) INTEGER
-* The leading dimension of the matrix B. LDB >= max(1, N).
-*
-* C (input/output) COMPLEX*16 array, dimension (LDC, N)
-* On entry, C contains the right-hand-side of the first matrix
-* equation in (1).
-* On exit, if IJOB = 0, C has been overwritten by the solution
-* R.
-*
-* LDC (input) INTEGER
-* The leading dimension of the matrix C. LDC >= max(1, M).
-*
-* D (input) COMPLEX*16 array, dimension (LDD, M)
-* On entry, D contains an upper triangular matrix.
-*
-* LDD (input) INTEGER
-* The leading dimension of the matrix D. LDD >= max(1, M).
-*
-* E (input) COMPLEX*16 array, dimension (LDE, N)
-* On entry, E contains an upper triangular matrix.
-*
-* LDE (input) INTEGER
-* The leading dimension of the matrix E. LDE >= max(1, N).
-*
-* F (input/output) COMPLEX*16 array, dimension (LDF, N)
-* On entry, F contains the right-hand-side of the second matrix
-* equation in (1).
-* On exit, if IJOB = 0, F has been overwritten by the solution
-* L.
-*
-* LDF (input) INTEGER
-* The leading dimension of the matrix F. LDF >= max(1, M).
-*
-* SCALE (output) DOUBLE PRECISION
-* On exit, 0 <= SCALE <= 1. If 0 < SCALE < 1, the solutions
-* R and L (C and F on entry) will hold the solutions to a
-* slightly perturbed system but the input matrices A, B, D and
-* E have not been changed. If SCALE = 0, R and L will hold the
-* solutions to the homogeneous system with C = F = 0.
-* Normally, SCALE = 1.
-*
-* RDSUM (input/output) DOUBLE PRECISION
-* On entry, the sum of squares of computed contributions to
-* the Dif-estimate under computation by ZTGSYL, where the
-* scaling factor RDSCAL (see below) has been factored out.
-* On exit, the corresponding sum of squares updated with the
-* contributions from the current sub-system.
-* If TRANS = 'T' RDSUM is not touched.
-* NOTE: RDSUM only makes sense when ZTGSY2 is called by
-* ZTGSYL.
-*
-* RDSCAL (input/output) DOUBLE PRECISION
-* On entry, scaling factor used to prevent overflow in RDSUM.
-* On exit, RDSCAL is updated w.r.t. the current contributions
-* in RDSUM.
-* If TRANS = 'T', RDSCAL is not touched.
-* NOTE: RDSCAL only makes sense when ZTGSY2 is called by
-* ZTGSYL.
-*
-* INFO (output) INTEGER
-* On exit, if INFO is set to
-* =0: Successful exit
-* <0: If INFO = -i, input argument number i is illegal.
-* >0: The matrix pairs (A, D) and (B, E) have common or very
-* close eigenvalues.
-*
-* Further Details
-* ===============
-*
-* Based on contributions by
-* Bo Kagstrom and Peter Poromaa, Department of Computing Science,
-* Umea University, S-901 87 Umea, Sweden.
-*
-* =====================================================================
-*
-* .. Parameters ..
- DOUBLE PRECISION ZERO, ONE
- INTEGER LDZ
- PARAMETER ( ZERO = 0.0D+0, ONE = 1.0D+0, LDZ = 2 )
-* ..
-* .. Local Scalars ..
- LOGICAL NOTRAN
- INTEGER I, IERR, J, K
- DOUBLE PRECISION SCALOC
- COMPLEX*16 ALPHA
-* ..
-* .. Local Arrays ..
- INTEGER IPIV( LDZ ), JPIV( LDZ )
- COMPLEX*16 RHS( LDZ ), Z( LDZ, LDZ )
-* ..
-* .. External Functions ..
- LOGICAL LSAME
- EXTERNAL LSAME
-* ..
-* .. External Subroutines ..
- EXTERNAL XERBLA, ZAXPY, ZGESC2, ZGETC2, ZLATDF, ZSCAL
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC DCMPLX, DCONJG, MAX
-* ..
-* .. Executable Statements ..
-*
-* Decode and test input parameters
-*
- INFO = 0
- IERR = 0
- NOTRAN = LSAME( TRANS, 'N' )
- IF( .NOT.NOTRAN .AND. .NOT.LSAME( TRANS, 'C' ) ) THEN
- INFO = -1
- ELSE IF( NOTRAN ) THEN
- IF( ( IJOB.LT.0 ) .OR. ( IJOB.GT.2 ) ) THEN
- INFO = -2
- END IF
- END IF
- IF( INFO.EQ.0 ) THEN
- IF( M.LE.0 ) THEN
- INFO = -3
- ELSE IF( N.LE.0 ) THEN
- INFO = -4
- ELSE IF( LDA.LT.MAX( 1, M ) ) THEN
- INFO = -5
- ELSE IF( LDB.LT.MAX( 1, N ) ) THEN
- INFO = -8
- ELSE IF( LDC.LT.MAX( 1, M ) ) THEN
- INFO = -10
- ELSE IF( LDD.LT.MAX( 1, M ) ) THEN
- INFO = -12
- ELSE IF( LDE.LT.MAX( 1, N ) ) THEN
- INFO = -14
- ELSE IF( LDF.LT.MAX( 1, M ) ) THEN
- INFO = -16
- END IF
- END IF
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'ZTGSY2', -INFO )
- RETURN
- END IF
-*
- IF( NOTRAN ) THEN
-*
-* Solve (I, J) - system
-* A(I, I) * R(I, J) - L(I, J) * B(J, J) = C(I, J)
-* D(I, I) * R(I, J) - L(I, J) * E(J, J) = F(I, J)
-* for I = M, M - 1, ..., 1; J = 1, 2, ..., N
-*
- SCALE = ONE
- SCALOC = ONE
- DO 30 J = 1, N
- DO 20 I = M, 1, -1
-*
-* Build 2 by 2 system
-*
- Z( 1, 1 ) = A( I, I )
- Z( 2, 1 ) = D( I, I )
- Z( 1, 2 ) = -B( J, J )
- Z( 2, 2 ) = -E( J, J )
-*
-* Set up right hand side(s)
-*
- RHS( 1 ) = C( I, J )
- RHS( 2 ) = F( I, J )
-*
-* Solve Z * x = RHS
-*
- CALL ZGETC2( LDZ, Z, LDZ, IPIV, JPIV, IERR )
- IF( IERR.GT.0 )
- $ INFO = IERR
- IF( IJOB.EQ.0 ) THEN
- CALL ZGESC2( LDZ, Z, LDZ, RHS, IPIV, JPIV, SCALOC )
- IF( SCALOC.NE.ONE ) THEN
- DO 10 K = 1, N
- CALL ZSCAL( M, DCMPLX( SCALOC, ZERO ),
- $ C( 1, K ), 1 )
- CALL ZSCAL( M, DCMPLX( SCALOC, ZERO ),
- $ F( 1, K ), 1 )
- 10 CONTINUE
- SCALE = SCALE*SCALOC
- END IF
- ELSE
- CALL ZLATDF( IJOB, LDZ, Z, LDZ, RHS, RDSUM, RDSCAL,
- $ IPIV, JPIV )
- END IF
-*
-* Unpack solution vector(s)
-*
- C( I, J ) = RHS( 1 )
- F( I, J ) = RHS( 2 )
-*
-* Substitute R(I, J) and L(I, J) into remaining equation.
-*
- IF( I.GT.1 ) THEN
- ALPHA = -RHS( 1 )
- CALL ZAXPY( I-1, ALPHA, A( 1, I ), 1, C( 1, J ), 1 )
- CALL ZAXPY( I-1, ALPHA, D( 1, I ), 1, F( 1, J ), 1 )
- END IF
- IF( J.LT.N ) THEN
- CALL ZAXPY( N-J, RHS( 2 ), B( J, J+1 ), LDB,
- $ C( I, J+1 ), LDC )
- CALL ZAXPY( N-J, RHS( 2 ), E( J, J+1 ), LDE,
- $ F( I, J+1 ), LDF )
- END IF
-*
- 20 CONTINUE
- 30 CONTINUE
- ELSE
-*
-* Solve transposed (I, J) - system:
-* A(I, I)' * R(I, J) + D(I, I)' * L(J, J) = C(I, J)
-* R(I, I) * B(J, J) + L(I, J) * E(J, J) = -F(I, J)
-* for I = 1, 2, ..., M, J = N, N - 1, ..., 1
-*
- SCALE = ONE
- SCALOC = ONE
- DO 80 I = 1, M
- DO 70 J = N, 1, -1
-*
-* Build 2 by 2 system Z'
-*
- Z( 1, 1 ) = DCONJG( A( I, I ) )
- Z( 2, 1 ) = -DCONJG( B( J, J ) )
- Z( 1, 2 ) = DCONJG( D( I, I ) )
- Z( 2, 2 ) = -DCONJG( E( J, J ) )
-*
-*
-* Set up right hand side(s)
-*
- RHS( 1 ) = C( I, J )
- RHS( 2 ) = F( I, J )
-*
-* Solve Z' * x = RHS
-*
- CALL ZGETC2( LDZ, Z, LDZ, IPIV, JPIV, IERR )
- IF( IERR.GT.0 )
- $ INFO = IERR
- CALL ZGESC2( LDZ, Z, LDZ, RHS, IPIV, JPIV, SCALOC )
- IF( SCALOC.NE.ONE ) THEN
- DO 40 K = 1, N
- CALL ZSCAL( M, DCMPLX( SCALOC, ZERO ), C( 1, K ),
- $ 1 )
- CALL ZSCAL( M, DCMPLX( SCALOC, ZERO ), F( 1, K ),
- $ 1 )
- 40 CONTINUE
- SCALE = SCALE*SCALOC
- END IF
-*
-* Unpack solution vector(s)
-*
- C( I, J ) = RHS( 1 )
- F( I, J ) = RHS( 2 )
-*
-* Substitute R(I, J) and L(I, J) into remaining equation.
-*
- DO 50 K = 1, J - 1
- F( I, K ) = F( I, K ) + RHS( 1 )*DCONJG( B( K, J ) ) +
- $ RHS( 2 )*DCONJG( E( K, J ) )
- 50 CONTINUE
- DO 60 K = I + 1, M
- C( K, J ) = C( K, J ) - DCONJG( A( I, K ) )*RHS( 1 ) -
- $ DCONJG( D( I, K ) )*RHS( 2 )
- 60 CONTINUE
-*
- 70 CONTINUE
- 80 CONTINUE
- END IF
- RETURN
-*
-* End of ZTGSY2
-*
- END
diff --git a/src/lib/lapack/ztgsyl.f b/src/lib/lapack/ztgsyl.f
deleted file mode 100644
index af808a31..00000000
--- a/src/lib/lapack/ztgsyl.f
+++ /dev/null
@@ -1,575 +0,0 @@
- SUBROUTINE ZTGSYL( TRANS, IJOB, M, N, A, LDA, B, LDB, C, LDC, D,
- $ LDD, E, LDE, F, LDF, SCALE, DIF, WORK, LWORK,
- $ IWORK, INFO )
-*
-* -- LAPACK routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- CHARACTER TRANS
- INTEGER IJOB, INFO, LDA, LDB, LDC, LDD, LDE, LDF,
- $ LWORK, M, N
- DOUBLE PRECISION DIF, SCALE
-* ..
-* .. Array Arguments ..
- INTEGER IWORK( * )
- COMPLEX*16 A( LDA, * ), B( LDB, * ), C( LDC, * ),
- $ D( LDD, * ), E( LDE, * ), F( LDF, * ),
- $ WORK( * )
-* ..
-*
-* Purpose
-* =======
-*
-* ZTGSYL solves the generalized Sylvester equation:
-*
-* A * R - L * B = scale * C (1)
-* D * R - L * E = scale * F
-*
-* where R and L are unknown m-by-n matrices, (A, D), (B, E) and
-* (C, F) are given matrix pairs of size m-by-m, n-by-n and m-by-n,
-* respectively, with complex entries. A, B, D and E are upper
-* triangular (i.e., (A,D) and (B,E) in generalized Schur form).
-*
-* The solution (R, L) overwrites (C, F). 0 <= SCALE <= 1
-* is an output scaling factor chosen to avoid overflow.
-*
-* In matrix notation (1) is equivalent to solve Zx = scale*b, where Z
-* is defined as
-*
-* Z = [ kron(In, A) -kron(B', Im) ] (2)
-* [ kron(In, D) -kron(E', Im) ],
-*
-* Here Ix is the identity matrix of size x and X' is the conjugate
-* transpose of X. Kron(X, Y) is the Kronecker product between the
-* matrices X and Y.
-*
-* If TRANS = 'C', y in the conjugate transposed system Z'*y = scale*b
-* is solved for, which is equivalent to solve for R and L in
-*
-* A' * R + D' * L = scale * C (3)
-* R * B' + L * E' = scale * -F
-*
-* This case (TRANS = 'C') is used to compute an one-norm-based estimate
-* of Dif[(A,D), (B,E)], the separation between the matrix pairs (A,D)
-* and (B,E), using ZLACON.
-*
-* If IJOB >= 1, ZTGSYL computes a Frobenius norm-based estimate of
-* Dif[(A,D),(B,E)]. That is, the reciprocal of a lower bound on the
-* reciprocal of the smallest singular value of Z.
-*
-* This is a level-3 BLAS algorithm.
-*
-* Arguments
-* =========
-*
-* TRANS (input) CHARACTER*1
-* = 'N': solve the generalized sylvester equation (1).
-* = 'C': solve the "conjugate transposed" system (3).
-*
-* IJOB (input) INTEGER
-* Specifies what kind of functionality to be performed.
-* =0: solve (1) only.
-* =1: The functionality of 0 and 3.
-* =2: The functionality of 0 and 4.
-* =3: Only an estimate of Dif[(A,D), (B,E)] is computed.
-* (look ahead strategy is used).
-* =4: Only an estimate of Dif[(A,D), (B,E)] is computed.
-* (ZGECON on sub-systems is used).
-* Not referenced if TRANS = 'C'.
-*
-* M (input) INTEGER
-* The order of the matrices A and D, and the row dimension of
-* the matrices C, F, R and L.
-*
-* N (input) INTEGER
-* The order of the matrices B and E, and the column dimension
-* of the matrices C, F, R and L.
-*
-* A (input) COMPLEX*16 array, dimension (LDA, M)
-* The upper triangular matrix A.
-*
-* LDA (input) INTEGER
-* The leading dimension of the array A. LDA >= max(1, M).
-*
-* B (input) COMPLEX*16 array, dimension (LDB, N)
-* The upper triangular matrix B.
-*
-* LDB (input) INTEGER
-* The leading dimension of the array B. LDB >= max(1, N).
-*
-* C (input/output) COMPLEX*16 array, dimension (LDC, N)
-* On entry, C contains the right-hand-side of the first matrix
-* equation in (1) or (3).
-* On exit, if IJOB = 0, 1 or 2, C has been overwritten by
-* the solution R. If IJOB = 3 or 4 and TRANS = 'N', C holds R,
-* the solution achieved during the computation of the
-* Dif-estimate.
-*
-* LDC (input) INTEGER
-* The leading dimension of the array C. LDC >= max(1, M).
-*
-* D (input) COMPLEX*16 array, dimension (LDD, M)
-* The upper triangular matrix D.
-*
-* LDD (input) INTEGER
-* The leading dimension of the array D. LDD >= max(1, M).
-*
-* E (input) COMPLEX*16 array, dimension (LDE, N)
-* The upper triangular matrix E.
-*
-* LDE (input) INTEGER
-* The leading dimension of the array E. LDE >= max(1, N).
-*
-* F (input/output) COMPLEX*16 array, dimension (LDF, N)
-* On entry, F contains the right-hand-side of the second matrix
-* equation in (1) or (3).
-* On exit, if IJOB = 0, 1 or 2, F has been overwritten by
-* the solution L. If IJOB = 3 or 4 and TRANS = 'N', F holds L,
-* the solution achieved during the computation of the
-* Dif-estimate.
-*
-* LDF (input) INTEGER
-* The leading dimension of the array F. LDF >= max(1, M).
-*
-* DIF (output) DOUBLE PRECISION
-* On exit DIF is the reciprocal of a lower bound of the
-* reciprocal of the Dif-function, i.e. DIF is an upper bound of
-* Dif[(A,D), (B,E)] = sigma-min(Z), where Z as in (2).
-* IF IJOB = 0 or TRANS = 'C', DIF is not referenced.
-*
-* SCALE (output) DOUBLE PRECISION
-* On exit SCALE is the scaling factor in (1) or (3).
-* If 0 < SCALE < 1, C and F hold the solutions R and L, resp.,
-* to a slightly perturbed system but the input matrices A, B,
-* D and E have not been changed. If SCALE = 0, R and L will
-* hold the solutions to the homogenious system with C = F = 0.
-*
-* WORK (workspace/output) COMPLEX*16 array, dimension (MAX(1,LWORK))
-* On exit, if INFO = 0, WORK(1) returns the optimal LWORK.
-*
-* LWORK (input) INTEGER
-* The dimension of the array WORK. LWORK > = 1.
-* If IJOB = 1 or 2 and TRANS = 'N', LWORK >= max(1,2*M*N).
-*
-* If LWORK = -1, then a workspace query is assumed; the routine
-* only calculates the optimal size of the WORK array, returns
-* this value as the first entry of the WORK array, and no error
-* message related to LWORK is issued by XERBLA.
-*
-* IWORK (workspace) INTEGER array, dimension (M+N+2)
-* If IJOB = 0, IWORK is not referenced.
-*
-* INFO (output) INTEGER
-* =0: successful exit
-* <0: If INFO = -i, the i-th argument had an illegal value.
-* >0: (A, D) and (B, E) have common or very close
-* eigenvalues.
-*
-* Further Details
-* ===============
-*
-* Based on contributions by
-* Bo Kagstrom and Peter Poromaa, Department of Computing Science,
-* Umea University, S-901 87 Umea, Sweden.
-*
-* [1] B. Kagstrom and P. Poromaa, LAPACK-Style Algorithms and Software
-* for Solving the Generalized Sylvester Equation and Estimating the
-* Separation between Regular Matrix Pairs, Report UMINF - 93.23,
-* Department of Computing Science, Umea University, S-901 87 Umea,
-* Sweden, December 1993, Revised April 1994, Also as LAPACK Working
-* Note 75. To appear in ACM Trans. on Math. Software, Vol 22,
-* No 1, 1996.
-*
-* [2] B. Kagstrom, A Perturbation Analysis of the Generalized Sylvester
-* Equation (AR - LB, DR - LE ) = (C, F), SIAM J. Matrix Anal.
-* Appl., 15(4):1045-1060, 1994.
-*
-* [3] B. Kagstrom and L. Westin, Generalized Schur Methods with
-* Condition Estimators for Solving the Generalized Sylvester
-* Equation, IEEE Transactions on Automatic Control, Vol. 34, No. 7,
-* July 1989, pp 745-751.
-*
-* =====================================================================
-* Replaced various illegal calls to CCOPY by calls to CLASET.
-* Sven Hammarling, 1/5/02.
-*
-* .. Parameters ..
- DOUBLE PRECISION ZERO, ONE
- PARAMETER ( ZERO = 0.0D+0, ONE = 1.0D+0 )
- COMPLEX*16 CZERO
- PARAMETER ( CZERO = (0.0D+0, 0.0D+0) )
-* ..
-* .. Local Scalars ..
- LOGICAL LQUERY, NOTRAN
- INTEGER I, IE, IFUNC, IROUND, IS, ISOLVE, J, JE, JS, K,
- $ LINFO, LWMIN, MB, NB, P, PQ, Q
- DOUBLE PRECISION DSCALE, DSUM, SCALE2, SCALOC
-* ..
-* .. External Functions ..
- LOGICAL LSAME
- INTEGER ILAENV
- EXTERNAL LSAME, ILAENV
-* ..
-* .. External Subroutines ..
- EXTERNAL XERBLA, ZGEMM, ZLACPY, ZLASET, ZSCAL, ZTGSY2
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC DBLE, DCMPLX, MAX, SQRT
-* ..
-* .. Executable Statements ..
-*
-* Decode and test input parameters
-*
- INFO = 0
- NOTRAN = LSAME( TRANS, 'N' )
- LQUERY = ( LWORK.EQ.-1 )
-*
- IF( .NOT.NOTRAN .AND. .NOT.LSAME( TRANS, 'C' ) ) THEN
- INFO = -1
- ELSE IF( NOTRAN ) THEN
- IF( ( IJOB.LT.0 ) .OR. ( IJOB.GT.4 ) ) THEN
- INFO = -2
- END IF
- END IF
- IF( INFO.EQ.0 ) THEN
- IF( M.LE.0 ) THEN
- INFO = -3
- ELSE IF( N.LE.0 ) THEN
- INFO = -4
- ELSE IF( LDA.LT.MAX( 1, M ) ) THEN
- INFO = -6
- ELSE IF( LDB.LT.MAX( 1, N ) ) THEN
- INFO = -8
- ELSE IF( LDC.LT.MAX( 1, M ) ) THEN
- INFO = -10
- ELSE IF( LDD.LT.MAX( 1, M ) ) THEN
- INFO = -12
- ELSE IF( LDE.LT.MAX( 1, N ) ) THEN
- INFO = -14
- ELSE IF( LDF.LT.MAX( 1, M ) ) THEN
- INFO = -16
- END IF
- END IF
-*
- IF( INFO.EQ.0 ) THEN
- IF( NOTRAN ) THEN
- IF( IJOB.EQ.1 .OR. IJOB.EQ.2 ) THEN
- LWMIN = MAX( 1, 2*M*N )
- ELSE
- LWMIN = 1
- END IF
- ELSE
- LWMIN = 1
- END IF
- WORK( 1 ) = LWMIN
-*
- IF( LWORK.LT.LWMIN .AND. .NOT.LQUERY ) THEN
- INFO = -20
- END IF
- END IF
-*
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'ZTGSYL', -INFO )
- RETURN
- ELSE IF( LQUERY ) THEN
- RETURN
- END IF
-*
-* Quick return if possible
-*
- IF( M.EQ.0 .OR. N.EQ.0 ) THEN
- SCALE = 1
- IF( NOTRAN ) THEN
- IF( IJOB.NE.0 ) THEN
- DIF = 0
- END IF
- END IF
- RETURN
- END IF
-*
-* Determine optimal block sizes MB and NB
-*
- MB = ILAENV( 2, 'ZTGSYL', TRANS, M, N, -1, -1 )
- NB = ILAENV( 5, 'ZTGSYL', TRANS, M, N, -1, -1 )
-*
- ISOLVE = 1
- IFUNC = 0
- IF( NOTRAN ) THEN
- IF( IJOB.GE.3 ) THEN
- IFUNC = IJOB - 2
- CALL ZLASET( 'F', M, N, CZERO, CZERO, C, LDC )
- CALL ZLASET( 'F', M, N, CZERO, CZERO, F, LDF )
- ELSE IF( IJOB.GE.1 .AND. NOTRAN ) THEN
- ISOLVE = 2
- END IF
- END IF
-*
- IF( ( MB.LE.1 .AND. NB.LE.1 ) .OR. ( MB.GE.M .AND. NB.GE.N ) )
- $ THEN
-*
-* Use unblocked Level 2 solver
-*
- DO 30 IROUND = 1, ISOLVE
-*
- SCALE = ONE
- DSCALE = ZERO
- DSUM = ONE
- PQ = M*N
- CALL ZTGSY2( TRANS, IFUNC, M, N, A, LDA, B, LDB, C, LDC, D,
- $ LDD, E, LDE, F, LDF, SCALE, DSUM, DSCALE,
- $ INFO )
- IF( DSCALE.NE.ZERO ) THEN
- IF( IJOB.EQ.1 .OR. IJOB.EQ.3 ) THEN
- DIF = SQRT( DBLE( 2*M*N ) ) / ( DSCALE*SQRT( DSUM ) )
- ELSE
- DIF = SQRT( DBLE( PQ ) ) / ( DSCALE*SQRT( DSUM ) )
- END IF
- END IF
- IF( ISOLVE.EQ.2 .AND. IROUND.EQ.1 ) THEN
- IF( NOTRAN ) THEN
- IFUNC = IJOB
- END IF
- SCALE2 = SCALE
- CALL ZLACPY( 'F', M, N, C, LDC, WORK, M )
- CALL ZLACPY( 'F', M, N, F, LDF, WORK( M*N+1 ), M )
- CALL ZLASET( 'F', M, N, CZERO, CZERO, C, LDC )
- CALL ZLASET( 'F', M, N, CZERO, CZERO, F, LDF )
- ELSE IF( ISOLVE.EQ.2 .AND. IROUND.EQ.2 ) THEN
- CALL ZLACPY( 'F', M, N, WORK, M, C, LDC )
- CALL ZLACPY( 'F', M, N, WORK( M*N+1 ), M, F, LDF )
- SCALE = SCALE2
- END IF
- 30 CONTINUE
-*
- RETURN
-*
- END IF
-*
-* Determine block structure of A
-*
- P = 0
- I = 1
- 40 CONTINUE
- IF( I.GT.M )
- $ GO TO 50
- P = P + 1
- IWORK( P ) = I
- I = I + MB
- IF( I.GE.M )
- $ GO TO 50
- GO TO 40
- 50 CONTINUE
- IWORK( P+1 ) = M + 1
- IF( IWORK( P ).EQ.IWORK( P+1 ) )
- $ P = P - 1
-*
-* Determine block structure of B
-*
- Q = P + 1
- J = 1
- 60 CONTINUE
- IF( J.GT.N )
- $ GO TO 70
-*
- Q = Q + 1
- IWORK( Q ) = J
- J = J + NB
- IF( J.GE.N )
- $ GO TO 70
- GO TO 60
-*
- 70 CONTINUE
- IWORK( Q+1 ) = N + 1
- IF( IWORK( Q ).EQ.IWORK( Q+1 ) )
- $ Q = Q - 1
-*
- IF( NOTRAN ) THEN
- DO 150 IROUND = 1, ISOLVE
-*
-* Solve (I, J) - subsystem
-* A(I, I) * R(I, J) - L(I, J) * B(J, J) = C(I, J)
-* D(I, I) * R(I, J) - L(I, J) * E(J, J) = F(I, J)
-* for I = P, P - 1, ..., 1; J = 1, 2, ..., Q
-*
- PQ = 0
- SCALE = ONE
- DSCALE = ZERO
- DSUM = ONE
- DO 130 J = P + 2, Q
- JS = IWORK( J )
- JE = IWORK( J+1 ) - 1
- NB = JE - JS + 1
- DO 120 I = P, 1, -1
- IS = IWORK( I )
- IE = IWORK( I+1 ) - 1
- MB = IE - IS + 1
- CALL ZTGSY2( TRANS, IFUNC, MB, NB, A( IS, IS ), LDA,
- $ B( JS, JS ), LDB, C( IS, JS ), LDC,
- $ D( IS, IS ), LDD, E( JS, JS ), LDE,
- $ F( IS, JS ), LDF, SCALOC, DSUM, DSCALE,
- $ LINFO )
- IF( LINFO.GT.0 )
- $ INFO = LINFO
- PQ = PQ + MB*NB
- IF( SCALOC.NE.ONE ) THEN
- DO 80 K = 1, JS - 1
- CALL ZSCAL( M, DCMPLX( SCALOC, ZERO ),
- $ C( 1, K ), 1 )
- CALL ZSCAL( M, DCMPLX( SCALOC, ZERO ),
- $ F( 1, K ), 1 )
- 80 CONTINUE
- DO 90 K = JS, JE
- CALL ZSCAL( IS-1, DCMPLX( SCALOC, ZERO ),
- $ C( 1, K ), 1 )
- CALL ZSCAL( IS-1, DCMPLX( SCALOC, ZERO ),
- $ F( 1, K ), 1 )
- 90 CONTINUE
- DO 100 K = JS, JE
- CALL ZSCAL( M-IE, DCMPLX( SCALOC, ZERO ),
- $ C( IE+1, K ), 1 )
- CALL ZSCAL( M-IE, DCMPLX( SCALOC, ZERO ),
- $ F( IE+1, K ), 1 )
- 100 CONTINUE
- DO 110 K = JE + 1, N
- CALL ZSCAL( M, DCMPLX( SCALOC, ZERO ),
- $ C( 1, K ), 1 )
- CALL ZSCAL( M, DCMPLX( SCALOC, ZERO ),
- $ F( 1, K ), 1 )
- 110 CONTINUE
- SCALE = SCALE*SCALOC
- END IF
-*
-* Substitute R(I,J) and L(I,J) into remaining equation.
-*
- IF( I.GT.1 ) THEN
- CALL ZGEMM( 'N', 'N', IS-1, NB, MB,
- $ DCMPLX( -ONE, ZERO ), A( 1, IS ), LDA,
- $ C( IS, JS ), LDC, DCMPLX( ONE, ZERO ),
- $ C( 1, JS ), LDC )
- CALL ZGEMM( 'N', 'N', IS-1, NB, MB,
- $ DCMPLX( -ONE, ZERO ), D( 1, IS ), LDD,
- $ C( IS, JS ), LDC, DCMPLX( ONE, ZERO ),
- $ F( 1, JS ), LDF )
- END IF
- IF( J.LT.Q ) THEN
- CALL ZGEMM( 'N', 'N', MB, N-JE, NB,
- $ DCMPLX( ONE, ZERO ), F( IS, JS ), LDF,
- $ B( JS, JE+1 ), LDB,
- $ DCMPLX( ONE, ZERO ), C( IS, JE+1 ),
- $ LDC )
- CALL ZGEMM( 'N', 'N', MB, N-JE, NB,
- $ DCMPLX( ONE, ZERO ), F( IS, JS ), LDF,
- $ E( JS, JE+1 ), LDE,
- $ DCMPLX( ONE, ZERO ), F( IS, JE+1 ),
- $ LDF )
- END IF
- 120 CONTINUE
- 130 CONTINUE
- IF( DSCALE.NE.ZERO ) THEN
- IF( IJOB.EQ.1 .OR. IJOB.EQ.3 ) THEN
- DIF = SQRT( DBLE( 2*M*N ) ) / ( DSCALE*SQRT( DSUM ) )
- ELSE
- DIF = SQRT( DBLE( PQ ) ) / ( DSCALE*SQRT( DSUM ) )
- END IF
- END IF
- IF( ISOLVE.EQ.2 .AND. IROUND.EQ.1 ) THEN
- IF( NOTRAN ) THEN
- IFUNC = IJOB
- END IF
- SCALE2 = SCALE
- CALL ZLACPY( 'F', M, N, C, LDC, WORK, M )
- CALL ZLACPY( 'F', M, N, F, LDF, WORK( M*N+1 ), M )
- CALL ZLASET( 'F', M, N, CZERO, CZERO, C, LDC )
- CALL ZLASET( 'F', M, N, CZERO, CZERO, F, LDF )
- ELSE IF( ISOLVE.EQ.2 .AND. IROUND.EQ.2 ) THEN
- CALL ZLACPY( 'F', M, N, WORK, M, C, LDC )
- CALL ZLACPY( 'F', M, N, WORK( M*N+1 ), M, F, LDF )
- SCALE = SCALE2
- END IF
- 150 CONTINUE
- ELSE
-*
-* Solve transposed (I, J)-subsystem
-* A(I, I)' * R(I, J) + D(I, I)' * L(I, J) = C(I, J)
-* R(I, J) * B(J, J) + L(I, J) * E(J, J) = -F(I, J)
-* for I = 1,2,..., P; J = Q, Q-1,..., 1
-*
- SCALE = ONE
- DO 210 I = 1, P
- IS = IWORK( I )
- IE = IWORK( I+1 ) - 1
- MB = IE - IS + 1
- DO 200 J = Q, P + 2, -1
- JS = IWORK( J )
- JE = IWORK( J+1 ) - 1
- NB = JE - JS + 1
- CALL ZTGSY2( TRANS, IFUNC, MB, NB, A( IS, IS ), LDA,
- $ B( JS, JS ), LDB, C( IS, JS ), LDC,
- $ D( IS, IS ), LDD, E( JS, JS ), LDE,
- $ F( IS, JS ), LDF, SCALOC, DSUM, DSCALE,
- $ LINFO )
- IF( LINFO.GT.0 )
- $ INFO = LINFO
- IF( SCALOC.NE.ONE ) THEN
- DO 160 K = 1, JS - 1
- CALL ZSCAL( M, DCMPLX( SCALOC, ZERO ), C( 1, K ),
- $ 1 )
- CALL ZSCAL( M, DCMPLX( SCALOC, ZERO ), F( 1, K ),
- $ 1 )
- 160 CONTINUE
- DO 170 K = JS, JE
- CALL ZSCAL( IS-1, DCMPLX( SCALOC, ZERO ),
- $ C( 1, K ), 1 )
- CALL ZSCAL( IS-1, DCMPLX( SCALOC, ZERO ),
- $ F( 1, K ), 1 )
- 170 CONTINUE
- DO 180 K = JS, JE
- CALL ZSCAL( M-IE, DCMPLX( SCALOC, ZERO ),
- $ C( IE+1, K ), 1 )
- CALL ZSCAL( M-IE, DCMPLX( SCALOC, ZERO ),
- $ F( IE+1, K ), 1 )
- 180 CONTINUE
- DO 190 K = JE + 1, N
- CALL ZSCAL( M, DCMPLX( SCALOC, ZERO ), C( 1, K ),
- $ 1 )
- CALL ZSCAL( M, DCMPLX( SCALOC, ZERO ), F( 1, K ),
- $ 1 )
- 190 CONTINUE
- SCALE = SCALE*SCALOC
- END IF
-*
-* Substitute R(I,J) and L(I,J) into remaining equation.
-*
- IF( J.GT.P+2 ) THEN
- CALL ZGEMM( 'N', 'C', MB, JS-1, NB,
- $ DCMPLX( ONE, ZERO ), C( IS, JS ), LDC,
- $ B( 1, JS ), LDB, DCMPLX( ONE, ZERO ),
- $ F( IS, 1 ), LDF )
- CALL ZGEMM( 'N', 'C', MB, JS-1, NB,
- $ DCMPLX( ONE, ZERO ), F( IS, JS ), LDF,
- $ E( 1, JS ), LDE, DCMPLX( ONE, ZERO ),
- $ F( IS, 1 ), LDF )
- END IF
- IF( I.LT.P ) THEN
- CALL ZGEMM( 'C', 'N', M-IE, NB, MB,
- $ DCMPLX( -ONE, ZERO ), A( IS, IE+1 ), LDA,
- $ C( IS, JS ), LDC, DCMPLX( ONE, ZERO ),
- $ C( IE+1, JS ), LDC )
- CALL ZGEMM( 'C', 'N', M-IE, NB, MB,
- $ DCMPLX( -ONE, ZERO ), D( IS, IE+1 ), LDD,
- $ F( IS, JS ), LDF, DCMPLX( ONE, ZERO ),
- $ C( IE+1, JS ), LDC )
- END IF
- 200 CONTINUE
- 210 CONTINUE
- END IF
-*
- WORK( 1 ) = LWMIN
-*
- RETURN
-*
-* End of ZTGSYL
-*
- END
diff --git a/src/lib/lapack/ztrevc.f b/src/lib/lapack/ztrevc.f
deleted file mode 100644
index 21142f42..00000000
--- a/src/lib/lapack/ztrevc.f
+++ /dev/null
@@ -1,386 +0,0 @@
- SUBROUTINE ZTREVC( SIDE, HOWMNY, SELECT, N, T, LDT, VL, LDVL, VR,
- $ LDVR, MM, M, WORK, RWORK, INFO )
-*
-* -- LAPACK routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- CHARACTER HOWMNY, SIDE
- INTEGER INFO, LDT, LDVL, LDVR, M, MM, N
-* ..
-* .. Array Arguments ..
- LOGICAL SELECT( * )
- DOUBLE PRECISION RWORK( * )
- COMPLEX*16 T( LDT, * ), VL( LDVL, * ), VR( LDVR, * ),
- $ WORK( * )
-* ..
-*
-* Purpose
-* =======
-*
-* ZTREVC computes some or all of the right and/or left eigenvectors of
-* a complex upper triangular matrix T.
-* Matrices of this type are produced by the Schur factorization of
-* a complex general matrix: A = Q*T*Q**H, as computed by ZHSEQR.
-*
-* The right eigenvector x and the left eigenvector y of T corresponding
-* to an eigenvalue w are defined by:
-*
-* T*x = w*x, (y**H)*T = w*(y**H)
-*
-* where y**H denotes the conjugate transpose of the vector y.
-* The eigenvalues are not input to this routine, but are read directly
-* from the diagonal of T.
-*
-* This routine returns the matrices X and/or Y of right and left
-* eigenvectors of T, or the products Q*X and/or Q*Y, where Q is an
-* input matrix. If Q is the unitary factor that reduces a matrix A to
-* Schur form T, then Q*X and Q*Y are the matrices of right and left
-* eigenvectors of A.
-*
-* Arguments
-* =========
-*
-* SIDE (input) CHARACTER*1
-* = 'R': compute right eigenvectors only;
-* = 'L': compute left eigenvectors only;
-* = 'B': compute both right and left eigenvectors.
-*
-* HOWMNY (input) CHARACTER*1
-* = 'A': compute all right and/or left eigenvectors;
-* = 'B': compute all right and/or left eigenvectors,
-* backtransformed using the matrices supplied in
-* VR and/or VL;
-* = 'S': compute selected right and/or left eigenvectors,
-* as indicated by the logical array SELECT.
-*
-* SELECT (input) LOGICAL array, dimension (N)
-* If HOWMNY = 'S', SELECT specifies the eigenvectors to be
-* computed.
-* The eigenvector corresponding to the j-th eigenvalue is
-* computed if SELECT(j) = .TRUE..
-* Not referenced if HOWMNY = 'A' or 'B'.
-*
-* N (input) INTEGER
-* The order of the matrix T. N >= 0.
-*
-* T (input/output) COMPLEX*16 array, dimension (LDT,N)
-* The upper triangular matrix T. T is modified, but restored
-* on exit.
-*
-* LDT (input) INTEGER
-* The leading dimension of the array T. LDT >= max(1,N).
-*
-* VL (input/output) COMPLEX*16 array, dimension (LDVL,MM)
-* On entry, if SIDE = 'L' or 'B' and HOWMNY = 'B', VL must
-* contain an N-by-N matrix Q (usually the unitary matrix Q of
-* Schur vectors returned by ZHSEQR).
-* On exit, if SIDE = 'L' or 'B', VL contains:
-* if HOWMNY = 'A', the matrix Y of left eigenvectors of T;
-* if HOWMNY = 'B', the matrix Q*Y;
-* if HOWMNY = 'S', the left eigenvectors of T specified by
-* SELECT, stored consecutively in the columns
-* of VL, in the same order as their
-* eigenvalues.
-* Not referenced if SIDE = 'R'.
-*
-* LDVL (input) INTEGER
-* The leading dimension of the array VL. LDVL >= 1, and if
-* SIDE = 'L' or 'B', LDVL >= N.
-*
-* VR (input/output) COMPLEX*16 array, dimension (LDVR,MM)
-* On entry, if SIDE = 'R' or 'B' and HOWMNY = 'B', VR must
-* contain an N-by-N matrix Q (usually the unitary matrix Q of
-* Schur vectors returned by ZHSEQR).
-* On exit, if SIDE = 'R' or 'B', VR contains:
-* if HOWMNY = 'A', the matrix X of right eigenvectors of T;
-* if HOWMNY = 'B', the matrix Q*X;
-* if HOWMNY = 'S', the right eigenvectors of T specified by
-* SELECT, stored consecutively in the columns
-* of VR, in the same order as their
-* eigenvalues.
-* Not referenced if SIDE = 'L'.
-*
-* LDVR (input) INTEGER
-* The leading dimension of the array VR. LDVR >= 1, and if
-* SIDE = 'R' or 'B'; LDVR >= N.
-*
-* MM (input) INTEGER
-* The number of columns in the arrays VL and/or VR. MM >= M.
-*
-* M (output) INTEGER
-* The number of columns in the arrays VL and/or VR actually
-* used to store the eigenvectors. If HOWMNY = 'A' or 'B', M
-* is set to N. Each selected eigenvector occupies one
-* column.
-*
-* WORK (workspace) COMPLEX*16 array, dimension (2*N)
-*
-* RWORK (workspace) DOUBLE PRECISION array, dimension (N)
-*
-* INFO (output) INTEGER
-* = 0: successful exit
-* < 0: if INFO = -i, the i-th argument had an illegal value
-*
-* Further Details
-* ===============
-*
-* The algorithm used in this program is basically backward (forward)
-* substitution, with scaling to make the the code robust against
-* possible overflow.
-*
-* Each eigenvector is normalized so that the element of largest
-* magnitude has magnitude 1; here the magnitude of a complex number
-* (x,y) is taken to be |x| + |y|.
-*
-* =====================================================================
-*
-* .. Parameters ..
- DOUBLE PRECISION ZERO, ONE
- PARAMETER ( ZERO = 0.0D+0, ONE = 1.0D+0 )
- COMPLEX*16 CMZERO, CMONE
- PARAMETER ( CMZERO = ( 0.0D+0, 0.0D+0 ),
- $ CMONE = ( 1.0D+0, 0.0D+0 ) )
-* ..
-* .. Local Scalars ..
- LOGICAL ALLV, BOTHV, LEFTV, OVER, RIGHTV, SOMEV
- INTEGER I, II, IS, J, K, KI
- DOUBLE PRECISION OVFL, REMAX, SCALE, SMIN, SMLNUM, ULP, UNFL
- COMPLEX*16 CDUM
-* ..
-* .. External Functions ..
- LOGICAL LSAME
- INTEGER IZAMAX
- DOUBLE PRECISION DLAMCH, DZASUM
- EXTERNAL LSAME, IZAMAX, DLAMCH, DZASUM
-* ..
-* .. External Subroutines ..
- EXTERNAL XERBLA, ZCOPY, ZDSCAL, ZGEMV, ZLATRS
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC ABS, DBLE, DCMPLX, DCONJG, DIMAG, MAX
-* ..
-* .. Statement Functions ..
- DOUBLE PRECISION CABS1
-* ..
-* .. Statement Function definitions ..
- CABS1( CDUM ) = ABS( DBLE( CDUM ) ) + ABS( DIMAG( CDUM ) )
-* ..
-* .. Executable Statements ..
-*
-* Decode and test the input parameters
-*
- BOTHV = LSAME( SIDE, 'B' )
- RIGHTV = LSAME( SIDE, 'R' ) .OR. BOTHV
- LEFTV = LSAME( SIDE, 'L' ) .OR. BOTHV
-*
- ALLV = LSAME( HOWMNY, 'A' )
- OVER = LSAME( HOWMNY, 'B' )
- SOMEV = LSAME( HOWMNY, 'S' )
-*
-* Set M to the number of columns required to store the selected
-* eigenvectors.
-*
- IF( SOMEV ) THEN
- M = 0
- DO 10 J = 1, N
- IF( SELECT( J ) )
- $ M = M + 1
- 10 CONTINUE
- ELSE
- M = N
- END IF
-*
- INFO = 0
- IF( .NOT.RIGHTV .AND. .NOT.LEFTV ) THEN
- INFO = -1
- ELSE IF( .NOT.ALLV .AND. .NOT.OVER .AND. .NOT.SOMEV ) THEN
- INFO = -2
- ELSE IF( N.LT.0 ) THEN
- INFO = -4
- ELSE IF( LDT.LT.MAX( 1, N ) ) THEN
- INFO = -6
- ELSE IF( LDVL.LT.1 .OR. ( LEFTV .AND. LDVL.LT.N ) ) THEN
- INFO = -8
- ELSE IF( LDVR.LT.1 .OR. ( RIGHTV .AND. LDVR.LT.N ) ) THEN
- INFO = -10
- ELSE IF( MM.LT.M ) THEN
- INFO = -11
- END IF
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'ZTREVC', -INFO )
- RETURN
- END IF
-*
-* Quick return if possible.
-*
- IF( N.EQ.0 )
- $ RETURN
-*
-* Set the constants to control overflow.
-*
- UNFL = DLAMCH( 'Safe minimum' )
- OVFL = ONE / UNFL
- CALL DLABAD( UNFL, OVFL )
- ULP = DLAMCH( 'Precision' )
- SMLNUM = UNFL*( N / ULP )
-*
-* Store the diagonal elements of T in working array WORK.
-*
- DO 20 I = 1, N
- WORK( I+N ) = T( I, I )
- 20 CONTINUE
-*
-* Compute 1-norm of each column of strictly upper triangular
-* part of T to control overflow in triangular solver.
-*
- RWORK( 1 ) = ZERO
- DO 30 J = 2, N
- RWORK( J ) = DZASUM( J-1, T( 1, J ), 1 )
- 30 CONTINUE
-*
- IF( RIGHTV ) THEN
-*
-* Compute right eigenvectors.
-*
- IS = M
- DO 80 KI = N, 1, -1
-*
- IF( SOMEV ) THEN
- IF( .NOT.SELECT( KI ) )
- $ GO TO 80
- END IF
- SMIN = MAX( ULP*( CABS1( T( KI, KI ) ) ), SMLNUM )
-*
- WORK( 1 ) = CMONE
-*
-* Form right-hand side.
-*
- DO 40 K = 1, KI - 1
- WORK( K ) = -T( K, KI )
- 40 CONTINUE
-*
-* Solve the triangular system:
-* (T(1:KI-1,1:KI-1) - T(KI,KI))*X = SCALE*WORK.
-*
- DO 50 K = 1, KI - 1
- T( K, K ) = T( K, K ) - T( KI, KI )
- IF( CABS1( T( K, K ) ).LT.SMIN )
- $ T( K, K ) = SMIN
- 50 CONTINUE
-*
- IF( KI.GT.1 ) THEN
- CALL ZLATRS( 'Upper', 'No transpose', 'Non-unit', 'Y',
- $ KI-1, T, LDT, WORK( 1 ), SCALE, RWORK,
- $ INFO )
- WORK( KI ) = SCALE
- END IF
-*
-* Copy the vector x or Q*x to VR and normalize.
-*
- IF( .NOT.OVER ) THEN
- CALL ZCOPY( KI, WORK( 1 ), 1, VR( 1, IS ), 1 )
-*
- II = IZAMAX( KI, VR( 1, IS ), 1 )
- REMAX = ONE / CABS1( VR( II, IS ) )
- CALL ZDSCAL( KI, REMAX, VR( 1, IS ), 1 )
-*
- DO 60 K = KI + 1, N
- VR( K, IS ) = CMZERO
- 60 CONTINUE
- ELSE
- IF( KI.GT.1 )
- $ CALL ZGEMV( 'N', N, KI-1, CMONE, VR, LDVR, WORK( 1 ),
- $ 1, DCMPLX( SCALE ), VR( 1, KI ), 1 )
-*
- II = IZAMAX( N, VR( 1, KI ), 1 )
- REMAX = ONE / CABS1( VR( II, KI ) )
- CALL ZDSCAL( N, REMAX, VR( 1, KI ), 1 )
- END IF
-*
-* Set back the original diagonal elements of T.
-*
- DO 70 K = 1, KI - 1
- T( K, K ) = WORK( K+N )
- 70 CONTINUE
-*
- IS = IS - 1
- 80 CONTINUE
- END IF
-*
- IF( LEFTV ) THEN
-*
-* Compute left eigenvectors.
-*
- IS = 1
- DO 130 KI = 1, N
-*
- IF( SOMEV ) THEN
- IF( .NOT.SELECT( KI ) )
- $ GO TO 130
- END IF
- SMIN = MAX( ULP*( CABS1( T( KI, KI ) ) ), SMLNUM )
-*
- WORK( N ) = CMONE
-*
-* Form right-hand side.
-*
- DO 90 K = KI + 1, N
- WORK( K ) = -DCONJG( T( KI, K ) )
- 90 CONTINUE
-*
-* Solve the triangular system:
-* (T(KI+1:N,KI+1:N) - T(KI,KI))'*X = SCALE*WORK.
-*
- DO 100 K = KI + 1, N
- T( K, K ) = T( K, K ) - T( KI, KI )
- IF( CABS1( T( K, K ) ).LT.SMIN )
- $ T( K, K ) = SMIN
- 100 CONTINUE
-*
- IF( KI.LT.N ) THEN
- CALL ZLATRS( 'Upper', 'Conjugate transpose', 'Non-unit',
- $ 'Y', N-KI, T( KI+1, KI+1 ), LDT,
- $ WORK( KI+1 ), SCALE, RWORK, INFO )
- WORK( KI ) = SCALE
- END IF
-*
-* Copy the vector x or Q*x to VL and normalize.
-*
- IF( .NOT.OVER ) THEN
- CALL ZCOPY( N-KI+1, WORK( KI ), 1, VL( KI, IS ), 1 )
-*
- II = IZAMAX( N-KI+1, VL( KI, IS ), 1 ) + KI - 1
- REMAX = ONE / CABS1( VL( II, IS ) )
- CALL ZDSCAL( N-KI+1, REMAX, VL( KI, IS ), 1 )
-*
- DO 110 K = 1, KI - 1
- VL( K, IS ) = CMZERO
- 110 CONTINUE
- ELSE
- IF( KI.LT.N )
- $ CALL ZGEMV( 'N', N, N-KI, CMONE, VL( 1, KI+1 ), LDVL,
- $ WORK( KI+1 ), 1, DCMPLX( SCALE ),
- $ VL( 1, KI ), 1 )
-*
- II = IZAMAX( N, VL( 1, KI ), 1 )
- REMAX = ONE / CABS1( VL( II, KI ) )
- CALL ZDSCAL( N, REMAX, VL( 1, KI ), 1 )
- END IF
-*
-* Set back the original diagonal elements of T.
-*
- DO 120 K = KI + 1, N
- T( K, K ) = WORK( K+N )
- 120 CONTINUE
-*
- IS = IS + 1
- 130 CONTINUE
- END IF
-*
- RETURN
-*
-* End of ZTREVC
-*
- END
diff --git a/src/lib/lapack/ztrexc.f b/src/lib/lapack/ztrexc.f
deleted file mode 100644
index 69313696..00000000
--- a/src/lib/lapack/ztrexc.f
+++ /dev/null
@@ -1,162 +0,0 @@
- SUBROUTINE ZTREXC( COMPQ, N, T, LDT, Q, LDQ, IFST, ILST, INFO )
-*
-* -- LAPACK routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- CHARACTER COMPQ
- INTEGER IFST, ILST, INFO, LDQ, LDT, N
-* ..
-* .. Array Arguments ..
- COMPLEX*16 Q( LDQ, * ), T( LDT, * )
-* ..
-*
-* Purpose
-* =======
-*
-* ZTREXC reorders the Schur factorization of a complex matrix
-* A = Q*T*Q**H, so that the diagonal element of T with row index IFST
-* is moved to row ILST.
-*
-* The Schur form T is reordered by a unitary similarity transformation
-* Z**H*T*Z, and optionally the matrix Q of Schur vectors is updated by
-* postmultplying it with Z.
-*
-* Arguments
-* =========
-*
-* COMPQ (input) CHARACTER*1
-* = 'V': update the matrix Q of Schur vectors;
-* = 'N': do not update Q.
-*
-* N (input) INTEGER
-* The order of the matrix T. N >= 0.
-*
-* T (input/output) COMPLEX*16 array, dimension (LDT,N)
-* On entry, the upper triangular matrix T.
-* On exit, the reordered upper triangular matrix.
-*
-* LDT (input) INTEGER
-* The leading dimension of the array T. LDT >= max(1,N).
-*
-* Q (input/output) COMPLEX*16 array, dimension (LDQ,N)
-* On entry, if COMPQ = 'V', the matrix Q of Schur vectors.
-* On exit, if COMPQ = 'V', Q has been postmultiplied by the
-* unitary transformation matrix Z which reorders T.
-* If COMPQ = 'N', Q is not referenced.
-*
-* LDQ (input) INTEGER
-* The leading dimension of the array Q. LDQ >= max(1,N).
-*
-* IFST (input) INTEGER
-* ILST (input) INTEGER
-* Specify the reordering of the diagonal elements of T:
-* The element with row index IFST is moved to row ILST by a
-* sequence of transpositions between adjacent elements.
-* 1 <= IFST <= N; 1 <= ILST <= N.
-*
-* INFO (output) INTEGER
-* = 0: successful exit
-* < 0: if INFO = -i, the i-th argument had an illegal value
-*
-* =====================================================================
-*
-* .. Local Scalars ..
- LOGICAL WANTQ
- INTEGER K, M1, M2, M3
- DOUBLE PRECISION CS
- COMPLEX*16 SN, T11, T22, TEMP
-* ..
-* .. External Functions ..
- LOGICAL LSAME
- EXTERNAL LSAME
-* ..
-* .. External Subroutines ..
- EXTERNAL XERBLA, ZLARTG, ZROT
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC DCONJG, MAX
-* ..
-* .. Executable Statements ..
-*
-* Decode and test the input parameters.
-*
- INFO = 0
- WANTQ = LSAME( COMPQ, 'V' )
- IF( .NOT.LSAME( COMPQ, 'N' ) .AND. .NOT.WANTQ ) THEN
- INFO = -1
- ELSE IF( N.LT.0 ) THEN
- INFO = -2
- ELSE IF( LDT.LT.MAX( 1, N ) ) THEN
- INFO = -4
- ELSE IF( LDQ.LT.1 .OR. ( WANTQ .AND. LDQ.LT.MAX( 1, N ) ) ) THEN
- INFO = -6
- ELSE IF( IFST.LT.1 .OR. IFST.GT.N ) THEN
- INFO = -7
- ELSE IF( ILST.LT.1 .OR. ILST.GT.N ) THEN
- INFO = -8
- END IF
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'ZTREXC', -INFO )
- RETURN
- END IF
-*
-* Quick return if possible
-*
- IF( N.EQ.1 .OR. IFST.EQ.ILST )
- $ RETURN
-*
- IF( IFST.LT.ILST ) THEN
-*
-* Move the IFST-th diagonal element forward down the diagonal.
-*
- M1 = 0
- M2 = -1
- M3 = 1
- ELSE
-*
-* Move the IFST-th diagonal element backward up the diagonal.
-*
- M1 = -1
- M2 = 0
- M3 = -1
- END IF
-*
- DO 10 K = IFST + M1, ILST + M2, M3
-*
-* Interchange the k-th and (k+1)-th diagonal elements.
-*
- T11 = T( K, K )
- T22 = T( K+1, K+1 )
-*
-* Determine the transformation to perform the interchange.
-*
- CALL ZLARTG( T( K, K+1 ), T22-T11, CS, SN, TEMP )
-*
-* Apply transformation to the matrix T.
-*
- IF( K+2.LE.N )
- $ CALL ZROT( N-K-1, T( K, K+2 ), LDT, T( K+1, K+2 ), LDT, CS,
- $ SN )
- CALL ZROT( K-1, T( 1, K ), 1, T( 1, K+1 ), 1, CS,
- $ DCONJG( SN ) )
-*
- T( K, K ) = T22
- T( K+1, K+1 ) = T11
-*
- IF( WANTQ ) THEN
-*
-* Accumulate transformation in the matrix Q.
-*
- CALL ZROT( N, Q( 1, K ), 1, Q( 1, K+1 ), 1, CS,
- $ DCONJG( SN ) )
- END IF
-*
- 10 CONTINUE
-*
- RETURN
-*
-* End of ZTREXC
-*
- END
diff --git a/src/lib/lapack/ztrsen.f b/src/lib/lapack/ztrsen.f
deleted file mode 100644
index a07a22f6..00000000
--- a/src/lib/lapack/ztrsen.f
+++ /dev/null
@@ -1,359 +0,0 @@
- SUBROUTINE ZTRSEN( JOB, COMPQ, SELECT, N, T, LDT, Q, LDQ, W, M, S,
- $ SEP, WORK, LWORK, INFO )
-*
-* -- LAPACK routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* Modified to call ZLACN2 in place of ZLACON, 10 Feb 03, SJH.
-*
-* .. Scalar Arguments ..
- CHARACTER COMPQ, JOB
- INTEGER INFO, LDQ, LDT, LWORK, M, N
- DOUBLE PRECISION S, SEP
-* ..
-* .. Array Arguments ..
- LOGICAL SELECT( * )
- COMPLEX*16 Q( LDQ, * ), T( LDT, * ), W( * ), WORK( * )
-* ..
-*
-* Purpose
-* =======
-*
-* ZTRSEN reorders the Schur factorization of a complex matrix
-* A = Q*T*Q**H, so that a selected cluster of eigenvalues appears in
-* the leading positions on the diagonal of the upper triangular matrix
-* T, and the leading columns of Q form an orthonormal basis of the
-* corresponding right invariant subspace.
-*
-* Optionally the routine computes the reciprocal condition numbers of
-* the cluster of eigenvalues and/or the invariant subspace.
-*
-* Arguments
-* =========
-*
-* JOB (input) CHARACTER*1
-* Specifies whether condition numbers are required for the
-* cluster of eigenvalues (S) or the invariant subspace (SEP):
-* = 'N': none;
-* = 'E': for eigenvalues only (S);
-* = 'V': for invariant subspace only (SEP);
-* = 'B': for both eigenvalues and invariant subspace (S and
-* SEP).
-*
-* COMPQ (input) CHARACTER*1
-* = 'V': update the matrix Q of Schur vectors;
-* = 'N': do not update Q.
-*
-* SELECT (input) LOGICAL array, dimension (N)
-* SELECT specifies the eigenvalues in the selected cluster. To
-* select the j-th eigenvalue, SELECT(j) must be set to .TRUE..
-*
-* N (input) INTEGER
-* The order of the matrix T. N >= 0.
-*
-* T (input/output) COMPLEX*16 array, dimension (LDT,N)
-* On entry, the upper triangular matrix T.
-* On exit, T is overwritten by the reordered matrix T, with the
-* selected eigenvalues as the leading diagonal elements.
-*
-* LDT (input) INTEGER
-* The leading dimension of the array T. LDT >= max(1,N).
-*
-* Q (input/output) COMPLEX*16 array, dimension (LDQ,N)
-* On entry, if COMPQ = 'V', the matrix Q of Schur vectors.
-* On exit, if COMPQ = 'V', Q has been postmultiplied by the
-* unitary transformation matrix which reorders T; the leading M
-* columns of Q form an orthonormal basis for the specified
-* invariant subspace.
-* If COMPQ = 'N', Q is not referenced.
-*
-* LDQ (input) INTEGER
-* The leading dimension of the array Q.
-* LDQ >= 1; and if COMPQ = 'V', LDQ >= N.
-*
-* W (output) COMPLEX*16 array, dimension (N)
-* The reordered eigenvalues of T, in the same order as they
-* appear on the diagonal of T.
-*
-* M (output) INTEGER
-* The dimension of the specified invariant subspace.
-* 0 <= M <= N.
-*
-* S (output) DOUBLE PRECISION
-* If JOB = 'E' or 'B', S is a lower bound on the reciprocal
-* condition number for the selected cluster of eigenvalues.
-* S cannot underestimate the true reciprocal condition number
-* by more than a factor of sqrt(N). If M = 0 or N, S = 1.
-* If JOB = 'N' or 'V', S is not referenced.
-*
-* SEP (output) DOUBLE PRECISION
-* If JOB = 'V' or 'B', SEP is the estimated reciprocal
-* condition number of the specified invariant subspace. If
-* M = 0 or N, SEP = norm(T).
-* If JOB = 'N' or 'E', SEP is not referenced.
-*
-* WORK (workspace/output) COMPLEX*16 array, dimension (MAX(1,LWORK))
-* On exit, if INFO = 0, WORK(1) returns the optimal LWORK.
-*
-* LWORK (input) INTEGER
-* The dimension of the array WORK.
-* If JOB = 'N', LWORK >= 1;
-* if JOB = 'E', LWORK = max(1,M*(N-M));
-* if JOB = 'V' or 'B', LWORK >= max(1,2*M*(N-M)).
-*
-* If LWORK = -1, then a workspace query is assumed; the routine
-* only calculates the optimal size of the WORK array, returns
-* this value as the first entry of the WORK array, and no error
-* message related to LWORK is issued by XERBLA.
-*
-* INFO (output) INTEGER
-* = 0: successful exit
-* < 0: if INFO = -i, the i-th argument had an illegal value
-*
-* Further Details
-* ===============
-*
-* ZTRSEN first collects the selected eigenvalues by computing a unitary
-* transformation Z to move them to the top left corner of T. In other
-* words, the selected eigenvalues are the eigenvalues of T11 in:
-*
-* Z'*T*Z = ( T11 T12 ) n1
-* ( 0 T22 ) n2
-* n1 n2
-*
-* where N = n1+n2 and Z' means the conjugate transpose of Z. The first
-* n1 columns of Z span the specified invariant subspace of T.
-*
-* If T has been obtained from the Schur factorization of a matrix
-* A = Q*T*Q', then the reordered Schur factorization of A is given by
-* A = (Q*Z)*(Z'*T*Z)*(Q*Z)', and the first n1 columns of Q*Z span the
-* corresponding invariant subspace of A.
-*
-* The reciprocal condition number of the average of the eigenvalues of
-* T11 may be returned in S. S lies between 0 (very badly conditioned)
-* and 1 (very well conditioned). It is computed as follows. First we
-* compute R so that
-*
-* P = ( I R ) n1
-* ( 0 0 ) n2
-* n1 n2
-*
-* is the projector on the invariant subspace associated with T11.
-* R is the solution of the Sylvester equation:
-*
-* T11*R - R*T22 = T12.
-*
-* Let F-norm(M) denote the Frobenius-norm of M and 2-norm(M) denote
-* the two-norm of M. Then S is computed as the lower bound
-*
-* (1 + F-norm(R)**2)**(-1/2)
-*
-* on the reciprocal of 2-norm(P), the true reciprocal condition number.
-* S cannot underestimate 1 / 2-norm(P) by more than a factor of
-* sqrt(N).
-*
-* An approximate error bound for the computed average of the
-* eigenvalues of T11 is
-*
-* EPS * norm(T) / S
-*
-* where EPS is the machine precision.
-*
-* The reciprocal condition number of the right invariant subspace
-* spanned by the first n1 columns of Z (or of Q*Z) is returned in SEP.
-* SEP is defined as the separation of T11 and T22:
-*
-* sep( T11, T22 ) = sigma-min( C )
-*
-* where sigma-min(C) is the smallest singular value of the
-* n1*n2-by-n1*n2 matrix
-*
-* C = kprod( I(n2), T11 ) - kprod( transpose(T22), I(n1) )
-*
-* I(m) is an m by m identity matrix, and kprod denotes the Kronecker
-* product. We estimate sigma-min(C) by the reciprocal of an estimate of
-* the 1-norm of inverse(C). The true reciprocal 1-norm of inverse(C)
-* cannot differ from sigma-min(C) by more than a factor of sqrt(n1*n2).
-*
-* When SEP is small, small changes in T can cause large changes in
-* the invariant subspace. An approximate bound on the maximum angular
-* error in the computed right invariant subspace is
-*
-* EPS * norm(T) / SEP
-*
-* =====================================================================
-*
-* .. Parameters ..
- DOUBLE PRECISION ZERO, ONE
- PARAMETER ( ZERO = 0.0D+0, ONE = 1.0D+0 )
-* ..
-* .. Local Scalars ..
- LOGICAL LQUERY, WANTBH, WANTQ, WANTS, WANTSP
- INTEGER IERR, K, KASE, KS, LWMIN, N1, N2, NN
- DOUBLE PRECISION EST, RNORM, SCALE
-* ..
-* .. Local Arrays ..
- INTEGER ISAVE( 3 )
- DOUBLE PRECISION RWORK( 1 )
-* ..
-* .. External Functions ..
- LOGICAL LSAME
- DOUBLE PRECISION ZLANGE
- EXTERNAL LSAME, ZLANGE
-* ..
-* .. External Subroutines ..
- EXTERNAL XERBLA, ZLACN2, ZLACPY, ZTREXC, ZTRSYL
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC MAX, SQRT
-* ..
-* .. Executable Statements ..
-*
-* Decode and test the input parameters.
-*
- WANTBH = LSAME( JOB, 'B' )
- WANTS = LSAME( JOB, 'E' ) .OR. WANTBH
- WANTSP = LSAME( JOB, 'V' ) .OR. WANTBH
- WANTQ = LSAME( COMPQ, 'V' )
-*
-* Set M to the number of selected eigenvalues.
-*
- M = 0
- DO 10 K = 1, N
- IF( SELECT( K ) )
- $ M = M + 1
- 10 CONTINUE
-*
- N1 = M
- N2 = N - M
- NN = N1*N2
-*
- INFO = 0
- LQUERY = ( LWORK.EQ.-1 )
-*
- IF( WANTSP ) THEN
- LWMIN = MAX( 1, 2*NN )
- ELSE IF( LSAME( JOB, 'N' ) ) THEN
- LWMIN = 1
- ELSE IF( LSAME( JOB, 'E' ) ) THEN
- LWMIN = MAX( 1, NN )
- END IF
-*
- IF( .NOT.LSAME( JOB, 'N' ) .AND. .NOT.WANTS .AND. .NOT.WANTSP )
- $ THEN
- INFO = -1
- ELSE IF( .NOT.LSAME( COMPQ, 'N' ) .AND. .NOT.WANTQ ) THEN
- INFO = -2
- ELSE IF( N.LT.0 ) THEN
- INFO = -4
- ELSE IF( LDT.LT.MAX( 1, N ) ) THEN
- INFO = -6
- ELSE IF( LDQ.LT.1 .OR. ( WANTQ .AND. LDQ.LT.N ) ) THEN
- INFO = -8
- ELSE IF( LWORK.LT.LWMIN .AND. .NOT.LQUERY ) THEN
- INFO = -14
- END IF
-*
- IF( INFO.EQ.0 ) THEN
- WORK( 1 ) = LWMIN
- END IF
-*
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'ZTRSEN', -INFO )
- RETURN
- ELSE IF( LQUERY ) THEN
- RETURN
- END IF
-*
-* Quick return if possible
-*
- IF( M.EQ.N .OR. M.EQ.0 ) THEN
- IF( WANTS )
- $ S = ONE
- IF( WANTSP )
- $ SEP = ZLANGE( '1', N, N, T, LDT, RWORK )
- GO TO 40
- END IF
-*
-* Collect the selected eigenvalues at the top left corner of T.
-*
- KS = 0
- DO 20 K = 1, N
- IF( SELECT( K ) ) THEN
- KS = KS + 1
-*
-* Swap the K-th eigenvalue to position KS.
-*
- IF( K.NE.KS )
- $ CALL ZTREXC( COMPQ, N, T, LDT, Q, LDQ, K, KS, IERR )
- END IF
- 20 CONTINUE
-*
- IF( WANTS ) THEN
-*
-* Solve the Sylvester equation for R:
-*
-* T11*R - R*T22 = scale*T12
-*
- CALL ZLACPY( 'F', N1, N2, T( 1, N1+1 ), LDT, WORK, N1 )
- CALL ZTRSYL( 'N', 'N', -1, N1, N2, T, LDT, T( N1+1, N1+1 ),
- $ LDT, WORK, N1, SCALE, IERR )
-*
-* Estimate the reciprocal of the condition number of the cluster
-* of eigenvalues.
-*
- RNORM = ZLANGE( 'F', N1, N2, WORK, N1, RWORK )
- IF( RNORM.EQ.ZERO ) THEN
- S = ONE
- ELSE
- S = SCALE / ( SQRT( SCALE*SCALE / RNORM+RNORM )*
- $ SQRT( RNORM ) )
- END IF
- END IF
-*
- IF( WANTSP ) THEN
-*
-* Estimate sep(T11,T22).
-*
- EST = ZERO
- KASE = 0
- 30 CONTINUE
- CALL ZLACN2( NN, WORK( NN+1 ), WORK, EST, KASE, ISAVE )
- IF( KASE.NE.0 ) THEN
- IF( KASE.EQ.1 ) THEN
-*
-* Solve T11*R - R*T22 = scale*X.
-*
- CALL ZTRSYL( 'N', 'N', -1, N1, N2, T, LDT,
- $ T( N1+1, N1+1 ), LDT, WORK, N1, SCALE,
- $ IERR )
- ELSE
-*
-* Solve T11'*R - R*T22' = scale*X.
-*
- CALL ZTRSYL( 'C', 'C', -1, N1, N2, T, LDT,
- $ T( N1+1, N1+1 ), LDT, WORK, N1, SCALE,
- $ IERR )
- END IF
- GO TO 30
- END IF
-*
- SEP = SCALE / EST
- END IF
-*
- 40 CONTINUE
-*
-* Copy reordered eigenvalues to W.
-*
- DO 50 K = 1, N
- W( K ) = T( K, K )
- 50 CONTINUE
-*
- WORK( 1 ) = LWMIN
-*
- RETURN
-*
-* End of ZTRSEN
-*
- END
diff --git a/src/lib/lapack/ztrsyl.f b/src/lib/lapack/ztrsyl.f
deleted file mode 100644
index d2e0ecc7..00000000
--- a/src/lib/lapack/ztrsyl.f
+++ /dev/null
@@ -1,365 +0,0 @@
- SUBROUTINE ZTRSYL( TRANA, TRANB, ISGN, M, N, A, LDA, B, LDB, C,
- $ LDC, SCALE, INFO )
-*
-* -- LAPACK routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- CHARACTER TRANA, TRANB
- INTEGER INFO, ISGN, LDA, LDB, LDC, M, N
- DOUBLE PRECISION SCALE
-* ..
-* .. Array Arguments ..
- COMPLEX*16 A( LDA, * ), B( LDB, * ), C( LDC, * )
-* ..
-*
-* Purpose
-* =======
-*
-* ZTRSYL solves the complex Sylvester matrix equation:
-*
-* op(A)*X + X*op(B) = scale*C or
-* op(A)*X - X*op(B) = scale*C,
-*
-* where op(A) = A or A**H, and A and B are both upper triangular. A is
-* M-by-M and B is N-by-N; the right hand side C and the solution X are
-* M-by-N; and scale is an output scale factor, set <= 1 to avoid
-* overflow in X.
-*
-* Arguments
-* =========
-*
-* TRANA (input) CHARACTER*1
-* Specifies the option op(A):
-* = 'N': op(A) = A (No transpose)
-* = 'C': op(A) = A**H (Conjugate transpose)
-*
-* TRANB (input) CHARACTER*1
-* Specifies the option op(B):
-* = 'N': op(B) = B (No transpose)
-* = 'C': op(B) = B**H (Conjugate transpose)
-*
-* ISGN (input) INTEGER
-* Specifies the sign in the equation:
-* = +1: solve op(A)*X + X*op(B) = scale*C
-* = -1: solve op(A)*X - X*op(B) = scale*C
-*
-* M (input) INTEGER
-* The order of the matrix A, and the number of rows in the
-* matrices X and C. M >= 0.
-*
-* N (input) INTEGER
-* The order of the matrix B, and the number of columns in the
-* matrices X and C. N >= 0.
-*
-* A (input) COMPLEX*16 array, dimension (LDA,M)
-* The upper triangular matrix A.
-*
-* LDA (input) INTEGER
-* The leading dimension of the array A. LDA >= max(1,M).
-*
-* B (input) COMPLEX*16 array, dimension (LDB,N)
-* The upper triangular matrix B.
-*
-* LDB (input) INTEGER
-* The leading dimension of the array B. LDB >= max(1,N).
-*
-* C (input/output) COMPLEX*16 array, dimension (LDC,N)
-* On entry, the M-by-N right hand side matrix C.
-* On exit, C is overwritten by the solution matrix X.
-*
-* LDC (input) INTEGER
-* The leading dimension of the array C. LDC >= max(1,M)
-*
-* SCALE (output) DOUBLE PRECISION
-* The scale factor, scale, set <= 1 to avoid overflow in X.
-*
-* INFO (output) INTEGER
-* = 0: successful exit
-* < 0: if INFO = -i, the i-th argument had an illegal value
-* = 1: A and B have common or very close eigenvalues; perturbed
-* values were used to solve the equation (but the matrices
-* A and B are unchanged).
-*
-* =====================================================================
-*
-* .. Parameters ..
- DOUBLE PRECISION ONE
- PARAMETER ( ONE = 1.0D+0 )
-* ..
-* .. Local Scalars ..
- LOGICAL NOTRNA, NOTRNB
- INTEGER J, K, L
- DOUBLE PRECISION BIGNUM, DA11, DB, EPS, SCALOC, SGN, SMIN,
- $ SMLNUM
- COMPLEX*16 A11, SUML, SUMR, VEC, X11
-* ..
-* .. Local Arrays ..
- DOUBLE PRECISION DUM( 1 )
-* ..
-* .. External Functions ..
- LOGICAL LSAME
- DOUBLE PRECISION DLAMCH, ZLANGE
- COMPLEX*16 ZDOTC, ZDOTU, ZLADIV
- EXTERNAL LSAME, DLAMCH, ZLANGE, ZDOTC, ZDOTU, ZLADIV
-* ..
-* .. External Subroutines ..
- EXTERNAL DLABAD, XERBLA, ZDSCAL
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC ABS, DBLE, DCMPLX, DCONJG, DIMAG, MAX, MIN
-* ..
-* .. Executable Statements ..
-*
-* Decode and Test input parameters
-*
- NOTRNA = LSAME( TRANA, 'N' )
- NOTRNB = LSAME( TRANB, 'N' )
-*
- INFO = 0
- IF( .NOT.NOTRNA .AND. .NOT.LSAME( TRANA, 'C' ) ) THEN
- INFO = -1
- ELSE IF( .NOT.NOTRNB .AND. .NOT.LSAME( TRANB, 'C' ) ) THEN
- INFO = -2
- ELSE IF( ISGN.NE.1 .AND. ISGN.NE.-1 ) THEN
- INFO = -3
- ELSE IF( M.LT.0 ) THEN
- INFO = -4
- ELSE IF( N.LT.0 ) THEN
- INFO = -5
- ELSE IF( LDA.LT.MAX( 1, M ) ) THEN
- INFO = -7
- ELSE IF( LDB.LT.MAX( 1, N ) ) THEN
- INFO = -9
- ELSE IF( LDC.LT.MAX( 1, M ) ) THEN
- INFO = -11
- END IF
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'ZTRSYL', -INFO )
- RETURN
- END IF
-*
-* Quick return if possible
-*
- IF( M.EQ.0 .OR. N.EQ.0 )
- $ RETURN
-*
-* Set constants to control overflow
-*
- EPS = DLAMCH( 'P' )
- SMLNUM = DLAMCH( 'S' )
- BIGNUM = ONE / SMLNUM
- CALL DLABAD( SMLNUM, BIGNUM )
- SMLNUM = SMLNUM*DBLE( M*N ) / EPS
- BIGNUM = ONE / SMLNUM
- SMIN = MAX( SMLNUM, EPS*ZLANGE( 'M', M, M, A, LDA, DUM ),
- $ EPS*ZLANGE( 'M', N, N, B, LDB, DUM ) )
- SCALE = ONE
- SGN = ISGN
-*
- IF( NOTRNA .AND. NOTRNB ) THEN
-*
-* Solve A*X + ISGN*X*B = scale*C.
-*
-* The (K,L)th block of X is determined starting from
-* bottom-left corner column by column by
-*
-* A(K,K)*X(K,L) + ISGN*X(K,L)*B(L,L) = C(K,L) - R(K,L)
-*
-* Where
-* M L-1
-* R(K,L) = SUM [A(K,I)*X(I,L)] +ISGN*SUM [X(K,J)*B(J,L)].
-* I=K+1 J=1
-*
- DO 30 L = 1, N
- DO 20 K = M, 1, -1
-*
- SUML = ZDOTU( M-K, A( K, MIN( K+1, M ) ), LDA,
- $ C( MIN( K+1, M ), L ), 1 )
- SUMR = ZDOTU( L-1, C( K, 1 ), LDC, B( 1, L ), 1 )
- VEC = C( K, L ) - ( SUML+SGN*SUMR )
-*
- SCALOC = ONE
- A11 = A( K, K ) + SGN*B( L, L )
- DA11 = ABS( DBLE( A11 ) ) + ABS( DIMAG( A11 ) )
- IF( DA11.LE.SMIN ) THEN
- A11 = SMIN
- DA11 = SMIN
- INFO = 1
- END IF
- DB = ABS( DBLE( VEC ) ) + ABS( DIMAG( VEC ) )
- IF( DA11.LT.ONE .AND. DB.GT.ONE ) THEN
- IF( DB.GT.BIGNUM*DA11 )
- $ SCALOC = ONE / DB
- END IF
- X11 = ZLADIV( VEC*DCMPLX( SCALOC ), A11 )
-*
- IF( SCALOC.NE.ONE ) THEN
- DO 10 J = 1, N
- CALL ZDSCAL( M, SCALOC, C( 1, J ), 1 )
- 10 CONTINUE
- SCALE = SCALE*SCALOC
- END IF
- C( K, L ) = X11
-*
- 20 CONTINUE
- 30 CONTINUE
-*
- ELSE IF( .NOT.NOTRNA .AND. NOTRNB ) THEN
-*
-* Solve A' *X + ISGN*X*B = scale*C.
-*
-* The (K,L)th block of X is determined starting from
-* upper-left corner column by column by
-*
-* A'(K,K)*X(K,L) + ISGN*X(K,L)*B(L,L) = C(K,L) - R(K,L)
-*
-* Where
-* K-1 L-1
-* R(K,L) = SUM [A'(I,K)*X(I,L)] + ISGN*SUM [X(K,J)*B(J,L)]
-* I=1 J=1
-*
- DO 60 L = 1, N
- DO 50 K = 1, M
-*
- SUML = ZDOTC( K-1, A( 1, K ), 1, C( 1, L ), 1 )
- SUMR = ZDOTU( L-1, C( K, 1 ), LDC, B( 1, L ), 1 )
- VEC = C( K, L ) - ( SUML+SGN*SUMR )
-*
- SCALOC = ONE
- A11 = DCONJG( A( K, K ) ) + SGN*B( L, L )
- DA11 = ABS( DBLE( A11 ) ) + ABS( DIMAG( A11 ) )
- IF( DA11.LE.SMIN ) THEN
- A11 = SMIN
- DA11 = SMIN
- INFO = 1
- END IF
- DB = ABS( DBLE( VEC ) ) + ABS( DIMAG( VEC ) )
- IF( DA11.LT.ONE .AND. DB.GT.ONE ) THEN
- IF( DB.GT.BIGNUM*DA11 )
- $ SCALOC = ONE / DB
- END IF
-*
- X11 = ZLADIV( VEC*DCMPLX( SCALOC ), A11 )
-*
- IF( SCALOC.NE.ONE ) THEN
- DO 40 J = 1, N
- CALL ZDSCAL( M, SCALOC, C( 1, J ), 1 )
- 40 CONTINUE
- SCALE = SCALE*SCALOC
- END IF
- C( K, L ) = X11
-*
- 50 CONTINUE
- 60 CONTINUE
-*
- ELSE IF( .NOT.NOTRNA .AND. .NOT.NOTRNB ) THEN
-*
-* Solve A'*X + ISGN*X*B' = C.
-*
-* The (K,L)th block of X is determined starting from
-* upper-right corner column by column by
-*
-* A'(K,K)*X(K,L) + ISGN*X(K,L)*B'(L,L) = C(K,L) - R(K,L)
-*
-* Where
-* K-1
-* R(K,L) = SUM [A'(I,K)*X(I,L)] +
-* I=1
-* N
-* ISGN*SUM [X(K,J)*B'(L,J)].
-* J=L+1
-*
- DO 90 L = N, 1, -1
- DO 80 K = 1, M
-*
- SUML = ZDOTC( K-1, A( 1, K ), 1, C( 1, L ), 1 )
- SUMR = ZDOTC( N-L, C( K, MIN( L+1, N ) ), LDC,
- $ B( L, MIN( L+1, N ) ), LDB )
- VEC = C( K, L ) - ( SUML+SGN*DCONJG( SUMR ) )
-*
- SCALOC = ONE
- A11 = DCONJG( A( K, K )+SGN*B( L, L ) )
- DA11 = ABS( DBLE( A11 ) ) + ABS( DIMAG( A11 ) )
- IF( DA11.LE.SMIN ) THEN
- A11 = SMIN
- DA11 = SMIN
- INFO = 1
- END IF
- DB = ABS( DBLE( VEC ) ) + ABS( DIMAG( VEC ) )
- IF( DA11.LT.ONE .AND. DB.GT.ONE ) THEN
- IF( DB.GT.BIGNUM*DA11 )
- $ SCALOC = ONE / DB
- END IF
-*
- X11 = ZLADIV( VEC*DCMPLX( SCALOC ), A11 )
-*
- IF( SCALOC.NE.ONE ) THEN
- DO 70 J = 1, N
- CALL ZDSCAL( M, SCALOC, C( 1, J ), 1 )
- 70 CONTINUE
- SCALE = SCALE*SCALOC
- END IF
- C( K, L ) = X11
-*
- 80 CONTINUE
- 90 CONTINUE
-*
- ELSE IF( NOTRNA .AND. .NOT.NOTRNB ) THEN
-*
-* Solve A*X + ISGN*X*B' = C.
-*
-* The (K,L)th block of X is determined starting from
-* bottom-left corner column by column by
-*
-* A(K,K)*X(K,L) + ISGN*X(K,L)*B'(L,L) = C(K,L) - R(K,L)
-*
-* Where
-* M N
-* R(K,L) = SUM [A(K,I)*X(I,L)] + ISGN*SUM [X(K,J)*B'(L,J)]
-* I=K+1 J=L+1
-*
- DO 120 L = N, 1, -1
- DO 110 K = M, 1, -1
-*
- SUML = ZDOTU( M-K, A( K, MIN( K+1, M ) ), LDA,
- $ C( MIN( K+1, M ), L ), 1 )
- SUMR = ZDOTC( N-L, C( K, MIN( L+1, N ) ), LDC,
- $ B( L, MIN( L+1, N ) ), LDB )
- VEC = C( K, L ) - ( SUML+SGN*DCONJG( SUMR ) )
-*
- SCALOC = ONE
- A11 = A( K, K ) + SGN*DCONJG( B( L, L ) )
- DA11 = ABS( DBLE( A11 ) ) + ABS( DIMAG( A11 ) )
- IF( DA11.LE.SMIN ) THEN
- A11 = SMIN
- DA11 = SMIN
- INFO = 1
- END IF
- DB = ABS( DBLE( VEC ) ) + ABS( DIMAG( VEC ) )
- IF( DA11.LT.ONE .AND. DB.GT.ONE ) THEN
- IF( DB.GT.BIGNUM*DA11 )
- $ SCALOC = ONE / DB
- END IF
-*
- X11 = ZLADIV( VEC*DCMPLX( SCALOC ), A11 )
-*
- IF( SCALOC.NE.ONE ) THEN
- DO 100 J = 1, N
- CALL ZDSCAL( M, SCALOC, C( 1, J ), 1 )
- 100 CONTINUE
- SCALE = SCALE*SCALOC
- END IF
- C( K, L ) = X11
-*
- 110 CONTINUE
- 120 CONTINUE
-*
- END IF
-*
- RETURN
-*
-* End of ZTRSYL
-*
- END
diff --git a/src/lib/lapack/ztrti2.f b/src/lib/lapack/ztrti2.f
deleted file mode 100644
index 73c7bbc3..00000000
--- a/src/lib/lapack/ztrti2.f
+++ /dev/null
@@ -1,146 +0,0 @@
- SUBROUTINE ZTRTI2( UPLO, DIAG, N, A, LDA, INFO )
-*
-* -- LAPACK routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- CHARACTER DIAG, UPLO
- INTEGER INFO, LDA, N
-* ..
-* .. Array Arguments ..
- COMPLEX*16 A( LDA, * )
-* ..
-*
-* Purpose
-* =======
-*
-* ZTRTI2 computes the inverse of a complex upper or lower triangular
-* matrix.
-*
-* This is the Level 2 BLAS version of the algorithm.
-*
-* Arguments
-* =========
-*
-* UPLO (input) CHARACTER*1
-* Specifies whether the matrix A is upper or lower triangular.
-* = 'U': Upper triangular
-* = 'L': Lower triangular
-*
-* DIAG (input) CHARACTER*1
-* Specifies whether or not the matrix A is unit triangular.
-* = 'N': Non-unit triangular
-* = 'U': Unit triangular
-*
-* N (input) INTEGER
-* The order of the matrix A. N >= 0.
-*
-* A (input/output) COMPLEX*16 array, dimension (LDA,N)
-* On entry, the triangular matrix A. If UPLO = 'U', the
-* leading n by n upper triangular part of the array A contains
-* the upper triangular matrix, and the strictly lower
-* triangular part of A is not referenced. If UPLO = 'L', the
-* leading n by n lower triangular part of the array A contains
-* the lower triangular matrix, and the strictly upper
-* triangular part of A is not referenced. If DIAG = 'U', the
-* diagonal elements of A are also not referenced and are
-* assumed to be 1.
-*
-* On exit, the (triangular) inverse of the original matrix, in
-* the same storage format.
-*
-* LDA (input) INTEGER
-* The leading dimension of the array A. LDA >= max(1,N).
-*
-* INFO (output) INTEGER
-* = 0: successful exit
-* < 0: if INFO = -k, the k-th argument had an illegal value
-*
-* =====================================================================
-*
-* .. Parameters ..
- COMPLEX*16 ONE
- PARAMETER ( ONE = ( 1.0D+0, 0.0D+0 ) )
-* ..
-* .. Local Scalars ..
- LOGICAL NOUNIT, UPPER
- INTEGER J
- COMPLEX*16 AJJ
-* ..
-* .. External Functions ..
- LOGICAL LSAME
- EXTERNAL LSAME
-* ..
-* .. External Subroutines ..
- EXTERNAL XERBLA, ZSCAL, ZTRMV
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC MAX
-* ..
-* .. Executable Statements ..
-*
-* Test the input parameters.
-*
- INFO = 0
- UPPER = LSAME( UPLO, 'U' )
- NOUNIT = LSAME( DIAG, 'N' )
- IF( .NOT.UPPER .AND. .NOT.LSAME( UPLO, 'L' ) ) THEN
- INFO = -1
- ELSE IF( .NOT.NOUNIT .AND. .NOT.LSAME( DIAG, 'U' ) ) THEN
- INFO = -2
- ELSE IF( N.LT.0 ) THEN
- INFO = -3
- ELSE IF( LDA.LT.MAX( 1, N ) ) THEN
- INFO = -5
- END IF
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'ZTRTI2', -INFO )
- RETURN
- END IF
-*
- IF( UPPER ) THEN
-*
-* Compute inverse of upper triangular matrix.
-*
- DO 10 J = 1, N
- IF( NOUNIT ) THEN
- A( J, J ) = ONE / A( J, J )
- AJJ = -A( J, J )
- ELSE
- AJJ = -ONE
- END IF
-*
-* Compute elements 1:j-1 of j-th column.
-*
- CALL ZTRMV( 'Upper', 'No transpose', DIAG, J-1, A, LDA,
- $ A( 1, J ), 1 )
- CALL ZSCAL( J-1, AJJ, A( 1, J ), 1 )
- 10 CONTINUE
- ELSE
-*
-* Compute inverse of lower triangular matrix.
-*
- DO 20 J = N, 1, -1
- IF( NOUNIT ) THEN
- A( J, J ) = ONE / A( J, J )
- AJJ = -A( J, J )
- ELSE
- AJJ = -ONE
- END IF
- IF( J.LT.N ) THEN
-*
-* Compute elements j+1:n of j-th column.
-*
- CALL ZTRMV( 'Lower', 'No transpose', DIAG, N-J,
- $ A( J+1, J+1 ), LDA, A( J+1, J ), 1 )
- CALL ZSCAL( N-J, AJJ, A( J+1, J ), 1 )
- END IF
- 20 CONTINUE
- END IF
-*
- RETURN
-*
-* End of ZTRTI2
-*
- END
diff --git a/src/lib/lapack/ztrtri.f b/src/lib/lapack/ztrtri.f
deleted file mode 100644
index 7caa9771..00000000
--- a/src/lib/lapack/ztrtri.f
+++ /dev/null
@@ -1,177 +0,0 @@
- SUBROUTINE ZTRTRI( UPLO, DIAG, N, A, LDA, INFO )
-*
-* -- LAPACK routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- CHARACTER DIAG, UPLO
- INTEGER INFO, LDA, N
-* ..
-* .. Array Arguments ..
- COMPLEX*16 A( LDA, * )
-* ..
-*
-* Purpose
-* =======
-*
-* ZTRTRI computes the inverse of a complex upper or lower triangular
-* matrix A.
-*
-* This is the Level 3 BLAS version of the algorithm.
-*
-* Arguments
-* =========
-*
-* UPLO (input) CHARACTER*1
-* = 'U': A is upper triangular;
-* = 'L': A is lower triangular.
-*
-* DIAG (input) CHARACTER*1
-* = 'N': A is non-unit triangular;
-* = 'U': A is unit triangular.
-*
-* N (input) INTEGER
-* The order of the matrix A. N >= 0.
-*
-* A (input/output) COMPLEX*16 array, dimension (LDA,N)
-* On entry, the triangular matrix A. If UPLO = 'U', the
-* leading N-by-N upper triangular part of the array A contains
-* the upper triangular matrix, and the strictly lower
-* triangular part of A is not referenced. If UPLO = 'L', the
-* leading N-by-N lower triangular part of the array A contains
-* the lower triangular matrix, and the strictly upper
-* triangular part of A is not referenced. If DIAG = 'U', the
-* diagonal elements of A are also not referenced and are
-* assumed to be 1.
-* On exit, the (triangular) inverse of the original matrix, in
-* the same storage format.
-*
-* LDA (input) INTEGER
-* The leading dimension of the array A. LDA >= max(1,N).
-*
-* INFO (output) INTEGER
-* = 0: successful exit
-* < 0: if INFO = -i, the i-th argument had an illegal value
-* > 0: if INFO = i, A(i,i) is exactly zero. The triangular
-* matrix is singular and its inverse can not be computed.
-*
-* =====================================================================
-*
-* .. Parameters ..
- COMPLEX*16 ONE, ZERO
- PARAMETER ( ONE = ( 1.0D+0, 0.0D+0 ),
- $ ZERO = ( 0.0D+0, 0.0D+0 ) )
-* ..
-* .. Local Scalars ..
- LOGICAL NOUNIT, UPPER
- INTEGER J, JB, NB, NN
-* ..
-* .. External Functions ..
- LOGICAL LSAME
- INTEGER ILAENV
- EXTERNAL LSAME, ILAENV
-* ..
-* .. External Subroutines ..
- EXTERNAL XERBLA, ZTRMM, ZTRSM, ZTRTI2
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC MAX, MIN
-* ..
-* .. Executable Statements ..
-*
-* Test the input parameters.
-*
- INFO = 0
- UPPER = LSAME( UPLO, 'U' )
- NOUNIT = LSAME( DIAG, 'N' )
- IF( .NOT.UPPER .AND. .NOT.LSAME( UPLO, 'L' ) ) THEN
- INFO = -1
- ELSE IF( .NOT.NOUNIT .AND. .NOT.LSAME( DIAG, 'U' ) ) THEN
- INFO = -2
- ELSE IF( N.LT.0 ) THEN
- INFO = -3
- ELSE IF( LDA.LT.MAX( 1, N ) ) THEN
- INFO = -5
- END IF
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'ZTRTRI', -INFO )
- RETURN
- END IF
-*
-* Quick return if possible
-*
- IF( N.EQ.0 )
- $ RETURN
-*
-* Check for singularity if non-unit.
-*
- IF( NOUNIT ) THEN
- DO 10 INFO = 1, N
- IF( A( INFO, INFO ).EQ.ZERO )
- $ RETURN
- 10 CONTINUE
- INFO = 0
- END IF
-*
-* Determine the block size for this environment.
-*
- NB = ILAENV( 1, 'ZTRTRI', UPLO // DIAG, N, -1, -1, -1 )
- IF( NB.LE.1 .OR. NB.GE.N ) THEN
-*
-* Use unblocked code
-*
- CALL ZTRTI2( UPLO, DIAG, N, A, LDA, INFO )
- ELSE
-*
-* Use blocked code
-*
- IF( UPPER ) THEN
-*
-* Compute inverse of upper triangular matrix
-*
- DO 20 J = 1, N, NB
- JB = MIN( NB, N-J+1 )
-*
-* Compute rows 1:j-1 of current block column
-*
- CALL ZTRMM( 'Left', 'Upper', 'No transpose', DIAG, J-1,
- $ JB, ONE, A, LDA, A( 1, J ), LDA )
- CALL ZTRSM( 'Right', 'Upper', 'No transpose', DIAG, J-1,
- $ JB, -ONE, A( J, J ), LDA, A( 1, J ), LDA )
-*
-* Compute inverse of current diagonal block
-*
- CALL ZTRTI2( 'Upper', DIAG, JB, A( J, J ), LDA, INFO )
- 20 CONTINUE
- ELSE
-*
-* Compute inverse of lower triangular matrix
-*
- NN = ( ( N-1 ) / NB )*NB + 1
- DO 30 J = NN, 1, -NB
- JB = MIN( NB, N-J+1 )
- IF( J+JB.LE.N ) THEN
-*
-* Compute rows j+jb:n of current block column
-*
- CALL ZTRMM( 'Left', 'Lower', 'No transpose', DIAG,
- $ N-J-JB+1, JB, ONE, A( J+JB, J+JB ), LDA,
- $ A( J+JB, J ), LDA )
- CALL ZTRSM( 'Right', 'Lower', 'No transpose', DIAG,
- $ N-J-JB+1, JB, -ONE, A( J, J ), LDA,
- $ A( J+JB, J ), LDA )
- END IF
-*
-* Compute inverse of current diagonal block
-*
- CALL ZTRTI2( 'Lower', DIAG, JB, A( J, J ), LDA, INFO )
- 30 CONTINUE
- END IF
- END IF
-*
- RETURN
-*
-* End of ZTRTRI
-*
- END
diff --git a/src/lib/lapack/ztzrzf.f b/src/lib/lapack/ztzrzf.f
deleted file mode 100644
index 5c9c6543..00000000
--- a/src/lib/lapack/ztzrzf.f
+++ /dev/null
@@ -1,244 +0,0 @@
- SUBROUTINE ZTZRZF( M, N, A, LDA, TAU, WORK, LWORK, INFO )
-*
-* -- LAPACK routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- INTEGER INFO, LDA, LWORK, M, N
-* ..
-* .. Array Arguments ..
- COMPLEX*16 A( LDA, * ), TAU( * ), WORK( * )
-* ..
-*
-* Purpose
-* =======
-*
-* ZTZRZF reduces the M-by-N ( M<=N ) complex upper trapezoidal matrix A
-* to upper triangular form by means of unitary transformations.
-*
-* The upper trapezoidal matrix A is factored as
-*
-* A = ( R 0 ) * Z,
-*
-* where Z is an N-by-N unitary matrix and R is an M-by-M upper
-* triangular matrix.
-*
-* Arguments
-* =========
-*
-* M (input) INTEGER
-* The number of rows of the matrix A. M >= 0.
-*
-* N (input) INTEGER
-* The number of columns of the matrix A. N >= M.
-*
-* A (input/output) COMPLEX*16 array, dimension (LDA,N)
-* On entry, the leading M-by-N upper trapezoidal part of the
-* array A must contain the matrix to be factorized.
-* On exit, the leading M-by-M upper triangular part of A
-* contains the upper triangular matrix R, and elements M+1 to
-* N of the first M rows of A, with the array TAU, represent the
-* unitary matrix Z as a product of M elementary reflectors.
-*
-* LDA (input) INTEGER
-* The leading dimension of the array A. LDA >= max(1,M).
-*
-* TAU (output) COMPLEX*16 array, dimension (M)
-* The scalar factors of the elementary reflectors.
-*
-* WORK (workspace/output) COMPLEX*16 array, dimension (MAX(1,LWORK))
-* On exit, if INFO = 0, WORK(1) returns the optimal LWORK.
-*
-* LWORK (input) INTEGER
-* The dimension of the array WORK. LWORK >= max(1,M).
-* For optimum performance LWORK >= M*NB, where NB is
-* the optimal blocksize.
-*
-* If LWORK = -1, then a workspace query is assumed; the routine
-* only calculates the optimal size of the WORK array, returns
-* this value as the first entry of the WORK array, and no error
-* message related to LWORK is issued by XERBLA.
-*
-* INFO (output) INTEGER
-* = 0: successful exit
-* < 0: if INFO = -i, the i-th argument had an illegal value
-*
-* Further Details
-* ===============
-*
-* Based on contributions by
-* A. Petitet, Computer Science Dept., Univ. of Tenn., Knoxville, USA
-*
-* The factorization is obtained by Householder's method. The kth
-* transformation matrix, Z( k ), which is used to introduce zeros into
-* the ( m - k + 1 )th row of A, is given in the form
-*
-* Z( k ) = ( I 0 ),
-* ( 0 T( k ) )
-*
-* where
-*
-* T( k ) = I - tau*u( k )*u( k )', u( k ) = ( 1 ),
-* ( 0 )
-* ( z( k ) )
-*
-* tau is a scalar and z( k ) is an ( n - m ) element vector.
-* tau and z( k ) are chosen to annihilate the elements of the kth row
-* of X.
-*
-* The scalar tau is returned in the kth element of TAU and the vector
-* u( k ) in the kth row of A, such that the elements of z( k ) are
-* in a( k, m + 1 ), ..., a( k, n ). The elements of R are returned in
-* the upper triangular part of A.
-*
-* Z is given by
-*
-* Z = Z( 1 ) * Z( 2 ) * ... * Z( m ).
-*
-* =====================================================================
-*
-* .. Parameters ..
- COMPLEX*16 ZERO
- PARAMETER ( ZERO = ( 0.0D+0, 0.0D+0 ) )
-* ..
-* .. Local Scalars ..
- LOGICAL LQUERY
- INTEGER I, IB, IWS, KI, KK, LDWORK, LWKOPT, M1, MU, NB,
- $ NBMIN, NX
-* ..
-* .. External Subroutines ..
- EXTERNAL XERBLA, ZLARZB, ZLARZT, ZLATRZ
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC MAX, MIN
-* ..
-* .. External Functions ..
- INTEGER ILAENV
- EXTERNAL ILAENV
-* ..
-* .. Executable Statements ..
-*
-* Test the input arguments
-*
- INFO = 0
- LQUERY = ( LWORK.EQ.-1 )
- IF( M.LT.0 ) THEN
- INFO = -1
- ELSE IF( N.LT.M ) THEN
- INFO = -2
- ELSE IF( LDA.LT.MAX( 1, M ) ) THEN
- INFO = -4
- END IF
-*
- IF( INFO.EQ.0 ) THEN
- IF( M.EQ.0 .OR. M.EQ.N ) THEN
- LWKOPT = 1
- ELSE
-*
-* Determine the block size.
-*
- NB = ILAENV( 1, 'ZGERQF', ' ', M, N, -1, -1 )
- LWKOPT = M*NB
- END IF
- WORK( 1 ) = LWKOPT
-*
- IF( LWORK.LT.MAX( 1, M ) .AND. .NOT.LQUERY ) THEN
- INFO = -7
- END IF
- END IF
-*
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'ZTZRZF', -INFO )
- RETURN
- ELSE IF( LQUERY ) THEN
- RETURN
- END IF
-*
-* Quick return if possible
-*
- IF( M.EQ.0 ) THEN
- RETURN
- ELSE IF( M.EQ.N ) THEN
- DO 10 I = 1, N
- TAU( I ) = ZERO
- 10 CONTINUE
- RETURN
- END IF
-*
- NBMIN = 2
- NX = 1
- IWS = M
- IF( NB.GT.1 .AND. NB.LT.M ) THEN
-*
-* Determine when to cross over from blocked to unblocked code.
-*
- NX = MAX( 0, ILAENV( 3, 'ZGERQF', ' ', M, N, -1, -1 ) )
- IF( NX.LT.M ) THEN
-*
-* Determine if workspace is large enough for blocked code.
-*
- LDWORK = M
- IWS = LDWORK*NB
- IF( LWORK.LT.IWS ) THEN
-*
-* Not enough workspace to use optimal NB: reduce NB and
-* determine the minimum value of NB.
-*
- NB = LWORK / LDWORK
- NBMIN = MAX( 2, ILAENV( 2, 'ZGERQF', ' ', M, N, -1,
- $ -1 ) )
- END IF
- END IF
- END IF
-*
- IF( NB.GE.NBMIN .AND. NB.LT.M .AND. NX.LT.M ) THEN
-*
-* Use blocked code initially.
-* The last kk rows are handled by the block method.
-*
- M1 = MIN( M+1, N )
- KI = ( ( M-NX-1 ) / NB )*NB
- KK = MIN( M, KI+NB )
-*
- DO 20 I = M - KK + KI + 1, M - KK + 1, -NB
- IB = MIN( M-I+1, NB )
-*
-* Compute the TZ factorization of the current block
-* A(i:i+ib-1,i:n)
-*
- CALL ZLATRZ( IB, N-I+1, N-M, A( I, I ), LDA, TAU( I ),
- $ WORK )
- IF( I.GT.1 ) THEN
-*
-* Form the triangular factor of the block reflector
-* H = H(i+ib-1) . . . H(i+1) H(i)
-*
- CALL ZLARZT( 'Backward', 'Rowwise', N-M, IB, A( I, M1 ),
- $ LDA, TAU( I ), WORK, LDWORK )
-*
-* Apply H to A(1:i-1,i:n) from the right
-*
- CALL ZLARZB( 'Right', 'No transpose', 'Backward',
- $ 'Rowwise', I-1, N-I+1, IB, N-M, A( I, M1 ),
- $ LDA, WORK, LDWORK, A( 1, I ), LDA,
- $ WORK( IB+1 ), LDWORK )
- END IF
- 20 CONTINUE
- MU = I + NB - 1
- ELSE
- MU = M
- END IF
-*
-* Use unblocked code to factor the last or only block
-*
- IF( MU.GT.0 )
- $ CALL ZLATRZ( MU, N, N-M, A, LDA, TAU, WORK )
-*
- WORK( 1 ) = LWKOPT
-*
- RETURN
-*
-* End of ZTZRZF
-*
- END
diff --git a/src/lib/lapack/zung2l.f b/src/lib/lapack/zung2l.f
deleted file mode 100644
index 29178b90..00000000
--- a/src/lib/lapack/zung2l.f
+++ /dev/null
@@ -1,128 +0,0 @@
- SUBROUTINE ZUNG2L( M, N, K, A, LDA, TAU, WORK, INFO )
-*
-* -- LAPACK routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- INTEGER INFO, K, LDA, M, N
-* ..
-* .. Array Arguments ..
- COMPLEX*16 A( LDA, * ), TAU( * ), WORK( * )
-* ..
-*
-* Purpose
-* =======
-*
-* ZUNG2L generates an m by n complex matrix Q with orthonormal columns,
-* which is defined as the last n columns of a product of k elementary
-* reflectors of order m
-*
-* Q = H(k) . . . H(2) H(1)
-*
-* as returned by ZGEQLF.
-*
-* Arguments
-* =========
-*
-* M (input) INTEGER
-* The number of rows of the matrix Q. M >= 0.
-*
-* N (input) INTEGER
-* The number of columns of the matrix Q. M >= N >= 0.
-*
-* K (input) INTEGER
-* The number of elementary reflectors whose product defines the
-* matrix Q. N >= K >= 0.
-*
-* A (input/output) COMPLEX*16 array, dimension (LDA,N)
-* On entry, the (n-k+i)-th column must contain the vector which
-* defines the elementary reflector H(i), for i = 1,2,...,k, as
-* returned by ZGEQLF in the last k columns of its array
-* argument A.
-* On exit, the m-by-n matrix Q.
-*
-* LDA (input) INTEGER
-* The first dimension of the array A. LDA >= max(1,M).
-*
-* TAU (input) COMPLEX*16 array, dimension (K)
-* TAU(i) must contain the scalar factor of the elementary
-* reflector H(i), as returned by ZGEQLF.
-*
-* WORK (workspace) COMPLEX*16 array, dimension (N)
-*
-* INFO (output) INTEGER
-* = 0: successful exit
-* < 0: if INFO = -i, the i-th argument has an illegal value
-*
-* =====================================================================
-*
-* .. Parameters ..
- COMPLEX*16 ONE, ZERO
- PARAMETER ( ONE = ( 1.0D+0, 0.0D+0 ),
- $ ZERO = ( 0.0D+0, 0.0D+0 ) )
-* ..
-* .. Local Scalars ..
- INTEGER I, II, J, L
-* ..
-* .. External Subroutines ..
- EXTERNAL XERBLA, ZLARF, ZSCAL
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC MAX
-* ..
-* .. Executable Statements ..
-*
-* Test the input arguments
-*
- INFO = 0
- IF( M.LT.0 ) THEN
- INFO = -1
- ELSE IF( N.LT.0 .OR. N.GT.M ) THEN
- INFO = -2
- ELSE IF( K.LT.0 .OR. K.GT.N ) THEN
- INFO = -3
- ELSE IF( LDA.LT.MAX( 1, M ) ) THEN
- INFO = -5
- END IF
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'ZUNG2L', -INFO )
- RETURN
- END IF
-*
-* Quick return if possible
-*
- IF( N.LE.0 )
- $ RETURN
-*
-* Initialise columns 1:n-k to columns of the unit matrix
-*
- DO 20 J = 1, N - K
- DO 10 L = 1, M
- A( L, J ) = ZERO
- 10 CONTINUE
- A( M-N+J, J ) = ONE
- 20 CONTINUE
-*
- DO 40 I = 1, K
- II = N - K + I
-*
-* Apply H(i) to A(1:m-k+i,1:n-k+i) from the left
-*
- A( M-N+II, II ) = ONE
- CALL ZLARF( 'Left', M-N+II, II-1, A( 1, II ), 1, TAU( I ), A,
- $ LDA, WORK )
- CALL ZSCAL( M-N+II-1, -TAU( I ), A( 1, II ), 1 )
- A( M-N+II, II ) = ONE - TAU( I )
-*
-* Set A(m-k+i+1:m,n-k+i) to zero
-*
- DO 30 L = M - N + II + 1, M
- A( L, II ) = ZERO
- 30 CONTINUE
- 40 CONTINUE
- RETURN
-*
-* End of ZUNG2L
-*
- END
diff --git a/src/lib/lapack/zung2r.f b/src/lib/lapack/zung2r.f
deleted file mode 100644
index cd89f26e..00000000
--- a/src/lib/lapack/zung2r.f
+++ /dev/null
@@ -1,130 +0,0 @@
- SUBROUTINE ZUNG2R( M, N, K, A, LDA, TAU, WORK, INFO )
-*
-* -- LAPACK routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- INTEGER INFO, K, LDA, M, N
-* ..
-* .. Array Arguments ..
- COMPLEX*16 A( LDA, * ), TAU( * ), WORK( * )
-* ..
-*
-* Purpose
-* =======
-*
-* ZUNG2R generates an m by n complex matrix Q with orthonormal columns,
-* which is defined as the first n columns of a product of k elementary
-* reflectors of order m
-*
-* Q = H(1) H(2) . . . H(k)
-*
-* as returned by ZGEQRF.
-*
-* Arguments
-* =========
-*
-* M (input) INTEGER
-* The number of rows of the matrix Q. M >= 0.
-*
-* N (input) INTEGER
-* The number of columns of the matrix Q. M >= N >= 0.
-*
-* K (input) INTEGER
-* The number of elementary reflectors whose product defines the
-* matrix Q. N >= K >= 0.
-*
-* A (input/output) COMPLEX*16 array, dimension (LDA,N)
-* On entry, the i-th column must contain the vector which
-* defines the elementary reflector H(i), for i = 1,2,...,k, as
-* returned by ZGEQRF in the first k columns of its array
-* argument A.
-* On exit, the m by n matrix Q.
-*
-* LDA (input) INTEGER
-* The first dimension of the array A. LDA >= max(1,M).
-*
-* TAU (input) COMPLEX*16 array, dimension (K)
-* TAU(i) must contain the scalar factor of the elementary
-* reflector H(i), as returned by ZGEQRF.
-*
-* WORK (workspace) COMPLEX*16 array, dimension (N)
-*
-* INFO (output) INTEGER
-* = 0: successful exit
-* < 0: if INFO = -i, the i-th argument has an illegal value
-*
-* =====================================================================
-*
-* .. Parameters ..
- COMPLEX*16 ONE, ZERO
- PARAMETER ( ONE = ( 1.0D+0, 0.0D+0 ),
- $ ZERO = ( 0.0D+0, 0.0D+0 ) )
-* ..
-* .. Local Scalars ..
- INTEGER I, J, L
-* ..
-* .. External Subroutines ..
- EXTERNAL XERBLA, ZLARF, ZSCAL
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC MAX
-* ..
-* .. Executable Statements ..
-*
-* Test the input arguments
-*
- INFO = 0
- IF( M.LT.0 ) THEN
- INFO = -1
- ELSE IF( N.LT.0 .OR. N.GT.M ) THEN
- INFO = -2
- ELSE IF( K.LT.0 .OR. K.GT.N ) THEN
- INFO = -3
- ELSE IF( LDA.LT.MAX( 1, M ) ) THEN
- INFO = -5
- END IF
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'ZUNG2R', -INFO )
- RETURN
- END IF
-*
-* Quick return if possible
-*
- IF( N.LE.0 )
- $ RETURN
-*
-* Initialise columns k+1:n to columns of the unit matrix
-*
- DO 20 J = K + 1, N
- DO 10 L = 1, M
- A( L, J ) = ZERO
- 10 CONTINUE
- A( J, J ) = ONE
- 20 CONTINUE
-*
- DO 40 I = K, 1, -1
-*
-* Apply H(i) to A(i:m,i:n) from the left
-*
- IF( I.LT.N ) THEN
- A( I, I ) = ONE
- CALL ZLARF( 'Left', M-I+1, N-I, A( I, I ), 1, TAU( I ),
- $ A( I, I+1 ), LDA, WORK )
- END IF
- IF( I.LT.M )
- $ CALL ZSCAL( M-I, -TAU( I ), A( I+1, I ), 1 )
- A( I, I ) = ONE - TAU( I )
-*
-* Set A(1:i-1,i) to zero
-*
- DO 30 L = 1, I - 1
- A( L, I ) = ZERO
- 30 CONTINUE
- 40 CONTINUE
- RETURN
-*
-* End of ZUNG2R
-*
- END
diff --git a/src/lib/lapack/zungbr.f b/src/lib/lapack/zungbr.f
deleted file mode 100644
index 94f74820..00000000
--- a/src/lib/lapack/zungbr.f
+++ /dev/null
@@ -1,245 +0,0 @@
- SUBROUTINE ZUNGBR( VECT, M, N, K, A, LDA, TAU, WORK, LWORK, INFO )
-*
-* -- LAPACK routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- CHARACTER VECT
- INTEGER INFO, K, LDA, LWORK, M, N
-* ..
-* .. Array Arguments ..
- COMPLEX*16 A( LDA, * ), TAU( * ), WORK( * )
-* ..
-*
-* Purpose
-* =======
-*
-* ZUNGBR generates one of the complex unitary matrices Q or P**H
-* determined by ZGEBRD when reducing a complex matrix A to bidiagonal
-* form: A = Q * B * P**H. Q and P**H are defined as products of
-* elementary reflectors H(i) or G(i) respectively.
-*
-* If VECT = 'Q', A is assumed to have been an M-by-K matrix, and Q
-* is of order M:
-* if m >= k, Q = H(1) H(2) . . . H(k) and ZUNGBR returns the first n
-* columns of Q, where m >= n >= k;
-* if m < k, Q = H(1) H(2) . . . H(m-1) and ZUNGBR returns Q as an
-* M-by-M matrix.
-*
-* If VECT = 'P', A is assumed to have been a K-by-N matrix, and P**H
-* is of order N:
-* if k < n, P**H = G(k) . . . G(2) G(1) and ZUNGBR returns the first m
-* rows of P**H, where n >= m >= k;
-* if k >= n, P**H = G(n-1) . . . G(2) G(1) and ZUNGBR returns P**H as
-* an N-by-N matrix.
-*
-* Arguments
-* =========
-*
-* VECT (input) CHARACTER*1
-* Specifies whether the matrix Q or the matrix P**H is
-* required, as defined in the transformation applied by ZGEBRD:
-* = 'Q': generate Q;
-* = 'P': generate P**H.
-*
-* M (input) INTEGER
-* The number of rows of the matrix Q or P**H to be returned.
-* M >= 0.
-*
-* N (input) INTEGER
-* The number of columns of the matrix Q or P**H to be returned.
-* N >= 0.
-* If VECT = 'Q', M >= N >= min(M,K);
-* if VECT = 'P', N >= M >= min(N,K).
-*
-* K (input) INTEGER
-* If VECT = 'Q', the number of columns in the original M-by-K
-* matrix reduced by ZGEBRD.
-* If VECT = 'P', the number of rows in the original K-by-N
-* matrix reduced by ZGEBRD.
-* K >= 0.
-*
-* A (input/output) COMPLEX*16 array, dimension (LDA,N)
-* On entry, the vectors which define the elementary reflectors,
-* as returned by ZGEBRD.
-* On exit, the M-by-N matrix Q or P**H.
-*
-* LDA (input) INTEGER
-* The leading dimension of the array A. LDA >= M.
-*
-* TAU (input) COMPLEX*16 array, dimension
-* (min(M,K)) if VECT = 'Q'
-* (min(N,K)) if VECT = 'P'
-* TAU(i) must contain the scalar factor of the elementary
-* reflector H(i) or G(i), which determines Q or P**H, as
-* returned by ZGEBRD in its array argument TAUQ or TAUP.
-*
-* WORK (workspace/output) COMPLEX*16 array, dimension (MAX(1,LWORK))
-* On exit, if INFO = 0, WORK(1) returns the optimal LWORK.
-*
-* LWORK (input) INTEGER
-* The dimension of the array WORK. LWORK >= max(1,min(M,N)).
-* For optimum performance LWORK >= min(M,N)*NB, where NB
-* is the optimal blocksize.
-*
-* If LWORK = -1, then a workspace query is assumed; the routine
-* only calculates the optimal size of the WORK array, returns
-* this value as the first entry of the WORK array, and no error
-* message related to LWORK is issued by XERBLA.
-*
-* INFO (output) INTEGER
-* = 0: successful exit
-* < 0: if INFO = -i, the i-th argument had an illegal value
-*
-* =====================================================================
-*
-* .. Parameters ..
- COMPLEX*16 ZERO, ONE
- PARAMETER ( ZERO = ( 0.0D+0, 0.0D+0 ),
- $ ONE = ( 1.0D+0, 0.0D+0 ) )
-* ..
-* .. Local Scalars ..
- LOGICAL LQUERY, WANTQ
- INTEGER I, IINFO, J, LWKOPT, MN, NB
-* ..
-* .. External Functions ..
- LOGICAL LSAME
- INTEGER ILAENV
- EXTERNAL LSAME, ILAENV
-* ..
-* .. External Subroutines ..
- EXTERNAL XERBLA, ZUNGLQ, ZUNGQR
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC MAX, MIN
-* ..
-* .. Executable Statements ..
-*
-* Test the input arguments
-*
- INFO = 0
- WANTQ = LSAME( VECT, 'Q' )
- MN = MIN( M, N )
- LQUERY = ( LWORK.EQ.-1 )
- IF( .NOT.WANTQ .AND. .NOT.LSAME( VECT, 'P' ) ) THEN
- INFO = -1
- ELSE IF( M.LT.0 ) THEN
- INFO = -2
- ELSE IF( N.LT.0 .OR. ( WANTQ .AND. ( N.GT.M .OR. N.LT.MIN( M,
- $ K ) ) ) .OR. ( .NOT.WANTQ .AND. ( M.GT.N .OR. M.LT.
- $ MIN( N, K ) ) ) ) THEN
- INFO = -3
- ELSE IF( K.LT.0 ) THEN
- INFO = -4
- ELSE IF( LDA.LT.MAX( 1, M ) ) THEN
- INFO = -6
- ELSE IF( LWORK.LT.MAX( 1, MN ) .AND. .NOT.LQUERY ) THEN
- INFO = -9
- END IF
-*
- IF( INFO.EQ.0 ) THEN
- IF( WANTQ ) THEN
- NB = ILAENV( 1, 'ZUNGQR', ' ', M, N, K, -1 )
- ELSE
- NB = ILAENV( 1, 'ZUNGLQ', ' ', M, N, K, -1 )
- END IF
- LWKOPT = MAX( 1, MN )*NB
- WORK( 1 ) = LWKOPT
- END IF
-*
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'ZUNGBR', -INFO )
- RETURN
- ELSE IF( LQUERY ) THEN
- RETURN
- END IF
-*
-* Quick return if possible
-*
- IF( M.EQ.0 .OR. N.EQ.0 ) THEN
- WORK( 1 ) = 1
- RETURN
- END IF
-*
- IF( WANTQ ) THEN
-*
-* Form Q, determined by a call to ZGEBRD to reduce an m-by-k
-* matrix
-*
- IF( M.GE.K ) THEN
-*
-* If m >= k, assume m >= n >= k
-*
- CALL ZUNGQR( M, N, K, A, LDA, TAU, WORK, LWORK, IINFO )
-*
- ELSE
-*
-* If m < k, assume m = n
-*
-* Shift the vectors which define the elementary reflectors one
-* column to the right, and set the first row and column of Q
-* to those of the unit matrix
-*
- DO 20 J = M, 2, -1
- A( 1, J ) = ZERO
- DO 10 I = J + 1, M
- A( I, J ) = A( I, J-1 )
- 10 CONTINUE
- 20 CONTINUE
- A( 1, 1 ) = ONE
- DO 30 I = 2, M
- A( I, 1 ) = ZERO
- 30 CONTINUE
- IF( M.GT.1 ) THEN
-*
-* Form Q(2:m,2:m)
-*
- CALL ZUNGQR( M-1, M-1, M-1, A( 2, 2 ), LDA, TAU, WORK,
- $ LWORK, IINFO )
- END IF
- END IF
- ELSE
-*
-* Form P', determined by a call to ZGEBRD to reduce a k-by-n
-* matrix
-*
- IF( K.LT.N ) THEN
-*
-* If k < n, assume k <= m <= n
-*
- CALL ZUNGLQ( M, N, K, A, LDA, TAU, WORK, LWORK, IINFO )
-*
- ELSE
-*
-* If k >= n, assume m = n
-*
-* Shift the vectors which define the elementary reflectors one
-* row downward, and set the first row and column of P' to
-* those of the unit matrix
-*
- A( 1, 1 ) = ONE
- DO 40 I = 2, N
- A( I, 1 ) = ZERO
- 40 CONTINUE
- DO 60 J = 2, N
- DO 50 I = J - 1, 2, -1
- A( I, J ) = A( I-1, J )
- 50 CONTINUE
- A( 1, J ) = ZERO
- 60 CONTINUE
- IF( N.GT.1 ) THEN
-*
-* Form P'(2:n,2:n)
-*
- CALL ZUNGLQ( N-1, N-1, N-1, A( 2, 2 ), LDA, TAU, WORK,
- $ LWORK, IINFO )
- END IF
- END IF
- END IF
- WORK( 1 ) = LWKOPT
- RETURN
-*
-* End of ZUNGBR
-*
- END
diff --git a/src/lib/lapack/zunghr.f b/src/lib/lapack/zunghr.f
deleted file mode 100644
index fcf32abf..00000000
--- a/src/lib/lapack/zunghr.f
+++ /dev/null
@@ -1,165 +0,0 @@
- SUBROUTINE ZUNGHR( N, ILO, IHI, A, LDA, TAU, WORK, LWORK, INFO )
-*
-* -- LAPACK routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- INTEGER IHI, ILO, INFO, LDA, LWORK, N
-* ..
-* .. Array Arguments ..
- COMPLEX*16 A( LDA, * ), TAU( * ), WORK( * )
-* ..
-*
-* Purpose
-* =======
-*
-* ZUNGHR generates a complex unitary matrix Q which is defined as the
-* product of IHI-ILO elementary reflectors of order N, as returned by
-* ZGEHRD:
-*
-* Q = H(ilo) H(ilo+1) . . . H(ihi-1).
-*
-* Arguments
-* =========
-*
-* N (input) INTEGER
-* The order of the matrix Q. N >= 0.
-*
-* ILO (input) INTEGER
-* IHI (input) INTEGER
-* ILO and IHI must have the same values as in the previous call
-* of ZGEHRD. Q is equal to the unit matrix except in the
-* submatrix Q(ilo+1:ihi,ilo+1:ihi).
-* 1 <= ILO <= IHI <= N, if N > 0; ILO=1 and IHI=0, if N=0.
-*
-* A (input/output) COMPLEX*16 array, dimension (LDA,N)
-* On entry, the vectors which define the elementary reflectors,
-* as returned by ZGEHRD.
-* On exit, the N-by-N unitary matrix Q.
-*
-* LDA (input) INTEGER
-* The leading dimension of the array A. LDA >= max(1,N).
-*
-* TAU (input) COMPLEX*16 array, dimension (N-1)
-* TAU(i) must contain the scalar factor of the elementary
-* reflector H(i), as returned by ZGEHRD.
-*
-* WORK (workspace/output) COMPLEX*16 array, dimension (MAX(1,LWORK))
-* On exit, if INFO = 0, WORK(1) returns the optimal LWORK.
-*
-* LWORK (input) INTEGER
-* The dimension of the array WORK. LWORK >= IHI-ILO.
-* For optimum performance LWORK >= (IHI-ILO)*NB, where NB is
-* the optimal blocksize.
-*
-* If LWORK = -1, then a workspace query is assumed; the routine
-* only calculates the optimal size of the WORK array, returns
-* this value as the first entry of the WORK array, and no error
-* message related to LWORK is issued by XERBLA.
-*
-* INFO (output) INTEGER
-* = 0: successful exit
-* < 0: if INFO = -i, the i-th argument had an illegal value
-*
-* =====================================================================
-*
-* .. Parameters ..
- COMPLEX*16 ZERO, ONE
- PARAMETER ( ZERO = ( 0.0D+0, 0.0D+0 ),
- $ ONE = ( 1.0D+0, 0.0D+0 ) )
-* ..
-* .. Local Scalars ..
- LOGICAL LQUERY
- INTEGER I, IINFO, J, LWKOPT, NB, NH
-* ..
-* .. External Subroutines ..
- EXTERNAL XERBLA, ZUNGQR
-* ..
-* .. External Functions ..
- INTEGER ILAENV
- EXTERNAL ILAENV
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC MAX, MIN
-* ..
-* .. Executable Statements ..
-*
-* Test the input arguments
-*
- INFO = 0
- NH = IHI - ILO
- LQUERY = ( LWORK.EQ.-1 )
- IF( N.LT.0 ) THEN
- INFO = -1
- ELSE IF( ILO.LT.1 .OR. ILO.GT.MAX( 1, N ) ) THEN
- INFO = -2
- ELSE IF( IHI.LT.MIN( ILO, N ) .OR. IHI.GT.N ) THEN
- INFO = -3
- ELSE IF( LDA.LT.MAX( 1, N ) ) THEN
- INFO = -5
- ELSE IF( LWORK.LT.MAX( 1, NH ) .AND. .NOT.LQUERY ) THEN
- INFO = -8
- END IF
-*
- IF( INFO.EQ.0 ) THEN
- NB = ILAENV( 1, 'ZUNGQR', ' ', NH, NH, NH, -1 )
- LWKOPT = MAX( 1, NH )*NB
- WORK( 1 ) = LWKOPT
- END IF
-*
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'ZUNGHR', -INFO )
- RETURN
- ELSE IF( LQUERY ) THEN
- RETURN
- END IF
-*
-* Quick return if possible
-*
- IF( N.EQ.0 ) THEN
- WORK( 1 ) = 1
- RETURN
- END IF
-*
-* Shift the vectors which define the elementary reflectors one
-* column to the right, and set the first ilo and the last n-ihi
-* rows and columns to those of the unit matrix
-*
- DO 40 J = IHI, ILO + 1, -1
- DO 10 I = 1, J - 1
- A( I, J ) = ZERO
- 10 CONTINUE
- DO 20 I = J + 1, IHI
- A( I, J ) = A( I, J-1 )
- 20 CONTINUE
- DO 30 I = IHI + 1, N
- A( I, J ) = ZERO
- 30 CONTINUE
- 40 CONTINUE
- DO 60 J = 1, ILO
- DO 50 I = 1, N
- A( I, J ) = ZERO
- 50 CONTINUE
- A( J, J ) = ONE
- 60 CONTINUE
- DO 80 J = IHI + 1, N
- DO 70 I = 1, N
- A( I, J ) = ZERO
- 70 CONTINUE
- A( J, J ) = ONE
- 80 CONTINUE
-*
- IF( NH.GT.0 ) THEN
-*
-* Generate Q(ilo+1:ihi,ilo+1:ihi)
-*
- CALL ZUNGQR( NH, NH, NH, A( ILO+1, ILO+1 ), LDA, TAU( ILO ),
- $ WORK, LWORK, IINFO )
- END IF
- WORK( 1 ) = LWKOPT
- RETURN
-*
-* End of ZUNGHR
-*
- END
diff --git a/src/lib/lapack/zungl2.f b/src/lib/lapack/zungl2.f
deleted file mode 100644
index 502411b4..00000000
--- a/src/lib/lapack/zungl2.f
+++ /dev/null
@@ -1,136 +0,0 @@
- SUBROUTINE ZUNGL2( M, N, K, A, LDA, TAU, WORK, INFO )
-*
-* -- LAPACK routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- INTEGER INFO, K, LDA, M, N
-* ..
-* .. Array Arguments ..
- COMPLEX*16 A( LDA, * ), TAU( * ), WORK( * )
-* ..
-*
-* Purpose
-* =======
-*
-* ZUNGL2 generates an m-by-n complex matrix Q with orthonormal rows,
-* which is defined as the first m rows of a product of k elementary
-* reflectors of order n
-*
-* Q = H(k)' . . . H(2)' H(1)'
-*
-* as returned by ZGELQF.
-*
-* Arguments
-* =========
-*
-* M (input) INTEGER
-* The number of rows of the matrix Q. M >= 0.
-*
-* N (input) INTEGER
-* The number of columns of the matrix Q. N >= M.
-*
-* K (input) INTEGER
-* The number of elementary reflectors whose product defines the
-* matrix Q. M >= K >= 0.
-*
-* A (input/output) COMPLEX*16 array, dimension (LDA,N)
-* On entry, the i-th row must contain the vector which defines
-* the elementary reflector H(i), for i = 1,2,...,k, as returned
-* by ZGELQF in the first k rows of its array argument A.
-* On exit, the m by n matrix Q.
-*
-* LDA (input) INTEGER
-* The first dimension of the array A. LDA >= max(1,M).
-*
-* TAU (input) COMPLEX*16 array, dimension (K)
-* TAU(i) must contain the scalar factor of the elementary
-* reflector H(i), as returned by ZGELQF.
-*
-* WORK (workspace) COMPLEX*16 array, dimension (M)
-*
-* INFO (output) INTEGER
-* = 0: successful exit
-* < 0: if INFO = -i, the i-th argument has an illegal value
-*
-* =====================================================================
-*
-* .. Parameters ..
- COMPLEX*16 ONE, ZERO
- PARAMETER ( ONE = ( 1.0D+0, 0.0D+0 ),
- $ ZERO = ( 0.0D+0, 0.0D+0 ) )
-* ..
-* .. Local Scalars ..
- INTEGER I, J, L
-* ..
-* .. External Subroutines ..
- EXTERNAL XERBLA, ZLACGV, ZLARF, ZSCAL
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC DCONJG, MAX
-* ..
-* .. Executable Statements ..
-*
-* Test the input arguments
-*
- INFO = 0
- IF( M.LT.0 ) THEN
- INFO = -1
- ELSE IF( N.LT.M ) THEN
- INFO = -2
- ELSE IF( K.LT.0 .OR. K.GT.M ) THEN
- INFO = -3
- ELSE IF( LDA.LT.MAX( 1, M ) ) THEN
- INFO = -5
- END IF
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'ZUNGL2', -INFO )
- RETURN
- END IF
-*
-* Quick return if possible
-*
- IF( M.LE.0 )
- $ RETURN
-*
- IF( K.LT.M ) THEN
-*
-* Initialise rows k+1:m to rows of the unit matrix
-*
- DO 20 J = 1, N
- DO 10 L = K + 1, M
- A( L, J ) = ZERO
- 10 CONTINUE
- IF( J.GT.K .AND. J.LE.M )
- $ A( J, J ) = ONE
- 20 CONTINUE
- END IF
-*
- DO 40 I = K, 1, -1
-*
-* Apply H(i)' to A(i:m,i:n) from the right
-*
- IF( I.LT.N ) THEN
- CALL ZLACGV( N-I, A( I, I+1 ), LDA )
- IF( I.LT.M ) THEN
- A( I, I ) = ONE
- CALL ZLARF( 'Right', M-I, N-I+1, A( I, I ), LDA,
- $ DCONJG( TAU( I ) ), A( I+1, I ), LDA, WORK )
- END IF
- CALL ZSCAL( N-I, -TAU( I ), A( I, I+1 ), LDA )
- CALL ZLACGV( N-I, A( I, I+1 ), LDA )
- END IF
- A( I, I ) = ONE - DCONJG( TAU( I ) )
-*
-* Set A(i,1:i-1) to zero
-*
- DO 30 L = 1, I - 1
- A( I, L ) = ZERO
- 30 CONTINUE
- 40 CONTINUE
- RETURN
-*
-* End of ZUNGL2
-*
- END
diff --git a/src/lib/lapack/zunglq.f b/src/lib/lapack/zunglq.f
deleted file mode 100644
index ab4a018f..00000000
--- a/src/lib/lapack/zunglq.f
+++ /dev/null
@@ -1,215 +0,0 @@
- SUBROUTINE ZUNGLQ( M, N, K, A, LDA, TAU, WORK, LWORK, INFO )
-*
-* -- LAPACK routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- INTEGER INFO, K, LDA, LWORK, M, N
-* ..
-* .. Array Arguments ..
- COMPLEX*16 A( LDA, * ), TAU( * ), WORK( * )
-* ..
-*
-* Purpose
-* =======
-*
-* ZUNGLQ generates an M-by-N complex matrix Q with orthonormal rows,
-* which is defined as the first M rows of a product of K elementary
-* reflectors of order N
-*
-* Q = H(k)' . . . H(2)' H(1)'
-*
-* as returned by ZGELQF.
-*
-* Arguments
-* =========
-*
-* M (input) INTEGER
-* The number of rows of the matrix Q. M >= 0.
-*
-* N (input) INTEGER
-* The number of columns of the matrix Q. N >= M.
-*
-* K (input) INTEGER
-* The number of elementary reflectors whose product defines the
-* matrix Q. M >= K >= 0.
-*
-* A (input/output) COMPLEX*16 array, dimension (LDA,N)
-* On entry, the i-th row must contain the vector which defines
-* the elementary reflector H(i), for i = 1,2,...,k, as returned
-* by ZGELQF in the first k rows of its array argument A.
-* On exit, the M-by-N matrix Q.
-*
-* LDA (input) INTEGER
-* The first dimension of the array A. LDA >= max(1,M).
-*
-* TAU (input) COMPLEX*16 array, dimension (K)
-* TAU(i) must contain the scalar factor of the elementary
-* reflector H(i), as returned by ZGELQF.
-*
-* WORK (workspace/output) COMPLEX*16 array, dimension (MAX(1,LWORK))
-* On exit, if INFO = 0, WORK(1) returns the optimal LWORK.
-*
-* LWORK (input) INTEGER
-* The dimension of the array WORK. LWORK >= max(1,M).
-* For optimum performance LWORK >= M*NB, where NB is
-* the optimal blocksize.
-*
-* If LWORK = -1, then a workspace query is assumed; the routine
-* only calculates the optimal size of the WORK array, returns
-* this value as the first entry of the WORK array, and no error
-* message related to LWORK is issued by XERBLA.
-*
-* INFO (output) INTEGER
-* = 0: successful exit;
-* < 0: if INFO = -i, the i-th argument has an illegal value
-*
-* =====================================================================
-*
-* .. Parameters ..
- COMPLEX*16 ZERO
- PARAMETER ( ZERO = ( 0.0D+0, 0.0D+0 ) )
-* ..
-* .. Local Scalars ..
- LOGICAL LQUERY
- INTEGER I, IB, IINFO, IWS, J, KI, KK, L, LDWORK,
- $ LWKOPT, NB, NBMIN, NX
-* ..
-* .. External Subroutines ..
- EXTERNAL XERBLA, ZLARFB, ZLARFT, ZUNGL2
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC MAX, MIN
-* ..
-* .. External Functions ..
- INTEGER ILAENV
- EXTERNAL ILAENV
-* ..
-* .. Executable Statements ..
-*
-* Test the input arguments
-*
- INFO = 0
- NB = ILAENV( 1, 'ZUNGLQ', ' ', M, N, K, -1 )
- LWKOPT = MAX( 1, M )*NB
- WORK( 1 ) = LWKOPT
- LQUERY = ( LWORK.EQ.-1 )
- IF( M.LT.0 ) THEN
- INFO = -1
- ELSE IF( N.LT.M ) THEN
- INFO = -2
- ELSE IF( K.LT.0 .OR. K.GT.M ) THEN
- INFO = -3
- ELSE IF( LDA.LT.MAX( 1, M ) ) THEN
- INFO = -5
- ELSE IF( LWORK.LT.MAX( 1, M ) .AND. .NOT.LQUERY ) THEN
- INFO = -8
- END IF
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'ZUNGLQ', -INFO )
- RETURN
- ELSE IF( LQUERY ) THEN
- RETURN
- END IF
-*
-* Quick return if possible
-*
- IF( M.LE.0 ) THEN
- WORK( 1 ) = 1
- RETURN
- END IF
-*
- NBMIN = 2
- NX = 0
- IWS = M
- IF( NB.GT.1 .AND. NB.LT.K ) THEN
-*
-* Determine when to cross over from blocked to unblocked code.
-*
- NX = MAX( 0, ILAENV( 3, 'ZUNGLQ', ' ', M, N, K, -1 ) )
- IF( NX.LT.K ) THEN
-*
-* Determine if workspace is large enough for blocked code.
-*
- LDWORK = M
- IWS = LDWORK*NB
- IF( LWORK.LT.IWS ) THEN
-*
-* Not enough workspace to use optimal NB: reduce NB and
-* determine the minimum value of NB.
-*
- NB = LWORK / LDWORK
- NBMIN = MAX( 2, ILAENV( 2, 'ZUNGLQ', ' ', M, N, K, -1 ) )
- END IF
- END IF
- END IF
-*
- IF( NB.GE.NBMIN .AND. NB.LT.K .AND. NX.LT.K ) THEN
-*
-* Use blocked code after the last block.
-* The first kk rows are handled by the block method.
-*
- KI = ( ( K-NX-1 ) / NB )*NB
- KK = MIN( K, KI+NB )
-*
-* Set A(kk+1:m,1:kk) to zero.
-*
- DO 20 J = 1, KK
- DO 10 I = KK + 1, M
- A( I, J ) = ZERO
- 10 CONTINUE
- 20 CONTINUE
- ELSE
- KK = 0
- END IF
-*
-* Use unblocked code for the last or only block.
-*
- IF( KK.LT.M )
- $ CALL ZUNGL2( M-KK, N-KK, K-KK, A( KK+1, KK+1 ), LDA,
- $ TAU( KK+1 ), WORK, IINFO )
-*
- IF( KK.GT.0 ) THEN
-*
-* Use blocked code
-*
- DO 50 I = KI + 1, 1, -NB
- IB = MIN( NB, K-I+1 )
- IF( I+IB.LE.M ) THEN
-*
-* Form the triangular factor of the block reflector
-* H = H(i) H(i+1) . . . H(i+ib-1)
-*
- CALL ZLARFT( 'Forward', 'Rowwise', N-I+1, IB, A( I, I ),
- $ LDA, TAU( I ), WORK, LDWORK )
-*
-* Apply H' to A(i+ib:m,i:n) from the right
-*
- CALL ZLARFB( 'Right', 'Conjugate transpose', 'Forward',
- $ 'Rowwise', M-I-IB+1, N-I+1, IB, A( I, I ),
- $ LDA, WORK, LDWORK, A( I+IB, I ), LDA,
- $ WORK( IB+1 ), LDWORK )
- END IF
-*
-* Apply H' to columns i:n of current block
-*
- CALL ZUNGL2( IB, N-I+1, IB, A( I, I ), LDA, TAU( I ), WORK,
- $ IINFO )
-*
-* Set columns 1:i-1 of current block to zero
-*
- DO 40 J = 1, I - 1
- DO 30 L = I, I + IB - 1
- A( L, J ) = ZERO
- 30 CONTINUE
- 40 CONTINUE
- 50 CONTINUE
- END IF
-*
- WORK( 1 ) = IWS
- RETURN
-*
-* End of ZUNGLQ
-*
- END
diff --git a/src/lib/lapack/zungql.f b/src/lib/lapack/zungql.f
deleted file mode 100644
index 4232abea..00000000
--- a/src/lib/lapack/zungql.f
+++ /dev/null
@@ -1,222 +0,0 @@
- SUBROUTINE ZUNGQL( M, N, K, A, LDA, TAU, WORK, LWORK, INFO )
-*
-* -- LAPACK routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- INTEGER INFO, K, LDA, LWORK, M, N
-* ..
-* .. Array Arguments ..
- COMPLEX*16 A( LDA, * ), TAU( * ), WORK( * )
-* ..
-*
-* Purpose
-* =======
-*
-* ZUNGQL generates an M-by-N complex matrix Q with orthonormal columns,
-* which is defined as the last N columns of a product of K elementary
-* reflectors of order M
-*
-* Q = H(k) . . . H(2) H(1)
-*
-* as returned by ZGEQLF.
-*
-* Arguments
-* =========
-*
-* M (input) INTEGER
-* The number of rows of the matrix Q. M >= 0.
-*
-* N (input) INTEGER
-* The number of columns of the matrix Q. M >= N >= 0.
-*
-* K (input) INTEGER
-* The number of elementary reflectors whose product defines the
-* matrix Q. N >= K >= 0.
-*
-* A (input/output) COMPLEX*16 array, dimension (LDA,N)
-* On entry, the (n-k+i)-th column must contain the vector which
-* defines the elementary reflector H(i), for i = 1,2,...,k, as
-* returned by ZGEQLF in the last k columns of its array
-* argument A.
-* On exit, the M-by-N matrix Q.
-*
-* LDA (input) INTEGER
-* The first dimension of the array A. LDA >= max(1,M).
-*
-* TAU (input) COMPLEX*16 array, dimension (K)
-* TAU(i) must contain the scalar factor of the elementary
-* reflector H(i), as returned by ZGEQLF.
-*
-* WORK (workspace/output) COMPLEX*16 array, dimension (MAX(1,LWORK))
-* On exit, if INFO = 0, WORK(1) returns the optimal LWORK.
-*
-* LWORK (input) INTEGER
-* The dimension of the array WORK. LWORK >= max(1,N).
-* For optimum performance LWORK >= N*NB, where NB is the
-* optimal blocksize.
-*
-* If LWORK = -1, then a workspace query is assumed; the routine
-* only calculates the optimal size of the WORK array, returns
-* this value as the first entry of the WORK array, and no error
-* message related to LWORK is issued by XERBLA.
-*
-* INFO (output) INTEGER
-* = 0: successful exit
-* < 0: if INFO = -i, the i-th argument has an illegal value
-*
-* =====================================================================
-*
-* .. Parameters ..
- COMPLEX*16 ZERO
- PARAMETER ( ZERO = ( 0.0D+0, 0.0D+0 ) )
-* ..
-* .. Local Scalars ..
- LOGICAL LQUERY
- INTEGER I, IB, IINFO, IWS, J, KK, L, LDWORK, LWKOPT,
- $ NB, NBMIN, NX
-* ..
-* .. External Subroutines ..
- EXTERNAL XERBLA, ZLARFB, ZLARFT, ZUNG2L
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC MAX, MIN
-* ..
-* .. External Functions ..
- INTEGER ILAENV
- EXTERNAL ILAENV
-* ..
-* .. Executable Statements ..
-*
-* Test the input arguments
-*
- INFO = 0
- LQUERY = ( LWORK.EQ.-1 )
- IF( M.LT.0 ) THEN
- INFO = -1
- ELSE IF( N.LT.0 .OR. N.GT.M ) THEN
- INFO = -2
- ELSE IF( K.LT.0 .OR. K.GT.N ) THEN
- INFO = -3
- ELSE IF( LDA.LT.MAX( 1, M ) ) THEN
- INFO = -5
- END IF
-*
- IF( INFO.EQ.0 ) THEN
- IF( N.EQ.0 ) THEN
- LWKOPT = 1
- ELSE
- NB = ILAENV( 1, 'ZUNGQL', ' ', M, N, K, -1 )
- LWKOPT = N*NB
- END IF
- WORK( 1 ) = LWKOPT
-*
- IF( LWORK.LT.MAX( 1, N ) .AND. .NOT.LQUERY ) THEN
- INFO = -8
- END IF
- END IF
-*
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'ZUNGQL', -INFO )
- RETURN
- ELSE IF( LQUERY ) THEN
- RETURN
- END IF
-*
-* Quick return if possible
-*
- IF( N.LE.0 ) THEN
- RETURN
- END IF
-*
- NBMIN = 2
- NX = 0
- IWS = N
- IF( NB.GT.1 .AND. NB.LT.K ) THEN
-*
-* Determine when to cross over from blocked to unblocked code.
-*
- NX = MAX( 0, ILAENV( 3, 'ZUNGQL', ' ', M, N, K, -1 ) )
- IF( NX.LT.K ) THEN
-*
-* Determine if workspace is large enough for blocked code.
-*
- LDWORK = N
- IWS = LDWORK*NB
- IF( LWORK.LT.IWS ) THEN
-*
-* Not enough workspace to use optimal NB: reduce NB and
-* determine the minimum value of NB.
-*
- NB = LWORK / LDWORK
- NBMIN = MAX( 2, ILAENV( 2, 'ZUNGQL', ' ', M, N, K, -1 ) )
- END IF
- END IF
- END IF
-*
- IF( NB.GE.NBMIN .AND. NB.LT.K .AND. NX.LT.K ) THEN
-*
-* Use blocked code after the first block.
-* The last kk columns are handled by the block method.
-*
- KK = MIN( K, ( ( K-NX+NB-1 ) / NB )*NB )
-*
-* Set A(m-kk+1:m,1:n-kk) to zero.
-*
- DO 20 J = 1, N - KK
- DO 10 I = M - KK + 1, M
- A( I, J ) = ZERO
- 10 CONTINUE
- 20 CONTINUE
- ELSE
- KK = 0
- END IF
-*
-* Use unblocked code for the first or only block.
-*
- CALL ZUNG2L( M-KK, N-KK, K-KK, A, LDA, TAU, WORK, IINFO )
-*
- IF( KK.GT.0 ) THEN
-*
-* Use blocked code
-*
- DO 50 I = K - KK + 1, K, NB
- IB = MIN( NB, K-I+1 )
- IF( N-K+I.GT.1 ) THEN
-*
-* Form the triangular factor of the block reflector
-* H = H(i+ib-1) . . . H(i+1) H(i)
-*
- CALL ZLARFT( 'Backward', 'Columnwise', M-K+I+IB-1, IB,
- $ A( 1, N-K+I ), LDA, TAU( I ), WORK, LDWORK )
-*
-* Apply H to A(1:m-k+i+ib-1,1:n-k+i-1) from the left
-*
- CALL ZLARFB( 'Left', 'No transpose', 'Backward',
- $ 'Columnwise', M-K+I+IB-1, N-K+I-1, IB,
- $ A( 1, N-K+I ), LDA, WORK, LDWORK, A, LDA,
- $ WORK( IB+1 ), LDWORK )
- END IF
-*
-* Apply H to rows 1:m-k+i+ib-1 of current block
-*
- CALL ZUNG2L( M-K+I+IB-1, IB, IB, A( 1, N-K+I ), LDA,
- $ TAU( I ), WORK, IINFO )
-*
-* Set rows m-k+i+ib:m of current block to zero
-*
- DO 40 J = N - K + I, N - K + I + IB - 1
- DO 30 L = M - K + I + IB, M
- A( L, J ) = ZERO
- 30 CONTINUE
- 40 CONTINUE
- 50 CONTINUE
- END IF
-*
- WORK( 1 ) = IWS
- RETURN
-*
-* End of ZUNGQL
-*
- END
diff --git a/src/lib/lapack/zungqr.f b/src/lib/lapack/zungqr.f
deleted file mode 100644
index bf5c6997..00000000
--- a/src/lib/lapack/zungqr.f
+++ /dev/null
@@ -1,216 +0,0 @@
- SUBROUTINE ZUNGQR( M, N, K, A, LDA, TAU, WORK, LWORK, INFO )
-*
-* -- LAPACK routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- INTEGER INFO, K, LDA, LWORK, M, N
-* ..
-* .. Array Arguments ..
- COMPLEX*16 A( LDA, * ), TAU( * ), WORK( * )
-* ..
-*
-* Purpose
-* =======
-*
-* ZUNGQR generates an M-by-N complex matrix Q with orthonormal columns,
-* which is defined as the first N columns of a product of K elementary
-* reflectors of order M
-*
-* Q = H(1) H(2) . . . H(k)
-*
-* as returned by ZGEQRF.
-*
-* Arguments
-* =========
-*
-* M (input) INTEGER
-* The number of rows of the matrix Q. M >= 0.
-*
-* N (input) INTEGER
-* The number of columns of the matrix Q. M >= N >= 0.
-*
-* K (input) INTEGER
-* The number of elementary reflectors whose product defines the
-* matrix Q. N >= K >= 0.
-*
-* A (input/output) COMPLEX*16 array, dimension (LDA,N)
-* On entry, the i-th column must contain the vector which
-* defines the elementary reflector H(i), for i = 1,2,...,k, as
-* returned by ZGEQRF in the first k columns of its array
-* argument A.
-* On exit, the M-by-N matrix Q.
-*
-* LDA (input) INTEGER
-* The first dimension of the array A. LDA >= max(1,M).
-*
-* TAU (input) COMPLEX*16 array, dimension (K)
-* TAU(i) must contain the scalar factor of the elementary
-* reflector H(i), as returned by ZGEQRF.
-*
-* WORK (workspace/output) COMPLEX*16 array, dimension (MAX(1,LWORK))
-* On exit, if INFO = 0, WORK(1) returns the optimal LWORK.
-*
-* LWORK (input) INTEGER
-* The dimension of the array WORK. LWORK >= max(1,N).
-* For optimum performance LWORK >= N*NB, where NB is the
-* optimal blocksize.
-*
-* If LWORK = -1, then a workspace query is assumed; the routine
-* only calculates the optimal size of the WORK array, returns
-* this value as the first entry of the WORK array, and no error
-* message related to LWORK is issued by XERBLA.
-*
-* INFO (output) INTEGER
-* = 0: successful exit
-* < 0: if INFO = -i, the i-th argument has an illegal value
-*
-* =====================================================================
-*
-* .. Parameters ..
- COMPLEX*16 ZERO
- PARAMETER ( ZERO = ( 0.0D+0, 0.0D+0 ) )
-* ..
-* .. Local Scalars ..
- LOGICAL LQUERY
- INTEGER I, IB, IINFO, IWS, J, KI, KK, L, LDWORK,
- $ LWKOPT, NB, NBMIN, NX
-* ..
-* .. External Subroutines ..
- EXTERNAL XERBLA, ZLARFB, ZLARFT, ZUNG2R
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC MAX, MIN
-* ..
-* .. External Functions ..
- INTEGER ILAENV
- EXTERNAL ILAENV
-* ..
-* .. Executable Statements ..
-*
-* Test the input arguments
-*
- INFO = 0
- NB = ILAENV( 1, 'ZUNGQR', ' ', M, N, K, -1 )
- LWKOPT = MAX( 1, N )*NB
- WORK( 1 ) = LWKOPT
- LQUERY = ( LWORK.EQ.-1 )
- IF( M.LT.0 ) THEN
- INFO = -1
- ELSE IF( N.LT.0 .OR. N.GT.M ) THEN
- INFO = -2
- ELSE IF( K.LT.0 .OR. K.GT.N ) THEN
- INFO = -3
- ELSE IF( LDA.LT.MAX( 1, M ) ) THEN
- INFO = -5
- ELSE IF( LWORK.LT.MAX( 1, N ) .AND. .NOT.LQUERY ) THEN
- INFO = -8
- END IF
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'ZUNGQR', -INFO )
- RETURN
- ELSE IF( LQUERY ) THEN
- RETURN
- END IF
-*
-* Quick return if possible
-*
- IF( N.LE.0 ) THEN
- WORK( 1 ) = 1
- RETURN
- END IF
-*
- NBMIN = 2
- NX = 0
- IWS = N
- IF( NB.GT.1 .AND. NB.LT.K ) THEN
-*
-* Determine when to cross over from blocked to unblocked code.
-*
- NX = MAX( 0, ILAENV( 3, 'ZUNGQR', ' ', M, N, K, -1 ) )
- IF( NX.LT.K ) THEN
-*
-* Determine if workspace is large enough for blocked code.
-*
- LDWORK = N
- IWS = LDWORK*NB
- IF( LWORK.LT.IWS ) THEN
-*
-* Not enough workspace to use optimal NB: reduce NB and
-* determine the minimum value of NB.
-*
- NB = LWORK / LDWORK
- NBMIN = MAX( 2, ILAENV( 2, 'ZUNGQR', ' ', M, N, K, -1 ) )
- END IF
- END IF
- END IF
-*
- IF( NB.GE.NBMIN .AND. NB.LT.K .AND. NX.LT.K ) THEN
-*
-* Use blocked code after the last block.
-* The first kk columns are handled by the block method.
-*
- KI = ( ( K-NX-1 ) / NB )*NB
- KK = MIN( K, KI+NB )
-*
-* Set A(1:kk,kk+1:n) to zero.
-*
- DO 20 J = KK + 1, N
- DO 10 I = 1, KK
- A( I, J ) = ZERO
- 10 CONTINUE
- 20 CONTINUE
- ELSE
- KK = 0
- END IF
-*
-* Use unblocked code for the last or only block.
-*
- IF( KK.LT.N )
- $ CALL ZUNG2R( M-KK, N-KK, K-KK, A( KK+1, KK+1 ), LDA,
- $ TAU( KK+1 ), WORK, IINFO )
-*
- IF( KK.GT.0 ) THEN
-*
-* Use blocked code
-*
- DO 50 I = KI + 1, 1, -NB
- IB = MIN( NB, K-I+1 )
- IF( I+IB.LE.N ) THEN
-*
-* Form the triangular factor of the block reflector
-* H = H(i) H(i+1) . . . H(i+ib-1)
-*
- CALL ZLARFT( 'Forward', 'Columnwise', M-I+1, IB,
- $ A( I, I ), LDA, TAU( I ), WORK, LDWORK )
-*
-* Apply H to A(i:m,i+ib:n) from the left
-*
- CALL ZLARFB( 'Left', 'No transpose', 'Forward',
- $ 'Columnwise', M-I+1, N-I-IB+1, IB,
- $ A( I, I ), LDA, WORK, LDWORK, A( I, I+IB ),
- $ LDA, WORK( IB+1 ), LDWORK )
- END IF
-*
-* Apply H to rows i:m of current block
-*
- CALL ZUNG2R( M-I+1, IB, IB, A( I, I ), LDA, TAU( I ), WORK,
- $ IINFO )
-*
-* Set rows 1:i-1 of current block to zero
-*
- DO 40 J = I, I + IB - 1
- DO 30 L = 1, I - 1
- A( L, J ) = ZERO
- 30 CONTINUE
- 40 CONTINUE
- 50 CONTINUE
- END IF
-*
- WORK( 1 ) = IWS
- RETURN
-*
-* End of ZUNGQR
-*
- END
diff --git a/src/lib/lapack/zungtr.f b/src/lib/lapack/zungtr.f
deleted file mode 100644
index 5de7c109..00000000
--- a/src/lib/lapack/zungtr.f
+++ /dev/null
@@ -1,184 +0,0 @@
- SUBROUTINE ZUNGTR( UPLO, N, A, LDA, TAU, WORK, LWORK, INFO )
-*
-* -- LAPACK routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- CHARACTER UPLO
- INTEGER INFO, LDA, LWORK, N
-* ..
-* .. Array Arguments ..
- COMPLEX*16 A( LDA, * ), TAU( * ), WORK( * )
-* ..
-*
-* Purpose
-* =======
-*
-* ZUNGTR generates a complex unitary matrix Q which is defined as the
-* product of n-1 elementary reflectors of order N, as returned by
-* ZHETRD:
-*
-* if UPLO = 'U', Q = H(n-1) . . . H(2) H(1),
-*
-* if UPLO = 'L', Q = H(1) H(2) . . . H(n-1).
-*
-* Arguments
-* =========
-*
-* UPLO (input) CHARACTER*1
-* = 'U': Upper triangle of A contains elementary reflectors
-* from ZHETRD;
-* = 'L': Lower triangle of A contains elementary reflectors
-* from ZHETRD.
-*
-* N (input) INTEGER
-* The order of the matrix Q. N >= 0.
-*
-* A (input/output) COMPLEX*16 array, dimension (LDA,N)
-* On entry, the vectors which define the elementary reflectors,
-* as returned by ZHETRD.
-* On exit, the N-by-N unitary matrix Q.
-*
-* LDA (input) INTEGER
-* The leading dimension of the array A. LDA >= N.
-*
-* TAU (input) COMPLEX*16 array, dimension (N-1)
-* TAU(i) must contain the scalar factor of the elementary
-* reflector H(i), as returned by ZHETRD.
-*
-* WORK (workspace/output) COMPLEX*16 array, dimension (MAX(1,LWORK))
-* On exit, if INFO = 0, WORK(1) returns the optimal LWORK.
-*
-* LWORK (input) INTEGER
-* The dimension of the array WORK. LWORK >= N-1.
-* For optimum performance LWORK >= (N-1)*NB, where NB is
-* the optimal blocksize.
-*
-* If LWORK = -1, then a workspace query is assumed; the routine
-* only calculates the optimal size of the WORK array, returns
-* this value as the first entry of the WORK array, and no error
-* message related to LWORK is issued by XERBLA.
-*
-* INFO (output) INTEGER
-* = 0: successful exit
-* < 0: if INFO = -i, the i-th argument had an illegal value
-*
-* =====================================================================
-*
-* .. Parameters ..
- COMPLEX*16 ZERO, ONE
- PARAMETER ( ZERO = ( 0.0D+0, 0.0D+0 ),
- $ ONE = ( 1.0D+0, 0.0D+0 ) )
-* ..
-* .. Local Scalars ..
- LOGICAL LQUERY, UPPER
- INTEGER I, IINFO, J, LWKOPT, NB
-* ..
-* .. External Functions ..
- LOGICAL LSAME
- INTEGER ILAENV
- EXTERNAL LSAME, ILAENV
-* ..
-* .. External Subroutines ..
- EXTERNAL XERBLA, ZUNGQL, ZUNGQR
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC MAX
-* ..
-* .. Executable Statements ..
-*
-* Test the input arguments
-*
- INFO = 0
- LQUERY = ( LWORK.EQ.-1 )
- UPPER = LSAME( UPLO, 'U' )
- IF( .NOT.UPPER .AND. .NOT.LSAME( UPLO, 'L' ) ) THEN
- INFO = -1
- ELSE IF( N.LT.0 ) THEN
- INFO = -2
- ELSE IF( LDA.LT.MAX( 1, N ) ) THEN
- INFO = -4
- ELSE IF( LWORK.LT.MAX( 1, N-1 ) .AND. .NOT.LQUERY ) THEN
- INFO = -7
- END IF
-*
- IF( INFO.EQ.0 ) THEN
- IF( UPPER ) THEN
- NB = ILAENV( 1, 'ZUNGQL', ' ', N-1, N-1, N-1, -1 )
- ELSE
- NB = ILAENV( 1, 'ZUNGQR', ' ', N-1, N-1, N-1, -1 )
- END IF
- LWKOPT = MAX( 1, N-1 )*NB
- WORK( 1 ) = LWKOPT
- END IF
-*
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'ZUNGTR', -INFO )
- RETURN
- ELSE IF( LQUERY ) THEN
- RETURN
- END IF
-*
-* Quick return if possible
-*
- IF( N.EQ.0 ) THEN
- WORK( 1 ) = 1
- RETURN
- END IF
-*
- IF( UPPER ) THEN
-*
-* Q was determined by a call to ZHETRD with UPLO = 'U'
-*
-* Shift the vectors which define the elementary reflectors one
-* column to the left, and set the last row and column of Q to
-* those of the unit matrix
-*
- DO 20 J = 1, N - 1
- DO 10 I = 1, J - 1
- A( I, J ) = A( I, J+1 )
- 10 CONTINUE
- A( N, J ) = ZERO
- 20 CONTINUE
- DO 30 I = 1, N - 1
- A( I, N ) = ZERO
- 30 CONTINUE
- A( N, N ) = ONE
-*
-* Generate Q(1:n-1,1:n-1)
-*
- CALL ZUNGQL( N-1, N-1, N-1, A, LDA, TAU, WORK, LWORK, IINFO )
-*
- ELSE
-*
-* Q was determined by a call to ZHETRD with UPLO = 'L'.
-*
-* Shift the vectors which define the elementary reflectors one
-* column to the right, and set the first row and column of Q to
-* those of the unit matrix
-*
- DO 50 J = N, 2, -1
- A( 1, J ) = ZERO
- DO 40 I = J + 1, N
- A( I, J ) = A( I, J-1 )
- 40 CONTINUE
- 50 CONTINUE
- A( 1, 1 ) = ONE
- DO 60 I = 2, N
- A( I, 1 ) = ZERO
- 60 CONTINUE
- IF( N.GT.1 ) THEN
-*
-* Generate Q(2:n,2:n)
-*
- CALL ZUNGQR( N-1, N-1, N-1, A( 2, 2 ), LDA, TAU, WORK,
- $ LWORK, IINFO )
- END IF
- END IF
- WORK( 1 ) = LWKOPT
- RETURN
-*
-* End of ZUNGTR
-*
- END
diff --git a/src/lib/lapack/zunm2r.f b/src/lib/lapack/zunm2r.f
deleted file mode 100644
index 7d4c067a..00000000
--- a/src/lib/lapack/zunm2r.f
+++ /dev/null
@@ -1,201 +0,0 @@
- SUBROUTINE ZUNM2R( SIDE, TRANS, M, N, K, A, LDA, TAU, C, LDC,
- $ WORK, INFO )
-*
-* -- LAPACK routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- CHARACTER SIDE, TRANS
- INTEGER INFO, K, LDA, LDC, M, N
-* ..
-* .. Array Arguments ..
- COMPLEX*16 A( LDA, * ), C( LDC, * ), TAU( * ), WORK( * )
-* ..
-*
-* Purpose
-* =======
-*
-* ZUNM2R overwrites the general complex m-by-n matrix C with
-*
-* Q * C if SIDE = 'L' and TRANS = 'N', or
-*
-* Q'* C if SIDE = 'L' and TRANS = 'C', or
-*
-* C * Q if SIDE = 'R' and TRANS = 'N', or
-*
-* C * Q' if SIDE = 'R' and TRANS = 'C',
-*
-* where Q is a complex unitary matrix defined as the product of k
-* elementary reflectors
-*
-* Q = H(1) H(2) . . . H(k)
-*
-* as returned by ZGEQRF. Q is of order m if SIDE = 'L' and of order n
-* if SIDE = 'R'.
-*
-* Arguments
-* =========
-*
-* SIDE (input) CHARACTER*1
-* = 'L': apply Q or Q' from the Left
-* = 'R': apply Q or Q' from the Right
-*
-* TRANS (input) CHARACTER*1
-* = 'N': apply Q (No transpose)
-* = 'C': apply Q' (Conjugate transpose)
-*
-* M (input) INTEGER
-* The number of rows of the matrix C. M >= 0.
-*
-* N (input) INTEGER
-* The number of columns of the matrix C. N >= 0.
-*
-* K (input) INTEGER
-* The number of elementary reflectors whose product defines
-* the matrix Q.
-* If SIDE = 'L', M >= K >= 0;
-* if SIDE = 'R', N >= K >= 0.
-*
-* A (input) COMPLEX*16 array, dimension (LDA,K)
-* The i-th column must contain the vector which defines the
-* elementary reflector H(i), for i = 1,2,...,k, as returned by
-* ZGEQRF in the first k columns of its array argument A.
-* A is modified by the routine but restored on exit.
-*
-* LDA (input) INTEGER
-* The leading dimension of the array A.
-* If SIDE = 'L', LDA >= max(1,M);
-* if SIDE = 'R', LDA >= max(1,N).
-*
-* TAU (input) COMPLEX*16 array, dimension (K)
-* TAU(i) must contain the scalar factor of the elementary
-* reflector H(i), as returned by ZGEQRF.
-*
-* C (input/output) COMPLEX*16 array, dimension (LDC,N)
-* On entry, the m-by-n matrix C.
-* On exit, C is overwritten by Q*C or Q'*C or C*Q' or C*Q.
-*
-* LDC (input) INTEGER
-* The leading dimension of the array C. LDC >= max(1,M).
-*
-* WORK (workspace) COMPLEX*16 array, dimension
-* (N) if SIDE = 'L',
-* (M) if SIDE = 'R'
-*
-* INFO (output) INTEGER
-* = 0: successful exit
-* < 0: if INFO = -i, the i-th argument had an illegal value
-*
-* =====================================================================
-*
-* .. Parameters ..
- COMPLEX*16 ONE
- PARAMETER ( ONE = ( 1.0D+0, 0.0D+0 ) )
-* ..
-* .. Local Scalars ..
- LOGICAL LEFT, NOTRAN
- INTEGER I, I1, I2, I3, IC, JC, MI, NI, NQ
- COMPLEX*16 AII, TAUI
-* ..
-* .. External Functions ..
- LOGICAL LSAME
- EXTERNAL LSAME
-* ..
-* .. External Subroutines ..
- EXTERNAL XERBLA, ZLARF
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC DCONJG, MAX
-* ..
-* .. Executable Statements ..
-*
-* Test the input arguments
-*
- INFO = 0
- LEFT = LSAME( SIDE, 'L' )
- NOTRAN = LSAME( TRANS, 'N' )
-*
-* NQ is the order of Q
-*
- IF( LEFT ) THEN
- NQ = M
- ELSE
- NQ = N
- END IF
- IF( .NOT.LEFT .AND. .NOT.LSAME( SIDE, 'R' ) ) THEN
- INFO = -1
- ELSE IF( .NOT.NOTRAN .AND. .NOT.LSAME( TRANS, 'C' ) ) THEN
- INFO = -2
- ELSE IF( M.LT.0 ) THEN
- INFO = -3
- ELSE IF( N.LT.0 ) THEN
- INFO = -4
- ELSE IF( K.LT.0 .OR. K.GT.NQ ) THEN
- INFO = -5
- ELSE IF( LDA.LT.MAX( 1, NQ ) ) THEN
- INFO = -7
- ELSE IF( LDC.LT.MAX( 1, M ) ) THEN
- INFO = -10
- END IF
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'ZUNM2R', -INFO )
- RETURN
- END IF
-*
-* Quick return if possible
-*
- IF( M.EQ.0 .OR. N.EQ.0 .OR. K.EQ.0 )
- $ RETURN
-*
- IF( ( LEFT .AND. .NOT.NOTRAN .OR. .NOT.LEFT .AND. NOTRAN ) ) THEN
- I1 = 1
- I2 = K
- I3 = 1
- ELSE
- I1 = K
- I2 = 1
- I3 = -1
- END IF
-*
- IF( LEFT ) THEN
- NI = N
- JC = 1
- ELSE
- MI = M
- IC = 1
- END IF
-*
- DO 10 I = I1, I2, I3
- IF( LEFT ) THEN
-*
-* H(i) or H(i)' is applied to C(i:m,1:n)
-*
- MI = M - I + 1
- IC = I
- ELSE
-*
-* H(i) or H(i)' is applied to C(1:m,i:n)
-*
- NI = N - I + 1
- JC = I
- END IF
-*
-* Apply H(i) or H(i)'
-*
- IF( NOTRAN ) THEN
- TAUI = TAU( I )
- ELSE
- TAUI = DCONJG( TAU( I ) )
- END IF
- AII = A( I, I )
- A( I, I ) = ONE
- CALL ZLARF( SIDE, MI, NI, A( I, I ), 1, TAUI, C( IC, JC ), LDC,
- $ WORK )
- A( I, I ) = AII
- 10 CONTINUE
- RETURN
-*
-* End of ZUNM2R
-*
- END
diff --git a/src/lib/lapack/zunmbr.f b/src/lib/lapack/zunmbr.f
deleted file mode 100644
index b32ce338..00000000
--- a/src/lib/lapack/zunmbr.f
+++ /dev/null
@@ -1,288 +0,0 @@
- SUBROUTINE ZUNMBR( VECT, SIDE, TRANS, M, N, K, A, LDA, TAU, C,
- $ LDC, WORK, LWORK, INFO )
-*
-* -- LAPACK routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- CHARACTER SIDE, TRANS, VECT
- INTEGER INFO, K, LDA, LDC, LWORK, M, N
-* ..
-* .. Array Arguments ..
- COMPLEX*16 A( LDA, * ), C( LDC, * ), TAU( * ), WORK( * )
-* ..
-*
-* Purpose
-* =======
-*
-* If VECT = 'Q', ZUNMBR overwrites the general complex M-by-N matrix C
-* with
-* SIDE = 'L' SIDE = 'R'
-* TRANS = 'N': Q * C C * Q
-* TRANS = 'C': Q**H * C C * Q**H
-*
-* If VECT = 'P', ZUNMBR overwrites the general complex M-by-N matrix C
-* with
-* SIDE = 'L' SIDE = 'R'
-* TRANS = 'N': P * C C * P
-* TRANS = 'C': P**H * C C * P**H
-*
-* Here Q and P**H are the unitary matrices determined by ZGEBRD when
-* reducing a complex matrix A to bidiagonal form: A = Q * B * P**H. Q
-* and P**H are defined as products of elementary reflectors H(i) and
-* G(i) respectively.
-*
-* Let nq = m if SIDE = 'L' and nq = n if SIDE = 'R'. Thus nq is the
-* order of the unitary matrix Q or P**H that is applied.
-*
-* If VECT = 'Q', A is assumed to have been an NQ-by-K matrix:
-* if nq >= k, Q = H(1) H(2) . . . H(k);
-* if nq < k, Q = H(1) H(2) . . . H(nq-1).
-*
-* If VECT = 'P', A is assumed to have been a K-by-NQ matrix:
-* if k < nq, P = G(1) G(2) . . . G(k);
-* if k >= nq, P = G(1) G(2) . . . G(nq-1).
-*
-* Arguments
-* =========
-*
-* VECT (input) CHARACTER*1
-* = 'Q': apply Q or Q**H;
-* = 'P': apply P or P**H.
-*
-* SIDE (input) CHARACTER*1
-* = 'L': apply Q, Q**H, P or P**H from the Left;
-* = 'R': apply Q, Q**H, P or P**H from the Right.
-*
-* TRANS (input) CHARACTER*1
-* = 'N': No transpose, apply Q or P;
-* = 'C': Conjugate transpose, apply Q**H or P**H.
-*
-* M (input) INTEGER
-* The number of rows of the matrix C. M >= 0.
-*
-* N (input) INTEGER
-* The number of columns of the matrix C. N >= 0.
-*
-* K (input) INTEGER
-* If VECT = 'Q', the number of columns in the original
-* matrix reduced by ZGEBRD.
-* If VECT = 'P', the number of rows in the original
-* matrix reduced by ZGEBRD.
-* K >= 0.
-*
-* A (input) COMPLEX*16 array, dimension
-* (LDA,min(nq,K)) if VECT = 'Q'
-* (LDA,nq) if VECT = 'P'
-* The vectors which define the elementary reflectors H(i) and
-* G(i), whose products determine the matrices Q and P, as
-* returned by ZGEBRD.
-*
-* LDA (input) INTEGER
-* The leading dimension of the array A.
-* If VECT = 'Q', LDA >= max(1,nq);
-* if VECT = 'P', LDA >= max(1,min(nq,K)).
-*
-* TAU (input) COMPLEX*16 array, dimension (min(nq,K))
-* TAU(i) must contain the scalar factor of the elementary
-* reflector H(i) or G(i) which determines Q or P, as returned
-* by ZGEBRD in the array argument TAUQ or TAUP.
-*
-* C (input/output) COMPLEX*16 array, dimension (LDC,N)
-* On entry, the M-by-N matrix C.
-* On exit, C is overwritten by Q*C or Q**H*C or C*Q**H or C*Q
-* or P*C or P**H*C or C*P or C*P**H.
-*
-* LDC (input) INTEGER
-* The leading dimension of the array C. LDC >= max(1,M).
-*
-* WORK (workspace/output) COMPLEX*16 array, dimension (MAX(1,LWORK))
-* On exit, if INFO = 0, WORK(1) returns the optimal LWORK.
-*
-* LWORK (input) INTEGER
-* The dimension of the array WORK.
-* If SIDE = 'L', LWORK >= max(1,N);
-* if SIDE = 'R', LWORK >= max(1,M);
-* if N = 0 or M = 0, LWORK >= 1.
-* For optimum performance LWORK >= max(1,N*NB) if SIDE = 'L',
-* and LWORK >= max(1,M*NB) if SIDE = 'R', where NB is the
-* optimal blocksize. (NB = 0 if M = 0 or N = 0.)
-*
-* If LWORK = -1, then a workspace query is assumed; the routine
-* only calculates the optimal size of the WORK array, returns
-* this value as the first entry of the WORK array, and no error
-* message related to LWORK is issued by XERBLA.
-*
-* INFO (output) INTEGER
-* = 0: successful exit
-* < 0: if INFO = -i, the i-th argument had an illegal value
-*
-* =====================================================================
-*
-* .. Local Scalars ..
- LOGICAL APPLYQ, LEFT, LQUERY, NOTRAN
- CHARACTER TRANST
- INTEGER I1, I2, IINFO, LWKOPT, MI, NB, NI, NQ, NW
-* ..
-* .. External Functions ..
- LOGICAL LSAME
- INTEGER ILAENV
- EXTERNAL LSAME, ILAENV
-* ..
-* .. External Subroutines ..
- EXTERNAL XERBLA, ZUNMLQ, ZUNMQR
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC MAX, MIN
-* ..
-* .. Executable Statements ..
-*
-* Test the input arguments
-*
- INFO = 0
- APPLYQ = LSAME( VECT, 'Q' )
- LEFT = LSAME( SIDE, 'L' )
- NOTRAN = LSAME( TRANS, 'N' )
- LQUERY = ( LWORK.EQ.-1 )
-*
-* NQ is the order of Q or P and NW is the minimum dimension of WORK
-*
- IF( LEFT ) THEN
- NQ = M
- NW = N
- ELSE
- NQ = N
- NW = M
- END IF
- IF( M.EQ.0 .OR. N.EQ.0 ) THEN
- NW = 0
- END IF
- IF( .NOT.APPLYQ .AND. .NOT.LSAME( VECT, 'P' ) ) THEN
- INFO = -1
- ELSE IF( .NOT.LEFT .AND. .NOT.LSAME( SIDE, 'R' ) ) THEN
- INFO = -2
- ELSE IF( .NOT.NOTRAN .AND. .NOT.LSAME( TRANS, 'C' ) ) THEN
- INFO = -3
- ELSE IF( M.LT.0 ) THEN
- INFO = -4
- ELSE IF( N.LT.0 ) THEN
- INFO = -5
- ELSE IF( K.LT.0 ) THEN
- INFO = -6
- ELSE IF( ( APPLYQ .AND. LDA.LT.MAX( 1, NQ ) ) .OR.
- $ ( .NOT.APPLYQ .AND. LDA.LT.MAX( 1, MIN( NQ, K ) ) ) )
- $ THEN
- INFO = -8
- ELSE IF( LDC.LT.MAX( 1, M ) ) THEN
- INFO = -11
- ELSE IF( LWORK.LT.MAX( 1, NW ) .AND. .NOT.LQUERY ) THEN
- INFO = -13
- END IF
-*
- IF( INFO.EQ.0 ) THEN
- IF( NW.GT.0 ) THEN
- IF( APPLYQ ) THEN
- IF( LEFT ) THEN
- NB = ILAENV( 1, 'ZUNMQR', SIDE // TRANS, M-1, N, M-1,
- $ -1 )
- ELSE
- NB = ILAENV( 1, 'ZUNMQR', SIDE // TRANS, M, N-1, N-1,
- $ -1 )
- END IF
- ELSE
- IF( LEFT ) THEN
- NB = ILAENV( 1, 'ZUNMLQ', SIDE // TRANS, M-1, N, M-1,
- $ -1 )
- ELSE
- NB = ILAENV( 1, 'ZUNMLQ', SIDE // TRANS, M, N-1, N-1,
- $ -1 )
- END IF
- END IF
- LWKOPT = MAX( 1, NW*NB )
- ELSE
- LWKOPT = 1
- END IF
- WORK( 1 ) = LWKOPT
- END IF
-*
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'ZUNMBR', -INFO )
- RETURN
- ELSE IF( LQUERY ) THEN
- RETURN
- END IF
-*
-* Quick return if possible
-*
- IF( M.EQ.0 .OR. N.EQ.0 )
- $ RETURN
-*
- IF( APPLYQ ) THEN
-*
-* Apply Q
-*
- IF( NQ.GE.K ) THEN
-*
-* Q was determined by a call to ZGEBRD with nq >= k
-*
- CALL ZUNMQR( SIDE, TRANS, M, N, K, A, LDA, TAU, C, LDC,
- $ WORK, LWORK, IINFO )
- ELSE IF( NQ.GT.1 ) THEN
-*
-* Q was determined by a call to ZGEBRD with nq < k
-*
- IF( LEFT ) THEN
- MI = M - 1
- NI = N
- I1 = 2
- I2 = 1
- ELSE
- MI = M
- NI = N - 1
- I1 = 1
- I2 = 2
- END IF
- CALL ZUNMQR( SIDE, TRANS, MI, NI, NQ-1, A( 2, 1 ), LDA, TAU,
- $ C( I1, I2 ), LDC, WORK, LWORK, IINFO )
- END IF
- ELSE
-*
-* Apply P
-*
- IF( NOTRAN ) THEN
- TRANST = 'C'
- ELSE
- TRANST = 'N'
- END IF
- IF( NQ.GT.K ) THEN
-*
-* P was determined by a call to ZGEBRD with nq > k
-*
- CALL ZUNMLQ( SIDE, TRANST, M, N, K, A, LDA, TAU, C, LDC,
- $ WORK, LWORK, IINFO )
- ELSE IF( NQ.GT.1 ) THEN
-*
-* P was determined by a call to ZGEBRD with nq <= k
-*
- IF( LEFT ) THEN
- MI = M - 1
- NI = N
- I1 = 2
- I2 = 1
- ELSE
- MI = M
- NI = N - 1
- I1 = 1
- I2 = 2
- END IF
- CALL ZUNMLQ( SIDE, TRANST, MI, NI, NQ-1, A( 1, 2 ), LDA,
- $ TAU, C( I1, I2 ), LDC, WORK, LWORK, IINFO )
- END IF
- END IF
- WORK( 1 ) = LWKOPT
- RETURN
-*
-* End of ZUNMBR
-*
- END
diff --git a/src/lib/lapack/zunml2.f b/src/lib/lapack/zunml2.f
deleted file mode 100644
index cced4a77..00000000
--- a/src/lib/lapack/zunml2.f
+++ /dev/null
@@ -1,205 +0,0 @@
- SUBROUTINE ZUNML2( SIDE, TRANS, M, N, K, A, LDA, TAU, C, LDC,
- $ WORK, INFO )
-*
-* -- LAPACK routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- CHARACTER SIDE, TRANS
- INTEGER INFO, K, LDA, LDC, M, N
-* ..
-* .. Array Arguments ..
- COMPLEX*16 A( LDA, * ), C( LDC, * ), TAU( * ), WORK( * )
-* ..
-*
-* Purpose
-* =======
-*
-* ZUNML2 overwrites the general complex m-by-n matrix C with
-*
-* Q * C if SIDE = 'L' and TRANS = 'N', or
-*
-* Q'* C if SIDE = 'L' and TRANS = 'C', or
-*
-* C * Q if SIDE = 'R' and TRANS = 'N', or
-*
-* C * Q' if SIDE = 'R' and TRANS = 'C',
-*
-* where Q is a complex unitary matrix defined as the product of k
-* elementary reflectors
-*
-* Q = H(k)' . . . H(2)' H(1)'
-*
-* as returned by ZGELQF. Q is of order m if SIDE = 'L' and of order n
-* if SIDE = 'R'.
-*
-* Arguments
-* =========
-*
-* SIDE (input) CHARACTER*1
-* = 'L': apply Q or Q' from the Left
-* = 'R': apply Q or Q' from the Right
-*
-* TRANS (input) CHARACTER*1
-* = 'N': apply Q (No transpose)
-* = 'C': apply Q' (Conjugate transpose)
-*
-* M (input) INTEGER
-* The number of rows of the matrix C. M >= 0.
-*
-* N (input) INTEGER
-* The number of columns of the matrix C. N >= 0.
-*
-* K (input) INTEGER
-* The number of elementary reflectors whose product defines
-* the matrix Q.
-* If SIDE = 'L', M >= K >= 0;
-* if SIDE = 'R', N >= K >= 0.
-*
-* A (input) COMPLEX*16 array, dimension
-* (LDA,M) if SIDE = 'L',
-* (LDA,N) if SIDE = 'R'
-* The i-th row must contain the vector which defines the
-* elementary reflector H(i), for i = 1,2,...,k, as returned by
-* ZGELQF in the first k rows of its array argument A.
-* A is modified by the routine but restored on exit.
-*
-* LDA (input) INTEGER
-* The leading dimension of the array A. LDA >= max(1,K).
-*
-* TAU (input) COMPLEX*16 array, dimension (K)
-* TAU(i) must contain the scalar factor of the elementary
-* reflector H(i), as returned by ZGELQF.
-*
-* C (input/output) COMPLEX*16 array, dimension (LDC,N)
-* On entry, the m-by-n matrix C.
-* On exit, C is overwritten by Q*C or Q'*C or C*Q' or C*Q.
-*
-* LDC (input) INTEGER
-* The leading dimension of the array C. LDC >= max(1,M).
-*
-* WORK (workspace) COMPLEX*16 array, dimension
-* (N) if SIDE = 'L',
-* (M) if SIDE = 'R'
-*
-* INFO (output) INTEGER
-* = 0: successful exit
-* < 0: if INFO = -i, the i-th argument had an illegal value
-*
-* =====================================================================
-*
-* .. Parameters ..
- COMPLEX*16 ONE
- PARAMETER ( ONE = ( 1.0D+0, 0.0D+0 ) )
-* ..
-* .. Local Scalars ..
- LOGICAL LEFT, NOTRAN
- INTEGER I, I1, I2, I3, IC, JC, MI, NI, NQ
- COMPLEX*16 AII, TAUI
-* ..
-* .. External Functions ..
- LOGICAL LSAME
- EXTERNAL LSAME
-* ..
-* .. External Subroutines ..
- EXTERNAL XERBLA, ZLACGV, ZLARF
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC DCONJG, MAX
-* ..
-* .. Executable Statements ..
-*
-* Test the input arguments
-*
- INFO = 0
- LEFT = LSAME( SIDE, 'L' )
- NOTRAN = LSAME( TRANS, 'N' )
-*
-* NQ is the order of Q
-*
- IF( LEFT ) THEN
- NQ = M
- ELSE
- NQ = N
- END IF
- IF( .NOT.LEFT .AND. .NOT.LSAME( SIDE, 'R' ) ) THEN
- INFO = -1
- ELSE IF( .NOT.NOTRAN .AND. .NOT.LSAME( TRANS, 'C' ) ) THEN
- INFO = -2
- ELSE IF( M.LT.0 ) THEN
- INFO = -3
- ELSE IF( N.LT.0 ) THEN
- INFO = -4
- ELSE IF( K.LT.0 .OR. K.GT.NQ ) THEN
- INFO = -5
- ELSE IF( LDA.LT.MAX( 1, K ) ) THEN
- INFO = -7
- ELSE IF( LDC.LT.MAX( 1, M ) ) THEN
- INFO = -10
- END IF
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'ZUNML2', -INFO )
- RETURN
- END IF
-*
-* Quick return if possible
-*
- IF( M.EQ.0 .OR. N.EQ.0 .OR. K.EQ.0 )
- $ RETURN
-*
- IF( ( LEFT .AND. NOTRAN .OR. .NOT.LEFT .AND. .NOT.NOTRAN ) ) THEN
- I1 = 1
- I2 = K
- I3 = 1
- ELSE
- I1 = K
- I2 = 1
- I3 = -1
- END IF
-*
- IF( LEFT ) THEN
- NI = N
- JC = 1
- ELSE
- MI = M
- IC = 1
- END IF
-*
- DO 10 I = I1, I2, I3
- IF( LEFT ) THEN
-*
-* H(i) or H(i)' is applied to C(i:m,1:n)
-*
- MI = M - I + 1
- IC = I
- ELSE
-*
-* H(i) or H(i)' is applied to C(1:m,i:n)
-*
- NI = N - I + 1
- JC = I
- END IF
-*
-* Apply H(i) or H(i)'
-*
- IF( NOTRAN ) THEN
- TAUI = DCONJG( TAU( I ) )
- ELSE
- TAUI = TAU( I )
- END IF
- IF( I.LT.NQ )
- $ CALL ZLACGV( NQ-I, A( I, I+1 ), LDA )
- AII = A( I, I )
- A( I, I ) = ONE
- CALL ZLARF( SIDE, MI, NI, A( I, I ), LDA, TAUI, C( IC, JC ),
- $ LDC, WORK )
- A( I, I ) = AII
- IF( I.LT.NQ )
- $ CALL ZLACGV( NQ-I, A( I, I+1 ), LDA )
- 10 CONTINUE
- RETURN
-*
-* End of ZUNML2
-*
- END
diff --git a/src/lib/lapack/zunmlq.f b/src/lib/lapack/zunmlq.f
deleted file mode 100644
index b1708757..00000000
--- a/src/lib/lapack/zunmlq.f
+++ /dev/null
@@ -1,267 +0,0 @@
- SUBROUTINE ZUNMLQ( SIDE, TRANS, M, N, K, A, LDA, TAU, C, LDC,
- $ WORK, LWORK, INFO )
-*
-* -- LAPACK routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- CHARACTER SIDE, TRANS
- INTEGER INFO, K, LDA, LDC, LWORK, M, N
-* ..
-* .. Array Arguments ..
- COMPLEX*16 A( LDA, * ), C( LDC, * ), TAU( * ), WORK( * )
-* ..
-*
-* Purpose
-* =======
-*
-* ZUNMLQ overwrites the general complex M-by-N matrix C with
-*
-* SIDE = 'L' SIDE = 'R'
-* TRANS = 'N': Q * C C * Q
-* TRANS = 'C': Q**H * C C * Q**H
-*
-* where Q is a complex unitary matrix defined as the product of k
-* elementary reflectors
-*
-* Q = H(k)' . . . H(2)' H(1)'
-*
-* as returned by ZGELQF. Q is of order M if SIDE = 'L' and of order N
-* if SIDE = 'R'.
-*
-* Arguments
-* =========
-*
-* SIDE (input) CHARACTER*1
-* = 'L': apply Q or Q**H from the Left;
-* = 'R': apply Q or Q**H from the Right.
-*
-* TRANS (input) CHARACTER*1
-* = 'N': No transpose, apply Q;
-* = 'C': Conjugate transpose, apply Q**H.
-*
-* M (input) INTEGER
-* The number of rows of the matrix C. M >= 0.
-*
-* N (input) INTEGER
-* The number of columns of the matrix C. N >= 0.
-*
-* K (input) INTEGER
-* The number of elementary reflectors whose product defines
-* the matrix Q.
-* If SIDE = 'L', M >= K >= 0;
-* if SIDE = 'R', N >= K >= 0.
-*
-* A (input) COMPLEX*16 array, dimension
-* (LDA,M) if SIDE = 'L',
-* (LDA,N) if SIDE = 'R'
-* The i-th row must contain the vector which defines the
-* elementary reflector H(i), for i = 1,2,...,k, as returned by
-* ZGELQF in the first k rows of its array argument A.
-* A is modified by the routine but restored on exit.
-*
-* LDA (input) INTEGER
-* The leading dimension of the array A. LDA >= max(1,K).
-*
-* TAU (input) COMPLEX*16 array, dimension (K)
-* TAU(i) must contain the scalar factor of the elementary
-* reflector H(i), as returned by ZGELQF.
-*
-* C (input/output) COMPLEX*16 array, dimension (LDC,N)
-* On entry, the M-by-N matrix C.
-* On exit, C is overwritten by Q*C or Q**H*C or C*Q**H or C*Q.
-*
-* LDC (input) INTEGER
-* The leading dimension of the array C. LDC >= max(1,M).
-*
-* WORK (workspace/output) COMPLEX*16 array, dimension (MAX(1,LWORK))
-* On exit, if INFO = 0, WORK(1) returns the optimal LWORK.
-*
-* LWORK (input) INTEGER
-* The dimension of the array WORK.
-* If SIDE = 'L', LWORK >= max(1,N);
-* if SIDE = 'R', LWORK >= max(1,M).
-* For optimum performance LWORK >= N*NB if SIDE 'L', and
-* LWORK >= M*NB if SIDE = 'R', where NB is the optimal
-* blocksize.
-*
-* If LWORK = -1, then a workspace query is assumed; the routine
-* only calculates the optimal size of the WORK array, returns
-* this value as the first entry of the WORK array, and no error
-* message related to LWORK is issued by XERBLA.
-*
-* INFO (output) INTEGER
-* = 0: successful exit
-* < 0: if INFO = -i, the i-th argument had an illegal value
-*
-* =====================================================================
-*
-* .. Parameters ..
- INTEGER NBMAX, LDT
- PARAMETER ( NBMAX = 64, LDT = NBMAX+1 )
-* ..
-* .. Local Scalars ..
- LOGICAL LEFT, LQUERY, NOTRAN
- CHARACTER TRANST
- INTEGER I, I1, I2, I3, IB, IC, IINFO, IWS, JC, LDWORK,
- $ LWKOPT, MI, NB, NBMIN, NI, NQ, NW
-* ..
-* .. Local Arrays ..
- COMPLEX*16 T( LDT, NBMAX )
-* ..
-* .. External Functions ..
- LOGICAL LSAME
- INTEGER ILAENV
- EXTERNAL LSAME, ILAENV
-* ..
-* .. External Subroutines ..
- EXTERNAL XERBLA, ZLARFB, ZLARFT, ZUNML2
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC MAX, MIN
-* ..
-* .. Executable Statements ..
-*
-* Test the input arguments
-*
- INFO = 0
- LEFT = LSAME( SIDE, 'L' )
- NOTRAN = LSAME( TRANS, 'N' )
- LQUERY = ( LWORK.EQ.-1 )
-*
-* NQ is the order of Q and NW is the minimum dimension of WORK
-*
- IF( LEFT ) THEN
- NQ = M
- NW = N
- ELSE
- NQ = N
- NW = M
- END IF
- IF( .NOT.LEFT .AND. .NOT.LSAME( SIDE, 'R' ) ) THEN
- INFO = -1
- ELSE IF( .NOT.NOTRAN .AND. .NOT.LSAME( TRANS, 'C' ) ) THEN
- INFO = -2
- ELSE IF( M.LT.0 ) THEN
- INFO = -3
- ELSE IF( N.LT.0 ) THEN
- INFO = -4
- ELSE IF( K.LT.0 .OR. K.GT.NQ ) THEN
- INFO = -5
- ELSE IF( LDA.LT.MAX( 1, K ) ) THEN
- INFO = -7
- ELSE IF( LDC.LT.MAX( 1, M ) ) THEN
- INFO = -10
- ELSE IF( LWORK.LT.MAX( 1, NW ) .AND. .NOT.LQUERY ) THEN
- INFO = -12
- END IF
-*
- IF( INFO.EQ.0 ) THEN
-*
-* Determine the block size. NB may be at most NBMAX, where NBMAX
-* is used to define the local array T.
-*
- NB = MIN( NBMAX, ILAENV( 1, 'ZUNMLQ', SIDE // TRANS, M, N, K,
- $ -1 ) )
- LWKOPT = MAX( 1, NW )*NB
- WORK( 1 ) = LWKOPT
- END IF
-*
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'ZUNMLQ', -INFO )
- RETURN
- ELSE IF( LQUERY ) THEN
- RETURN
- END IF
-*
-* Quick return if possible
-*
- IF( M.EQ.0 .OR. N.EQ.0 .OR. K.EQ.0 ) THEN
- WORK( 1 ) = 1
- RETURN
- END IF
-*
- NBMIN = 2
- LDWORK = NW
- IF( NB.GT.1 .AND. NB.LT.K ) THEN
- IWS = NW*NB
- IF( LWORK.LT.IWS ) THEN
- NB = LWORK / LDWORK
- NBMIN = MAX( 2, ILAENV( 2, 'ZUNMLQ', SIDE // TRANS, M, N, K,
- $ -1 ) )
- END IF
- ELSE
- IWS = NW
- END IF
-*
- IF( NB.LT.NBMIN .OR. NB.GE.K ) THEN
-*
-* Use unblocked code
-*
- CALL ZUNML2( SIDE, TRANS, M, N, K, A, LDA, TAU, C, LDC, WORK,
- $ IINFO )
- ELSE
-*
-* Use blocked code
-*
- IF( ( LEFT .AND. NOTRAN ) .OR.
- $ ( .NOT.LEFT .AND. .NOT.NOTRAN ) ) THEN
- I1 = 1
- I2 = K
- I3 = NB
- ELSE
- I1 = ( ( K-1 ) / NB )*NB + 1
- I2 = 1
- I3 = -NB
- END IF
-*
- IF( LEFT ) THEN
- NI = N
- JC = 1
- ELSE
- MI = M
- IC = 1
- END IF
-*
- IF( NOTRAN ) THEN
- TRANST = 'C'
- ELSE
- TRANST = 'N'
- END IF
-*
- DO 10 I = I1, I2, I3
- IB = MIN( NB, K-I+1 )
-*
-* Form the triangular factor of the block reflector
-* H = H(i) H(i+1) . . . H(i+ib-1)
-*
- CALL ZLARFT( 'Forward', 'Rowwise', NQ-I+1, IB, A( I, I ),
- $ LDA, TAU( I ), T, LDT )
- IF( LEFT ) THEN
-*
-* H or H' is applied to C(i:m,1:n)
-*
- MI = M - I + 1
- IC = I
- ELSE
-*
-* H or H' is applied to C(1:m,i:n)
-*
- NI = N - I + 1
- JC = I
- END IF
-*
-* Apply H or H'
-*
- CALL ZLARFB( SIDE, TRANST, 'Forward', 'Rowwise', MI, NI, IB,
- $ A( I, I ), LDA, T, LDT, C( IC, JC ), LDC, WORK,
- $ LDWORK )
- 10 CONTINUE
- END IF
- WORK( 1 ) = LWKOPT
- RETURN
-*
-* End of ZUNMLQ
-*
- END
diff --git a/src/lib/lapack/zunmqr.f b/src/lib/lapack/zunmqr.f
deleted file mode 100644
index f9b1e98f..00000000
--- a/src/lib/lapack/zunmqr.f
+++ /dev/null
@@ -1,260 +0,0 @@
- SUBROUTINE ZUNMQR( SIDE, TRANS, M, N, K, A, LDA, TAU, C, LDC,
- $ WORK, LWORK, INFO )
-*
-* -- LAPACK routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- CHARACTER SIDE, TRANS
- INTEGER INFO, K, LDA, LDC, LWORK, M, N
-* ..
-* .. Array Arguments ..
- COMPLEX*16 A( LDA, * ), C( LDC, * ), TAU( * ), WORK( * )
-* ..
-*
-* Purpose
-* =======
-*
-* ZUNMQR overwrites the general complex M-by-N matrix C with
-*
-* SIDE = 'L' SIDE = 'R'
-* TRANS = 'N': Q * C C * Q
-* TRANS = 'C': Q**H * C C * Q**H
-*
-* where Q is a complex unitary matrix defined as the product of k
-* elementary reflectors
-*
-* Q = H(1) H(2) . . . H(k)
-*
-* as returned by ZGEQRF. Q is of order M if SIDE = 'L' and of order N
-* if SIDE = 'R'.
-*
-* Arguments
-* =========
-*
-* SIDE (input) CHARACTER*1
-* = 'L': apply Q or Q**H from the Left;
-* = 'R': apply Q or Q**H from the Right.
-*
-* TRANS (input) CHARACTER*1
-* = 'N': No transpose, apply Q;
-* = 'C': Conjugate transpose, apply Q**H.
-*
-* M (input) INTEGER
-* The number of rows of the matrix C. M >= 0.
-*
-* N (input) INTEGER
-* The number of columns of the matrix C. N >= 0.
-*
-* K (input) INTEGER
-* The number of elementary reflectors whose product defines
-* the matrix Q.
-* If SIDE = 'L', M >= K >= 0;
-* if SIDE = 'R', N >= K >= 0.
-*
-* A (input) COMPLEX*16 array, dimension (LDA,K)
-* The i-th column must contain the vector which defines the
-* elementary reflector H(i), for i = 1,2,...,k, as returned by
-* ZGEQRF in the first k columns of its array argument A.
-* A is modified by the routine but restored on exit.
-*
-* LDA (input) INTEGER
-* The leading dimension of the array A.
-* If SIDE = 'L', LDA >= max(1,M);
-* if SIDE = 'R', LDA >= max(1,N).
-*
-* TAU (input) COMPLEX*16 array, dimension (K)
-* TAU(i) must contain the scalar factor of the elementary
-* reflector H(i), as returned by ZGEQRF.
-*
-* C (input/output) COMPLEX*16 array, dimension (LDC,N)
-* On entry, the M-by-N matrix C.
-* On exit, C is overwritten by Q*C or Q**H*C or C*Q**H or C*Q.
-*
-* LDC (input) INTEGER
-* The leading dimension of the array C. LDC >= max(1,M).
-*
-* WORK (workspace/output) COMPLEX*16 array, dimension (MAX(1,LWORK))
-* On exit, if INFO = 0, WORK(1) returns the optimal LWORK.
-*
-* LWORK (input) INTEGER
-* The dimension of the array WORK.
-* If SIDE = 'L', LWORK >= max(1,N);
-* if SIDE = 'R', LWORK >= max(1,M).
-* For optimum performance LWORK >= N*NB if SIDE = 'L', and
-* LWORK >= M*NB if SIDE = 'R', where NB is the optimal
-* blocksize.
-*
-* If LWORK = -1, then a workspace query is assumed; the routine
-* only calculates the optimal size of the WORK array, returns
-* this value as the first entry of the WORK array, and no error
-* message related to LWORK is issued by XERBLA.
-*
-* INFO (output) INTEGER
-* = 0: successful exit
-* < 0: if INFO = -i, the i-th argument had an illegal value
-*
-* =====================================================================
-*
-* .. Parameters ..
- INTEGER NBMAX, LDT
- PARAMETER ( NBMAX = 64, LDT = NBMAX+1 )
-* ..
-* .. Local Scalars ..
- LOGICAL LEFT, LQUERY, NOTRAN
- INTEGER I, I1, I2, I3, IB, IC, IINFO, IWS, JC, LDWORK,
- $ LWKOPT, MI, NB, NBMIN, NI, NQ, NW
-* ..
-* .. Local Arrays ..
- COMPLEX*16 T( LDT, NBMAX )
-* ..
-* .. External Functions ..
- LOGICAL LSAME
- INTEGER ILAENV
- EXTERNAL LSAME, ILAENV
-* ..
-* .. External Subroutines ..
- EXTERNAL XERBLA, ZLARFB, ZLARFT, ZUNM2R
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC MAX, MIN
-* ..
-* .. Executable Statements ..
-*
-* Test the input arguments
-*
- INFO = 0
- LEFT = LSAME( SIDE, 'L' )
- NOTRAN = LSAME( TRANS, 'N' )
- LQUERY = ( LWORK.EQ.-1 )
-*
-* NQ is the order of Q and NW is the minimum dimension of WORK
-*
- IF( LEFT ) THEN
- NQ = M
- NW = N
- ELSE
- NQ = N
- NW = M
- END IF
- IF( .NOT.LEFT .AND. .NOT.LSAME( SIDE, 'R' ) ) THEN
- INFO = -1
- ELSE IF( .NOT.NOTRAN .AND. .NOT.LSAME( TRANS, 'C' ) ) THEN
- INFO = -2
- ELSE IF( M.LT.0 ) THEN
- INFO = -3
- ELSE IF( N.LT.0 ) THEN
- INFO = -4
- ELSE IF( K.LT.0 .OR. K.GT.NQ ) THEN
- INFO = -5
- ELSE IF( LDA.LT.MAX( 1, NQ ) ) THEN
- INFO = -7
- ELSE IF( LDC.LT.MAX( 1, M ) ) THEN
- INFO = -10
- ELSE IF( LWORK.LT.MAX( 1, NW ) .AND. .NOT.LQUERY ) THEN
- INFO = -12
- END IF
-*
- IF( INFO.EQ.0 ) THEN
-*
-* Determine the block size. NB may be at most NBMAX, where NBMAX
-* is used to define the local array T.
-*
- NB = MIN( NBMAX, ILAENV( 1, 'ZUNMQR', SIDE // TRANS, M, N, K,
- $ -1 ) )
- LWKOPT = MAX( 1, NW )*NB
- WORK( 1 ) = LWKOPT
- END IF
-*
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'ZUNMQR', -INFO )
- RETURN
- ELSE IF( LQUERY ) THEN
- RETURN
- END IF
-*
-* Quick return if possible
-*
- IF( M.EQ.0 .OR. N.EQ.0 .OR. K.EQ.0 ) THEN
- WORK( 1 ) = 1
- RETURN
- END IF
-*
- NBMIN = 2
- LDWORK = NW
- IF( NB.GT.1 .AND. NB.LT.K ) THEN
- IWS = NW*NB
- IF( LWORK.LT.IWS ) THEN
- NB = LWORK / LDWORK
- NBMIN = MAX( 2, ILAENV( 2, 'ZUNMQR', SIDE // TRANS, M, N, K,
- $ -1 ) )
- END IF
- ELSE
- IWS = NW
- END IF
-*
- IF( NB.LT.NBMIN .OR. NB.GE.K ) THEN
-*
-* Use unblocked code
-*
- CALL ZUNM2R( SIDE, TRANS, M, N, K, A, LDA, TAU, C, LDC, WORK,
- $ IINFO )
- ELSE
-*
-* Use blocked code
-*
- IF( ( LEFT .AND. .NOT.NOTRAN ) .OR.
- $ ( .NOT.LEFT .AND. NOTRAN ) ) THEN
- I1 = 1
- I2 = K
- I3 = NB
- ELSE
- I1 = ( ( K-1 ) / NB )*NB + 1
- I2 = 1
- I3 = -NB
- END IF
-*
- IF( LEFT ) THEN
- NI = N
- JC = 1
- ELSE
- MI = M
- IC = 1
- END IF
-*
- DO 10 I = I1, I2, I3
- IB = MIN( NB, K-I+1 )
-*
-* Form the triangular factor of the block reflector
-* H = H(i) H(i+1) . . . H(i+ib-1)
-*
- CALL ZLARFT( 'Forward', 'Columnwise', NQ-I+1, IB, A( I, I ),
- $ LDA, TAU( I ), T, LDT )
- IF( LEFT ) THEN
-*
-* H or H' is applied to C(i:m,1:n)
-*
- MI = M - I + 1
- IC = I
- ELSE
-*
-* H or H' is applied to C(1:m,i:n)
-*
- NI = N - I + 1
- JC = I
- END IF
-*
-* Apply H or H'
-*
- CALL ZLARFB( SIDE, TRANS, 'Forward', 'Columnwise', MI, NI,
- $ IB, A( I, I ), LDA, T, LDT, C( IC, JC ), LDC,
- $ WORK, LDWORK )
- 10 CONTINUE
- END IF
- WORK( 1 ) = LWKOPT
- RETURN
-*
-* End of ZUNMQR
-*
- END
diff --git a/src/lib/lapack/zunmr3.f b/src/lib/lapack/zunmr3.f
deleted file mode 100644
index 111c1c95..00000000
--- a/src/lib/lapack/zunmr3.f
+++ /dev/null
@@ -1,212 +0,0 @@
- SUBROUTINE ZUNMR3( SIDE, TRANS, M, N, K, L, A, LDA, TAU, C, LDC,
- $ WORK, INFO )
-*
-* -- LAPACK routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- CHARACTER SIDE, TRANS
- INTEGER INFO, K, L, LDA, LDC, M, N
-* ..
-* .. Array Arguments ..
- COMPLEX*16 A( LDA, * ), C( LDC, * ), TAU( * ), WORK( * )
-* ..
-*
-* Purpose
-* =======
-*
-* ZUNMR3 overwrites the general complex m by n matrix C with
-*
-* Q * C if SIDE = 'L' and TRANS = 'N', or
-*
-* Q'* C if SIDE = 'L' and TRANS = 'C', or
-*
-* C * Q if SIDE = 'R' and TRANS = 'N', or
-*
-* C * Q' if SIDE = 'R' and TRANS = 'C',
-*
-* where Q is a complex unitary matrix defined as the product of k
-* elementary reflectors
-*
-* Q = H(1) H(2) . . . H(k)
-*
-* as returned by ZTZRZF. Q is of order m if SIDE = 'L' and of order n
-* if SIDE = 'R'.
-*
-* Arguments
-* =========
-*
-* SIDE (input) CHARACTER*1
-* = 'L': apply Q or Q' from the Left
-* = 'R': apply Q or Q' from the Right
-*
-* TRANS (input) CHARACTER*1
-* = 'N': apply Q (No transpose)
-* = 'C': apply Q' (Conjugate transpose)
-*
-* M (input) INTEGER
-* The number of rows of the matrix C. M >= 0.
-*
-* N (input) INTEGER
-* The number of columns of the matrix C. N >= 0.
-*
-* K (input) INTEGER
-* The number of elementary reflectors whose product defines
-* the matrix Q.
-* If SIDE = 'L', M >= K >= 0;
-* if SIDE = 'R', N >= K >= 0.
-*
-* L (input) INTEGER
-* The number of columns of the matrix A containing
-* the meaningful part of the Householder reflectors.
-* If SIDE = 'L', M >= L >= 0, if SIDE = 'R', N >= L >= 0.
-*
-* A (input) COMPLEX*16 array, dimension
-* (LDA,M) if SIDE = 'L',
-* (LDA,N) if SIDE = 'R'
-* The i-th row must contain the vector which defines the
-* elementary reflector H(i), for i = 1,2,...,k, as returned by
-* ZTZRZF in the last k rows of its array argument A.
-* A is modified by the routine but restored on exit.
-*
-* LDA (input) INTEGER
-* The leading dimension of the array A. LDA >= max(1,K).
-*
-* TAU (input) COMPLEX*16 array, dimension (K)
-* TAU(i) must contain the scalar factor of the elementary
-* reflector H(i), as returned by ZTZRZF.
-*
-* C (input/output) COMPLEX*16 array, dimension (LDC,N)
-* On entry, the m-by-n matrix C.
-* On exit, C is overwritten by Q*C or Q'*C or C*Q' or C*Q.
-*
-* LDC (input) INTEGER
-* The leading dimension of the array C. LDC >= max(1,M).
-*
-* WORK (workspace) COMPLEX*16 array, dimension
-* (N) if SIDE = 'L',
-* (M) if SIDE = 'R'
-*
-* INFO (output) INTEGER
-* = 0: successful exit
-* < 0: if INFO = -i, the i-th argument had an illegal value
-*
-* Further Details
-* ===============
-*
-* Based on contributions by
-* A. Petitet, Computer Science Dept., Univ. of Tenn., Knoxville, USA
-*
-* =====================================================================
-*
-* .. Local Scalars ..
- LOGICAL LEFT, NOTRAN
- INTEGER I, I1, I2, I3, IC, JA, JC, MI, NI, NQ
- COMPLEX*16 TAUI
-* ..
-* .. External Functions ..
- LOGICAL LSAME
- EXTERNAL LSAME
-* ..
-* .. External Subroutines ..
- EXTERNAL XERBLA, ZLARZ
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC DCONJG, MAX
-* ..
-* .. Executable Statements ..
-*
-* Test the input arguments
-*
- INFO = 0
- LEFT = LSAME( SIDE, 'L' )
- NOTRAN = LSAME( TRANS, 'N' )
-*
-* NQ is the order of Q
-*
- IF( LEFT ) THEN
- NQ = M
- ELSE
- NQ = N
- END IF
- IF( .NOT.LEFT .AND. .NOT.LSAME( SIDE, 'R' ) ) THEN
- INFO = -1
- ELSE IF( .NOT.NOTRAN .AND. .NOT.LSAME( TRANS, 'C' ) ) THEN
- INFO = -2
- ELSE IF( M.LT.0 ) THEN
- INFO = -3
- ELSE IF( N.LT.0 ) THEN
- INFO = -4
- ELSE IF( K.LT.0 .OR. K.GT.NQ ) THEN
- INFO = -5
- ELSE IF( L.LT.0 .OR. ( LEFT .AND. ( L.GT.M ) ) .OR.
- $ ( .NOT.LEFT .AND. ( L.GT.N ) ) ) THEN
- INFO = -6
- ELSE IF( LDA.LT.MAX( 1, K ) ) THEN
- INFO = -8
- ELSE IF( LDC.LT.MAX( 1, M ) ) THEN
- INFO = -11
- END IF
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'ZUNMR3', -INFO )
- RETURN
- END IF
-*
-* Quick return if possible
-*
- IF( M.EQ.0 .OR. N.EQ.0 .OR. K.EQ.0 )
- $ RETURN
-*
- IF( ( LEFT .AND. .NOT.NOTRAN .OR. .NOT.LEFT .AND. NOTRAN ) ) THEN
- I1 = 1
- I2 = K
- I3 = 1
- ELSE
- I1 = K
- I2 = 1
- I3 = -1
- END IF
-*
- IF( LEFT ) THEN
- NI = N
- JA = M - L + 1
- JC = 1
- ELSE
- MI = M
- JA = N - L + 1
- IC = 1
- END IF
-*
- DO 10 I = I1, I2, I3
- IF( LEFT ) THEN
-*
-* H(i) or H(i)' is applied to C(i:m,1:n)
-*
- MI = M - I + 1
- IC = I
- ELSE
-*
-* H(i) or H(i)' is applied to C(1:m,i:n)
-*
- NI = N - I + 1
- JC = I
- END IF
-*
-* Apply H(i) or H(i)'
-*
- IF( NOTRAN ) THEN
- TAUI = TAU( I )
- ELSE
- TAUI = DCONJG( TAU( I ) )
- END IF
- CALL ZLARZ( SIDE, MI, NI, L, A( I, JA ), LDA, TAUI,
- $ C( IC, JC ), LDC, WORK )
-*
- 10 CONTINUE
-*
- RETURN
-*
-* End of ZUNMR3
-*
- END
diff --git a/src/lib/lapack/zunmrz.f b/src/lib/lapack/zunmrz.f
deleted file mode 100644
index c7637050..00000000
--- a/src/lib/lapack/zunmrz.f
+++ /dev/null
@@ -1,296 +0,0 @@
- SUBROUTINE ZUNMRZ( SIDE, TRANS, M, N, K, L, A, LDA, TAU, C, LDC,
- $ WORK, LWORK, INFO )
-*
-* -- LAPACK routine (version 3.1) --
-* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd..
-* November 2006
-*
-* .. Scalar Arguments ..
- CHARACTER SIDE, TRANS
- INTEGER INFO, K, L, LDA, LDC, LWORK, M, N
-* ..
-* .. Array Arguments ..
- COMPLEX*16 A( LDA, * ), C( LDC, * ), TAU( * ), WORK( * )
-* ..
-*
-* Purpose
-* =======
-*
-* ZUNMRZ overwrites the general complex M-by-N matrix C with
-*
-* SIDE = 'L' SIDE = 'R'
-* TRANS = 'N': Q * C C * Q
-* TRANS = 'C': Q**H * C C * Q**H
-*
-* where Q is a complex unitary matrix defined as the product of k
-* elementary reflectors
-*
-* Q = H(1) H(2) . . . H(k)
-*
-* as returned by ZTZRZF. Q is of order M if SIDE = 'L' and of order N
-* if SIDE = 'R'.
-*
-* Arguments
-* =========
-*
-* SIDE (input) CHARACTER*1
-* = 'L': apply Q or Q**H from the Left;
-* = 'R': apply Q or Q**H from the Right.
-*
-* TRANS (input) CHARACTER*1
-* = 'N': No transpose, apply Q;
-* = 'C': Conjugate transpose, apply Q**H.
-*
-* M (input) INTEGER
-* The number of rows of the matrix C. M >= 0.
-*
-* N (input) INTEGER
-* The number of columns of the matrix C. N >= 0.
-*
-* K (input) INTEGER
-* The number of elementary reflectors whose product defines
-* the matrix Q.
-* If SIDE = 'L', M >= K >= 0;
-* if SIDE = 'R', N >= K >= 0.
-*
-* L (input) INTEGER
-* The number of columns of the matrix A containing
-* the meaningful part of the Householder reflectors.
-* If SIDE = 'L', M >= L >= 0, if SIDE = 'R', N >= L >= 0.
-*
-* A (input) COMPLEX*16 array, dimension
-* (LDA,M) if SIDE = 'L',
-* (LDA,N) if SIDE = 'R'
-* The i-th row must contain the vector which defines the
-* elementary reflector H(i), for i = 1,2,...,k, as returned by
-* ZTZRZF in the last k rows of its array argument A.
-* A is modified by the routine but restored on exit.
-*
-* LDA (input) INTEGER
-* The leading dimension of the array A. LDA >= max(1,K).
-*
-* TAU (input) COMPLEX*16 array, dimension (K)
-* TAU(i) must contain the scalar factor of the elementary
-* reflector H(i), as returned by ZTZRZF.
-*
-* C (input/output) COMPLEX*16 array, dimension (LDC,N)
-* On entry, the M-by-N matrix C.
-* On exit, C is overwritten by Q*C or Q**H*C or C*Q**H or C*Q.
-*
-* LDC (input) INTEGER
-* The leading dimension of the array C. LDC >= max(1,M).
-*
-* WORK (workspace/output) COMPLEX*16 array, dimension (MAX(1,LWORK))
-* On exit, if INFO = 0, WORK(1) returns the optimal LWORK.
-*
-* LWORK (input) INTEGER
-* The dimension of the array WORK.
-* If SIDE = 'L', LWORK >= max(1,N);
-* if SIDE = 'R', LWORK >= max(1,M).
-* For optimum performance LWORK >= N*NB if SIDE = 'L', and
-* LWORK >= M*NB if SIDE = 'R', where NB is the optimal
-* blocksize.
-*
-* If LWORK = -1, then a workspace query is assumed; the routine
-* only calculates the optimal size of the WORK array, returns
-* this value as the first entry of the WORK array, and no error
-* message related to LWORK is issued by XERBLA.
-*
-* INFO (output) INTEGER
-* = 0: successful exit
-* < 0: if INFO = -i, the i-th argument had an illegal value
-*
-* Further Details
-* ===============
-*
-* Based on contributions by
-* A. Petitet, Computer Science Dept., Univ. of Tenn., Knoxville, USA
-*
-* =====================================================================
-*
-* .. Parameters ..
- INTEGER NBMAX, LDT
- PARAMETER ( NBMAX = 64, LDT = NBMAX+1 )
-* ..
-* .. Local Scalars ..
- LOGICAL LEFT, LQUERY, NOTRAN
- CHARACTER TRANST
- INTEGER I, I1, I2, I3, IB, IC, IINFO, IWS, JA, JC,
- $ LDWORK, LWKOPT, MI, NB, NBMIN, NI, NQ, NW
-* ..
-* .. Local Arrays ..
- COMPLEX*16 T( LDT, NBMAX )
-* ..
-* .. External Functions ..
- LOGICAL LSAME
- INTEGER ILAENV
- EXTERNAL LSAME, ILAENV
-* ..
-* .. External Subroutines ..
- EXTERNAL XERBLA, ZLARZB, ZLARZT, ZUNMR3
-* ..
-* .. Intrinsic Functions ..
- INTRINSIC MAX, MIN
-* ..
-* .. Executable Statements ..
-*
-* Test the input arguments
-*
- INFO = 0
- LEFT = LSAME( SIDE, 'L' )
- NOTRAN = LSAME( TRANS, 'N' )
- LQUERY = ( LWORK.EQ.-1 )
-*
-* NQ is the order of Q and NW is the minimum dimension of WORK
-*
- IF( LEFT ) THEN
- NQ = M
- NW = MAX( 1, N )
- ELSE
- NQ = N
- NW = MAX( 1, M )
- END IF
- IF( .NOT.LEFT .AND. .NOT.LSAME( SIDE, 'R' ) ) THEN
- INFO = -1
- ELSE IF( .NOT.NOTRAN .AND. .NOT.LSAME( TRANS, 'C' ) ) THEN
- INFO = -2
- ELSE IF( M.LT.0 ) THEN
- INFO = -3
- ELSE IF( N.LT.0 ) THEN
- INFO = -4
- ELSE IF( K.LT.0 .OR. K.GT.NQ ) THEN
- INFO = -5
- ELSE IF( L.LT.0 .OR. ( LEFT .AND. ( L.GT.M ) ) .OR.
- $ ( .NOT.LEFT .AND. ( L.GT.N ) ) ) THEN
- INFO = -6
- ELSE IF( LDA.LT.MAX( 1, K ) ) THEN
- INFO = -8
- ELSE IF( LDC.LT.MAX( 1, M ) ) THEN
- INFO = -11
- END IF
-*
- IF( INFO.EQ.0 ) THEN
- IF( M.EQ.0 .OR. N.EQ.0 ) THEN
- LWKOPT = 1
-*
-* Determine the block size. NB may be at most NBMAX, where
-* NBMAX is used to define the local array T.
-*
- NB = MIN( NBMAX, ILAENV( 1, 'ZUNMRQ', SIDE // TRANS, M, N,
- $ K, -1 ) )
- LWKOPT = NW*NB
- END IF
- WORK( 1 ) = LWKOPT
-*
- IF( LWORK.LT.MAX( 1, NW ) .AND. .NOT.LQUERY ) THEN
- INFO = -13
- END IF
- END IF
-*
- IF( INFO.NE.0 ) THEN
- CALL XERBLA( 'ZUNMRZ', -INFO )
- RETURN
- ELSE IF( LQUERY ) THEN
- RETURN
- END IF
-*
-* Quick return if possible
-*
- IF( M.EQ.0 .OR. N.EQ.0 ) THEN
- RETURN
- END IF
-*
-* Determine the block size. NB may be at most NBMAX, where NBMAX
-* is used to define the local array T.
-*
- NB = MIN( NBMAX, ILAENV( 1, 'ZUNMRQ', SIDE // TRANS, M, N, K,
- $ -1 ) )
- NBMIN = 2
- LDWORK = NW
- IF( NB.GT.1 .AND. NB.LT.K ) THEN
- IWS = NW*NB
- IF( LWORK.LT.IWS ) THEN
- NB = LWORK / LDWORK
- NBMIN = MAX( 2, ILAENV( 2, 'ZUNMRQ', SIDE // TRANS, M, N, K,
- $ -1 ) )
- END IF
- ELSE
- IWS = NW
- END IF
-*
- IF( NB.LT.NBMIN .OR. NB.GE.K ) THEN
-*
-* Use unblocked code
-*
- CALL ZUNMR3( SIDE, TRANS, M, N, K, L, A, LDA, TAU, C, LDC,
- $ WORK, IINFO )
- ELSE
-*
-* Use blocked code
-*
- IF( ( LEFT .AND. .NOT.NOTRAN ) .OR.
- $ ( .NOT.LEFT .AND. NOTRAN ) ) THEN
- I1 = 1
- I2 = K
- I3 = NB
- ELSE
- I1 = ( ( K-1 ) / NB )*NB + 1
- I2 = 1
- I3 = -NB
- END IF
-*
- IF( LEFT ) THEN
- NI = N
- JC = 1
- JA = M - L + 1
- ELSE
- MI = M
- IC = 1
- JA = N - L + 1
- END IF
-*
- IF( NOTRAN ) THEN
- TRANST = 'C'
- ELSE
- TRANST = 'N'
- END IF
-*
- DO 10 I = I1, I2, I3
- IB = MIN( NB, K-I+1 )
-*
-* Form the triangular factor of the block reflector
-* H = H(i+ib-1) . . . H(i+1) H(i)
-*
- CALL ZLARZT( 'Backward', 'Rowwise', L, IB, A( I, JA ), LDA,
- $ TAU( I ), T, LDT )
-*
- IF( LEFT ) THEN
-*
-* H or H' is applied to C(i:m,1:n)
-*
- MI = M - I + 1
- IC = I
- ELSE
-*
-* H or H' is applied to C(1:m,i:n)
-*
- NI = N - I + 1
- JC = I
- END IF
-*
-* Apply H or H'
-*
- CALL ZLARZB( SIDE, TRANST, 'Backward', 'Rowwise', MI, NI,
- $ IB, L, A( I, JA ), LDA, T, LDT, C( IC, JC ),
- $ LDC, WORK, LDWORK )
- 10 CONTINUE
-*
- END IF
-*
- WORK( 1 ) = LWKOPT
-*
- RETURN
-*
-* End of ZUNMRZ
-*
- END