Changeset 159 for codes/icosagcm/trunk/src/timeloop_gcm.f90
- Timestamp:
- 06/25/13 09:32:16 (11 years ago)
- File:
-
- 1 edited
Legend:
- Unmodified
- Added
- Removed
-
codes/icosagcm/trunk/src/timeloop_gcm.f90
r158 r159 11 11 TYPE(t_message) :: req_ps0, req_theta_rhodz0, req_u0, req_q0 12 12 13 TYPE(t_field),POINTER :: f_phis(:)14 13 TYPE(t_field),POINTER :: f_q(:) 15 TYPE(t_field),POINTER :: f_dtheta(:), f_rhodz(:) 16 TYPE(t_field),POINTER :: f_ps(:),f_psm1(:), f_psm2(:) 17 TYPE(t_field),POINTER :: f_u(:),f_um1(:),f_um2(:) 18 TYPE(t_field),POINTER :: f_theta_rhodz(:),f_theta_rhodzm1(:),f_theta_rhodzm2(:) 19 TYPE(t_field),POINTER :: f_dps(:),f_dpsm1(:), f_dpsm2(:) 20 TYPE(t_field),POINTER :: f_du(:),f_dum1(:),f_dum2(:) 21 TYPE(t_field),POINTER :: f_dtheta_rhodz(:),f_dtheta_rhodzm1(:),f_dtheta_rhodzm2(:) 14 TYPE(t_field),POINTER :: f_rhodz(:), f_mass(:), f_massm1(:), f_massm2(:), f_dmass(:) 15 TYPE(t_field),POINTER :: f_phis(:), f_ps(:),f_psm1(:), f_psm2(:), f_dps(:) 16 TYPE(t_field),POINTER :: f_u(:),f_um1(:),f_um2(:), f_du(:) 17 TYPE(t_field),POINTER :: f_theta_rhodz(:),f_theta_rhodzm1(:),f_theta_rhodzm2(:), f_dtheta_rhodz(:) 22 18 TYPE(t_field),POINTER :: f_hflux(:), f_wflux(:), f_hfluxt(:), f_wfluxt(:) 23 19 … … 34 30 USE caldyn_mod 35 31 USE etat0_mod 32 USE disvert_mod 36 33 USE guided_mod 37 34 USE advect_tracer_mod … … 45 42 IMPLICIT NONE 46 43 47 CHARACTER(len=255) :: scheme_name 48 49 CALL allocate_field(f_dps,field_t,type_real) 50 CALL allocate_field(f_du,field_u,type_real,llm) 51 CALL allocate_field(f_dtheta_rhodz,field_t,type_real,llm) 52 ! Model state at current time step (RK/MLF/Euler) 53 CALL allocate_field(f_phis,field_t,type_real) 54 CALL allocate_field(f_ps,field_t,type_real) 55 CALL allocate_field(f_u,field_u,type_real,llm) 56 CALL allocate_field(f_theta_rhodz,field_t,type_real,llm) 57 ! Model state at previous time step (RK/MLF) 58 CALL allocate_field(f_psm1,field_t,type_real) 59 CALL allocate_field(f_um1,field_u,type_real,llm) 60 CALL allocate_field(f_theta_rhodzm1,field_t,type_real,llm) 61 ! Tracers 62 CALL allocate_field(f_q,field_t,type_real,llm,nqtot) 63 CALL allocate_field(f_rhodz,field_t,type_real,llm) 64 ! Mass fluxes 65 CALL allocate_field(f_hflux,field_u,type_real,llm) ! instantaneous mass fluxes 66 CALL allocate_field(f_wflux,field_t,type_real,llm+1) ! computed by caldyn 67 CALL allocate_field(f_hfluxt,field_u,type_real,llm) ! mass "fluxes" accumulated in time 68 CALL allocate_field(f_wfluxt,field_t,type_real,llm+1) 69 44 CHARACTER(len=255) :: def 70 45 71 46 !---------------------------------------------------- … … 122 97 123 98 124 125 126 127 scheme_name='runge_kutta' 128 CALL getin('scheme',scheme_name) 129 130 SELECT CASE (TRIM(scheme_name)) 99 def='eta_mass' 100 CALL getin('caldyn_eta',def) 101 SELECT CASE(TRIM(def)) 102 CASE('eta_mass') 103 caldyn_eta=eta_mass 104 CASE('eta_lag') 105 caldyn_eta=eta_lag 106 CASE DEFAULT 107 IF (is_mpi_root) PRINT *,'Bad selector for variable caldyn_eta : <', TRIM(def),'> options are <eta_mass>, <eta_lag>' 108 STOP 109 END SELECT 110 IF (is_mpi_root) PRINT *, 'caldyn_eta=',TRIM(def), caldyn_eta, eta_lag, eta_mass 111 112 ! Time-independant orography 113 CALL allocate_field(f_phis,field_t,type_real,name='phis') 114 ! Trends 115 CALL allocate_field(f_du,field_u,type_real,llm,name='du') 116 CALL allocate_field(f_dtheta_rhodz,field_t,type_real,llm,name='dtheta_rhodz') 117 ! Model state at current time step (RK/MLF/Euler) 118 CALL allocate_field(f_ps,field_t,type_real, name='ps') 119 CALL allocate_field(f_mass,field_t,type_real,llm,name='mass') 120 CALL allocate_field(f_u,field_u,type_real,llm,name='u') 121 CALL allocate_field(f_theta_rhodz,field_t,type_real,llm,name='theta_rhodz') 122 ! Model state at previous time step (RK/MLF) 123 CALL allocate_field(f_um1,field_u,type_real,llm,name='um1') 124 CALL allocate_field(f_theta_rhodzm1,field_t,type_real,llm,name='theta_rhodzm1') 125 ! Tracers 126 CALL allocate_field(f_q,field_t,type_real,llm,nqtot) 127 CALL allocate_field(f_rhodz,field_t,type_real,llm,name='rhodz') 128 ! Mass fluxes 129 CALL allocate_field(f_hflux,field_u,type_real,llm) ! instantaneous mass fluxes 130 CALL allocate_field(f_hfluxt,field_u,type_real,llm) ! mass "fluxes" accumulated in time 131 CALL allocate_field(f_wflux,field_t,type_real,llm+1) ! vertical mass fluxes 132 133 IF(caldyn_eta == eta_mass) THEN ! eta = mass coordinate (default) 134 CALL allocate_field(f_dps,field_t,type_real,name='dps') 135 CALL allocate_field(f_psm1,field_t,type_real,name='psm1') 136 CALL allocate_field(f_wfluxt,field_t,type_real,llm+1,name='wfluxt') 137 ! the following are unused but must point to something 138 f_massm1 => f_mass 139 f_dmass => f_mass 140 ELSE ! eta = Lagrangian vertical coordinate 141 CALL allocate_field(f_mass,field_t,type_real,llm) 142 CALL allocate_field(f_massm1,field_t,type_real,llm) 143 CALL allocate_field(f_dmass,field_t,type_real,llm) 144 ! the following are unused but must point to something 145 f_wfluxt => f_wflux 146 f_dps => f_phis 147 f_psm1 => f_phis 148 END IF 149 150 151 def='runge_kutta' 152 CALL getin('scheme',def) 153 154 SELECT CASE (TRIM(def)) 131 155 CASE('euler') 132 156 scheme=euler … … 141 165 nb_stage=matsuno_period+1 142 166 ! Model state 2 time steps ago (MLF) 143 CALL allocate_field(f_psm2,field_t,type_real)144 167 CALL allocate_field(f_theta_rhodzm2,field_t,type_real,llm) 145 168 CALL allocate_field(f_um2,field_u,type_real,llm) 169 IF(caldyn_eta == eta_mass) THEN ! eta = mass coordinate (default) 170 CALL allocate_field(f_psm2,field_t,type_real) 171 ! the following are unused but must point to something 172 f_massm2 => f_mass 173 ELSE ! eta = Lagrangian vertical coordinate 174 CALL allocate_field(f_massm2,field_t,type_real,llm) 175 ! the following are unused but must point to something 176 f_psm2 => f_phis 177 END IF 178 146 179 CASE default 147 PRINT*,'Bad selector for variable scheme : <', TRIM( scheme_name), &180 PRINT*,'Bad selector for variable scheme : <', TRIM(def), & 148 181 ' > options are <euler>, <runge_kutta>, <leapfrog_matsuno>' 149 182 STOP … … 157 190 CALL init_check_conserve 158 191 CALL init_physics 159 CALL etat0(f_ps,f_ phis,f_theta_rhodz,f_u, f_q)192 CALL etat0(f_ps,f_mass,f_phis,f_theta_rhodz,f_u, f_q) 160 193 161 194 CALL transfert_request(f_phis,req_i0) … … 173 206 USE icosa 174 207 USE dissip_gcm_mod 208 USE disvert_mod 175 209 USE caldyn_mod 210 USE caldyn_gcm_mod, ONLY : req_ps 176 211 USE etat0_mod 177 212 USE guided_mod … … 184 219 USE check_conserve_mod 185 220 IMPLICIT NONE 186 REAL(rstd),POINTER :: phis(:)187 221 REAL(rstd),POINTER :: q(:,:,:) 188 REAL(rstd),POINTER :: ps(:) ,psm1(:), psm2(:) 189 REAL(rstd),POINTER :: u(:,:) , um1(:,:), um2(:,:) 190 REAL(rstd),POINTER :: rhodz(:,:), theta_rhodz(:,:) , theta_rhodzm1(:,:), theta_rhodzm2(:,:) 191 REAL(rstd),POINTER :: dps(:), dpsm1(:), dpsm2(:) 192 REAL(rstd),POINTER :: du(:,:), dum1(:,:), dum2(:,:) 193 REAL(rstd),POINTER :: dtheta_rhodz(:,:),dtheta_rhodzm1(:,:),dtheta_rhodzm2(:,:) 222 REAL(rstd),POINTER :: phis(:), ps(:) ,psm1(:), psm2(:), dps(:) 223 REAL(rstd),POINTER :: u(:,:) , um1(:,:), um2(:,:), du(:,:) 224 REAL(rstd),POINTER :: rhodz(:,:), mass(:,:), massm1(:,:), massm2(:,:), dmass(:,:) 225 REAL(rstd),POINTER :: theta_rhodz(:,:) , theta_rhodzm1(:,:), theta_rhodzm2(:,:), dtheta_rhodz(:,:) 194 226 REAL(rstd),POINTER :: hflux(:,:),wflux(:,:),hfluxt(:,:),wfluxt(:,:) 195 227 196 228 INTEGER :: ind 197 229 INTEGER :: it,i,j,n, stage 198 CHARACTER(len=255) :: scheme_name199 230 LOGICAL :: fluxt_zero(ndomain) ! set to .TRUE. to start accumulating fluxes in time 200 231 LOGICAL, PARAMETER :: check=.FALSE. 201 232 202 CALL caldyn_BC(f_phis, f_wflux) 233 CALL caldyn_BC(f_phis, f_wflux) ! set constant values in first/last interfaces 203 234 204 235 !$OMP BARRIER … … 234 265 DO stage=1,nb_stage 235 266 CALL caldyn((stage==1) .AND. (MOD(it,itau_out)==0), & 236 f_phis,f_ps,f_ theta_rhodz,f_u, f_q, &267 f_phis,f_ps,f_mass,f_theta_rhodz,f_u, f_q, & 237 268 f_hflux, f_wflux, f_dps, f_dtheta_rhodz, f_du) 238 269 SELECT CASE (scheme) … … 333 364 334 365 SUBROUTINE RK_scheme(stage) 335 USE caldyn_gcm_mod336 366 IMPLICIT NONE 337 367 INTEGER :: ind, stage … … 344 374 tau = dt*coef(stage) 345 375 346 DO ind=1,ndomain 347 CALL swap_dimensions(ind) 348 CALL swap_geometry(ind) 349 ps=f_ps(ind) 350 psm1=f_psm1(ind) 351 dps=f_dps(ind) 352 353 IF (stage==1) THEN ! first stage : save model state in XXm1 354 IF (omp_first) THEN 355 DO j=jj_begin,jj_end 356 DO i=ii_begin,ii_end 357 ij=(j-1)*iim+i 358 psm1(ij)=ps(ij) 376 ! if mass coordinate, deal with ps first on one core 377 IF(caldyn_eta==eta_mass) THEN 378 IF (omp_first) THEN 379 DO ind=1,ndomain 380 CALL swap_dimensions(ind) 381 CALL swap_geometry(ind) 382 ps=f_ps(ind) 383 psm1=f_psm1(ind) 384 dps=f_dps(ind) 385 386 IF (stage==1) THEN ! first stage : save model state in XXm1 387 DO j=jj_begin,jj_end 388 DO i=ii_begin,ii_end 389 ij=(j-1)*iim+i 390 psm1(ij)=ps(ij) 391 ENDDO 392 ENDDO 393 ENDIF 394 395 ! updates are of the form x1 := x0 + tau*f(x1) 396 DO j=jj_begin,jj_end 397 DO i=ii_begin,ii_end 398 ij=(j-1)*iim+i 399 ps(ij)=psm1(ij)+tau*dps(ij) 400 ENDDO 359 401 ENDDO 360 ENDDO 361 ENDIF 362 END IF 363 364 ! updates are of the form x1 := x0 + tau*f(x1) 365 IF (omp_first) THEN 366 DO j=jj_begin,jj_end 367 DO i=ii_begin,ii_end 368 ij=(j-1)*iim+i 369 ps(ij)=psm1(ij)+tau*dps(ij) 370 ENDDO 371 ENDDO 372 ENDIF 373 374 ENDDO 375 376 CALL send_message(f_ps,req_ps) 377 378 379 402 ENDDO 403 ENDIF 404 405 CALL send_message(f_ps,req_ps) 406 END IF 407 408 ! now deal with other prognostic variables 380 409 DO ind=1,ndomain 381 410 CALL swap_dimensions(ind) … … 386 415 387 416 IF (stage==1) THEN ! first stage : save model state in XXm1 388 389 DO l=ll_begin,ll_end417 418 DO l=ll_begin,ll_end 390 419 DO j=jj_begin,jj_end 391 420 DO i=ii_begin,ii_end … … 398 427 ENDDO 399 428 ENDDO 429 430 IF(caldyn_eta==eta_lag) THEN ! mass = additional prognostic variable 431 DO l=ll_begin,ll_end 432 DO j=jj_begin,jj_end 433 DO i=ii_begin,ii_end 434 ij=(j-1)*iim+i 435 massm1(ij,l)=mass(ij,l) 436 ENDDO 437 ENDDO 438 ENDDO 439 END IF 400 440 401 441 END IF … … 413 453 ENDDO 414 454 ENDDO 415 455 IF(caldyn_eta==eta_lag) THEN ! mass = additional prognostic variable 456 DO l=ll_begin,ll_end 457 DO j=jj_begin,jj_end 458 DO i=ii_begin,ii_end 459 ij=(j-1)*iim+i 460 mass(ij,l)=massm1(ij,l)+tau*dmass(ij,l) 461 ENDDO 462 ENDDO 463 ENDDO 464 END IF 465 416 466 IF(stage==nb_stage) THEN ! accumulate mass fluxes at last stage 417 467 hflux=f_hflux(ind); hfluxt=f_hfluxt(ind) … … 476 526 END SUBROUTINE timeloop 477 527 478 SUBROUTINE compute_rhodz(comp, ps, rhodz) 479 USE icosa 480 USE disvert_mod 481 USE omp_para 482 LOGICAL, INTENT(IN) :: comp ! .TRUE. to compute, .FALSE. to check 483 REAL(rstd), INTENT(IN) :: ps(iim*jjm) 484 REAL(rstd), INTENT(INOUT) :: rhodz(iim*jjm,llm) 485 REAL(rstd) :: m, err 486 INTEGER :: l,i,j,ij,dd 487 err=0. 488 489 dd=0 490 491 DO l = ll_begin, ll_end 492 DO j=jj_begin-dd,jj_end+dd 493 DO i=ii_begin-dd,ii_end+dd 494 ij=(j-1)*iim+i 495 m = ( ap(l) - ap(l+1) + (bp(l)-bp(l+1))*ps(ij) )/g 496 IF(comp) THEN 497 rhodz(ij,l) = m 498 ELSE 499 err = MAX(err,abs(m-rhodz(ij,l))) 500 END IF 501 ENDDO 502 ENDDO 503 ENDDO 504 505 IF(.NOT. comp) THEN 506 IF(err>1e-10) THEN 507 PRINT *, 'Discrepancy between ps and rhodz detected', err 508 STOP 509 ELSE 510 ! PRINT *, 'No discrepancy between ps and rhodz detected' 511 END IF 512 END IF 513 514 END SUBROUTINE compute_rhodz 515 516 SUBROUTINE accumulate_fluxes(hflux,wflux, hfluxt,wfluxt, tau,fluxt_zero) 528 SUBROUTINE accumulate_fluxes(hflux,wflux, hfluxt,wfluxt, tau,fluxt_zero) 517 529 USE icosa 518 530 USE omp_para 531 USE disvert_mod 532 IMPLICIT NONE 519 533 REAL(rstd), INTENT(IN) :: hflux(3*iim*jjm,llm), wflux(iim*jjm,llm+1) 520 534 REAL(rstd), INTENT(INOUT) :: hfluxt(3*iim*jjm,llm), wfluxt(iim*jjm,llm+1) … … 538 552 ENDDO 539 553 540 DO l=ll_begin,ll_endp1 541 DO j=jj_begin,jj_end 542 DO i=ii_begin,ii_end 543 ij=(j-1)*iim+i 544 wfluxt(ij,l) = tau*wflux(ij,l) 545 ENDDO 546 ENDDO 547 ENDDO 554 IF(caldyn_eta==eta_mass) THEN ! no need for vertical fluxes if eta_lag 555 DO l=ll_begin,ll_endp1 556 DO j=jj_begin,jj_end 557 DO i=ii_begin,ii_end 558 ij=(j-1)*iim+i 559 wfluxt(ij,l) = tau*wflux(ij,l) 560 ENDDO 561 ENDDO 562 ENDDO 563 END IF 548 564 ELSE 549 565 … … 559 575 ENDDO 560 576 561 DO l=ll_begin,ll_endp1 562 DO j=jj_begin,jj_end 563 DO i=ii_begin,ii_end 564 ij=(j-1)*iim+i 565 wfluxt(ij,l) = wfluxt(ij,l)+tau*wflux(ij,l) 566 ENDDO 567 ENDDO 568 ENDDO 569 570 END IF 577 IF(caldyn_eta==eta_mass) THEN ! no need for vertical fluxes if eta_lag 578 DO l=ll_begin,ll_endp1 579 DO j=jj_begin,jj_end 580 DO i=ii_begin,ii_end 581 ij=(j-1)*iim+i 582 wfluxt(ij,l) = wfluxt(ij,l)+tau*wflux(ij,l) 583 ENDDO 584 ENDDO 585 ENDDO 586 END IF 587 588 END IF 571 589 572 590 END SUBROUTINE accumulate_fluxes
Note: See TracChangeset
for help on using the changeset viewer.