source: codes/icosagcm/trunk/src/dcmip/guided_ncar_mod.f90

Last change on this file was 899, checked in by adurocher, 5 years ago

trunk : Fixed GCC warnings

Fixed iso c bindings
fixed warnings with -Wall -Wno-aliasing -Wno-unused -Wno-unused-dummy-argument -Wno-maybe-uninitialized -Wno-tabs warnings
Removed all unused variables (-Wunused-variable)
vector%dot_product is now dot_product_3d to avoid compilation warning "dot_product shadows intrinsic" with GCC

File size: 5.1 KB
Line 
1MODULE guided_ncar_mod
2  USE icosa
3  PRIVATE
4 
5  INTEGER,SAVE :: case_wind
6!$OMP THREADPRIVATE(case_wind)
7 
8  REAL(rstd), PARAMETER :: alpha=0.0 ! tilt of solid-body rotation
9  REAL(rstd), PARAMETER :: tau_hadley=daysec, tau = 12*daysec ! 12 days               ! see p. 16
10  REAL(rstd), PARAMETER :: w0_deform = 23000*pi/tau, b=0.2, ptop=25494.4  ! see p. 16
11  REAL(rstd), PARAMETER :: u0_hadley=40.,w0_hadley=0.15 ,ztop= 12000. 
12  INTEGER, PARAMETER    :: K_hadley=5
13
14  PUBLIC init_guided, guided
15
16CONTAINS
17
18  SUBROUTINE init_guided
19    IMPLICIT NONE
20    CHARACTER(LEN=255) :: wind
21    wind='deform'
22    CALL getin('dcmip1_wind',wind)
23    SELECT CASE(TRIM(wind))
24    CASE('solid')
25       case_wind=0
26    CASE('deform')
27       case_wind=1
28    CASE('hadley')
29       case_wind=2
30    CASE DEFAULT
31       PRINT*,'Bad selector for variable ncar_adv_wind : <', TRIM(wind),'> options are <solid>, <deform>, <hadley>'
32       END SELECT
33  END SUBROUTINE init_guided
34 
35  SUBROUTINE guided(tt, f_ps, f_theta_rhodz, f_u, f_q)
36  USE icosa
37    IMPLICIT NONE
38    REAL(rstd), INTENT(IN):: tt
39    TYPE(t_field),POINTER :: f_ps(:)
40    TYPE(t_field),POINTER :: f_theta_rhodz(:)
41    TYPE(t_field),POINTER :: f_u(:) 
42    TYPE(t_field),POINTER :: f_q(:) 
43   
44    REAL(rstd),POINTER :: ue(:,:)
45    INTEGER :: ind
46   
47    DO ind = 1 , ndomain
48      IF (.NOT. assigned_domain(ind)) CYCLE
49      CALL swap_dimensions(ind)
50      CALL swap_geometry(ind) 
51      ue = f_u(ind) 
52      CALL wind_profile(tt,ue)
53    END DO   
54
55  END SUBROUTINE guided
56 
57
58  SUBROUTINE wind_profile(tt,ue)
59    USE icosa
60    USE disvert_mod
61    IMPLICIT NONE
62    REAL(rstd),INTENT(IN)  :: tt ! current time
63    REAL(rstd),INTENT(OUT) :: ue(iim*3*jjm,llm)
64    REAL(rstd) :: nx(3),n_norm,Velocity(3,llm)
65    INTEGER :: i,j,n,l
66    REAL(rstd) :: pitbytau,kk, pr, zr, u0, u1, v0
67
68    pitbytau = pi*tt/tau
69    kk = 10*radius/tau
70    u0 = 2*pi*radius/tau ! for solid-body rotation
71!---------------------------------------------------------
72    DO l = 1,llm 
73       pr = presnivs(l)
74       zr = -kappa*cpp*ncar_T0/g*log(pr/ncar_p0)  ! reciprocal of (1) p. 13, isothermal atmosphere
75       u1 = w0_deform*radius/b/ptop*cos(2*pitbytau)*(exp((ptop-pr)/b/ptop)-exp((pr-ncar_p0)/b/ptop))
76       v0 = -radius*w0_hadley*pi/(5.0*ztop)*(ncar_p0/pr)*cos(pi*zr/ztop)*cos(pi*tt/tau_hadley) ! for Hadley cell
77
78       DO j=jj_begin-1,jj_end+1
79          DO i=ii_begin-1,ii_end+1
80             n=(j-1)*iim+i
81             CALL compute_velocity(xyz_e(n+u_right,:),l,velocity(:,l))
82             CALL cross_product2(xyz_v(n+z_rdown,:)/radius,xyz_v(n+z_rup,:)/radius,nx)       
83             ue(n+u_right,l)=1e-10
84             n_norm=sqrt(sum(nx(:)**2))
85             IF (n_norm>1e-30) THEN
86                nx=-nx/n_norm*ne(n,right)
87                ue(n+u_right,l)=sum(nx(:)*velocity(:,l))
88                IF (ABS(ue(n+u_right,l))<1e-100) PRINT *,"ue(n+u_right)==0",i,j,velocity(:,1)
89             ENDIF
90             
91             CALL compute_velocity(xyz_e(n+u_lup,:),l,velocity(:,l))
92             CALL cross_product2(xyz_v(n+z_up,:)/radius,xyz_v(n+z_lup,:)/radius,nx)
93             
94             ue(n+u_lup,l)=1e-10
95             n_norm=sqrt(sum(nx(:)**2))
96             IF (n_norm>1e-30) THEN
97                nx=-nx/n_norm*ne(n,lup)
98                ue(n+u_lup,l)=sum(nx(:)*velocity(:,l))
99             ENDIF
100             
101             CALL compute_velocity(xyz_e(n+u_ldown,:),l,velocity(:,l))
102             CALL cross_product2(xyz_v(n+z_ldown,:)/radius,xyz_v(n+z_down,:)/radius,nx)
103             
104             ue(n+u_ldown,l)=1e-10
105             n_norm=sqrt(sum(nx(:)**2))
106             IF (n_norm>1e-30) THEN
107                nx=-nx/n_norm*ne(n,ldown)
108                ue(n+u_ldown,l)=sum(nx(:)*velocity(:,l))
109                IF (ABS(ue(n+u_ldown,l))<1e-100) PRINT *,"ue(n+u_ldown)==0",i,j
110             ENDIF
111          ENDDO
112       ENDDO
113    END DO
114   
115  CONTAINS
116           
117    SUBROUTINE compute_velocity(x,l,velocity)
118      IMPLICIT NONE
119      REAL(rstd),INTENT(IN)  :: x(3)
120      INTEGER,INTENT(IN)::l
121      REAL(rstd),INTENT(OUT) :: velocity(3)
122      REAL(rstd) :: e_lat(3), e_lon(3)
123      REAL(rstd) :: lon,lat
124      REAL(rstd) :: u,v
125             
126      CALL xyz2lonlat(x/radius,lon,lat)
127      e_lat(1) = -cos(lon)*sin(lat)
128      e_lat(2) = -sin(lon)*sin(lat)
129      e_lat(3) = cos(lat)
130       
131      e_lon(1) = -sin(lon)
132      e_lon(2) = cos(lon)
133      e_lon(3) = 0
134
135      u = 0.0 ; v = 0.0
136   
137      SELECT CASE(case_wind) 
138      CASE(0)  ! Solid-body rotation
139         u=u0*(cos(lat)*cos(alpha)+sin(lat)*sin(alpha)*cos(lon))
140         v=-u0*sin(lon)*sin(alpha)
141      CASE(1)  ! 3D Deformational flow -
142         lon = lon-2*pitbytau
143         u = kk*sin(lon)*sin(lon)*sin(2*lat)*cos(pitbytau)+ u0*cos(lat)
144         u = u + u1*cos(lon)*cos(lat)**2
145         v = kk*sin(2*lon)*cos(lat)*cos(pitbytau) 
146      CASE(2) ! Hadley-like flow
147         u = u0_hadley*cos(lat)
148         v = v0*cos(lat)*sin(5.*lat)    ! Eq. 37 p. 19
149      CASE DEFAULT 
150         PRINT*,"not valid choice of wind" 
151      END SELECT
152     
153      Velocity(:)=(u*e_lon(:)+v*e_lat(:)+1e-50)
154     
155    END SUBROUTINE compute_velocity
156   
157  END SUBROUTINE  wind_profile
158
159
160END MODULE guided_ncar_mod
Note: See TracBrowser for help on using the repository browser.