00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011 subroutine psmile_control_cell_gauss2_dble (grid_id, &
00012 ic, nc, list, j, k, &
00013 coords1, coords2, shape, &
00014 corners1, corners2, corner_shape, nbr_corners, &
00015 tol, fnd, ierror)
00016
00017
00018
00019 use PRISM_constants
00020
00021 use PSMILe, dummy_interface => PSMILe_Control_cell_gauss2_dble
00022 #ifdef DEBUG_TRACE
00023 use psmile_debug_trace
00024 #endif
00025
00026 Implicit none
00027
00028
00029
00030 Integer, Intent (In) :: grid_id
00031
00032
00033
00034 Integer, Intent (In) :: nc
00035
00036
00037
00038 Integer, Intent (In) :: ic (nc)
00039
00040
00041
00042
00043 Integer, Intent (In) :: list (nc)
00044
00045
00046
00047 Integer, Intent (In) :: j
00048
00049
00050
00051 Integer, Intent (In) :: k
00052
00053
00054
00055
00056 Integer, Intent (In) :: shape (2, ndim_3d)
00057
00058
00059
00060
00061 Double Precision, Intent (In) ::
00062 coords1 (shape(1,1):shape(2,1), shape(1,2):shape(2,2),
00063 shape(1,3):shape(2,3))
00064
00065 Double Precision, Intent (In) ::
00066 coords2 (shape(1,1):shape(2,1), shape(1,2):shape(2,2),
00067 shape(1,3):shape(2,3))
00068
00069
00070
00071 Integer, Intent (In) :: corner_shape (2, ndim_2d)
00072
00073
00074
00075 Integer, Intent (In) :: nbr_corners
00076
00077
00078
00079
00080 Double Precision, Intent (In) ::
00081 corners1 ( corner_shape(1,1):corner_shape(2,1), nbr_corners)
00082
00083
00084
00085 Double Precision, Intent (In) ::
00086 corners2 ( corner_shape(1,1):corner_shape(2,1), nbr_corners)
00087
00088
00089
00090 Double Precision, Intent (In) :: tol
00091
00092
00093
00094
00095
00096
00097 Logical, Intent (Out) :: fnd (nc)
00098
00099
00100
00101 Integer, Intent (Out) :: ierror
00102
00103
00104
00105
00106
00107
00108
00109
00110
00111
00112
00113 Integer, Parameter :: ntet = 3
00114
00115 Double Precision, Parameter :: eps = 1.0d-9
00116 Double Precision, Parameter :: rmxeps = 1.0d30
00117 Double Precision, Parameter :: dzero = 0.0
00118
00119
00120
00121
00122
00123 Double Precision :: tol1
00124
00125
00126
00127 Integer :: i, jj, m, n
00128
00129
00130
00131 Integer, Save :: ijkedg (2, ntet)
00132
00133
00134
00135 Double Precision :: xyzpnt (nc, ntet, ndim_2d),
00136 xyzref (nc, ntet+1, ndim_2d)
00137 Double Precision :: xyzedg (nc, ntet, ndim_2d, 2)
00138 Double Precision :: d1, d2
00139 Double Precision :: det (nc, ntet)
00140 Double Precision :: dnorm
00141
00142
00143
00144
00145
00146
00147
00148
00149
00150
00151
00152
00153
00154
00155
00156
00157
00158
00159
00160
00161
00162
00163
00164
00165 Character(len=len_cvs_string), save :: mycvs =
00166 '$Id: psmile_control_cell_gauss2_dble.F90 2927 2011-01-28 14:04:12Z hanke $'
00167
00168
00169
00170
00171
00172
00173
00174
00175
00176
00177
00178
00179 data ((ijkedg (jj, n), jj = 1, 2), n = 1, ntet) &
00180 / 2, 4, 3, 1, 4, 2/
00181
00182
00183
00184
00185
00186
00187
00188 #ifdef VERBOSE
00189 print 9990, trim(ch_id), nc
00190
00191 call psmile_flushstd
00192 #endif /* VERBOSE */
00193
00194 #ifdef PRISM_ASSERTION
00195 if (tol < 0.0) then
00196 call psmile_assert (__FILE__, __LINE__, &
00197 "tol must be >= 0.0")
00198 endif
00199
00200
00201 do i = 1, nc
00202 if (ic(i) < corner_shape(1,1) .or. ic(i) > corner_shape(2,1) ) then
00203 exit
00204 endif
00205 end do
00206
00207 if (i <= nc) then
00208 print *, 'i, ic', i, ic(i)
00209 print *, 'corner_shape', corner_shape
00210 call psmile_assert (__FILE__, __LINE__, &
00211 'wrong index')
00212 endif
00213 #endif
00214
00215 ierror = 0
00216
00217
00218
00219
00220 xyzref (:, 1, 1) = corners1 (ic(:), 1)
00221 xyzref (:, 1, 2) = corners2 (ic(:), 1)
00222
00223 xyzref (:, 2, 1) = corners1 (ic(:), 2)
00224 xyzref (:, 2, 2) = xyzref (:, 1, 2)
00225
00226 xyzref (:, 3, 1) = xyzref (:, 2, 1)
00227 xyzref (:, 3, 2) = corners2 (ic(:), 2)
00228
00229 xyzref (:, 4, 1) = xyzref (:, 1, 1)
00230 xyzref (:, 4, 2) = xyzref (:, 3, 2)
00231
00232 #ifdef DEBUG_TRACE
00233 do i = 1, nc
00234 if ( list(i) == ictl_ind(1) .and. j == ictl_ind(2) ) then
00235 print *, 'Search coords ', &
00236 coords1(list(i),j,shape(1,3)), coords2(list(i),j,shape(1,3))
00237 print *, 'Corners: '
00238 print *, ' C1 : ', xyzref (i, 1, 1), xyzref (i, 1, 2)
00239 print *, ' C2 : ', xyzref (i, 2, 1), xyzref (i, 2, 2)
00240 print *, ' C3 : ', xyzref (i, 3, 1), xyzref (i, 3, 2)
00241 print *, ' C4 : ', xyzref (i, 4, 1), xyzref (i, 4, 2)
00242 endif
00243 enddo
00244 #endif
00245 do n = 1, ntet
00246 xyzpnt (:, n, 1) = coords1 (list(:), j, k) - xyzref (:, n, 1)
00247 xyzpnt (:, n, 2) = coords2 (list(:), j, k) - xyzref (:, n, 2)
00248
00249 do m = 1, 2
00250
00251 do i = 1, nc
00252 xyzedg (i, n, 1, m) = xyzref (i, ijkedg(m, n), 1) &
00253 - xyzref (i, n, 1)
00254
00255 xyzedg (i, n, 2, m) = xyzref (i, ijkedg(m, n), 2) &
00256 - xyzref (i, n, 2)
00257 end do
00258 end do
00259 end do
00260
00261
00262
00263
00264
00265 det(:, :) = xyzedg(:, :, 1,1)*xyzedg(:, :, 2,2) &
00266 - xyzedg(:, :, 1,2)*xyzedg(:, :, 2,1)
00267
00268 #define ALLOW_DEGRADED_CELL
00269 #ifdef ALLOW_DEGRADED_CELL
00270
00271
00272
00273 do n = 1, ntet
00274
00275 do i = 1, nc
00276 dnorm = abs(xyzedg(i, n,1,1)) + abs(xyzedg(i, n,2,1)) + &
00277 abs(xyzedg(i, n,1,2)) + abs(xyzedg(i, n,2,2))
00278
00279 if (abs(det(i, n)) < eps*dnorm*dnorm .or. dnorm == dzero) then
00280 det (i, n) = sign (rmxeps, det(i, n))
00281 else
00282 det (i, n) = 1.0d0 / det (i, n)
00283 endif
00284 end do
00285 end do
00286
00287 #else
00288
00289 loop_n: do n = 1, ntet
00290
00291 do i = 1, nc
00292 dnorm = abs(xyzedg(i, n,1,1)) + abs(xyzedg(i, n,2,1)) + &
00293 abs(xyzedg(i, n,1,2)) + abs(xyzedg(i, n,2,2))
00294
00295 if (abs(det(i, n)) < eps*dnorm*dnorm .or. &
00296 dnorm(i,n) == dzero) then
00297 det (i, n) = dnorm * 1e-25
00298
00299
00300
00301 endif
00302 end do
00303 end do
00304
00305 #ifdef PRINT_DEGRADED_CELL
00306 if (n < ntet) then
00307
00308
00309
00310 print 9960, trim(ch_id), grid_id, ic (i), &
00311 (xyzref (i, n, 1), xyzref (i, n, 2), n = 1, 4)
00312
00313 do n = 1, ntet
00314 if (abs(det(i, n)) < eps) then
00315 print 9950, n, det (i, n), dnorm, &
00316 xyzedg (i, n,1, 1), xyzedg (i, n,1, 2), &
00317 xyzedg (i, n,2, 1), xyzedg (i, n,2, 2)
00318 endif
00319 end do
00320
00321 nicht gefunden fnd (i) = .false. versucht, durch
00322 ganz kleine Determinante zu loesen
00323 endif
00324 #endif /* PRINT_DEGRADED_CELL */
00325
00326 det (:, :) = 1.0d0 / det (:, :)
00327
00328 #endif /* ALLOW_DEGRADED_CELL */
00329
00330
00331
00332
00333 tol1 = tol + 1.0
00334 fnd (:) = .false.
00335
00336 do n = 1, ntet
00337
00338 do i = 1, nc
00339
00340 d1 = (xyzpnt(i, n,1)*xyzedg(i, n,2,2)- &
00341 xyzpnt(i, n,2)*xyzedg(i, n,1,2)) * det (i, n)
00342 d2 = (xyzpnt(i, n,2)*xyzedg(i, n,1,1)- &
00343 xyzpnt(i, n,1)*xyzedg(i, n,2,1)) * det (i, n)
00344
00345 fnd (i) = fnd (i) .or. &
00346 (min(d1, d2) >= -tol .and. &
00347 max(d1,dzero) + max(d2,dzero) <= tol1)
00348 end do
00349 end do
00350
00351
00352
00353 #ifdef VERBOSE
00354 print 9980, trim(ch_id), count(fnd(:))
00355
00356 call psmile_flushstd
00357 #endif /* VERBOSE */
00358
00359
00360
00361
00362 9990 format (1x, a, ': psmile_control_cell_gauss2_dble: nc', i5)
00363 9980 format (1x, a, ': psmile_control_cell_gauss2_dble: eof, suc', i5)
00364
00365 #ifdef PRINT_DEGRADED_CELL
00366 9960 format (1x, a, ': psmile_control_cell_gauss2_dble: grid id =', i5, &
00367 /1x, ' Grid cell (', i4,
00368 ') is degraded! Cell coordinates are:', 1p, &
00369 4 (/1x, '(', 1 (e17.9, ','), e17.9, ')'))
00370 9950 format (1x, i1, '-th spawn; det =', 1p, e17.9, ' (', e17.9, &
00371 ') of', 2 (/1x, 2e17.9, ','))
00372 #endif
00373
00374 end subroutine psmile_control_cell_gauss2_dble