source: utilities.f@ cb47b9c

Last change on this file since cb47b9c was cb47b9c, checked in by baerbaer <baerbaer@…>, 14 years ago

Explicitly declare variables.

All variables should be declared so that we can remove the implicit statements
from the beginning of the INCL.H file.

git-svn-id: svn+ssh://svn.berlios.de/svnroot/repos/smmp/trunk@25 26dc1dd8-5c4e-0410-9ffe-d298b4865968

  • Property mode set to 100644
File size: 6.6 KB
Line 
1! *********************************************************************
2! This file contains distributeWorkLoad, fileNameMP
3!
4! Copyright 2007 Frank Eisenmenger, U.H.E. Hansmann,
5! Jan H. Meinke, Sandipan Mohanty
6!
7! *********************************************************************
8
9!! Calculate the best way to distribute the work load across processors.
10! It calculates the average number of interactions and then tries to
11! assign a number of interactions to each processor that is as close
12! as possible to the average. The routine should be called once for
13! every molecule in the system.
14!
15! @param num_ppr Number of processors per replica
16! @param nml index of molecule or zero.
17!
18! @author Jan H. Meinke
19 subroutine distributeWorkLoad(num_ppr,nml)
20
21 include 'INCL.H'
22
23 integer num_ppr, nml
24 integer idxOfFirstVariable, idxOfLastVariable
25 integer at, atct, ivw, i, j, isum, i14
26 integer totalct, irank, itarget
27 double precision ipps
28
29 if (nml.eq.0) then
30 idxOfFirstVariable = ivrml1(1)
31 idxOfLastVariable = ivrml1(ntlml) + nvrml(ntlml) -1
32 i1ms = imsml1(ntlml)+ nmsml(ntlml)
33 do i = 0, MAX_PROC
34 do j = 1, mxml
35 workPerProcessor(j, i) = 0
36 end do
37 end do
38 else
39 idxOfFirstVariable = ivrml1(nml)
40 idxOfLastVariable = ivrml1(nml) + nvrml(nml) - 1
41 i1ms = imsml1(nml)+ nmsml(nml)
42 do i = 0, MAX_PROC
43 workPerProcessor(nml, i) = 0
44 end do
45 end if
46
47 isum = 0
48 do io = idxOfLastVariable, idxOfFirstVariable, - 1
49 iv = iorvr(io)
50 i2ms = i1ms - 1
51 i1ms = imsvr1(iv)
52 do ms = i1ms, i2ms
53 do at = latms1(ms), latms2(ms)
54 do ivw=ivwat1(at),ivwat2(at)
55 do j=lvwat1(ivw),lvwat2(ivw)
56 isum = isum + 1
57 end do
58 end do
59 do i14=i14at1(at),i14at2(at)
60 isum = isum + 1
61 end do
62 end do
63 end do
64 end do
65 ipps = isum / num_ppr
66 write (*,*) "Total number of interactions:", isum
67 write (*,*) "Average # of interactions per processor", ipps
68
69 totalct = 0
70 irank = 1
71 itarget = int(irank * ipps)
72 if (nml.eq.0) then
73 i1ms = imsml1(ntlml)+ nmsml(ntlml)
74 else
75 i1ms = imsml1(nml)+ nmsml(nml)
76 end if
77 do io = idxOfLastVariable, idxOfFirstVariable, - 1
78 isum = 0
79 iv = iorvr(io)
80 i2ms = i1ms - 1
81 i1ms = imsvr1(iv)
82 do ms = i1ms, i2ms
83 do at = latms1(ms), latms2(ms)
84 atct = atct + 1
85 do ivw=ivwat1(at),ivwat2(at)
86 do j=lvwat1(ivw),lvwat2(ivw)
87 isum = isum + 1
88 end do
89 end do
90 do i14=i14at1(at),i14at2(at)
91 isum = isum + 1
92 end do
93 end do
94 end do
95 if ((totalct + isum).gt.itarget) then
96 if((.not.irank.eq.num_ppr)
97 & .and.
98 & (abs(totalct-itarget)
99 & .lt.abs(totalct + isum - itarget))) then
100 workPerProcessor(nml, irank) = io + 1
101! write (*,*) io + 1, totalct, itarget
102 else
103 workPerProcessor(nml, irank) = io
104! write (*,*) io, totalct + isum, itarget
105 end if
106 irank = irank + 1
107 itarget = int(irank * ipps)
108 end if
109 totalct = totalct + isum
110 end do
111 workPerProcessor(nml, 0) = idxOfLastVariable + 1
112 workPerProcessor(nml, num_ppr) = ivrml1(nml)
113
114 end subroutine distributeWorkLoad
115
116!-----------------------------------------------------------------------
117! The function fileNameMP takes a template of a file name in the
118! variable base. The position of the first and last character that
119! may be replaced by rank in the string are given in i1 (first) and
120! i2 (last).
121! The function returns an empty string if the rank would need more
122! characters than is allowed by the template.
123! For example,
124! \code
125! rank = 11
126! fileName = fileNameMP('base_0000.dat', 6, 9, rank)
127! write (*,*), fileName
128! \endcode
129! will output base_0011.dat.
130!
131! @param base the base file name, e.g., base_0000.dat.
132! @param i1 index of the first character that may be replaced
133! @param i2 index of the last character that may be replaced
134! @param rank the number that should be inserted into the file name.
135!
136! @return file name for rank
137!-----------------------------------------------------------------------
138 character*80 function fileNameMP(base, i1, i2, rank)
139
140 character*(*) base
141! i1, i2: Index of first and last character that can be replaced
142! rank: rank of node
143 integer i1, i2, rank
144
145 fileNameMP = base
146 if ((i2 - i1 + 1).le.log10(1.0 * rank)) then
147 print *,'too few characters available to label '
148 print *,'filenames with rank = ',rank
149 stop
150 endif
151
152! TODO: Allow arbitrary rank
153
154 if (rank.lt.10) then
155 write(fileNameMP(i2:i2), '(i1)') rank
156 elseif (rank.lt.100) then
157 write(fileNameMP(i2-1:i2), '(i2)') rank
158 elseif (rank.lt.1000) then
159 write(fileNameMP(i2-2:i2), '(i3)') rank
160 elseif (rank.lt.10000) then
161 write(fileNameMP(i2-3:i2), '(i4)') rank
162 elseif (rank.lt.100000) then
163 write(fileNameMP(i2-4:i2), '(i5)') rank
164 elseif (rank.lt.1000000) then
165 write(fileNameMP(i2-5:i2), '(i6)') rank
166 endif
167 end function fileNameMP
168! End fileNameMP
169
170
171!----------------------------------------------------------------------
172! Add messages to log. This routine takes the log (debugging) mes-
173! sages and writes them to the log file if the log level is less or
174! equal to the maximum log level given by the global variable
175! MAXLOGLEVEL.
176!
177! @author Jan H. Meinke
178!
179! @param loglevel level at which this message should be added to
180! the log.
181! @param message message to be written to the log.
182! @param rank global rank of this node if running an MPI job zero
183! otherwise.
184!----------------------------------------------------------------------
185 subroutine addLogMessage(loglevel, message, rank)
186
187 integer :: loglevel, rank
188 character(LEN=*) :: message
189
190 if (loglevel <= MAXLOGLEVEL) then
191 write(LOGFILEUNIT, *) message
192 end if
193
194 end subroutine addLogMessage
Note: See TracBrowser for help on using the repository browser.