1 | !WRF:DRIVER_LAYER:DECOMPOSITION |
---|
2 | ! |
---|
3 | |
---|
4 | MODULE module_machine |
---|
5 | |
---|
6 | USE module_driver_constants |
---|
7 | |
---|
8 | ! Machine characteristics and utilities here. |
---|
9 | |
---|
10 | ! Tile strategy defined constants |
---|
11 | INTEGER, PARAMETER :: TILE_X = 1, TILE_Y = 2, TILE_XY = 3 |
---|
12 | |
---|
13 | TYPE machine_type |
---|
14 | INTEGER :: tile_strategy |
---|
15 | END TYPE machine_type |
---|
16 | |
---|
17 | TYPE (machine_type) machine_info |
---|
18 | |
---|
19 | CONTAINS |
---|
20 | |
---|
21 | RECURSIVE SUBROUTINE rlocproc(p,maxi,nproc,ml,mr,ret) |
---|
22 | IMPLICIT NONE |
---|
23 | INTEGER, INTENT(IN) :: p, maxi, nproc, ml, mr |
---|
24 | INTEGER, INTENT(OUT) :: ret |
---|
25 | INTEGER :: width, rem, ret2, bl, br, mid, adjust, & |
---|
26 | p_r, maxi_r, nproc_r, zero |
---|
27 | adjust = 0 |
---|
28 | rem = mod( maxi, nproc ) |
---|
29 | width = maxi / nproc |
---|
30 | mid = maxi / 2 |
---|
31 | IF ( rem>0 .AND. (((mod(rem,2).EQ.0).OR.(rem.GT.2)).OR.(p.LE.mid))) THEN |
---|
32 | width = width + 1 |
---|
33 | END IF |
---|
34 | IF ( p.LE.mid .AND. mod(rem,2).NE.0 ) THEN |
---|
35 | adjust = adjust + 1 |
---|
36 | END IF |
---|
37 | bl = max(width,ml) ; |
---|
38 | br = max(width,mr) ; |
---|
39 | IF (p<bl) THEN |
---|
40 | ret = 0 |
---|
41 | ELSE IF (p>maxi-br-1) THEN |
---|
42 | ret = nproc-1 |
---|
43 | ELSE |
---|
44 | p_r = p - bl |
---|
45 | maxi_r = maxi-bl-br+adjust |
---|
46 | nproc_r = max(nproc-2,1) |
---|
47 | zero = 0 |
---|
48 | CALL rlocproc( p_r, maxi_r, nproc_r, zero, zero, ret2 ) ! Recursive |
---|
49 | ret = ret2 + 1 |
---|
50 | END IF |
---|
51 | RETURN |
---|
52 | END SUBROUTINE rlocproc |
---|
53 | |
---|
54 | INTEGER FUNCTION locproc( i, m, numpart ) |
---|
55 | implicit none |
---|
56 | integer, intent(in) :: i, m, numpart |
---|
57 | integer :: retval, ii, im, inumpart, zero |
---|
58 | ii = i |
---|
59 | im = m |
---|
60 | inumpart = numpart |
---|
61 | zero = 0 |
---|
62 | CALL rlocproc( ii, im, inumpart, zero, zero, retval ) |
---|
63 | locproc = retval |
---|
64 | RETURN |
---|
65 | END FUNCTION locproc |
---|
66 | |
---|
67 | SUBROUTINE patchmap( res, y, x, py, px ) |
---|
68 | implicit none |
---|
69 | INTEGER, INTENT(IN) :: y, x, py, px |
---|
70 | INTEGER, DIMENSION(x,y), INTENT(OUT) :: res |
---|
71 | INTEGER :: i, j, p_min, p_maj |
---|
72 | DO j = 0,y-1 |
---|
73 | p_maj = locproc( j, y, py ) |
---|
74 | DO i = 0,x-1 |
---|
75 | p_min = locproc( i, x, px ) |
---|
76 | res(i+1,j+1) = p_min + px*p_maj |
---|
77 | END DO |
---|
78 | END DO |
---|
79 | RETURN |
---|
80 | END SUBROUTINE patchmap |
---|
81 | |
---|
82 | SUBROUTINE region_bounds( region_start, region_end, & |
---|
83 | num_p, p, & |
---|
84 | patch_start, patch_end ) |
---|
85 | ! 1-D decomposition routine: Given starting and ending indices of a |
---|
86 | ! vector, the number of patches dividing the vector, and the number of |
---|
87 | ! the patch, give the start and ending indices of the patch within the |
---|
88 | ! vector. This will work with tiles too. Implementation note. This is |
---|
89 | ! implemented somewhat inefficiently, now, with a loop, so we can use the |
---|
90 | ! locproc function above, which returns processor number for a given |
---|
91 | ! index, whereas what we want is index for a given processor number. |
---|
92 | ! With a little thought and a lot of debugging, we can come up with a |
---|
93 | ! direct expression for what we want. For time being, we loop... |
---|
94 | ! Remember that processor numbering starts with zero. |
---|
95 | |
---|
96 | IMPLICIT NONE |
---|
97 | INTEGER, INTENT(IN) :: region_start, region_end, num_p, p |
---|
98 | INTEGER, INTENT(OUT) :: patch_start, patch_end |
---|
99 | INTEGER :: offset, i |
---|
100 | patch_end = -999999999 |
---|
101 | patch_start = 999999999 |
---|
102 | offset = region_start |
---|
103 | do i = 0, region_end - offset |
---|
104 | if ( locproc( i, region_end-region_start+1, num_p ) == p ) then |
---|
105 | patch_end = max(patch_end,i) |
---|
106 | patch_start = min(patch_start,i) |
---|
107 | endif |
---|
108 | enddo |
---|
109 | patch_start = patch_start + offset |
---|
110 | patch_end = patch_end + offset |
---|
111 | RETURN |
---|
112 | END SUBROUTINE region_bounds |
---|
113 | |
---|
114 | SUBROUTINE least_aspect( nparts, minparts_y, minparts_x, nparts_y, nparts_x ) |
---|
115 | IMPLICIT NONE |
---|
116 | ! Input data. |
---|
117 | INTEGER, INTENT(IN) :: nparts, & |
---|
118 | minparts_y, minparts_x |
---|
119 | ! Output data. |
---|
120 | INTEGER, INTENT(OUT) :: nparts_y, nparts_x |
---|
121 | ! Local data. |
---|
122 | INTEGER :: x, y, mini |
---|
123 | mini = 2*nparts |
---|
124 | nparts_y = 1 |
---|
125 | nparts_x = nparts |
---|
126 | DO y = 1, nparts |
---|
127 | IF ( mod( nparts, y ) .eq. 0 ) THEN |
---|
128 | x = nparts / y |
---|
129 | IF ( abs( y-x ) .LT. mini & |
---|
130 | .AND. y .GE. minparts_y & |
---|
131 | .AND. x .GE. minparts_x ) THEN |
---|
132 | mini = abs( y-x ) |
---|
133 | nparts_y = y |
---|
134 | nparts_x = x |
---|
135 | END IF |
---|
136 | END IF |
---|
137 | END DO |
---|
138 | END SUBROUTINE least_aspect |
---|
139 | |
---|
140 | SUBROUTINE init_module_machine |
---|
141 | machine_info%tile_strategy = TILE_Y |
---|
142 | END SUBROUTINE init_module_machine |
---|
143 | |
---|
144 | END MODULE module_machine |
---|
145 | |
---|
146 | SUBROUTINE wrf_sizeof_integer( retval ) |
---|
147 | IMPLICIT NONE |
---|
148 | INTEGER retval |
---|
149 | ! IWORDSIZE is defined by CPP |
---|
150 | retval = IWORDSIZE |
---|
151 | RETURN |
---|
152 | END SUBROUTINE wrf_sizeof_integer |
---|
153 | |
---|
154 | SUBROUTINE wrf_sizeof_real( retval ) |
---|
155 | IMPLICIT NONE |
---|
156 | INTEGER retval |
---|
157 | ! RWORDSIZE is defined by CPP |
---|
158 | retval = RWORDSIZE |
---|
159 | RETURN |
---|
160 | END SUBROUTINE wrf_sizeof_real |
---|
161 | |
---|
162 | SUBROUTINE wrf_sizeof_doubleprecision( retval ) |
---|
163 | IMPLICIT NONE |
---|
164 | INTEGER retval |
---|
165 | ! DWORDSIZE is defined by CPP |
---|
166 | retval = DWORDSIZE |
---|
167 | RETURN |
---|
168 | END SUBROUTINE wrf_sizeof_doubleprecision |
---|
169 | |
---|
170 | SUBROUTINE wrf_sizeof_logical( retval ) |
---|
171 | IMPLICIT NONE |
---|
172 | INTEGER retval |
---|
173 | ! LWORDSIZE is defined by CPP |
---|
174 | retval = LWORDSIZE |
---|
175 | RETURN |
---|
176 | END SUBROUTINE wrf_sizeof_logical |
---|
177 | |
---|