CONGEN  5.0
Configuration generation for SCATCI
congen_distribution.f90
Go to the documentation of this file.
1 ! Copyright 2019
2 !
3 ! For a comprehensive list of the developers that contributed to these codes
4 ! see the UK-AMOR website.
5 !
6 ! This file is part of UKRmol-in (UKRmol+ suite).
7 !
8 ! UKRmol-in is free software: you can redistribute it and/or modify
9 ! it under the terms of the GNU General Public License as published by
10 ! the Free Software Foundation, either version 3 of the License, or
11 ! (at your option) any later version.
12 !
13 ! UKRmol-in is distributed in the hope that it will be useful,
14 ! but WITHOUT ANY WARRANTY; without even the implied warranty of
15 ! MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
16 ! GNU General Public License for more details.
17 !
18 ! You should have received a copy of the GNU General Public License
19 ! along with UKRmol-in (in source/COPYING). Alternatively, you can also visit
20 ! <https://www.gnu.org/licenses/>.
24 
25  implicit none
26 
27  ! module entry point
28  public distrb
29 
30  ! internal support routines
31  private assign
32  private cplea, cplem
33  private cgcoef
34  private getsa, getsm, getso
35  private packdet
36  private print1, print2, print3, print4, print5
37  private state
38  private wfn
39 
40 contains
41 
53  subroutine assign (nshl, ndist, nused, refcon, excon, qnstor, nx, nftw)
54 
55  ! Reminder of some used global variables:
56  ! pqn(1,nshl) 0 for pseudoshell, sequence number for real shell
57  ! pqn(2,nshl) starting index for pseudoshell
58  ! pqn(3,nshl) ending index for pseudoshell
59  ! occshl(nshl) occupation
60  ! sshl(nshl) sym-values per shell
61  ! nst(m,n) pointer to shell index and order count
62  ! nshsym(nsym) counter for number of shells in s symmetry
63  ! qnshlr(nshl) work area stores index of shells
64 
65  use congen_data, only : ntcon, test, nrcon, nobt, nst, nshsym, nobi, ift, occshl, pqn => pqnst, sshl => sshlst, qnshlr
66 
67  integer :: ndist, nftw, nshl, nused, nx
68  integer, dimension(nobt) :: excon
69  integer, dimension(*) :: qnstor
70  integer, dimension(nobt,max(ntcon,1)) :: refcon ! JMC changing the 2nd dimension from 2
71  intent (in) nftw, nshl, nx, refcon
72  intent (out) nused, qnstor
73  intent (inout) excon, ndist
74 
75  integer, save :: allow, i, ic, it, ita, itest, j, ks, kss, mrun, mt, nav, navm1, ndrop, nrep, nshrun, nt
76 
77  ! workspace limits
78  if (ift /= 0) then
79  nav = nx
80  navm1 = nav - 1
81  ift = 0
82  end if
83 
84  ! categorize shells by symmetry (into NST array)
85 
86  mrun = 0 ! 1-based index of current symmetry being processed (-> number of symmetries processed)
87  nshrun = 0 ! 1-based index of current shell being processed (-> number of shells proccessed)
88 
89  do while (nshrun /= nshl) ! process all NSHL shells
90  mrun = mrun + 1
91  ita = 0 ! index of shell within symmetry (-> number of shells within symmetry)
92  do i = 1, nshl
93  if (mrun == sshl(i)) then
94  ita = ita + 1
95  nst(mrun,ita) = i
96  end if
97  end do
98  nshrun = nshrun + ita
99  end do
100 
101  ! initializations
102 
103  nshsym(1:mrun) = 0 ! number of shells processed so far per symmetry
104  ndist = 0 ! number of distributions generated (since the start of the program)
105  ndrop = 0 ! number of distributed shells stored (since the start of the program)
106  ks = 0 ! 1-based index of the current shell
107 
108  ! ???
109 
110  100 ks = ks + 1 ! next shell, please!
111  mt = sshl(ks) ! get symmetry number of the current shell
112  it = nshsym(mt) ! get number of shells with the same symmetry processed before the current one
113  nshsym(mt) = it + 1 ! update number of processed shells with that symmetry
114  qnshlr(ks) = pqn(2,ks) ! starting orbital of the set of orbitals this shell belongs to
115 
116  ! skip to 200 if any of the previous orbitals for this symmetry violate rules below
117  120 do i = 1, it
118  kss = nst(mt,i)
119  if (qnshlr(kss) == qnshlr(ks)) go to 200
120  if (occshl(kss) == occshl(ks) .and. &
121  qnshlr(kss) >= qnshlr(ks) .and. &
122  qnshlr(ks) >= pqn(2,kss) .and. &
123  qnshlr(kss) <= pqn(3,ks)) go to 200
124  end do
125 
126  if (ks < nshl) go to 100
127 
128  ! take into account possible constraints
129  if (ntcon /= 0) then
130  excon(1:nobt) = 0
131  do i = 1, nshl
132  j = nobi(sshl(i)) + qnshlr(i)
133  excon(j) = occshl(i)
134  end do
135 
136  allow = 0
137  itest = 0
138 
139  do ic = 1, ntcon
140  nrep = 0
141  do i = 1, nobt
142  nt = excon(i) - refcon(i,ic)
143  nrep = abs(nt) + nrep
144  end do
145  if (test(ic) /= 1) then
146  if (nrep <= nrcon(ic) + nrcon(ic)) go to 200
147  else
148  if (nrep <= nrcon(ic) + nrcon(ic)) allow = 1
149  end if
150  itest = itest + test(ic)
151  end do
152 
153  if (allow == 0 .and. itest /= 0) go to 200
154  end if
155 
156  ! allowed assignment is to be stored - check that there is enough space
157  if (ndrop + nshl >= navm1) then
158  write(nftw,'("1",31("*"),/," ",31("*"),"STORAGE OVERFLOW IN ASSIGN:",I8, " WORDS AVAILABLE")') nx
159  stop 70
160  end if
161 
162  ! store the assignment
163  ndist = ndist + 1
164  do i = 1, nshl
165  ndrop = ndrop + 1
166  qnstor(ndrop) = qnshlr(i)
167  end do
168 
169  ! ascend in assignment loops
170  200 do while (ks > 0)
171  mt = sshl(ks) ! get symmetry number of the current shell
172  it = nshsym(mt) - 1 ! get number of shells with the same symmetry processed before the current one
173  qnshlr(ks) = qnshlr(ks) + 1
174  if (qnshlr(ks) <= pqn(3,ks)) go to 120
175  nshsym(mt) = it
176  ks = ks - 1
177  end do
178 
179  nused = ndrop
180 
181  end subroutine assign
182 
183 
197  subroutine cgcoef (j1, j2, j3, m3, n, ms, c, intpfg)
198 
199  use precisn, only : wp
200  use consts, only : xzero, xone
201  use congen_data, only : binom, ind, nftw, thresh1
202 
203  integer :: intpfg, j1, j2, j3, m3, n
204  real(kind=wp), dimension(*) :: c
205  integer, dimension(2,*) :: ms
206  intent (in) intpfg, j1, j2, j3, m3
207  intent (inout) c, ms, n
208 
209  real(kind=wp) :: a, b, t
210  integer :: i, i1, i2, ii, jj, js, lb, lb1, lb2, lbh, lbl, m, m1, m2
211  integer, dimension(3) :: j, k, l
212 
213  js = (j1 + j2 + j3 - 1) / 2
214  j(1) = j1
215  j(2) = j2
216  j(3) = j3
217  k(1) = js - j2
218  k(2) = js - j3
219  k(3) = js - j1
220  n = 0
221  m = m3
222  if (j3 - 1 < abs(m - 1)) return
223  if (any(k < 0)) return
224  a = xone / (binom(ind(js+1)+k(2)) * binom(ind(j3)+k(1)))
225  l(3) = (j3 + m3 - 2) / 2
226  m1 = j1
227 
228  do jj = 1, j1
229  m2 = m3 - m1 + 1
230  if (abs(m2 - 1) <= j2 - 1) then
231  n = n + 1
232  ms(1,n) = m1
233  ms(2,n) = m2
234  l(1) = (j1 - m1) / 2
235  l(2) = (j2 + m2 - 2) / 2
236  b = a
237  do ii = 1, 3
238  b = binom(ind(j(ii)) + k(ii)) / binom(ind(j(ii)) + l(ii)) * b
239  end do
240  b = sqrt(b)
241  i1 = max(l(1) - k(1), l(2) - k(3), 0)
242  i2 = min(l(1), l(2), k(2))
243  t = xzero
244  if (i2 >= i1) then
245  lbl = ind(k(2) + 1) + i1
246  lbh = ind(k(2) + 1) + i2
247  lb1 = ind(k(1) + 1) + l(1) - i1
248  lb2 = ind(k(3) + 1) + l(2) - i1
249  do lb = lbl, lbh
250  t = binom(lb) * binom(lb1) * binom(lb2) - t
251  lb1 = lb1 - 1
252  lb2 = lb2 - 1
253  end do
254  end if
255  c(n) = b * t * (-xone)**i2
256  if (abs(c(n)) <= thresh1) n = n - 1
257  end if
258  m1 = m1 - 2
259  end do
260 
261  if (intpfg /= 0) then
262  write(nftw,'(" CGCOEF : CLEBSCH-GORDAN COEFFICIENTS FOR")')
263  write(nftw,'(" J1 =",I4," J2 =",I4," J3 =",I4," M3 =",I4,/)') j1, j2, j3, m3
264  write(nftw, '(/(E25.15,2I5))') (c(i), ms(1,i), ms(2,i), i=1,n)
265  end if
266 
267  end subroutine cgcoef
268 
269 
289  subroutine getsa (ne, l, is, isz, m, nc, c, iso)
290 
291  use precisn, only : wp
292  use consts, only : one => xone
293  use congen_data, only : root2
294 
295  integer :: is, isz, l, m, nc, ne
296  real(kind=wp), dimension(*) :: c
297  integer, dimension(*) :: iso
298  intent (in) is, isz, l, m, ne
299  intent (out) c, nc
300  intent (inout) iso
301 
302  nc = 1
303  c(1) = one
304  if (ne == 0) return
305  if (ne /= 4) then
306  if (ne < 2) then
307  iso(1) = 1 - isz / 2
308  if (l == 0) return
309  if (m < 0) iso(1) = iso(1) + 2
310  return
311  else if (ne == 2) then
312  if (l == 0) then
313  iso(1) = 0
314  iso(2) = 1
315  return
316  end if
317  if (isz + m /= 1) then
318  if (m /= 0) then
319  iso(1) = 1 - (l + l) / m
320  iso(2) = iso(1) + 1
321  return
322  end if
323  iso(1) = (3 - isz) / 4
324  iso(2) = iso(1) + 2
325  return
326  end if
327  nc = 2
328  iso(1) = 0
329  iso(2) = 3
330  iso(3) = 1
331  iso(4) = 2
332  c(1) = root2
333  c(2) = root2
334  if (is == 1) c(2) = -root2
335  return
336  else
337  if (m < 0) then
338  iso(1) = 1 - isz / 2
339  iso(2) = 2
340  iso(3) = 3
341  return
342  end if
343  iso(1) = 0
344  iso(2) = 1
345  iso(3) = 3 - isz / 2
346  return
347  end if
348  end if
349 
350  iso(3) = 2
351  iso(4) = 3
352  iso(1) = 0
353  iso(2) = 1
354 
355  end subroutine getsa
356 
357 
374  subroutine getsm (ne, isz, nc, c, iso)
375 
376  use precisn, only : wp
377  use consts, only : one => xone
378 
379  integer :: isz, nc, ne
380  real(kind=wp), dimension(*) :: c
381  integer, dimension(*) :: iso
382  intent (in) isz, ne
383  intent (out) c, iso, nc
384 
385  nc = 1
386  c(1) = one
387  iso(1) = 0
388  iso(2) = 1
389  if (ne == 1) iso(1) = 1 - isz / 2
390 
391  ! So the results will be:
392  !
393  ! isz ne iso(1) iso(2)
394  ! ---------------------------------
395  ! any /= 1 0 1
396  ! 1 == 1 1 1
397  ! 2 == 1 1 1
398  ! 3 == 1 0 1
399  ! 4 == 1 -1 1
400 
401  end subroutine getsm
402 
403 
416  subroutine getso (ns, intpfg, nti, iqns, ci, nd, id, cd, last)
417 
418  use precisn, only : wp
419  use congen_data, only : nes => occshl, ms => mshl, iqn => qnshl, ne => nnlecg, symtyp, nftw
420 
421  integer :: intpfg, last, nd, ns, nti
422  real(kind=wp), dimension(*) :: cd, ci
423  integer, dimension(*) :: id
424  integer, dimension(2,ns,*) :: iqns
425  intent (in) ci, intpfg, iqns, last, ns, nti
426  intent (inout) cd, id, nd
427 
428  real(kind=wp), dimension(100) :: c ! JMC change dimension to ns*(max nc=2) ??? (an overestimate, for safety).
429  real(kind=wp), dimension(ns) :: cs ! JMC changing the dimension from 50
430  integer :: i, ie1, ie2, is, isz, iti, kc, ke, kso, ld, ld1, ld2, ml, nc
431  integer, dimension(200) :: iso ! JMC change dimension to (max nc=2)*sum(nes(i),i=1,ns) ??? (an overestimate, for safety).
432  integer, dimension(150) :: jso ! JMC change dimension to max(ne, sum(nes(i),i=1,ns)) ???
433  integer, dimension(ns+1) :: lc, lso ! JMC changing the dimension from 51. Think LSO could be (NS) not (NS+1)...
434  integer, dimension(ns) :: lcs, lsos ! JMC changing the dimension from 50
435  real(kind=wp) :: t
436 
437  if (intpfg /= 0) then
438  write(nftw,'(" GETSO : NTI =",I10,/," IQNS :",/)') nti
439  do iti = 1, nti
440  write(nftw,'(20I5)') (iqns(1,is,iti), is=1,ns)
441  write(nftw,'(20I5)') (iqns(2,is,iti), is=1,ns)
442  end do
443  end if
444 
445  nd = 0
446  ld = 1
447 
448  do iti = 1, nti
449 
450  kc = 1
451  kso = 1
452 
453  do is = 1, ns
454  isz = iqns(1,is,iti)
455  if (symtyp <= 1) then
456  ml = iqns(2,is,iti)
457  call getsa (nes(is), ms(is), iqn(1,is), isz, ml, nc, c(kc), iso(kso))
458  else
459  call getsm (nes(is), isz, nc, c(kc), iso(kso))
460  end if
461  lc(is) = kc
462  lso(is) = kso
463  kc = kc + nc
464  kso = kso + nc * nes(is)
465  end do
466 
467  lc(ns + 1) = kc
468  is = 1
469  t = ci(iti)
470  ie2 = 0
471 
472  300 cs(is) = t
473  lsos(is) = lso(is)
474  lcs(is) = lc(is)
475 
476  if (nes(is) == 0) go to 415
477 
478  400 ie1 = ie2 + 1
479  ie2 = ie2 + nes(is)
480  kso = lsos(is)
481  do ke = ie1, ie2
482  jso(ke) = iso(kso)
483  kso = kso + 1
484  end do
485 
486  415 lsos(is) = kso
487  t = cs(is) * c(lcs(is))
488  lcs(is) = lcs(is) + 1
489  is = is + 1
490  if (is <= ns) go to 300
491 
492  nd = nd + 1
493  if (nd > last) then
494  write(nftw,'("0storage overflow")')
495  nd = 0
496  return
497  end if
498 
499  do ke = 1, ne
500  id(ld) = jso(ke)
501  ld = ld + 1
502  end do
503 
504  cd(nd) = t
505 
506  do while (is > 1)
507  is = is - 1
508  ie2 = ie2 - nes(is)
509  if (lcs(is) < lc(is + 1)) go to 400
510  end do
511 
512  end do
513 
514  if (intpfg /= 0) then
515  write(nftw,'(" GETSO : ND =",I6,/," CD, ID :",/)') nd
516  ld2 = 0
517  do i = 1, nd
518  ld1 = ld2 + 1
519  ld2 = ld2 + ne
520  write(nftw,'(E25.15,20I5)') cd(i), (id(ld), ld=ld1,ld2)
521  end do
522  end if
523 
524  end subroutine getso
525 
526 
574  subroutine cplea (nncsf, nadel, x, nftw)
575 
576  use iso_c_binding, only : c_loc, c_f_pointer
577  use precisn, only : wp
578  use congen_data, only : lg, next, nx, icdi, iexcon, indi, inodi, iqnstr, irfcon, ndel, confpf, ndist, nshl, &
581 
582  integer :: nadel, nftw, nncsf
583  real(wp), dimension(*), target :: x
584  integer, dimension(:), pointer :: int_ptr, irfcon_ptr, iexcon_ptr, iqnstr_ptr, nodi_ptr, ndi_ptr, ndel_ptr, nnext_ptr
585  integer, dimension(2,3,lg) :: qntmp
586 
587  integer :: gutry, i, idumm, iidis1, iidist, iocc, kc, kclim, kcs, kcsp, ks, &
588  m, mtry, nav, nnext, nused, shl1, shl2, spntry, z1=1
589 
590  real(wp), pointer :: x_ptr
591 
592  nstate = 0 ! number of states which may be formed with current distribution into shells
593  iidis1 = 0 ! number of the current shell distribution
594 
595  ! perform gross checks on symmetries allowed for dist
596 
597  if (gutot /= 0) then
598  gutry = 1
599  do i = 1, nshl
600  if (gushl(i) > 0) cycle
601  if (iand(occshl(i), z1) /= 0) gutry = -gutry
602  end do
603  if (gutry /= gutot) return
604  end if
605  spntry = 1
606  mtry = 0
607  do i = 1, nshl
608  m = mshl(i) + 1
609  if (gutot /= 0 ) m = m + m
610  iocc = occshl(i)
611  if (iocc > shlmx1(m) / 2) iocc = shlmx1(m) - iocc
612  spntry = spntry + iocc
613  mtry = mtry + iocc * mshl(i)
614  end do
615  if (spntry > qntot(1)) return
616  if (mtry - qntot(2) > 0 .or. iand(mtry - qntot(2), z1) /= 0) return
617 
618  ! initialize third shell coupling
619 
620  kclim = nshl - 1
621  do i = 1, kclim
622  qntmp(1,3,i) = 0
623  qntmp(2,3,i) = -1
624  end do
625 
626  ! initialize shell quantum numbers and loop limits for shell coupling
627 
628  spntry = 1
629  mtry = 0
630  do i = 1, nshl
631  m = mshl(i) + 1
632  if (gutot /= 0) m = m + m
633  qnshl(1,i) = 1
634  qnshl(2,i) = 0
635  qnshl(3,i) = 1
636  kslim(2,i) = 1
637  if (occshl(i) == 0 .or. occshl(i) == shlmx1(m)) cycle
638  spntry = spntry + 1
639  mtry = mtry + mshl(i)
640  qnshl(1,i) = 2
641  qnshl(2,i) = mshl(i)
642  qnshl(3,i) = 0
643  if (mshl(i) == 0) qnshl(3,i) = 1
644  if (occshl(i) /= 2) cycle
645  kslim(2,i) = 3
646  spntry = spntry - 1
647  mtry = mtry - mshl(i)
648  end do
649 
650  ! begin to decend into loops
651 
652  ks = 1
653  100 kslim(1,ks) = 1
654  if (kslim(2,ks) == 1) go to 120
655  qnshl(1,ks) = 3
656  qnshl(2,ks) = 0
657  qnshl(3,ks) = -1
658  spntry = spntry + 2
659  120 ks = ks + 1
660  if (ks < nshl) go to 100
661 
662  if (spntry < qntot(1) .or. mtry < qntot(2)) go to 600
663  kc = 1
664  kcs = nshl + 1
665  if (kclim /= 0) go to 300
666  if (qnshl(1,1) /= qntot(1) .or. qnshl(2,1) /= qntot(2)) go to 500
667  if (qnshl(2,1) == 0 .and. qnshl(3,1) /= qntot(3)) go to 500
668  go to 420
669  300 shl1 = cup(1,kc)
670  shl2 = cup(2,kc)
671  qnshl(1,kcs) = qnshl(1,shl1) + qnshl(1,shl2) - 1
672  spnmin(kc) = abs(qnshl(1,shl1) - qnshl(1,shl2)) + 1
673  qntmp(1,1,kc) = qnshl(2,shl1) + qnshl(2,shl2)
674  qnshl(2,kcs) = qnshl(2,shl1) + qnshl(2,shl2)
675  qntmp(1,2,kc) = abs(qnshl(2,shl1) - qnshl(2,shl2))
676  qntmp(2,1,kc) = qnshl(3,shl1) * qnshl(3,shl2)
677  qnshl(3,kcs) = qnshl(3,shl1) * qnshl(3,shl2)
678  qntmp(2,2,kc) = 0
679  mclim(1,kc) = 1
680  mclim(2,kc) = 1
681  if (qntmp(1,1,kc) == qntmp(1,2,kc)) go to 320
682  mclim(2,kc) = 2
683  if (qntmp(1,2,kc) /= 0) go to 320
684  mclim(2,kc) = 3
685  qntmp(2,2,kc) = 1
686  320 kc = kc + 1
687  kcs = kcs + 1
688  if (kc < kclim) go to 300
689 
690  ! test if the final coupling is in the range permitted
691 
692  kc = kclim
693  kcs = kcs - 1
694  if (qnshl(1,kcs) < qntot(1) .or. spnmin(kc) > qntot(1)) go to 500
695  qnshl(1,kcs) = qntot(1)
696  if (qnshl(2,kcs) /= qntot(2) .and. qntmp(1,2,kc) /= qntot(2)) go to 500
697  qnshl(2,kcs) = qntot(2)
698  qnshl(3,kcs) = qntot(3)
699  if (qntmp(1,1,kc) /= 0) go to 420
700  qnshl(3,kcs) = qntmp(2,1,kc)
701  if (qnshl(3,kcs) /= qntot(3)) go to 500
702 
703  ! for R-matrix calculations: reject couplings which do not preserve the target quantum numbers
704 
705  420 if (qntar(1) >= 0) then
706  kcsp = kcs - 1
707  if (kcs == 3) kcsp = 1
708  if (qnshl(1,kcsp) /= qntar(1)) go to 500
709  if (qnshl(2,kcsp) /= qntar(2)) go to 500
710  if (qnshl(3,kcsp) /= qntar(3)) go to 500
711  end if
712  nstate = nstate + 1
713  if (nstate /= 1) go to 400
714 
715  ! convert some real pointers to integer pointers for use in ASSIGN
716  x_ptr => x(irfcon) ; call c_f_pointer (c_loc(x_ptr), irfcon_ptr, (/1/))
717  x_ptr => x(iexcon) ; call c_f_pointer (c_loc(x_ptr), iexcon_ptr, (/1/))
718  x_ptr => x(iqnstr) ; call c_f_pointer (c_loc(x_ptr), iqnstr_ptr, (/1/))
719 
720  ! Assign pqn value and print type and distrib data for allowed state
721  call assign (nshl, ndist, nused, irfcon_ptr, iexcon_ptr, iqnstr_ptr, nx, nftw)
722 
723  if (ndist == 0) then
724  nstate = 0
725  return
726  end if
727 
728  nav = nx - nused
729  nnext = next + nused
730  if (nndel /= 0) go to 405
731  call print1 (iqnstr_ptr)
732  400 if (confpf >= 10 .and. nndel == 0) call print2 (0)
733  405 continue
734 
735  ! convert some real pointers to integer pointers for use in WFN
736  x_ptr => x(inodi) ; call c_f_pointer (c_loc(x_ptr), nodi_ptr, (/1/))
737  x_ptr => x(indi) ; call c_f_pointer (c_loc(x_ptr), ndi_ptr, (/1/))
738  x_ptr => x(ndel) ; call c_f_pointer (c_loc(x_ptr), ndel_ptr, (/1/))
739  x_ptr => x(iqnstr) ; call c_f_pointer (c_loc(x_ptr), iqnstr_ptr, (/1/))
740  x_ptr => x(nnext) ; call c_f_pointer (c_loc(x_ptr), nnext_ptr, (/1/))
741 
742  call wfn (nncsf, nadel, iidist, iidis1, nodi_ptr, ndi_ptr, x(icdi), ndel_ptr, iqnstr_ptr, x(nnext), nnext_ptr, nav)
743 
744  if (nndel > 0 .and. nadel > nndel .and. iidis1 == 0) return
745  if (nndel == 0) go to 500
746  if (iidist == 0) go to 500
747  if (nstate == 1) call print1 (iqnstr_ptr)
748  if (confpf >= 10 .and. iidis1 /= 0) call print2 (iidis1)
749 
750  ! ascend in coupling tree - ascend in the shell to shell coupling loops
751 
752  500 kc = kc - 1
753  kcs = kcs - 1
754  if (kc == 0) go to 600
755  mclim(1,kc) = mclim(1,kc) + 1
756  if (mclim(1,kc) <= mclim(2,kc)) go to 520
757  qnshl(1,kcs) = qnshl(1,kcs) - 2
758  if (qnshl(1,kcs) < spnmin(kc)) go to 500
759  mclim(1,kc) = 1
760  520 qnshl(2,kcs) = qntmp(1,mclim(1,kc),kc)
761  qnshl(3,kcs) = qntmp(2,mclim(1,kc),kc)
762  go to 320
763 
764  ! ascend in the loops which couple shells to themselves
765 
766  600 ks = ks - 1
767  if (ks == 0) go to 900
768  kslim(1,ks) = kslim(1,ks) + 1
769  if (kslim(1,ks) > kslim(2,ks)) go to 600
770  if (kslim(1,ks) == 3) go to 625
771 
772  ! couple to 1(2*l) and adjust spntry and mtry
773 
774  qnshl(1,ks) = 1
775  spntry = spntry - 2
776  qnshl(2,ks) = mshl(ks) + mshl(ks)
777  mtry = mtry + mshl(ks) + mshl(ks)
778  qnshl(3,ks) = 0
779  go to 120
780 
781  ! couple to 1(s+) and adjust spntry and mtry
782 
783  625 mtry = mtry - qnshl(2,ks)
784  qnshl(2,ks) = 0
785  qnshl(3,ks) = 1
786  go to 120
787 
788  900 if (nndel /= 0 .and. iidis1 /= 0) call print3 (iidis1, 1)
789  if (nndel == 0 .and. nstate /= 0) call print3 (idumm, 2)
790 
791  end subroutine cplea
792 
793 
801  subroutine cplem (nncsf, nadel, x, nftw)
802 
803  use iso_c_binding, only : c_loc, c_f_pointer
804  use precisn, only : wp
805  use global_utils, only : mprod
806  use congen_data, only : lg, next, nx, icdi, iexcon, indi, inodi, iqnstr, irfcon, ndel, confpf, ndist, nshl, &
808 
809  ! Reminder of some used global variables:
810  !
811  ! occshl(nshl) compressed shell occ's / all zeros deleted and pseudo shells expanded
812  ! mshl(nshl) symmetry number from zero to n-1 (mvalue)
813  ! qnshl(3,2*nshl-1) 1 -- mult / 2 -- symmetry / 3 -- +- (not used)
814  ! cup(3,nshl-1)
815  ! qntot(3) total qn's
816  ! qntmp(2*nshl-1) temp storage for true molecule sym values -- zeros passed to bowen in qnshl
817  ! spnmin(nshl-1) temp storage for lowest spin coupling
818  ! x(nx) real work area
819  ! nshl number of true shells occupied
820  ! nstate number of couplings (computed)
821  ! ntype proto-type number (input)
822  ! ndist number of pqn assignments
823  ! ncsf running csf number
824  ! symtyp >= 2 for molecule
825  ! conpf print flag
826 
827  integer :: nadel, nftw, nncsf
828  real(wp), dimension(*), target :: x
829  integer, dimension(:), pointer :: int_ptr, nodi_ptr, ndi_ptr, ndel_ptr, irfcon_ptr, iexcon_ptr, iqnstr_ptr, nnext_ptr
830  real(wp), pointer :: x_ptr
831 
832  integer :: i, idumm, iidis1, iidist, kc, kclim, kcs, kcsp, mtry, mu1, mu2, nav, nnext, nused, spntry
833  integer, dimension(2*lg) :: qntmp ! JMC increasing the dimension from LG to match 2nd dimension of QNSHL
834 
835  ! initialize
836 
837  nstate = 0 ! ?
838  mtry = 0 ! combination of IRRs of all shells
839  spntry = 1 ! maximal combination of spins of all shels
840  iidis1 = 0 ! ?
841 
842  do i = 1, nshl ! loop over all shells in the current set of orbitals
843  qnshl(1,i) = 1 ! default to singlet (2S+1)
844  qnshl(2,i) = 0 ! default to maximal symmetry (IRR = 1)
845  qnshl(3,i) = 1 ! default to +1 inversion symmetry
846  qntmp(i) = 0
847  if (occshl(i) == shlmx1(mshl(i) + 1)) cycle ! fully occupied shells do not contribute anything valuable -> skip
848  qnshl(1,i) = 2 ! but shells not fully occupied are doublets
849  spntry = spntry + 1 ! compose maximal possible total spin
850  qntmp(i) = mshl(i) ! the symmetry number of the shell
851  mtry = mprod(mtry + 1, qntmp(i) + 1, 0, nftw) - 1 ! combine IRR of all shells so far
852  end do
853 
854  if (spntry < qntot(1)) return ! jump out if impossible to compose the wanted total spin
855  if (mtry /= qntot(2)) return ! jump out if the combined IRR of all shells is not the wanted one
856  if (nshl == 1 .and. qnshl(1,1) /= qntot(1)) return ! jump out if the *only* shell violates spin requirement
857 
858  ! complete M-values for coupling of shells to each other
859 
860  kc = 0
861  kcs = nshl + 1
862 
863  if (nshl == 1 .and. qnshl(1,1) == qntot(1)) go to 360 ! trivial combination -- one contributing shell
864 
865  do i = 1, nshl - 1
866  qntmp(kcs) = mprod(qntmp(cup(1,i)) + 1, qntmp(cup(2,i)) + 1, 0, nftw) - 1
867  qnshl(2,kcs) = 0
868  qnshl(3,kcs) = 1
869  kcs = kcs + 1
870  end do
871 
872  ! begin to descend into shell to shell coupling tree
873 
874  kcs = nshl
875 
876  300 do while (kc < nshl - 1)
877  kc = kc + 1
878  kcs = kcs + 1
879  mu1 = qnshl(1,cup(1,kc))
880  mu2 = qnshl(1,cup(2,kc))
881  qnshl(1,kcs) = mu1 + mu2 - 1
882  spnmin(kc) = abs(mu1 - mu2) + 1
883  end do
884 
885  ! test for allowed state
886 
887  if (qnshl(1,kcs) < qntot(1) .or. spnmin(kc) > qntot(1)) go to 500
888  qnshl(1,kcs) = qntot(1)
889 
890  ! for R-matrix calculations: reject couplings which do not preserve the target quantum numbers
891 
892  360 if (qntar(1) >= 0) then
893  kcsp = kcs - 1
894  if (kcs == 3) kcsp = 1
895  if (qnshl(1,kcsp) /= qntar(1)) go to 500
896  end if
897 
898  nstate = nstate + 1
899 
900  ! first iteration: assign pqn value and print type and distrib data for allowed state
901 
902  if (nstate == 1) then
903  iexcon = 1
904 
905  ! convert some real pointers to integer pointers for use in ASSIGN
906  x_ptr => x(irfcon) ; call c_f_pointer (c_loc(x_ptr), irfcon_ptr, (/1/))
907  x_ptr => x(iexcon) ; call c_f_pointer (c_loc(x_ptr), iexcon_ptr, (/1/))
908  x_ptr => x(iqnstr) ; call c_f_pointer (c_loc(x_ptr), iqnstr_ptr, (/1/))
909 
910  call assign (nshl, ndist, nused, irfcon_ptr, iexcon_ptr, iqnstr_ptr, nx, nftw)
911 
912  if (ndist == 0) then
913  nstate = 0
914  return
915  end if
916 
917  nav = nx - nused
918  nnext = next + nused
919  if (nndel == 0) call print1 (iqnstr_ptr)
920  end if
921 
922  if (confpf >= 10 .and. nndel == 0) call print2 (0)
923 
924  ! convert some real pointers to integer pointers for use in WFN
925  x_ptr => x(inodi) ; call c_f_pointer (c_loc(x_ptr), nodi_ptr, (/1/))
926  x_ptr => x(indi) ; call c_f_pointer (c_loc(x_ptr), ndi_ptr, (/1/))
927  x_ptr => x(ndel) ; call c_f_pointer (c_loc(x_ptr), ndel_ptr, (/1/))
928  x_ptr => x(iqnstr) ; call c_f_pointer (c_loc(x_ptr), iqnstr_ptr, (/1/))
929  x_ptr => x(nnext) ; call c_f_pointer (c_loc(x_ptr), nnext_ptr, (/1/))
930 
931  call wfn (nncsf, nadel, iidist, iidis1, nodi_ptr, ndi_ptr, x(icdi), ndel_ptr, iqnstr_ptr, x(nnext), nnext_ptr, nav)
932 
933  if (nndel > 0 .and. nadel > nndel .and. iidis1 == 0) return
934 
935  if (nndel /= 0 .and. iidist /= 0) then
936  if (nstate == 1) call print1 (iqnstr_ptr)
937  if (confpf >= 10 .and. iidis1 /= 0) call print2 (iidis1)
938  end if
939 
940  ! ascend in coupling tree
941 
942  500 do while (kc > 1)
943  kc = kc - 1
944  kcs = kcs - 1
945  qnshl(1,kcs) = qnshl(1,kcs) - 2
946  if (qnshl(1,kcs) >= spnmin(kc)) go to 300
947  end do
948 
949  if (nndel /= 0 .and. iidis1 /= 0) call print3 (iidis1, 1)
950  if (nndel == 0) call print3 (idumm, 2)
951 
952  end subroutine cplem
953 
954 
994  subroutine distrb (nelecp, nshlp, shlmx, occshl, nslsv, kdssv, loopf, ksss, pqn, occst, shlmx1, pqnst, mshl, mshlst, &
995  gushl, gushst, cup, cupst, ndprod, symtyp, confpf, sshl, sshlst, ncsf, nncsf, nadel, nndel, x, nftw)
996 
997  use precisn, only : wp
998  use congen_data, only : ntyp, ndist, nstate, ncsft => ncsf, confpt => confpf, nshrun => nshl
999 
1000  integer :: confpf, nadel, ncsf, ndprod, nftw, nncsf, nndel, symtyp
1001  integer, dimension(3,*) :: cup, cupst, pqn, pqnst
1002  integer, dimension(*) :: gushl, gushst, kdssv, ksss, loopf, mshl, mshlst, nelecp, nshlp, nslsv, occshl, &
1003  occst, shlmx, shlmx1, sshl, sshlst
1004  real(kind=wp), dimension(*) :: x
1005  intent (in) confpf, cup, gushl, mshl, ncsf, ndprod, nelecp, nndel, nshlp, pqn, shlmx, shlmx1, sshl, symtyp
1006  intent (out) gushst, mshlst, pqnst, sshlst
1007  intent (inout) cupst, kdssv, ksss, loopf, nslsv, occshl, occst
1008 
1009  integer :: i, ibias, ic1, id, idd, it, it1, it2, ita, j, kds, kdsb, kdst, kprod, krun, ksi, kss, nadd, nadd2, ncrun, &
1010  nela, neleft, ninitx, nshlw, nslots
1011 
1012  confpt = confpf ! Print flag.
1013  ntyp = 0 ! Prototype number ...?
1014  nstate = 0 ! Global number of couplings computed (later) in "cplea" or "cplem".
1015  ndist = 0 ! Number of distributions generated from set of shells (set in "cplea"/"cplem" via "assign").
1016  ibias = 0 ! Offset in the list of shells.
1017  kprod = 0 ! Set of orbitals currently being processed.
1018  ninitx = sum(nshlp(1:ndprod)) ! Total number of shells in all sets of orbitals.
1019 
1020  orbital_set_loop: do
1021 
1022  kprod = kprod + 1 ! Move on to the next set of orbitals.
1023  kds = 0 ! Shell index within the set of orbitals.
1024  neleft = nelecp(kprod) ! (Remaining) number of movable electrons in the current set of orbitals.
1025  nshlw = nshlp(kprod) ! Number of shells in current set of orbitals.
1026  nslots = sum(shlmx(ibias + 1 : ibias + nshlw)) ! Total number of spin-orbitals in the current set of orbitals.
1027  occshl(ibias + 1 : ibias + nshlw) = 0 ! All shells in this set are un-occupied at the beginning.
1028 
1029  shell_loop: do
1030 
1031  kds = kds + 1 ! Move on to the next shell (orbital) within the current set of orbitals.
1032  kdsb = kds + ibias ! Global index of the current shell.
1033  occshl(kdsb) = min(neleft, shlmx(kdsb)) ! Put all available electrons in that shell, if possible.
1034 
1035  neleft = neleft - occshl(kdsb) ! Electrons that still did not fit into any shell.
1036  nslots = nslots - shlmx(kdsb) ! Number of free spin-orbitals for redistribution of remaining electrons.
1037 
1038  if (neleft /= 0) then
1039  if (nslots >= neleft) cycle shell_loop ! Enough room to redistribute the remaining electrons.
1040  do while (nslots <= neleft .and. kds /= 0) ! Repeat until there is either enough space, or all shells are empty.
1041  neleft = neleft + occshl(kdsb) ! Get back electrons from the last populated shell.
1042  occshl(kdsb) = 0 ! Its occupancy is now zero.
1043  nslots = nslots + shlmx(kdsb) ! The number of slots accordingly rises.
1044  kds = kds - 1 ! Return before the last shell.
1045  kdsb = kdsb - 1 ! Return before the last shell (global index).
1046  end do
1047  go to 130
1048  else if (kprod /= ndprod) then ! Not all sets of orbitals processed?
1049  nslsv(kprod) = nslots ! Store the number of free spin-orbitals (of the current set of orbitals).
1050  kdssv(kprod) = kds ! Store the last processed shell (of the current set of orbitals).
1051  ibias = ibias + nshlp(kprod) ! Move the global shell index offset to the beginning of the next set of orbitals.
1052  cycle orbital_set_loop ! Next set of orbitals, please!
1053  end if
1054 
1055  ! No electrons left and all sets of orbitals processed here...
1056 
1057  where (occshl(1:ninitx) == 0 .or. pqn(1,1:ninitx) /= 0)
1058  loopf(1:ninitx) = 1 ! Un-occupied or movable-to real shells.
1059  elsewhere
1060  loopf(1:ninitx) = 0 ! Occupied and non-movable shells.
1061  end where
1062 
1063  ksss(1:ninitx) = 0 !
1064  kdst = 0 !
1065  ksi = 0 ! Orbital set index.
1066 
1067  ! ----------------------------------------------------------------------------------------------------------
1068  ! expansion of pseudoshells and delete of zeroes follow the "st" arrays but for cupst are set up
1069 
1070  ksi_loop: do
1071 
1072  if (ksi == ninitx) then
1073 
1074  ! expand and compress the coupling scheme
1075  nshrun = ninitx
1076  ncrun = nshrun - 1
1077  cupst(1:3,1:ncrun) = cup(1:3,1:ncrun)
1078  krun = 0
1079 
1080  all_shell_loop: do i = 1, ninitx
1081  krun = krun + 1
1082  if (ksss(i) < 1) then
1083  ! delete section
1084  do id = 1, ncrun
1085  if (cupst(1,id) == krun) then ; it1 = cupst(2,id) ; it2 = cupst(3,id) ; exit ; end if
1086  if (cupst(2,id) == krun) then ; it1 = cupst(1,id) ; it2 = cupst(3,id) ; exit ; end if
1087  end do
1088 
1089  ncrun = ncrun - 1
1090 
1091  do idd = id, ncrun
1092  cupst(1:3,idd) = cupst(1:3,idd+1)
1093  end do
1094 
1095  do idd = 1, ncrun
1096  if (cupst(1,idd) == it2) then ; cupst(1,idd) = it1 ; exit ; end if
1097  if (cupst(2,idd) == it2) then ; cupst(2,idd) = it1 ; exit ; end if
1098  end do
1099 
1100  do idd = 1, ncrun
1101  do j = 1, 3
1102  if (cupst(j,idd) <= krun) cycle
1103  cupst(j,idd) = cupst(j,idd) - 1
1104  if (cupst(j,idd) >= it2) cupst(j,idd) = cupst(j,idd) - 1
1105  end do
1106  end do
1107 
1108  nshrun = nshrun - 1
1109  krun = krun - 1
1110  else if (ksss(i) > 1) then
1111  ! add section
1112  nadd = ksss(i) - 1
1113  nadd2 = nadd + nadd
1114  do idd = 1, ncrun
1115  cupst(3,idd) = cupst(3,idd) + nadd2
1116  do j = 1, 2
1117  if (cupst(j,idd) == krun) then
1118  cupst(j,idd) = nshrun + nadd2
1119  else if (cupst(j,idd) > krun .and. cupst(j,idd) <= nshrun) then
1120  cupst(j,idd) = cupst(j,idd) + nadd
1121  else if (cupst(j,idd) > krun .and. cupst(j,idd) > nshrun) then
1122  cupst(j,idd) = cupst(j,idd) + nadd2
1123  end if
1124  end do
1125  end do
1126  ic1 = krun
1127  nshrun = nshrun + nadd
1128  do idd = 1, nadd
1129  cupst(1,ncrun+idd) = ic1
1130  cupst(2,ncrun+idd) = krun + idd
1131  cupst(3,ncrun+idd) = nshrun + idd
1132  ic1 = nshrun + idd
1133  end do
1134  ncrun = ncrun + nadd
1135  krun = krun + nadd
1136  end if
1137  end do all_shell_loop ! end of add/delete loop
1138 
1139  ! now sort the expanded coupling array
1140  do i = 1, ncrun - 1
1141  do while (i /= cupst(3,i) - kdst)
1142  it = cupst(3,i) - kdst
1143  do j = 1, 3
1144  ita = cupst(j,it)
1145  cupst(j,it) = cupst(j,i)
1146  cupst(j,i) = ita
1147  end do
1148  end do
1149  end do
1150 
1151  ! generate a new wave function prototpe
1152  ntyp = ntyp + 1
1153  if (symtyp < 2) then
1154  call cplea (nncsf, nadel, x, nftw)
1155  else
1156  call cplem (nncsf, nadel, x, nftw)
1157  end if
1158  if (nstate == 0) ntyp = ntyp - 1
1159 
1160  ! end of coupling scheme section
1161  if (loopf(ksi) == 0) then
1162  go to 320
1163  else
1164  kdst = kdst - ksss(ksi)
1165  go to 360
1166  end if
1167  end if
1168 
1169  ksi = ksi + 1 ! Next set of orbitals, please.
1170  kss = 1 ! Shell index.
1171  if (occshl(ksi) == 0) cycle ksi_loop ! Do not process un-occupied shells.
1172  if (occshl(ksi) /= 0) continue
1173 
1174  nela = occshl(ksi) ! Occupation of current (ksi) shell.
1175  kss = 0 ! ... ???
1176 
1177  410 kss_loop: do while (kss <= pqn(3,ksi) - pqn(2,ksi)) ! Loop over prescribed orbitals in the current set.
1178  kss = kss + 1 ! Next orbital within ksi, please.
1179  kdst = kdst + 1 ! ... ???
1180  occst(kdst) = min(nela, shlmx1(sshl(ksi))) !
1181  if (kss /= 1 .and. kdst > 1) occst(kdst) = min(nela, occst(kdst-1))
1182  pqnst(1:3,kdst) = pqn(1:3,ksi)
1183  mshlst(kdst) = mshl(ksi)
1184  gushst(kdst) = gushl(ksi)
1185  sshlst(kdst) = sshl(ksi)
1186  nela = nela - occst(kdst)
1187  if (nela /= 0) then
1188  cycle kss_loop
1189  else
1190  ksss(ksi) = kss
1191  cycle ksi_loop
1192  end if
1193  end do kss_loop
1194 
1195  ! second part of the expansion of pseudoshells and deletion of zeros
1196  320 unkss_loop: do
1197  occst(kdst) = occst(kdst) - 1
1198  nela = nela + 1
1199  if (occst(kdst) /= 0) go to 410
1200  kss = kss - 1
1201  kdst = kdst - 1
1202  if (kss >= 1) then
1203  cycle unkss_loop
1204  else
1205  nela = 0
1206  go to 360
1207  end if
1208  end do unkss_loop
1209 
1210  360 unksi_loop: do
1211  ksi = ksi - 1
1212  if (ksi <= 0) exit ksi_loop ! sic
1213  if (loopf(ksi) == 0) then
1214  kss = ksss(ksi)
1215  go to 320
1216  end if
1217  kdst = kdst - ksss(ksi)
1218  end do unksi_loop
1219 
1220  ! end of pseudoshell expansion loops
1221 
1222  end do ksi_loop
1223 
1224  ! ----------------------------------------------------------------------------------------------------------
1225 
1226  ! last part of outer loop follows
1227 
1228  120 if (occshl(kdsb) == 0) go to 140
1229  occshl(kdsb) = occshl(kdsb) - 1 ! Remove one electron from the current shell.
1230  neleft = 1 ! Remember that we have it
1231  if (nndel /= 0 .and. nadel > nndel) exit orbital_set_loop
1232  if (kds < nshlp(kprod)) cycle shell_loop ! If we can push it into the NEXT shell, do it.
1233  neleft = neleft + occshl(kdsb) ! Otherwise, get back all electrons from the last shell.
1234  occshl(kdsb) = 0 ! Clear its population.
1235  nslots = nslots + shlmx(kdsb) ! Update available number of slots.
1236  kds = kds - 1 ! Move back one shell.
1237  kdsb = kdsb - 1 ! Global index, too.
1238 
1239  130 unkds_loop: do while (kds /= 0) ! Reset preceding shells one by one...
1240  if (occshl(kdsb) /= 0) then ! If shell occupied:
1241  occshl(kdsb) = occshl(kdsb) - 1 ! - remove one electron
1242  neleft = neleft + 1 ! - put among the unused electrons
1243  if (nndel /= 0 .and. nadel > nndel) exit orbital_set_loop
1244  cycle shell_loop ! - try to add the electrons to shells
1245  end if
1246  nslots = nslots + shlmx(kdsb) ! If not occupied, add these shells to list of known slots.
1247  kds = kds - 1 ! Recede by one more shell...
1248  kdsb = kdsb - 1 ! Global index too.
1249  end do unkds_loop
1250 
1251  140 kprod = kprod - 1 ! Recede by one group of orbitals.
1252  if (kprod == 0) exit orbital_set_loop ! If at beginning, exit subroutine.
1253  ibias = ibias - nshlp(kprod) ! Decrease global shell index offset.
1254  nslots = nslsv(kprod) ! Get (previously stored) number of free slots.
1255  kds = kdssv(kprod) ! Get (previously stored) index of the last shell in that set.
1256  kdsb = kds + ibias ! Get its global index.
1257  go to 120
1258 
1259  end do shell_loop
1260 
1261  end do orbital_set_loop
1262 
1263  ncsft = ncsf
1264 
1265  end subroutine distrb
1266 
1267 
1280  subroutine packdet (iqn, ni, jqn, nj, ci, cj, nt)
1281 
1282  use precisn, only : wp
1283 
1284  integer :: ni, nj, nt
1285  real(kind=wp), dimension(*) :: ci, cj
1286  integer, dimension(2,ni,*) :: iqn
1287  integer, dimension(2,nj,*) :: jqn
1288  intent (in) ci, iqn, ni, nj, nt
1289  intent (out) cj, jqn
1290 
1291  jqn(1:2,1:nj,1:nt) = iqn(1:2,1:nj,1:nt)
1292  cj(1:nt) = ci(1:nt)
1293 
1294  end subroutine packdet
1295 
1296 
1299  subroutine print1 (qnstor)
1300 
1301  use global_utils, only : getin
1302  use congen_data , only : confpf, ndist, ne, nshl, ntyp, occshl, pqnr => pqnst, mshl, gushl, qnshl, &
1303  nnelcg => nnlecg, symtyp, nftw, blnk43, header, lp, star, nitem
1304  use congen_pagecontrol, only : addl, newpg, space, taddl, taddl1
1305 
1306  integer, dimension(*), intent(in) :: qnstor
1307 
1308 
1309  integer :: i, ii, imax, j, jj, k, kf, ki, klabel, lt, lta, nlex, nstar
1310  character(len=4), dimension(3,4) :: label = reshape((/ ' NTY', 'P=XX', 'X ', &
1311  ' NDI', 'ST=Y', 'YYY ', &
1312  ' NST', 'ATE=', 'ZZZ ', &
1313  ' ', ' ', ' ' /) , (/ 3, 4/))
1314  character(len=16), parameter :: frmt = '(3A4,A8,I8,8I12)'
1315  character(len=1), dimension(12,4) :: labell
1316 
1317  equivalence(label(1,1), labell(1,1))
1318 
1319  ! print type(confpf.ge.1) and distribution data (confpf.ge.20)
1320  ne = nnelcg
1321  if (confpf < 1) return
1322  nlex = 0
1323  if (symtyp == 1) nlex = 1
1324  nstar = 20 + min(nitem, nshl) * 12
1325 
1326  klabel = 1
1327  call getin (ntyp, 3, labell(7,1), 0)
1328 
1329  if (confpf <= 1 .and. ntyp /= 1) then
1330  call taddl1 (5 + (6 + nlex) * ((nshl + nitem - 1) / nitem), lta)
1331  if (lta /= 0) then
1332  call space (2)
1333  else
1334  call newpg
1335  end if
1336  else
1337  call newpg
1338  end if
1339 
1340  do i = 1, nshl, nitem
1341  imax = min(i + nitem - 1, nshl)
1342  call addl (5 + nlex)
1343  write(nftw,frmt) (label(j,klabel), j=1,3), header(1), (j, j=i,imax)
1344  write(nftw,frmt) blnk43, header(2), (occshl(j), j=i,imax)
1345  write(nftw,frmt) blnk43, header(3), (mshl(j), j=i,imax)
1346  if (symtyp == 1) write(nftw,frmt) blnk43, header(4), (gushl(j), j=i,imax)
1347 
1348  ! print occshl and sym data
1349 
1350  klabel = 4
1351  write(nftw,'(3A4,A8,9(A3,2(I2,","),I2,")"))') blnk43, header(5), (lp, (pqnr(jj,j), jj=1,3), j=i,imax)
1352  if (symtyp < 2) then
1353  write(nftw,'(3A4,A8,9(A3,2(I2,","),I2,")"))') blnk43, header(6), (lp, (qnshl(jj,j), jj=1,3), j=i,imax)
1354  else
1355  write(nftw,frmt) blnk43, header(6), (qnshl(1,j), j=i,imax)
1356  end if
1357  call space (1)
1358  end do
1359 
1360  ! bypass printing of distributions if not required
1361 
1362  if (confpf >= 20) then
1363 
1364  ! print row of star separator
1365 
1366  call taddl (1, lt)
1367  if (lt > 0) write(nftw,'(" ",132A1)') (star, j=1,nstar)
1368  call space (1)
1369  kf = 0
1370  do ii = 1, ndist
1371  klabel = 2
1372  call getin (ii, 4, labell(8,2), 0)
1373  do i = 1, nshl, nitem
1374  imax = min(i + nitem - 1, nshl)
1375  call addl (4 + nlex)
1376  write(nftw,frmt) (label(j,klabel), j=1,3), header(1), (j, j=i,imax)
1377  write(nftw,frmt) blnk43, header(2), (occshl(j), j=i,imax)
1378  write(nftw,frmt) blnk43, header(3), (mshl(j), j=i,imax)
1379  if (symtyp == 1) write(nftw,frmt) blnk43, header(4), (gushl(j), j=i,imax)
1380  klabel = 4
1381  ki = kf + 1
1382  kf = ki + (imax - i)
1383  write(nftw,frmt) blnk43, header(5), (qnstor(k), k=ki,kf)
1384  call space (1)
1385  end do
1386  end do
1387 
1388  end if
1389 
1390  ! merge confpf >= 1 and confpf >= 20 paths
1391 
1392  call addl (1)
1393  write(nftw,'(" ",19("*"),5X,"TOTAL NUMBER OF DISTRIBUTIONS FOR NTYP =",I3," IS",I5)') ntyp, ndist
1394  if (confpf < 10) return
1395 
1396  ! prepare for state printing
1397 
1398  call space (1)
1399  call taddl (1, lt)
1400  if (lt > 0) write(nftw,'(" ",132A1)') (star, j=1,nstar)
1401  call space (1)
1402 
1403  end subroutine print1
1404 
1405 
1408  subroutine print2 (iidis1)
1409 
1410  use global_utils, only : getin
1412  use congen_pagecontrol, only : addl, space
1413 
1414  integer :: iidis1
1415  intent (in) iidis1
1416 
1417  integer :: i, imax, j, jj, kf, ki, klabel, ncsff, ncsfi, nshlm1
1418  character(len=4), dimension(3,4) :: label = reshape((/' NTY', 'P=XX', 'X ', &
1419  ' NDI', 'ST=Y', 'YYY ', &
1420  ' NST', 'ATE=', 'ZZZ ', &
1421  ' ', ' ', ' '/) , (/ 3, 4/))
1422  character(len=1), dimension(12,4) :: labell
1423 
1424  equivalence(label(1,1), labell(1,1))
1425 
1426  ! print state data
1427 
1428  nshlm1 = nshl - 1
1429  if (confpf < 10) return
1430  call getin (nstate, 3, labell(9,3), 0)
1431  if (nshlm1 <= 0) then
1432  call addl (1)
1433  write(nftw,'(3A4,A8,I8,8I12)') (label(j,3), j=1,3)
1434  return
1435  end if
1436  kf = nshl
1437  klabel = 3
1438  do i = 1, nshlm1, nitem
1439  imax = min(i + nitem - 1, nshlm1)
1440  call addl (2) ! JMC argument should probably be 3 as there are 3 writes below???
1441  write(nftw,'(3A4,A8,9(A3,2(I2,","),I2,")"))') (label(j,klabel), j=1,3), header(7), (lp, (cup(jj,j), jj=1,3), j=i,imax)
1442  klabel = 4
1443  ki = kf + 1
1444  kf = ki + (imax - i)
1445  write(nftw,'(3A4,A8,9(A3,2(I2,","),I2,")"))') blnk43, header(6), (lp, (qnshl(jj,j), jj=1,3), j=ki,kf)
1446  if (symtyp < 2) then
1447  write(nftw,'(3A4,A8,9(A3,2(I2,","),I2,")"))') blnk43, header(6), (lp, (qnshl(jj,j), jj=1,3), j=ki,kf)
1448  else
1449  write(nftw,'(3A4,A8,I8,8I12)') blnk43, header(6), (qnshl(1,j), j=ki,kf)
1450  end if
1451  call space (1)
1452  end do
1453 
1454  ! print CSF numbers for this state
1455 
1456  if (iidis1 /= 0) then
1457  ncsfi = ncsf - iidis1 + 1
1458  ncsff = ncsf
1459  else
1460  ncsfi = ncsf + 1
1461  ncsff = ncsf + ndist
1462  end if
1463 
1464  call addl (1)
1465  write(nftw,'(" ",19("*"),5X,"CSF NUMBERS",I6," TO",I6," GENERATED FOR NSTATE=",I3)') ncsfi, ncsff, nstate
1466  call space (1)
1467 
1468  end subroutine print2
1469 
1470 
1473  subroutine print3 (iidis1, i13)
1474 
1475  use congen_data, only : confpf, ncsf, ndist, nshl, nstate, ntyp, nftw, star, nitem
1476  use congen_pagecontrol, only : addl, space, taddl
1477 
1478  integer, intent(in) :: i13, iidis1
1479 
1480  integer :: i, j, lt, ncsfi, nstar, nstot
1481 
1482  ! print summary data
1483  if (i13 /= 2) then
1484  nstot = iidis1
1485  else
1486  if (confpf < 1) return
1487  nstot = nstate * ndist
1488  end if
1489  ncsfi = ncsf + 1 - nstot
1490  if (confpf >= 40) call space (1)
1491  call addl (2)
1492 
1493  write(nftw,'(" ",19("*"),5X,"TOTAL NUMBER OF STATES FOR NTYP=",I3," IS",I4)') ntyp, nstate
1494  write(nftw,'(20X,"CSF NUMBERS",I10," TO",I10," (",I9," CSFS) GENERATED")') ncsfi, ncsf, nstot
1495 
1496  nstar = 20 + min(nitem, nshl) * 12 ! JMC see PRINT1 to understand where this hardwiring has come from
1497  do i = 1, 2
1498  call taddl (1, lt)
1499  if (lt > 0) write(nftw,'(" ",132A1)') (star, j=1,nstar)
1500  end do
1501 
1502  end subroutine print3
1503 
1504 
1507  subroutine print4 (nd,x,ix)
1508 
1509  use precisn, only : wp
1510  use congen_data, only : ne, nftw
1511  use congen_pagecontrol, only : addl, space
1512 
1513  integer :: nd
1514  integer, dimension(*) :: ix
1515  real(kind=wp), dimension(*) :: x
1516  intent (in) ix, nd, x
1517 
1518  integer :: ie, ind, ip, ipi, it, j, nl, nitem
1519 
1520  ! print determinant and spin-orbital data
1521 
1522  ipi = 0
1523  it = 1
1524  nitem = 20
1525  nl = (ne + nitem - 1) / nitem
1526 
1527  do ind = 1, nd
1528  call addl (nl + it)
1529  if (it /= 0) then
1530  write(nftw,'(30X,"NUMBER OF DET IS",I3)') nd
1531  it = 0
1532  end if
1533  do ie = 1, ne, nitem
1534  ip = ipi + 1
1535  ipi = ip + min(nitem - 1, ne - ie)
1536  if (ie /= 1) then
1537  write(nftw,'(45X,20I4)') (ix(j), j=ip,ipi)
1538  else
1539  write(nftw,'(I25,5X,E15.8,20I4)') ind, x(ind), (ix(j), j=ip,ipi)
1540  end if
1541  end do
1542  end do
1543 
1544  call space (1)
1545 
1546  end subroutine print4
1547 
1548 
1551  subroutine print5 (nd, ndi)
1552 
1553  use congen_data, only : ncsf, nftw
1554  use congen_pagecontrol, only : addl
1555 
1556  integer :: nd
1557  integer, dimension(*) :: ndi
1558  intent (in) nd, ndi
1559 
1560  integer :: ind, ip, ipi, j, nrep
1561 
1562  ip = 1
1563  do ind = 1, nd
1564  nrep = ndi(ip)
1565  if (nrep == 0) then
1566  call addl (1)
1567  write(nftw, '(35X,2I5)') ind, nrep
1568  if (ind == 1) then
1569  write(nftw,'("+",29X,I5)') ncsf
1570  end if
1571  else
1572  call addl (2)
1573  ipi = ip + 1
1574  ip = ip + nrep
1575 
1576  if (ind /= 1) then
1577  write(nftw,'(35X,2I5,21I4/(45X,21I4))') ind, nrep, (ndi(j), j=ipi,ip)
1578  else
1579  write(nftw,'(30X,3I5,21I4/(45X,21I4))') ncsf, ind, nrep, (ndi(j), j=ipi,ip)
1580  end if
1581 
1582  ipi = ip + 1
1583  ip = ip + nrep
1584 
1585  write(nftw,'(45X,21I4)') (ndi(j), j = ipi,ip)
1586  end if
1587  ip = ip + 1
1588  end do
1589 
1590  end subroutine print5
1591 
1592 
1602  subroutine state (ns, x, last, nd, confpf)
1603 
1604  use iso_c_binding, only : c_loc, c_f_pointer
1605  use precisn, only : wp
1606  use congen_data, only : lratio, cup, iqn => qnshl, ne => nnlecg, isz => nisz
1607 
1608  integer :: confpf, last, nd, ns
1609  real(kind=wp), dimension(*), target :: x
1610  intent (in) confpf, last
1611  intent (inout) nd, x
1612 
1613  integer :: ic, id, intpfg, iqns, jqns, lc, ld, ldp, ldq, nam, ndmx, nt, ntmx
1614 
1615  real(wp), pointer :: x_ptr
1616  integer, pointer, dimension(:) :: iqns_ptr, jqns_ptr, ld_ptr
1617 
1618  x_ptr => x(1)
1619 
1620  intpfg = merge(1, 0, confpf > 40)
1621 
1622  nd = 0
1623  nam = ns + ns - 1
1624  ntmx = last / (nam + nam + 1)
1625  ic = 1
1626  iqns = ic + ntmx
1627 
1628  ! convert real pointer to integer pointer for use in WFCPLE
1629  x_ptr => x(iqns) ; call c_f_pointer (c_loc(x_ptr), iqns_ptr, (/1/))
1630 
1631  call wfcple (nam, iqn, isz, cup, iqns_ptr, x(ic), ntmx, nt, intpfg)
1632 
1633  if (nt == 0) return
1634 
1635  jqns = last - 2 * ns * nt + 1
1636  lc = jqns - nt
1637 
1638  ! convert real pointer to integer pointer for use in PACK
1639  x_ptr => x(jqns) ; call c_f_pointer (c_loc(x_ptr), jqns_ptr, (/1/))
1640 
1641  call packdet (iqns_ptr, nam, jqns_ptr, ns, x(1), x(lc), nt)
1642 
1643  ndmx = (lc - 1) / (ne + 1)
1644  ld = 1 + ndmx
1645 
1646  ! convert real pointer to integer pointer for use in GETSO
1647  x_ptr => x(ld) ; call c_f_pointer (c_loc(x_ptr), ld_ptr, (/1/))
1648 
1649  call getso (ns, intpfg, nt, jqns_ptr, x(lc), nd, ld_ptr, x(ic), ndmx)
1650 
1651  if (nd == 0) return
1652 
1653  ! Finalize
1654 
1655  ldp = nd + 1
1656  ldq = nd + (ne * nd + lratio - 1) / lratio
1657  do id = ldp, ldq
1658  x(id) = x(ld)
1659  ld = ld + 1
1660  end do
1661 
1662  end subroutine state
1663 
1664 
1667  subroutine wfcple (nam, iqn, isz, icup, iqns, c, last, lc2, intpfg)
1668 
1669  use precisn, only : wp
1670  use consts, only : one => xone
1671  use congen_data, only : root2, nftw, lg
1672 
1673  integer :: intpfg, isz, last, lc2, nam
1674  real(kind=wp), dimension(*) :: c
1675  integer, dimension(3,lg) :: icup
1676  integer, dimension(3,*) :: iqn
1677  integer, dimension(2,nam,*) :: iqns
1678  intent (in) icup, isz, last, nam
1679  intent (inout) c, iqns, lc2
1680 
1681  integer :: i, iam, ic, init, j, l, lc, lc1, lc3, m, mp, ms, n, n1, n2, n3, nc, niam, niam1
1682  logical, dimension(nam) :: ind ! JMC changing the dimension from 150
1683  integer, dimension(2,200) :: iszt ! JMC not sure how to dimension this...
1684  real(kind=wp) :: sign
1685 
1686  iqns(1,nam,1) = isz
1687  iqns(2,nam,1) = iqn(2,nam)
1688  c(1) = one
1689  lc2 = 1
1690  if (nam == 1) return
1691  do i = 1, nam
1692  ind(i) = .true.
1693  end do
1694  niam = (nam + 1) / 2
1695  100 n3 = nam
1696  110 if (ind(n3)) then
1697  if (n3 <= niam) go to 299
1698  ind(n3) = .false.
1699  init = last - lc2 + 1
1700  l = last
1701  lc = lc2
1702  do while (lc > 0)
1703  iqns(1:2,1:nam,l) = iqns(1:2,1:nam,lc)
1704  c(l) = c(lc)
1705  lc = lc - 1
1706  l = l - 1
1707  end do
1708  n = 1
1709  300 if (icup(3,n) == n3) then
1710  n1 = icup(1,n)
1711  n2 = icup(2,n)
1712  if (n1 > n3 .or. n2 > n3) go to 299
1713  if (.not.ind(n1) .or. .not.ind(n2)) go to 299
1714  if (n1 <= niam) ind(n1) = .false.
1715  if (n2 <= niam) ind(n2) = .false.
1716  lc2 = 0
1717  do l = init, last
1718  iqns(2,n1,l) = iqn(2,n1)
1719  iqns(2,n2,l) = iqn(2,n2)
1720  m = iqns(2,n3,l)
1721  if (abs(m) /= iqn(2,n1) + iqn(2,n2)) then
1722  mp = iqn(2,n1) - iqn(2,n2)
1723  if (abs(m) /= abs(mp)) go to 511
1724  n = n2
1725  if (m /= mp) n = n1
1726  iqns(2,n,l) = -iqns(2,n,l)
1727  else if (iqns(2,n3,l) < 0) then
1728  iqns(2,n1,l) = -iqns(2,n1,l)
1729  iqns(2,n2,l) = -iqns(2,n2,l)
1730  end if
1731  lc1 = lc2 + 1
1732  ms = iqns(1,n3,l)
1733  call cgcoef (iqn(1,n1), iqn(1,n2), iqn(1,n3), ms, nc, iszt, c(lc1), intpfg)
1734  if (nc > 0) then
1735  lc2 = lc2 + nc
1736  if (lc2 >= l) go to 899
1737  ic = 1
1738  do lc = lc1, lc2
1739  iqns(1:2,1:nam,lc) = iqns(1:2,1:nam,l)
1740  iqns(1,n1,lc) = iszt(1,ic)
1741  iqns(1,n2,lc) = iszt(2,ic)
1742  ic = ic + 1
1743  c(lc) = c(lc) * c(l)
1744  end do
1745  if (iqns(2,n3,l) < 0) then
1746  if (iqn(3,n1) >= 0 .and. iqn(3,n2) >= 0) cycle
1747  c(lc1:lc2) = -c(lc1:lc2)
1748  else if (iqns(2,n3,l) == 0) then
1749  if (iqn(2,n1) /= 0) then
1750  if (lc2 + nc >= l) go to 899
1751  lc3 = lc2
1752  sign = one
1753  if (iqn(3,n3) < 0) sign = -one
1754  do lc = lc1, lc3
1755  lc2 = lc2 + 1
1756  iqns(1:2,1:nam,lc2) = iqns(1:2,1:nam,lc)
1757  iqns(2,n1,lc2) = -iqns(2,n1,lc2)
1758  iqns(2,n2,lc2) = -iqns(2,n2,lc2)
1759  c(lc) = c(lc) * root2
1760  c(lc2) = c(lc) * sign
1761  end do
1762  cycle
1763  end if
1764  if (iqn(3,n1) * iqn(3,n2) /= iqn(3,n3)) go to 511
1765  end if
1766  cycle
1767  end if
1768  go to 511
1769  end do
1770  go to 100
1771  end if
1772  n = n + 1
1773  if (n < niam) go to 300
1774  go to 299
1775  end if
1776  n3 = n3 - 1
1777  if (n3 > 0) go to 110
1778  return
1779 
1780  299 niam1 = niam - 1
1781  write(nftw,'("0ERROR IN COUPLING TREE"//(3I5))') ((icup(i,j), i=1,3), j=1,niam1)
1782  lc2 = 0
1783  return
1784 
1785  511 write(nftw,'("0COUPLING IMPOSSIBLE MULTIPLICITIES FOLLOW"//(3I5))') (iqn(i,n1), iqn(i,n2), iqn(i,n3), i=1,3)
1786  lc2 = 0
1787  return
1788 
1789  899 write(nftw,'("0STORAGE OVERFLOW IN VECTOR COUPLING")')
1790  lc2 = 0
1791 
1792  end subroutine wfcple
1793 
1794 
1814  subroutine wfn (nncsf, nadel, iidist, iidis3, nodi, ndi, cdi, ndel, pqnshl, x, ix, nx)
1815 
1816  ! noi # of states (nodi)
1817  ! nid # of determinants (cdi)
1818  ! ni # of replacements (ndi)
1819 
1820  use precisn, only : wp
1821  use congen_data, only : lratio, iidis2, lcdi, lndi, ni, nid, noi, exdet, exref, norep, nonew, ntso, &
1822  noimx => nodimx, nidmx => cdimx, jmx => ndimx, megul, nsoi, ncall, nftw, &
1823  confpf, ncsf, ndist, nshl, occshl, sshl => sshlst, shlmx1, nndel, nelec => nnlecg, ndimx
1824 
1825  integer :: iidis3, iidist, nadel, nncsf, nx
1826  real(kind=wp), dimension(*) :: cdi, x
1827  integer, dimension(*) :: ix, ndel, ndi, nodi, pqnshl
1828  intent (in) ndel, pqnshl
1829  intent (out) iidis3
1830  intent (inout) cdi, iidist, nadel, ndi, nncsf, nodi
1831 
1832  integer :: det, i, ia, ib, id, idist, iidis1, irep, j, k, k1, kshl, kshlst, lf, li, nd, nii
1833 
1834  save iidis1 ! JMC adding this in consultation with Jonathan Tennyson because the variable was found to be used but not set in tests...
1835  ! The other variables initialized in the 1st call to this routine are (former) common block variables now in congen_data.
1836 
1837  ! reset counters for a new wave function group ("ncall = 1" is set in CSFGEN before calling DISTRB)
1838  if (ncall == 1) then
1839  lcdi = 0
1840  lndi = 0
1841  noi = 0
1842  nid = 0
1843  iidis1 = 0
1844  iidis2 = 0
1845  ni = 0
1846  ncall = 0
1847  end if
1848 
1849  ! here most work is done
1850  call state (nshl, x, nx, nd, confpf)
1851 
1852  if (nd <= 0) then
1853  write(nftw,'("1","******* ERROR IN WFN ND=0"//)')
1854  stop 70
1855  end if
1856 
1857  ! no distributions generated in ASSIGN
1858  if (ndist == 0) return
1859 
1860  if (nndel /= 0 .and. nadel > nndel) return
1861 
1862  iidist = 0
1863  kshlst = 0
1864 
1865  ! for all distributions generated by ASSIGN
1866  do idist = 1, ndist
1867 
1868  nncsf = nncsf + 1
1869 
1870  if (nndel /= 0 .and. ndel(nadel) /= nncsf) then
1871  kshlst = kshlst + nshl
1872  cycle
1873  end if
1874 
1875  ncsf = ncsf + 1
1876  if (nndel /= 0) then
1877  nadel = nadel + 1
1878  iidist = iidist + 1
1879  end if
1880 
1881  k = nd * lratio
1882  ia = nd * (2 * nelec + 1) + ni
1883  ib = nd + nid
1884  k1 = noi + 1
1885 
1886  if (ia > jmx .or. ib > nidmx .or. k1 > noimx) then
1887  if (nndel == 0 .or. iidis2 /= 0) then
1888  write(megul) noi, (nodi(i), i=1,noi)
1889  write(megul) nid, (cdi(i), i=1,nid)
1890  write(megul) ni, (ndi(i), i=1,ni)
1891  lcdi = lcdi + nid
1892  lndi = lndi + ni
1893  end if
1894  noi = 0
1895  ni = 0
1896  nid = 0
1897  end if
1898 
1899  nii = ni + 1
1900  do id = 1, nd
1901  exdet(1:ntso) = 0
1902  kshl = kshlst
1903  lf = 0
1904  do i = 1, nshl
1905  li = lf + 1
1906  lf = lf + occshl(i)
1907  kshl = kshl + 1
1908  do j = li, lf
1909  k = k + 1
1910  det = ix(k) + nsoi(sshl(i)) + (pqnshl(kshl) - 1) * shlmx1(sshl(i))
1911  exdet(det) = 1
1912  end do
1913  end do
1914  ia = 1
1915  ib = 1
1916  do i = 1, ntso
1917  if (exdet(i) < exref(i)) then
1918  norep(ia) = i
1919  ia = ia + 1
1920  else if (exdet(i) > exref(i)) then
1921  nonew(ib) = i
1922  ib = ib + 1
1923  end if
1924  end do
1925  irep = ib - 1
1926  ni = ni + 1
1927 
1928  ! ZM check that NI does not overflow NDIMX
1929  ! If NDI was allocatable we could resize it here
1930  if (ni + 2 * irep > ndimx) then
1931  write(nftw,'("******* ERROR IN WFN, NDIMX TOO SMALL",2I10)') ni + 2 * irep, ndimx
1932  stop 81
1933  end if
1934 
1935  ndi(ni) = irep
1936  do i = 1, irep
1937  ni = ni + 1
1938  ndi(ni) = norep(i)
1939  ndi(ni + irep) = nonew(i)
1940  end do
1941  ni = ni + irep
1942 
1943  end do
1944 
1945  if (confpf >= 40) call print5 (nd, ndi(nii))
1946  noi = noi + 1
1947 
1948  ! ZM check that NOI does not overflow NODIMX
1949  ! If NODI was allocatable we could resize it here
1950  if (noi > noimx) then
1951  write(nftw,'("******* ERROR IN WFN, NODIMX TOO SMALL",2I10)') noi, noimx
1952  stop 82
1953  end if
1954 
1955  nodi(noi) = nd
1956 
1957  ! ZM check that NID+ND does not overflow CDIMX
1958  ! If CDI was allocatable we could resize it here
1959  if (nid + nd > nidmx) then
1960  write(nftw,'("******* ERROR IN WFN, CDIMX TOO SMALL",2I10)') nid + nd, nidmx
1961  stop 83
1962  end if
1963 
1964  do i = 1, nd
1965  nid = nid + 1
1966  cdi(nid) = x(i)
1967  end do
1968 
1969  kshlst = kshl
1970 
1971  end do
1972 
1973  iidis1 = iidis1 + iidist
1974  iidis2 = iidist + iidis2
1975  if (confpf >= 30 .and. iidist > 0) call print4 (nd, x, ix(nd*lratio+1))
1976  iidis3 = iidis1
1977 
1978  end subroutine wfn
1979 
1980 end module congen_distribution
congen_data::header
character(len=8), dimension(7), parameter header
Definition: congen_data.f90:61
congen_data::mshl
integer, dimension(lg) mshl
Symmetry number from zero to n-1 (mvalue).
Definition: congen_data.f90:93
congen_data::nonew
integer, dimension(lg) nonew
Definition: congen_data.f90:137
congen_data::noi
integer noi
Number of determinants per CSF.
Definition: congen_data.f90:146
congen_data::lratio
integer lratio
Ratio of real size to integer size. Used to manage workspace data.
Definition: congen_data.f90:74
congen_data::nid
integer nid
Length of the integer array containing all packed determinants.
Definition: congen_data.f90:145
congen_data::megul
integer megul
File unit for binary output of generated configurations.
Definition: congen_data.f90:128
congen_data::nisz
integer nisz
Total S_z, set by CSFGEN, defaults to first element of qntot.
Definition: congen_data.f90:85
congen_data::root2
real(kind=wp), parameter root2
Note that this is actually inverse square root!
Definition: congen_data.f90:51
congen_data::lg
integer, parameter lg
??? used to dimension arrays below; also in CPLE[A,M].
Definition: congen_data.f90:39
congen_data::cup
integer, dimension(3, lg) cup
Coupling scheme data. ???
Definition: congen_data.f90:90
congen_pagecontrol
Page control.
Definition: congen_pagecontrol.f90:26
congen_data::ntcon
integer ntcon
Definition: congen_data.f90:111
congen_data::icdi
integer icdi
Position in workspace where the determinant coefficients start (one coeff per one determinant).
Definition: congen_data.f90:75
congen_data::kslim
integer, dimension(2, lg) kslim
Definition: congen_data.f90:98
congen_data::indi
integer indi
Position in workspace where packed determinants start (each as size + replacements).
Definition: congen_data.f90:77
congen_data::nstate
integer nstate
Number of couplings computed in congen_distribution::cplea or congen_distribution::cplem.
Definition: congen_data.f90:127
congen_data::nshsym
integer, dimension(nu) nshsym
Definition: congen_data.f90:115
congen_distribution::print5
subroutine, private print5(nd, ndi)
?
Definition: congen_distribution.f90:1552
congen_data::inodi
integer inodi
Position in workspace where CSFs start (as number of determinants per CSF).
Definition: congen_data.f90:78
congen_distribution::cplem
subroutine, private cplem(nncsf, nadel, x, nftw)
?
Definition: congen_distribution.f90:802
congen_data::blnk43
character(len=4), dimension(3), parameter blnk43
Definition: congen_data.f90:59
congen_data::qntar
integer, dimension(3) qntar
Coupling control for current wfn group. ???
Definition: congen_data.f90:101
congen_data::symtyp
integer symtyp
Symmetry type, 0 = C_infv, 1 = D_infh, 2 = {D_2h, C_2v, C_s, E}.
Definition: congen_data.f90:88
congen_data::ind
integer, dimension(jsmax+2) ind
Pascal triangle row pointers into congen_data::binom.
Definition: congen_data.f90:107
congen_data::ndist
integer ndist
Number of distributions generated from set of shells (set in congen_distribution::assign).
Definition: congen_data.f90:126
congen_distribution::getsm
subroutine, private getsm(ne, isz, nc, c, iso)
Form ne electrons in a shell coupled to (l,is).
Definition: congen_distribution.f90:375
congen_distribution::getso
subroutine, private getso(ns, intpfg, nti, iqns, ci, nd, id, cd, last)
?
Definition: congen_distribution.f90:417
congen_data::confpf
integer confpf
Print flag for the amount of print given of configurations and prototypes.
Definition: congen_data.f90:120
congen_data::nshl
integer nshl
Number of shells in the set of orbitals currently being processed.
Definition: congen_data.f90:123
congen_pagecontrol::taddl
subroutine, public taddl(lines, lt)
Add blank lines to output.
Definition: congen_pagecontrol.f90:170
congen_data::ni
integer ni
Number of determinants currently in memory.
Definition: congen_data.f90:144
congen_data::occshl
integer, dimension(lg) occshl
Compressed shell occupations, all zeros deleted and pseudo shells expanded.
Definition: congen_data.f90:94
congen_data::ncsf
integer ncsf
Total number of CSFs generated.
Definition: congen_data.f90:121
congen_distribution::getsa
subroutine, private getsa(ne, l, is, isz, m, nc, c, iso)
Form ne electrons in a shell coupled to (l,is).
Definition: congen_distribution.f90:290
congen_data::next
integer next
Position in the workspace indicating the first unused element.
Definition: congen_data.f90:147
congen_distribution::print3
subroutine, private print3(iidis1, i13)
?
Definition: congen_distribution.f90:1474
congen_distribution::cgcoef
subroutine, private cgcoef(j1, j2, j3, m3, n, ms, c, intpfg)
Clebsch-Gordan coefficients.
Definition: congen_distribution.f90:198
congen_data::nobt
integer nobt
Total number of all orbitals considered in the calculation, essentially equal to sum(nob).
Definition: congen_data.f90:110
congen_data::sshlst
integer, dimension(lg) sshlst
Definition: congen_data.f90:97
congen_data::qntot
integer, dimension(3) qntot
Total quantum numbers.
Definition: congen_data.f90:102
congen_data::nftw
integer nftw
Unit number for printing; may be changed via the STATE namelist so not a parameter.
Definition: congen_data.f90:57
congen_data::nitem
integer, parameter nitem
Number of interesting things printed per line in the PRINT* routines.
Definition: congen_data.f90:55
congen_data::iqnstr
integer iqnstr
Starting position in workspace for per-shell quantum numbers (e.g. congen_distribution::cplem).
Definition: congen_data.f90:79
congen_pagecontrol::space
subroutine, public space(lines)
Add blank lines to output.
Definition: congen_pagecontrol.f90:144
congen_distribution::wfcple
subroutine wfcple(nam, iqn, isz, icup, iqns, c, last, lc2, intpfg)
?
Definition: congen_distribution.f90:1668
congen_distribution::state
subroutine, private state(ns, x, last, nd, confpf)
?
Definition: congen_distribution.f90:1603
congen_pagecontrol::taddl1
subroutine, public taddl1(lines, lt)
Check available lines.
Definition: congen_pagecontrol.f90:193
congen_data::mclim
integer, dimension(2, lg) mclim
Definition: congen_data.f90:99
congen_data::ncall
integer ncall
Used to signal to "wfn" to initialize some variables.
Definition: congen_data.f90:129
congen_distribution::print4
subroutine, private print4(nd, x, ix)
?
Definition: congen_distribution.f90:1508
congen_data::qnshlr
integer, dimension(lg) qnshlr
Total quantum numbers for all shells in the set of orbitals being processed.
Definition: congen_data.f90:95
congen_data::irfcon
integer irfcon
Definition: congen_data.f90:80
congen_data::gushl
integer, dimension(lg) gushl
Gerade/ungerade per shell.
Definition: congen_data.f90:92
congen_data::spnmin
integer, dimension(lg) spnmin
Definition: congen_data.f90:96
congen_data::exdet
integer, dimension(:), allocatable exdet
Definition: congen_data.f90:135
congen_distribution::print2
subroutine, private print2(iidis1)
?
Definition: congen_distribution.f90:1409
congen_distribution::cplea
subroutine, private cplea(nncsf, nadel, x, nftw)
Loop through (and fill) all allowed couplings for a given electron distribution into shells.
Definition: congen_distribution.f90:575
congen_distribution::assign
subroutine, private assign(nshl, ndist, nused, refcon, excon, qnstor, nx, nftw)
Assign quantum numbers to real shells.
Definition: congen_distribution.f90:54
congen_data::lndi
integer lndi
Total number of integers forming packed determinants.
Definition: congen_data.f90:143
congen_data::shlmx1
integer, dimension(nu) shlmx1
Maximal occupancy of orbitals per symmetry.
Definition: congen_data.f90:103
congen_data::ndel
integer ndel
Workspace position used for the CSFs read from input.
Definition: congen_data.f90:81
congen_data::ne
integer ne
Definition: congen_data.f90:122
congen_data::ntyp
integer ntyp
Prototype number, updated in congen_distribution::distrb.
Definition: congen_data.f90:124
congen_data::ift
integer ift
Used to signal to congen_distribution::assign to initialize some variables.
Definition: congen_data.f90:109
congen_data::star
character(len=1), parameter star
Definition: congen_data.f90:67
congen_data::ntso
integer ntso
Total number of spin-orbitals, given the orbitals and their maximal occupacy (from group properties).
Definition: congen_data.f90:133
congen_data::iidis2
integer iidis2
Definition: congen_data.f90:141
congen_data::nnlecg
integer nnlecg
The total number of electrons which are movable within the current wfn group.
Definition: congen_data.f90:87
congen_data
Module containing parameters / data required throughout the CONGEN program.
Definition: congen_data.f90:32
congen_data::iexcon
integer iexcon
Position in workspace where EX constraints start.
Definition: congen_data.f90:76
congen_data::gutot
integer gutot
Total gerade (= +1) / ungerade (= -1) quantum number.
Definition: congen_data.f90:84
congen_data::nobi
integer, dimension(nu) nobi
Running index of the first orbital in each symmetry.
Definition: congen_data.f90:114
congen_pagecontrol::newpg
subroutine, public newpg
Start new page of output.
Definition: congen_pagecontrol.f90:121
congen_data::pqnst
integer, dimension(3, lg) pqnst
Definition: congen_data.f90:91
congen_distribution::wfn
subroutine, private wfn(nncsf, nadel, iidist, iidis3, nodi, ndi, cdi, ndel, pqnshl, x, ix, nx)
TODO...
Definition: congen_distribution.f90:1815
congen_data::exref
integer, dimension(:), allocatable exref
Population of spin-orbitals (0 = not populated, 1 = populated).
Definition: congen_data.f90:136
congen_distribution::distrb
subroutine, public distrb(nelecp, nshlp, shlmx, occshl, nslsv, kdssv, loopf, ksss, pqn, occst, shlmx1, pqnst, mshl, mshlst, gushl, gushst, cup, cupst, ndprod, symtyp, confpf, sshl, sshlst, ncsf, nncsf, nadel, nndel, x, nftw)
Distribute electrons to spin-orbitals.
Definition: congen_distribution.f90:996
congen_data::lp
character(len=3), parameter lp
Definition: congen_data.f90:66
congen_data::lcdi
integer lcdi
Total number of determinants (including those already flushed to disk).
Definition: congen_data.f90:142
congen_data::norep
integer, dimension(lg) norep
Definition: congen_data.f90:138
congen_data::thresh1
real(kind=wp), parameter thresh1
Threshold used in congen_distribution::cgcoef.
Definition: congen_data.f90:52
congen_data::binom
real(kind=wp), dimension((jsmax *jsmax+3 *jsmax+4)/2) binom
Table of precomputed Pascal triangle.
Definition: congen_data.f90:106
congen_distribution
Distribute electrons to available orbitals.
Definition: congen_distribution.f90:23
congen_data::test
integer, dimension(jz) test
Determines which of the two types of constraints will be used.
Definition: congen_data.f90:117
congen_data::qnshl
integer, dimension(3, 2 *lg) qnshl
Definition: congen_data.f90:100
congen_data::nst
integer, dimension(nu, lg) nst
Pointer to shell index and order count; only used in congen_distribution::assign.
Definition: congen_data.f90:118
congen_data::nx
integer nx
Full or remaining workspace size (depending on context).
Definition: congen_data.f90:148
congen_distribution::print1
subroutine, private print1(qnstor)
?
Definition: congen_distribution.f90:1300
congen_data::nodimx
integer nodimx
Maximal number of workspace elements usable for CSF information.
Definition: congen_data.f90:132
congen_pagecontrol::addl
subroutine, public addl(lines)
Add blank lines to output.
Definition: congen_pagecontrol.f90:50
congen_data::ndimx
integer ndimx
Maximal number of workspace elements usable for packed determinant data.
Definition: congen_data.f90:130
congen_distribution::packdet
subroutine, private packdet(iqn, ni, jqn, nj, ci, cj, nt)
Copy determinant data.
Definition: congen_distribution.f90:1281
congen_data::cdimx
integer cdimx
Maximal number of determinants.
Definition: congen_data.f90:125
congen_data::nrcon
integer, dimension(jz) nrcon
Definition: congen_data.f90:116
congen_data::nndel
integer nndel
Number of workspace elements used for reservation of space needed when reading CSFs from input.
Definition: congen_data.f90:86
congen_data::nsoi
integer, dimension(nu) nsoi
Running index of the first spin-orbital within given total symmetry.
Definition: congen_data.f90:139